diff options
author | Stefan Radomski <radomski@tk.informatik.tu-darmstadt.de> | 2013-03-20 08:00:41 (GMT) |
---|---|---|
committer | Stefan Radomski <radomski@tk.informatik.tu-darmstadt.de> | 2013-03-20 08:00:41 (GMT) |
commit | c6c1f3e2e333705bf7d54fffd4b18939a56f4ed8 (patch) | |
tree | 92af8be33c602a68d1912790cad657c2a012e2c0 /apps | |
parent | ccbf595c52fd705ec70abc774a29b153a7281334 (diff) | |
download | uscxml-c6c1f3e2e333705bf7d54fffd4b18939a56f4ed8.zip uscxml-c6c1f3e2e333705bf7d54fffd4b18939a56f4ed8.tar.gz uscxml-c6c1f3e2e333705bf7d54fffd4b18939a56f4ed8.tar.bz2 |
Started Syteminvoker
Diffstat (limited to 'apps')
-rw-r--r-- | apps/mmi-browser.cpp | 2 | ||||
-rw-r--r-- | apps/samples/miles/miles-connect.html (renamed from apps/samples/miles-connect.html) | 0 | ||||
-rw-r--r-- | apps/samples/miles/miles-disconnect.html (renamed from apps/samples/miles-disconnect.html) | 0 | ||||
-rw-r--r-- | apps/samples/miles/miles.scxml (renamed from apps/samples/miles.scxml) | 16 | ||||
-rw-r--r-- | apps/samples/server-push/server-push.scxml | 84 | ||||
-rw-r--r-- | apps/samples/vrml/README.md | 150 | ||||
-rw-r--r-- | apps/samples/vrml/viewer.html (renamed from apps/samples/viewer.html) | 0 | ||||
-rw-r--r-- | apps/samples/vrml/viewer.js (renamed from apps/samples/viewer.js) | 0 | ||||
-rw-r--r-- | apps/samples/vrml/vrml-server.scxml (renamed from apps/samples/vrml-server.scxml) | 24 |
9 files changed, 253 insertions, 23 deletions
diff --git a/apps/mmi-browser.cpp b/apps/mmi-browser.cpp index 8d3a12f..5127d7b 100644 --- a/apps/mmi-browser.cpp +++ b/apps/mmi-browser.cpp @@ -85,6 +85,8 @@ int main(int argc, char** argv) { Interpreter* interpreter = Interpreter::fromURI(argv[optind]); if (interpreter) { interpreter->setCmdLineOptions(argc, argv); +// interpreter->setCapabilities(Interpreter::CAN_NOTHING); +// interpreter->setCapabilities(Interpreter::CAN_BASIC_HTTP | Interpreter::CAN_GENERIC_HTTP); interpreter->start(); while(interpreter->runOnMainThread(25)); // interpreter->interpret(); diff --git a/apps/samples/miles-connect.html b/apps/samples/miles/miles-connect.html index ae5f77e..ae5f77e 100644 --- a/apps/samples/miles-connect.html +++ b/apps/samples/miles/miles-connect.html diff --git a/apps/samples/miles-disconnect.html b/apps/samples/miles/miles-disconnect.html index 30f5b39..30f5b39 100644 --- a/apps/samples/miles-disconnect.html +++ b/apps/samples/miles/miles-disconnect.html diff --git a/apps/samples/miles.scxml b/apps/samples/miles/miles.scxml index 4eef0eb..524729f 100644 --- a/apps/samples/miles.scxml +++ b/apps/samples/miles/miles.scxml @@ -8,8 +8,18 @@ </script> </finalize> </invoke> - + <state id="idle"> + <!-- XHR CORS preflight response --> + <transition event="http.options" target="idle"> + <script>dump(_event);</script> + <response status="200" requestexpr="_event.origin"> + <header name="Access-Control-Allow-Origin" value="*" /> + <header name="Access-Control-Allow-Methods" value="GET, OPTIONS" /> + <header name="Access-Control-Allow-Headers" value="X-Requested-With" /> + </response> + </transition> + <transition event="http.post" target="idle"> <script>dump(_event);</script> <if cond="_event.data.pathComponent[1] === 'session'"> @@ -30,11 +40,11 @@ <param name="problemName" expr="_event.data.content.problemName" /> </send> <response status="200" requestexpr="_event.origin" /> - + </elseif> <else> <response status="404" requestexpr="_event.origin" /> - + </else> </if> </transition> diff --git a/apps/samples/server-push/server-push.scxml b/apps/samples/server-push/server-push.scxml new file mode 100644 index 0000000..2574149 --- /dev/null +++ b/apps/samples/server-push/server-push.scxml @@ -0,0 +1,84 @@ +<!-- + Example for server-push with long-polling XMLHttpRequests. + Start in mmi-browser and connect http-browser via: + http://localhost:8080/push +--> + +<scxml name="push" datamodel="ecmascript"> + <script src="http://uscxml.tk.informatik.tu-darmstadt.de/scripts/dump.js" /> + <script src="http://uscxml.tk.informatik.tu-darmstadt.de/scripts/string.endsWith.js" /> + + <state id="main"> + <!-- We will only answer http requests when the heartbeat is emitted --> + <invoke type="heartbeat" id="heartbeat"> + <param name="interval" expr="'1s'" /> + </invoke> + <state id="idle"> + <!-- XHR CORS preflight response --> + <transition event="http.options" target="idle"> + <script>dump(_event);</script> + <response status="200" requestexpr="_event.origin"> + <header name="Access-Control-Allow-Origin" value="*" /> + <header name="Access-Control-Allow-Methods" value="POST, GET, OPTIONS" /> + <header name="Access-Control-Allow-Headers" value="X-Requested-With, Content-Type" /> + </response> + </transition> + + <transition event="http.post" target="idle"> + <script>dump(_event);</script> + <if cond="_event.name.endsWith('postponed')"> + <!-- This is an event we postponed before the heartbeat, respond --> + <response requestexpr="_event.origin"> + <content>This is awesome!</content> + </response> + <else> + <!-- Postpone until the heartbeat is emitted and send all events again --> + <postpone until="_event.name == 'heartbeat.1s'" chaining="true" /> + </else> + </if> + </transition> + + <transition event="http.get"> + <response requestexpr="_event.origin"> + <content> +<![CDATA[ +<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"> +<html> + <head> + <meta http-equiv="Content-Type" content="text/html;charset=utf-8" /> + <script src="http://ajax.googleapis.com/ajax/libs/dojo/1.8.3/dojo/dojo.js"></script> + + <script type="text/javascript"> + require(["dojo/domReady!", "dojo"], function(dom, dojo) { + var xhr = dojo.require("dojo/_base/xhr"); + var longpoll = function() { + xhr.post({ + // The URL to request + url: "http://localhost:8080/push/anywhere", + handleAs:"text", + headers:{ + "X-Requested-With": null, + "Content-Type": "application/json", + }, + load: function(result) { + dojo.byId("foo").innerHTML += result + "<br />"; + longpoll(); + } + }); + } + longpoll(); + }); + </script> + </head> + <body class="tundra"> + <div id="foo"></div> + </body> +</html> +]]> + </content> + </response> + </transition> + + </state> + </state> +</scxml>
\ No newline at end of file diff --git a/apps/samples/vrml/README.md b/apps/samples/vrml/README.md new file mode 100644 index 0000000..2a019da --- /dev/null +++ b/apps/samples/vrml/README.md @@ -0,0 +1,150 @@ +# VRML Server + +The VRML Server allows clients to retrieve sceneshots of 3D models on the filesystem in a variety of formats. + +## General Mode of Operation + +The VRML server will monitor its vrml directory recursively for <tt>vrml</tt> and <tt>wrl</tt> +files. Whenever such a file is found, it is converted into a native, binary representation and +saved in the tmp directory. Clients can now access sceneshots of this model by specifying the +desired pose and format. + +## Accessing Sceneshots + +In the simplest case, a sceneshot is retrieved by simply requested its respective URL on the VRML server: + +<tt>http://host/vrml/HARD_MP_VAL_000.png</tt> + +All paths start with vrml and then reflect the vrml directory structure as it is being monitored. When a directory +<tt>foo</tt> was added (either by creation or linking) in the vrml directory, its 3D models will be available at: + +<tt>http://host/vrml/foo/FANCY_MODEL_000.png</tt> + +When you do not pass any parameters, you will get a sceneshot of the model with its largest, axis aligned surface area +facing the camera. That is, the model will be rotated by multiples of 90deg to show the side of the bounding box which +has the largest surface area. The implied assumption is that this side is suited to identify the model and its eventual +problems the quickest. + +If you do not like the standard sceneshot, you can pass a couple of parameters to adapt most aspects of the scene: + +<table> + <tr><th>Name</th><th>Range</th><th>Description</th></tr> + <tr><td><tt>pitch</tt></td><td>[0 .. 2π] rad</td><td>Rotation along the x-axis</td></tr> + <tr><td><tt>roll</tt></td><td>[0 .. 2π] rad</td><td>Rotation along the z-axis</td></tr> + <tr><td><tt>yaw</tt></td><td>[0 .. 2π] rad</td><td>Rotation along the y-axis</td></tr> + <tr><td><tt>zoom</tt></td><td>[0 .. ∞] bounding-sphere units</td><td>Distance of camera to model center</td></tr> + <tr><td><tt>x</tt></td><td>[-∞ .. ∞] OpenGL units</td><td>Translation on x-axis</td></tr> + <tr><td><tt>y</tt></td><td>[-∞ .. ∞] OpenGL units</td><td>Translation on y-axis</td></tr> + <tr><td><tt>z</tt></td><td>[-∞ .. ∞] OpenGL units</td><td>Translation on z-axis (consider using zoom instead)</td></tr> + <tr><td><tt>width</tt></td><td>[0 .. BIG] pixels</td><td>The width of the image (limited by your GPU)</td></tr> + <tr><td><tt>height</tt></td><td>[0 .. BIG] pixels</td><td>The height of the image</td></tr> + <tr><td><tt>autorotate</tt></td><td>[<tt>on</tt> | <tt>off</tt>]</td><td>Whether or not to autorotate first</td></tr> +</table> + +<tt>http://host/vrml/HARD_MP_VAL_000.png?pitch=0.3&width=2560&height=1600</tt> + +There are some caveats: +<ul> + <li>With euler angles such as pitch/roll/yaw, a gimbal lock can occur. + <li>Choosing zoom, x, y or z to big will move the model off the clipping distance. + <li>width and height have no upper limit, this might be a potential DoS. + <li>When observing series of models with autorotating on, not every model is guaranteed to start with the same pose. + <li>The OpenGL units really ought to be expressed in multiples of bounding-sphere units. +</ul> + +## REST API + +The main purpose of the REST API is to provide clients with a list of available model files. + +<table> + <tr><th>Path</th><th>Type</th><th>Return Value</th><th>Example</th></tr> + <tr> + <td><tt>/vrml</tt></td> + <td><tt>GET</tt></td> + <td> + A JSON structure identifying all known models in the hierarchy as found on the filesystem.<br/> + + The entries are organized in a tree, reflecting the original locations relative to the vrml + directory. The suffix of <tt>png</tt> is just one example, supported extensions are ultimately + defined by the available <a href="http://www.link.de/here">OSG writer plugins</a>, but limited for + now to <tt>gif</tt>, <tt>jpg</tt>, <tt>png</tt>, <tt>tif</tt> and <tt>bmp</tt>. + </td> + <td> +<pre> +{ + "models": { + "HARD_MP_VAL_000": { + "path": "/HARD_MP_VAL_000.png", + "url": "http://host/vrml/HARD_MP_VAL_000.png" + }, + "HARD_MP_VAL_001": { + "path": "/HARD_MP_VAL_001.png", + "url": "http://host/vrml/HARD_MP_VAL_001.png" + }, + "data": { + "SOFT_MP_VAL_000": { + "path": "/data/SOFT_MP_VAL_000.png", + "url": "http://host/vrml/data/SOFT_MP_VAL_000.png" + }, + ... +</pre> + </td> + </tr> + + <tr> + <td><tt>/vrml/models</tt>, <tt>/vrml/wrls</tt></td> + <td><tt>GET</tt></td> + <td> + A JSON structure with information about the available binary model files in the tmp directory or the wrl + files in the vrml directory respectively.<br/> + + The entries correspond to the tree at <tt>/vrml</tt> but all paths are flattened using the path delimiter + ('<tt>:</tt>' per default). + </td> + <td> +<pre> +{ + "HARD_MP_VAL_000": { + "atime": 1363002503, + "ctime": 1362521747, + "dir": "/tmp", + "extension": "osgb", + "group": "/", + "mtime": "1362521747", + "name": "HARD_MP_VAL_000.osgb", + "path": "/tmp/HARD_MP_VAL_000.osgb", + "relDir": "/", + "relPath": "/HARD_MP_VAL_000.osgb", + "size": "580201", + "strippedName": "HARD_MP_VAL_000" + }, +... +</pre> + </td> + </tr> + + <tr> + <td><tt>/vrml/processed</tt></td> + <td><tt>GET</tt></td> + <td> + A JSON structure with information about the sceneshots that were requested recently and are still on disc.<br/> + + The individual entries within a model key encode the request parameters seperated by underscores, that is:<br/> + The euler angles <tt>pitch</tt>, <tt>roll</tt>, <tt>yaw</tt>, <tt>zoom</tt>, translation in <tt>x</tt>, translation + in <tt>y</tt>, translation in <tt>z</tt>, <tt>width</tt>, <tt>height</tt>, and whether or not to <tt>autorotate</tt>. + </td> + <td> + <pre> +{ + "HARD_MP_VAL_000": { + "0.94_0_0_1_0_0_0_640_480_on.png": { + "atime": 1363002687, + "ctime": 1363002687, + "dir": "/tmp", +... + </pre> + </td> + </tr> + + +</table> diff --git a/apps/samples/viewer.html b/apps/samples/vrml/viewer.html index 4cf971b..4cf971b 100644 --- a/apps/samples/viewer.html +++ b/apps/samples/vrml/viewer.html diff --git a/apps/samples/viewer.js b/apps/samples/vrml/viewer.js index dac3a96..dac3a96 100644 --- a/apps/samples/viewer.js +++ b/apps/samples/vrml/viewer.js diff --git a/apps/samples/vrml-server.scxml b/apps/samples/vrml/vrml-server.scxml index c5647b0..0d6517c 100644 --- a/apps/samples/vrml-server.scxml +++ b/apps/samples/vrml/vrml-server.scxml @@ -1,5 +1,7 @@ <scxml datamodel="ecmascript" name="vrml"> <script src="http://uscxml.tk.informatik.tu-darmstadt.de/scripts/dump.js" /> + <script src="http://uscxml.tk.informatik.tu-darmstadt.de/scripts/string.endsWith.js" /> + <script src="http://uscxml.tk.informatik.tu-darmstadt.de/scripts/array.last.js" /> <script> var wrls = {}; // information of the wrl, vrml files var models = {}; // information of the osgb files @@ -126,25 +128,7 @@ } return struct; } - - /** - * Provide an endsWith function for the string prototype - */ - if(!Array.prototype.last) { - String.prototype.endsWith = function(suffix) { - return this.indexOf(suffix, this.length - suffix.length) !== -1; - } - } - - /** - * Provide last() for arrays - */ - if(!Array.prototype.last) { - Array.prototype.last = function() { - return this[this.length - 1]; - } - } - + // check whether a given string represents a number function isNumber(n) { return !isNaN(parseFloat(n)) && isFinite(n); @@ -396,7 +380,7 @@ </response> </transition> - <!-- XHR CORS preflight response --> + <!-- XHR CORS preflight response --> <transition event="http.options" target="idle"> <script>dump(_event);</script> <response status="200" requestexpr="_event.origin"> |