From 624ad4f6d95938a7ad8a45d7f79b151bf970aedf Mon Sep 17 00:00:00 2001 From: Anne-Marie Date: Tue, 4 Nov 2025 12:05:42 +0100 Subject: [PATCH 1/9] added most important files for new test block, and notes --- AM.md | 65 + OpenRobertaServer/pom.xml | 12 +- .../src/main/resources/openRoberta.properties | 4 +- .../blockly/blockly_compressed.js | 1804 ++++++++--------- .../roberta/syntax/action/nao/ATesting.java | 33 + .../fhg/iais/roberta/visitor/INaoVisitor.java | 7 + .../iais/roberta/visitor/NaoSimMethods.java | 2 +- .../visitor/codegen/NaoPythonSimVisitor.java | 21 +- .../visitor/codegen/NaoPythonVisitor.java | 13 + .../NaoSimValidatorAndCollectorVisitor.java | 11 + .../NaoValidatorAndCollectorVisitor.java | 9 + RobotNAO/src/main/resources/nao.methods.yml | 7 + .../nao.program.toolbox.beginner.xml | 8 + pom.xml | 28 +- 14 files changed, 1086 insertions(+), 938 deletions(-) create mode 100644 AM.md create mode 100644 RobotNAO/src/main/java/de/fhg/iais/roberta/syntax/action/nao/ATesting.java diff --git a/AM.md b/AM.md new file mode 100644 index 0000000000..4c75a067fb --- /dev/null +++ b/AM.md @@ -0,0 +1,65 @@ +**Anne's New Notes** + +### General notes about the system +The code found within /openroberta-lab covers the back-end logic of OpenRoberta. +The block declarations, UI and general front-end logic is defined in the blockly git: +https://github.com/OpenRoberta/blockly.git + +OpenRoberta DOES actually have custom blocks! They're called 'functions' and are available in the expert-toolbox. + +Most changes I've made in this code have the comment 'newmethod' over them. This is so it's easier to search for those changes within the code, if anyone wants to look at it. + +**FOR REASONS UNBEKNOWNST TO ME, the 'Action' toolbox is currently fucked up. I think I know how to fix it, but just haven't had time to yet** + + +### How to run the OpenRoberta-Lab project +First, check the Prerequisites in the README.md in the root folder. + +To (re)generate the server, run these two commands from root folder (SEE NOTES BELOW!): +rm -rf OpenRobertaRobot/target + +mvn clean install -DskipTests + +**IMPORTANT NOTES** Firstly, the 'mvn install' command skips all tests (with the -DskipTests flag). This is because it will run tests for ALL robot modes. Since we only build the system for the NAO robot, tests will fail and abort the build. +Also, we should likely think about creating tests for any new features we implement. + +Secondly, you will likely experience errors when building. These errors are usually related to the 'target'-folders found within OpenRobertaRobot and OpenRobertaServer. If it complains that it failed to delete a file in the target folder, delete the file/folder manually and try the 'mvn install' command again, with the '-rf' flag provided in the terminal (this lets you avoid start the build from scratch, and simply continues the build from a snapshot). + +Then, we build the front-end: +cd OpenRobertaWeb +npm install && npm run build && npx gulp # build the frontend, check tsc and gulp, must succeed +cd .. +./ora.sh start-from-git # starts server, writes logging to the console + +Our OpenRoberta can be accessed at http://localhost:1999/ + +### Changing the blockly front-end +Changes to the blockly front-end must be done in the blockly git code. +Firstly, check out the first part of this page: +https://github.com/OpenRoberta/blockly/blob/master/README.md + +**We only care about the first part of the page (the closure-library and you need python version 2.7).** + +Our fork of the OpenRoberta blockly can be found here: +https://github.com/VictoriousAnnro/blockly_openRoberta + +When changes have been made to the blockly git code, run build.py with this command from the root folder of the blockly git: +python2.7 build.py + +Replace the blockly_compressed.js in this code (OpenRobertaServer\staticResources\blockly\blockly_compressed.js), with the file from the blockly git. + +Replace the OpenRobertaServer\staticResources\blockly\msg folder in this code with the msg-folder from the blockly git. + +After this, repeat the steps in "How to run the OpenRoberta-Lab project". +**I'll check whether it's necessary to re-generate the server and build the frontend every time we update the blockly_compressed.js later** + +### TO-DO +Overall, we're trying to do X things: +- Add feature that can locate code duplicates in the end-user's workspace + * We need to decide how we're gonna do this. Firstly, do we try to find duplicates in the python-code generated from the blocks? Or do we look at duplicate chunks of block UI elements? (As seen in the blockly git). + * Then, we need to figure out the algorithm/method to actually find the duplicates. Do we check for duplicates every time the user makes a change to the workspace? Every time they connect a new block to the stack? + +- Add feature to highlight duplicate chunks of code (the hightlight color should NOT be the same for all duplicate code! It should be easy for user to see which chunks are related). + + Add feature that explains why the chunks are being highlighted (let the user know why they should care about this). + +- Add feature to let the end-user create a custom block with few clicks (They must specify block name, variables, and where the variables are used. The feature takes care of moving the duplicate chunk into a custom block, and replacing the chunks with the new block). \ No newline at end of file diff --git a/OpenRobertaServer/pom.xml b/OpenRobertaServer/pom.xml index b1a0cc0bc2..5951eecd30 100644 --- a/OpenRobertaServer/pom.xml +++ b/OpenRobertaServer/pom.xml @@ -76,27 +76,27 @@ org.seleniumhq.selenium selenium-java - + de.fhg.iais.openroberta RobotCyberpi - + de.fhg.iais.openroberta RobotNAO - + de.fhg.iais.openroberta OpenRobertaRobot diff --git a/OpenRobertaServer/src/main/resources/openRoberta.properties b/OpenRobertaServer/src/main/resources/openRoberta.properties index e5106ada01..ed4158daee 100644 --- a/OpenRobertaServer/src/main/resources/openRoberta.properties +++ b/OpenRobertaServer/src/main/resources/openRoberta.properties @@ -52,7 +52,9 @@ server.staticresources.dir = OpenRobertaServer/staticResources # For instance, if your school offers nxt, calliope2017 and calliope2016 robots, use this white list: # robot.whitelist = sim, nxt, calliope2017, calliope2016 # Usually overwritten by command line parameter -d -robot.whitelist = rcj, edisonv3, edisonv2, txt4, spike, spikePybricks, thymio, wedo, ev3lejosv1, ev3dev, ev3c4ev3, xNN, nxt, microbit, microbitv2, joycar, botnroll, nao, bob3, rob3rta, sensebox, mbot, mbot2, festobionic, festobionicflower, uno, nano, mega, nano33ble, calliope2017NoBlue, calliope2017, calliope2016, calliopev3, robotino +#robot.whitelist = rcj, edisonv3, edisonv2, txt4, spike, spikePybricks, thymio, wedo, ev3lejosv1, ev3dev, ev3c4ev3, xNN, nxt, microbit, microbitv2, joycar, botnroll, nao, bob3, rob3rta, sensebox, mbot, mbot2, festobionic, festobionicflower, uno, nano, mega, nano33ble, calliope2017NoBlue, calliope2017, calliope2016, calliopev3, robotino +robot.whitelist = nao + robot.default = ev3lejosv1 # account activation / verification / reset # server.iptocountry.dir path where the db is located, db name is fix: IpToCountry.cvs diff --git a/OpenRobertaServer/staticResources/blockly/blockly_compressed.js b/OpenRobertaServer/staticResources/blockly/blockly_compressed.js index 0fb38e23b4..7d748b2fa9 100644 --- a/OpenRobertaServer/staticResources/blockly/blockly_compressed.js +++ b/OpenRobertaServer/staticResources/blockly/blockly_compressed.js @@ -6,69 +6,43 @@ Copyright The Closure Library Authors. SPDX-License-Identifier: Apache-2.0 */ -var $jscomp=$jscomp||{};$jscomp.scope={};$jscomp.arrayIteratorImpl=function(a){var b=0;return function(){return b=e}},"es6","es3"); -$jscomp.polyfill("String.prototype.startsWith",function(a){return a?a:function(b,c){var d=$jscomp.checkStringArgs(this,b,"startsWith");b+="";var e=d.length,f=b.length;c=Math.max(0,Math.min(c|0,d.length));for(var g=0;g=f}},"es6","es3"); -$jscomp.polyfill("String.prototype.repeat",function(a){return a?a:function(b){var c=$jscomp.checkStringArgs(this,null,"repeat");if(0>b||1342177279>>=1)c+=c;return d}},"es6","es3");$jscomp.polyfill("String.prototype.trimLeft",function(a){function b(){return this.replace(/^[\s\xa0]+/,"")}return a||b},"es_2019","es3"); -$jscomp.polyfill("Object.is",function(a){return a?a:function(b,c){return b===c?0!==b||1/b===1/c:b!==b&&c!==c}},"es6","es3");$jscomp.polyfill("Array.prototype.includes",function(a){return a?a:function(b,c){var d=this;d instanceof String&&(d=String(d));var e=d.length;c=c||0;for(0>c&&(c=Math.max(c+e,0));c>>0);goog.uidCounter_=0;goog.cloneObject=function(a){var b=goog.typeOf(a);if("object"==b||"array"==b){if("function"===typeof a.clone)return a.clone();b="array"==b?[]:{};for(var c in a)b[c]=goog.cloneObject(a[c]);return b}return a};goog.bindNative_=function(a,b,c){return a.call.apply(a.bind,arguments)}; -goog.bindJs_=function(a,b,c){if(!a)throw Error();if(2>>0);goog.uidCounter_=0;goog.cloneObject=function(a){var b=goog.typeOf(a);if(b=="object"||b=="array"){if(typeof a.clone==="function")return a.clone();b=b=="array"?[]:{};for(var c in a)b[c]=goog.cloneObject(a[c]);return b}return a};goog.bindNative_=function(a,b,c){return a.call.apply(a.bind,arguments)}; +goog.bindJs_=function(a,b,c){if(!a)throw Error();if(arguments.length>2){var d=Array.prototype.slice.call(arguments,2);return function(){var e=Array.prototype.slice.call(arguments);Array.prototype.unshift.apply(e,d);return a.apply(b,e)}}return function(){return a.apply(b,arguments)}};goog.bind=function(a,b,c){Function.prototype.bind&&Function.prototype.bind.toString().indexOf("native code")!=-1?goog.bind=goog.bindNative_:goog.bind=goog.bindJs_;return goog.bind.apply(null,arguments)}; goog.partial=function(a,b){var c=Array.prototype.slice.call(arguments,1);return function(){var d=c.slice();d.push.apply(d,arguments);return a.apply(this,d)}};goog.mixin=function(a,b){for(var c in b)a[c]=b[c]};goog.now=Date.now;goog.globalEval=function(a){(0,eval)(a)}; -goog.getCssName=function(a,b){if("."==String(a).charAt(0))throw Error('className passed in goog.getCssName must not start with ".". You passed: '+a);var c=function(e){return goog.cssNameMapping_[e]||e},d=function(e){e=e.split("-");for(var f=[],g=0;g=0;--b){var c=a[b].src,d=c.lastIndexOf("?");d=d==-1?c.length:d;if(c.substr(d-7,7)=="base.js"){goog.basePath=c.substr(0,d-7);break}}}},goog.findBasePath_(),goog.Transpiler=function(){this.requiresTranspilation_=null;this.transpilationTarget_=goog.TRANSPILE_TO_LANGUAGE},goog.Transpiler.prototype.createRequiresTranspilation_=function(){function a(g,h){e?d[g]=!0:h()?(c=g,d[g]=!1):e=d[g]=!0}function b(g){try{return!!eval(g)}catch(h){return!1}} var c="es3",d={es3:!1},e=!1,f=goog.global.navigator&&goog.global.navigator.userAgent?goog.global.navigator.userAgent:"";a("es5",function(){return b("[1,].length==1")});a("es6",function(){return f.match(/Edge\/(\d+)(\.\d)*/i)?!1:b('(()=>{"use strict";class X{constructor(){if(new.target!=String)throw 1;this.x=42}}let q=Reflect.construct(X,[],String);if(q.x!=42||!(q instanceof String))throw 1;for(const a of[2,3]){if(a==2)continue;function f(z={a}){let a=0;return z.a}{function f(){return 0;}}return f()==3}})()')}); -a("es7",function(){return b("2 ** 2 == 4")});a("es8",function(){return b("async () => 1, true")});a("es9",function(){return b("({...rest} = {}), true")});a("es_next",function(){return!1});return{target:c,map:d}},goog.Transpiler.prototype.needsTranspile=function(a,b){if("always"==goog.TRANSPILE)return!0;if("never"==goog.TRANSPILE)return!1;if(!this.requiresTranspilation_){var c=this.createRequiresTranspilation_();this.requiresTranspilation_=c.map;this.transpilationTarget_=this.transpilationTarget_|| -c.target}if(a in this.requiresTranspilation_)return this.requiresTranspilation_[a]?!0:!goog.inHtmlDocument_()||"es6"!=b||"noModule"in goog.global.document.createElement("script")?!1:!0;throw Error("Unknown language mode: "+a);},goog.Transpiler.prototype.transpile=function(a,b){return goog.transpile_(a,b,this.transpilationTarget_)},goog.transpiler_=new goog.Transpiler,goog.protectScriptTag_=function(a){return a.replace(/<\/(SCRIPT)/ig,"\\x3c/$1")},goog.DebugLoader_=function(){this.dependencies_={}; +a("es7",function(){return b("2 ** 2 == 4")});a("es8",function(){return b("async () => 1, true")});a("es9",function(){return b("({...rest} = {}), true")});a("es_next",function(){return!1});return{target:c,map:d}},goog.Transpiler.prototype.needsTranspile=function(a,b){if(goog.TRANSPILE=="always")return!0;if(goog.TRANSPILE=="never")return!1;if(!this.requiresTranspilation_){var c=this.createRequiresTranspilation_();this.requiresTranspilation_=c.map;this.transpilationTarget_=this.transpilationTarget_|| +c.target}if(a in this.requiresTranspilation_)return this.requiresTranspilation_[a]?!0:!goog.inHtmlDocument_()||b!="es6"||"noModule"in goog.global.document.createElement("script")?!1:!0;throw Error("Unknown language mode: "+a);},goog.Transpiler.prototype.transpile=function(a,b){return goog.transpile_(a,b,this.transpilationTarget_)},goog.transpiler_=new goog.Transpiler,goog.protectScriptTag_=function(a){return a.replace(/<\/(SCRIPT)/ig,"\\x3c/$1")},goog.DebugLoader_=function(){this.dependencies_={}; this.idToPath_={};this.written_={};this.loadingDeps_=[];this.depsToLoad_=[];this.paused_=!1;this.factory_=new goog.DependencyFactory(goog.transpiler_);this.deferredCallbacks_={};this.deferredQueue_=[]},goog.DebugLoader_.prototype.bootstrap=function(a,b){function c(){d&&(goog.global.setTimeout(d,0),d=null)}var d=b;if(a.length){b=[];for(var e=0;e=0&&(a=a.substring(b+3),b= +a.indexOf("/"),b>=0&&(a=a.substring(b+1)));return a},goog.Dependency.prototype.onLoad=function(a){this.loaded_?a():this.loadCallbacks_.push(a)},goog.Dependency.prototype.loaded=function(){this.loaded_=!0;var a=this.loadCallbacks_;this.loadCallbacks_=[];for(var b=0;b\x3c/script>";b.write(goog.TRUSTED_TYPES_POLICY_?goog.TRUSTED_TYPES_POLICY_.createHTML(d):d)}else{var e=b.createElement("script");e.defer=goog.Dependency.defer_;e.async=!1;e.type="text/javascript";(d=goog.getScriptNonce())&&e.setAttribute("nonce",d);goog.DebugLoader_.IS_OLD_IE_? -(a.pause(),e.onreadystatechange=function(){if("loaded"==e.readyState||"complete"==e.readyState)a.loaded(),a.resume()}):e.onload=function(){e.onload=null;a.loaded()};e.src=goog.TRUSTED_TYPES_POLICY_?goog.TRUSTED_TYPES_POLICY_.createScriptURL(this.path):this.path;b.head.appendChild(e)}}else goog.logToConsole_("Cannot use default debug loader outside of HTML documents."),"deps.js"==this.relativePath?(goog.logToConsole_("Consider setting CLOSURE_IMPORT_SCRIPT before loading base.js, or setting CLOSURE_NO_DEPS to true."), -a.loaded()):a.pause()},goog.Es6ModuleDependency=function(a,b,c,d,e){goog.Dependency.call(this,a,b,c,d,e)},goog.inherits(goog.Es6ModuleDependency,goog.Dependency),goog.Es6ModuleDependency.prototype.load=function(a){function b(l,m){l=m?'