#include "scriptable_controller.h" #include "luatb.h" #include "infos/PlayerInfo.h" #include "core/command/Executor.h" namespace orxonox { // Used https://csl.name/post/lua-and-cpp/ as a reference int ScriptableController::runScript(const std::string &file_path) { int ret; // Not having a script specified at all is not an error if(file_path.empty()) return 0; // Create a lua object lua_State *lua = luaL_newstate(); if(lua == nullptr) { orxout(internal_warning) << "ScriptableController: Falied to load script " << file_path << std::endl; return LUA_ERRMEM; } // Make standard libraries available in the Lua object luaL_openlibs(lua); // Register the API ScriptableControllerAPI *api = new ScriptableControllerAPI(lua, this); // Load the program; this supports both source code and bytecode files. if((ret = luaL_loadfile(lua, file_path.c_str())) != 0) { this->printLuaError(lua); delete api; return ret; } // Execute the script if((ret = lua_pcall(lua, 0, LUA_MULTRET, 0)) != 0) { this->printLuaError(lua); delete api; return ret; } // Remeber the api this->apis_.push_back(std::unique_ptr(api)); return 0; } void ScriptableController::setPlayer(PlayerInfo *player) { this->player_ = player; } void ScriptableController::registerWorldEntity(std::string id, WorldEntity *entity) { this->worldEntities_[id] = entity; } void ScriptableController::registerControllableEntity(std::string id, ControllableEntity *entity) { this->worldEntities_[id] = entity; } WorldEntity *ScriptableController::getWorldEntityByID(std::string id) const { if(id == "player" || id == "Player" || id == "PLAYER") return this->player_->getControllableEntity(); auto entity = this->worldEntities_.find(id); return entity != this->worldEntities_.end() ? entity->second : nullptr; } ControllableEntity *ScriptableController::getControllableEntityByID(std::string id) const { if(id == "player" || id == "Player" || id == "PLAYER") return this->player_->getControllableEntity(); auto entity = this->controllabelEntities_.find(id); return entity != this->controllabelEntities_.end() ? entity->second : nullptr; } void ScriptableController::printLuaError(lua_State *lua) { // The error message is on top of the stack. // Fetch it, print it and then pop it off the stack. // Yes, this is 'const char*' and not 'std::string' because that's what lua gives us. const char* message = lua_tostring(lua, -1); std::cout << message << std::endl; lua_pop(lua, 1); } }