From 398630710aef647a2d68705f46c4691994c0f5c9 Mon Sep 17 00:00:00 2001 From: Stefan Radomski Date: Wed, 3 Aug 2016 23:58:05 +0200 Subject: Fixed parts of issue 88 --- src/uscxml/Interpreter.cpp | 4 ++ src/uscxml/Interpreter.h | 7 ++++ src/uscxml/interpreter/InterpreterImpl.h | 4 ++ src/uscxml/plugins/datamodel/lua/LuaDataModel.cpp | 49 +++++++++++++++++++++-- test/issues/test-issue88.scxml | 28 +++++++++++++ 5 files changed, 89 insertions(+), 3 deletions(-) create mode 100644 test/issues/test-issue88.scxml diff --git a/src/uscxml/Interpreter.cpp b/src/uscxml/Interpreter.cpp index ff6de81..c16b70c 100644 --- a/src/uscxml/Interpreter.cpp +++ b/src/uscxml/Interpreter.cpp @@ -218,6 +218,10 @@ void Interpreter::setActionLanguage(ActionLanguage actionLanguage) { return _impl->setActionLanguage(actionLanguage); } +void Interpreter::setFactory(Factory* factory) { + return _impl->setFactory(factory); +} + void Interpreter::addMonitor(InterpreterMonitor* monitor) { return _impl->addMonitor(monitor); } diff --git a/src/uscxml/Interpreter.h b/src/uscxml/Interpreter.h index 630ea61..e7d8a19 100644 --- a/src/uscxml/Interpreter.h +++ b/src/uscxml/Interpreter.h @@ -29,6 +29,7 @@ #include "uscxml/interpreter/MicroStep.h" #include "uscxml/plugins/DataModel.h" +#include "uscxml/plugins/Factory.h" #include "uscxml/interpreter/ContentExecutor.h" #include "uscxml/interpreter/EventQueue.h" #include "uscxml/interpreter/InterpreterState.h" @@ -178,6 +179,11 @@ public: */ void setActionLanguage(ActionLanguage actionLanguage); + /** + * Provide a custom Factory to instantiate dynamic instances for this and invoked state-chart instances. + */ + void setFactory(Factory* factory); + /** * Attach a monitor to make more details of the interpreter observable. */ @@ -188,6 +194,7 @@ public: */ void removeMonitor(InterpreterMonitor* monitor); + /** * Return the actual implementation of the Interperter. */ diff --git a/src/uscxml/interpreter/InterpreterImpl.h b/src/uscxml/interpreter/InterpreterImpl.h index 84aab20..26f117d 100644 --- a/src/uscxml/interpreter/InterpreterImpl.h +++ b/src/uscxml/interpreter/InterpreterImpl.h @@ -235,6 +235,10 @@ public: _delayQueue = al.delayedQueue; } + void setFactory(Factory* factory) { + _factory = factory; + } + static std::map > getInstances(); virtual XERCESC_NS::DOMDocument* getDocument() { diff --git a/src/uscxml/plugins/datamodel/lua/LuaDataModel.cpp b/src/uscxml/plugins/datamodel/lua/LuaDataModel.cpp index 717def9..225e34c 100644 --- a/src/uscxml/plugins/datamodel/lua/LuaDataModel.cpp +++ b/src/uscxml/plugins/datamodel/lua/LuaDataModel.cpp @@ -70,7 +70,7 @@ static Data getLuaAsData(lua_State* _luaState, const luabridge::LuaRef& lua) { data.atom = "nil"; data.type = Data::INTERPRETED; } else if(lua.isNumber()) { - data.atom = toStr(lua.cast()); + data.atom = toStr(lua.cast()); data.type = Data::INTERPRETED; } else if(lua.isString()) { data.atom = lua.cast(); @@ -470,9 +470,52 @@ void LuaDataModel::assign(const std::string& location, const Data& data) { int retVals = luaEval(_luaState, location + " = " + location); lua_pop(_luaState, retVals); - luabridge::LuaRef lua = getDataAsLua(_luaState, data); - luabridge::setGlobal(_luaState, lua, location.c_str()); + // normalize location into dot notation + // TODO: This is still wrong as it treads arrays as kvps! + std::string normedLocation; + normedLocation.resize(location.size()); + for (size_t i = 0, j = 0; i < location.size(); i++, j++) { + if (location[i] == ']') { + j++; + } else if (location[i] == '[') { + normedLocation[i] = '.'; + } else { + normedLocation[i] = location[i]; + } + } + + std::list idPath = tokenize(normedLocation, '.'); + if (idPath.size() == 0) + return; + + luabridge::LuaRef lua = getDataAsLua(_luaState, data); + + if (idPath.size() == 1) { + // trivial case where we reference a simple toplevel identifier + luabridge::setGlobal(_luaState, lua, location.c_str()); + + } else { + std::string globalId = idPath.front(); + idPath.pop_front(); + + std::string field = idPath.back(); + idPath.pop_back(); + + luabridge::LuaRef topValue = luabridge::getGlobal(_luaState, globalId.c_str()); + luabridge::LuaRef value = topValue; + + for (auto ident : idPath) { + if (!value.isTable()) + value = luabridge::newTable(_luaState); + + luabridge::LuaRef tmp = value[ident]; + value = tmp; + } + value[field] = lua; + } + + // std::cout << Data::toJSON(evalAsData(location)) << std::endl; } } diff --git a/test/issues/test-issue88.scxml b/test/issues/test-issue88.scxml new file mode 100644 index 0000000..3ac55c7 --- /dev/null +++ b/test/issues/test-issue88.scxml @@ -0,0 +1,28 @@ + + + { + testInt=10, + testDouble=10.0, + testString='message' +} + + {0,1,2,3,4,5,6} + + + + + + + + + + + + + + + + + + + -- cgit v0.12