mirror of
https://github.com/OpenSpace/OpenSpace.git
synced 2026-04-23 20:50:59 -05:00
Feature/lua function cleanup (#1719)
General cleanup of Lua functions and handling of variable extract from a Lua state
This commit is contained in:
@@ -108,6 +108,7 @@ set(SOURCE_FILES
|
||||
rendering/renderabletrailorbit.cpp
|
||||
rendering/renderabletrailtrajectory.cpp
|
||||
rendering/screenspacedashboard.cpp
|
||||
rendering/screenspacedashboard_lua.inl
|
||||
rendering/screenspaceframebuffer.cpp
|
||||
rendering/screenspaceimagelocal.cpp
|
||||
rendering/screenspaceimageonline.cpp
|
||||
|
||||
@@ -54,79 +54,10 @@ namespace {
|
||||
#include "screenspacedashboard_codegen.cpp"
|
||||
} // namespace
|
||||
|
||||
#include "screenspacedashboard_lua.inl"
|
||||
|
||||
namespace openspace {
|
||||
|
||||
namespace luascriptfunctions {
|
||||
|
||||
/**
|
||||
* \ingroup LuaScripts
|
||||
* addDashboardItemToScreenSpace(string, table):
|
||||
*/
|
||||
int addDashboardItemToScreenSpace(lua_State* L) {
|
||||
ghoul::lua::checkArgumentsAndThrow(L, 2, "lua::addDashboardItemToScreenSpace");
|
||||
|
||||
const std::string& name = ghoul::lua::value<std::string>(L, 1);
|
||||
const int type = lua_type(L, 2);
|
||||
if (type != LUA_TTABLE) {
|
||||
return ghoul::lua::luaError(L, "Expected argument of type 'table'");
|
||||
}
|
||||
|
||||
ghoul::Dictionary d;
|
||||
try {
|
||||
ghoul::lua::luaDictionaryFromState(L, d);
|
||||
}
|
||||
catch (const ghoul::lua::LuaFormatException& e) {
|
||||
LERRORC("addDashboardItem", e.what());
|
||||
return 0;
|
||||
}
|
||||
|
||||
ScreenSpaceRenderable* ssr = global::renderEngine->screenSpaceRenderable(name);
|
||||
|
||||
if (!ssr) {
|
||||
return ghoul::lua::luaError(L, "Provided name is not a ScreenSpace item");
|
||||
}
|
||||
|
||||
ScreenSpaceDashboard* dash = dynamic_cast<ScreenSpaceDashboard*>(ssr);
|
||||
if (!dash) {
|
||||
return ghoul::lua::luaError(
|
||||
L,
|
||||
"Provided name is a ScreenSpace item but not a dashboard"
|
||||
);
|
||||
}
|
||||
|
||||
dash->dashboard().addDashboardItem(DashboardItem::createFromDictionary(d));
|
||||
|
||||
lua_settop(L, 0);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* \ingroup LuaScripts
|
||||
* removeDashboardItemsFromScreenSpace(string):
|
||||
*/
|
||||
int removeDashboardItemsFromScreenSpace(lua_State* L) {
|
||||
ghoul::lua::checkArgumentsAndThrow(L, 1, "lua::removeDashboardItemsFromScreenSpace");
|
||||
|
||||
const std::string& name = ghoul::lua::value<std::string>(L, 1);
|
||||
ScreenSpaceRenderable* ssr = global::renderEngine->screenSpaceRenderable(name);
|
||||
|
||||
if (!ssr) {
|
||||
return ghoul::lua::luaError(L, "Provided name is not a ScreenSpace item");
|
||||
}
|
||||
|
||||
ScreenSpaceDashboard* dash = dynamic_cast<ScreenSpaceDashboard*>(ssr);
|
||||
if (!dash) {
|
||||
return ghoul::lua::luaError(
|
||||
L,
|
||||
"Provided name is a ScreenSpace item but not a dashboard"
|
||||
);
|
||||
}
|
||||
|
||||
dash->dashboard().clearDashboardItems();
|
||||
return 0;
|
||||
}
|
||||
} // namespace luascriptfunctions
|
||||
|
||||
documentation::Documentation ScreenSpaceDashboard::Documentation() {
|
||||
return codegen::doc<Parameters>("base_screenspace_dashboard");
|
||||
}
|
||||
|
||||
@@ -0,0 +1,77 @@
|
||||
/*****************************************************************************************
|
||||
* *
|
||||
* OpenSpace *
|
||||
* *
|
||||
* Copyright (c) 2014-2021 *
|
||||
* *
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy of this *
|
||||
* software and associated documentation files (the "Software"), to deal in the Software *
|
||||
* without restriction, including without limitation the rights to use, copy, modify, *
|
||||
* merge, publish, distribute, sublicense, and/or sell copies of the Software, and to *
|
||||
* permit persons to whom the Software is furnished to do so, subject to the following *
|
||||
* conditions: *
|
||||
* *
|
||||
* The above copyright notice and this permission notice shall be included in all copies *
|
||||
* or substantial portions of the Software. *
|
||||
* *
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, *
|
||||
* INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A *
|
||||
* PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT *
|
||||
* HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF *
|
||||
* CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE *
|
||||
* OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. *
|
||||
****************************************************************************************/
|
||||
|
||||
namespace openspace::luascriptfunctions {
|
||||
|
||||
/**
|
||||
* \ingroup LuaScripts
|
||||
* addDashboardItemToScreenSpace(string, table):
|
||||
*/
|
||||
int addDashboardItemToScreenSpace(lua_State* L) {
|
||||
ghoul::lua::checkArgumentsAndThrow(L, 2, "lua::addDashboardItemToScreenSpace");
|
||||
auto [name, d] = ghoul::lua::values<std::string, ghoul::Dictionary>(L);
|
||||
|
||||
ScreenSpaceRenderable* ssr = global::renderEngine->screenSpaceRenderable(name);
|
||||
if (!ssr) {
|
||||
return ghoul::lua::luaError(L, "Provided name is not a ScreenSpace item");
|
||||
}
|
||||
|
||||
ScreenSpaceDashboard* dash = dynamic_cast<ScreenSpaceDashboard*>(ssr);
|
||||
if (!dash) {
|
||||
return ghoul::lua::luaError(
|
||||
L,
|
||||
"Provided name is a ScreenSpace item but not a dashboard"
|
||||
);
|
||||
}
|
||||
|
||||
dash->dashboard().addDashboardItem(DashboardItem::createFromDictionary(d));
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* \ingroup LuaScripts
|
||||
* removeDashboardItemsFromScreenSpace(string):
|
||||
*/
|
||||
int removeDashboardItemsFromScreenSpace(lua_State* L) {
|
||||
ghoul::lua::checkArgumentsAndThrow(L, 1, "lua::removeDashboardItemsFromScreenSpace");
|
||||
const std::string name = ghoul::lua::value<std::string>(L);
|
||||
|
||||
ScreenSpaceRenderable* ssr = global::renderEngine->screenSpaceRenderable(name);
|
||||
if (!ssr) {
|
||||
return ghoul::lua::luaError(L, "Provided name is not a ScreenSpace item");
|
||||
}
|
||||
|
||||
ScreenSpaceDashboard* dash = dynamic_cast<ScreenSpaceDashboard*>(ssr);
|
||||
if (!dash) {
|
||||
return ghoul::lua::luaError(
|
||||
L,
|
||||
"Provided name is a ScreenSpace item but not a dashboard"
|
||||
);
|
||||
}
|
||||
|
||||
dash->dashboard().clearDashboardItems();
|
||||
return 0;
|
||||
}
|
||||
|
||||
} // namespace openspace::luascriptfunctions
|
||||
@@ -88,43 +88,45 @@ ExoplanetSystem findExoplanetSystemInData(std::string_view starName) {
|
||||
std::string name;
|
||||
std::getline(ss, name, ',');
|
||||
|
||||
if (name.substr(0, name.length() - 2) == starName) {
|
||||
std::string location_s;
|
||||
std::getline(ss, location_s);
|
||||
long location = std::stol(location_s.c_str());
|
||||
if (name.substr(0, name.length() - 2) != starName) {
|
||||
continue;
|
||||
}
|
||||
|
||||
data.seekg(location);
|
||||
data.read(reinterpret_cast<char*>(&p), sizeof(ExoplanetDataEntry));
|
||||
std::string location_s;
|
||||
std::getline(ss, location_s);
|
||||
long location = std::stol(location_s.c_str());
|
||||
|
||||
sanitizeNameString(name);
|
||||
data.seekg(location);
|
||||
data.read(reinterpret_cast<char*>(&p), sizeof(ExoplanetDataEntry));
|
||||
|
||||
if (!hasSufficientData(p)) {
|
||||
LWARNING(fmt::format("Insufficient data for exoplanet: '{}'", name));
|
||||
continue;
|
||||
}
|
||||
sanitizeNameString(name);
|
||||
|
||||
system.planetNames.push_back(name);
|
||||
system.planetsData.push_back(p);
|
||||
if (!hasSufficientData(p)) {
|
||||
LWARNING(fmt::format("Insufficient data for exoplanet: '{}'", name));
|
||||
continue;
|
||||
}
|
||||
|
||||
// Star data - Should not vary between planets, but one data entry might
|
||||
// lack data for the host star while another does not. So for every planet,
|
||||
// update star data if needed
|
||||
const glm::vec3 pos{ p.positionX, p.positionY, p.positionZ };
|
||||
if (system.starData.position != pos && isValidPosition(pos)) {
|
||||
system.starData.position = pos;
|
||||
}
|
||||
if (system.starData.radius != p.rStar && !std::isnan(p.rStar)) {
|
||||
system.starData.radius = p.rStar;
|
||||
}
|
||||
if (system.starData.bv != p.bmv && !std::isnan(p.bmv)) {
|
||||
system.starData.bv = p.bmv;
|
||||
}
|
||||
if (system.starData.teff != p.teff && !std::isnan(p.teff)) {
|
||||
system.starData.teff = p.teff;
|
||||
}
|
||||
if (system.starData.luminosity != p.luminosity && !std::isnan(p.luminosity)) {
|
||||
system.starData.luminosity = p.luminosity;
|
||||
}
|
||||
system.planetNames.push_back(name);
|
||||
system.planetsData.push_back(p);
|
||||
|
||||
// Star data - Should not vary between planets, but one data entry might lack data
|
||||
// for the host star while another does not. So for every planet, update star data
|
||||
// if needed
|
||||
const glm::vec3 pos = glm::vec3(p.positionX, p.positionY, p.positionZ);
|
||||
if (system.starData.position != pos && isValidPosition(pos)) {
|
||||
system.starData.position = pos;
|
||||
}
|
||||
if (system.starData.radius != p.rStar && !std::isnan(p.rStar)) {
|
||||
system.starData.radius = p.rStar;
|
||||
}
|
||||
if (system.starData.bv != p.bmv && !std::isnan(p.bmv)) {
|
||||
system.starData.bv = p.bmv;
|
||||
}
|
||||
if (system.starData.teff != p.teff && !std::isnan(p.teff)) {
|
||||
system.starData.teff = p.teff;
|
||||
}
|
||||
if (system.starData.luminosity != p.luminosity && !std::isnan(p.luminosity)) {
|
||||
system.starData.luminosity = p.luminosity;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -555,50 +557,40 @@ void createExoplanetSystem(const std::string& starName) {
|
||||
|
||||
int addExoplanetSystem(lua_State* L) {
|
||||
ghoul::lua::checkArgumentsAndThrow(L, 1, "lua::addExoplanetSystem");
|
||||
std::variant<std::string, ghoul::Dictionary> v =
|
||||
ghoul::lua::value<std::variant<std::string, ghoul::Dictionary>>(L);
|
||||
|
||||
const int t = lua_type(L, 1);
|
||||
if (t == LUA_TSTRING) {
|
||||
if (std::holds_alternative<std::string>(v)) {
|
||||
// The user provided a single name
|
||||
const std::string& starName = ghoul::lua::value<std::string>(L, 1);
|
||||
std::string starName = std::get<std::string>(v);
|
||||
createExoplanetSystem(starName);
|
||||
}
|
||||
else if (t == LUA_TTABLE) {
|
||||
else {
|
||||
// A list of names was provided
|
||||
ghoul::Dictionary d;
|
||||
ghoul::lua::luaDictionaryFromState(L, d);
|
||||
|
||||
for (size_t i = 1; i <= d.size(); ++i) {
|
||||
if (!d.hasValue<std::string>(std::to_string(i))) {
|
||||
ghoul::Dictionary starNames = ghoul::lua::value<ghoul::Dictionary>(L);
|
||||
for (size_t i = 1; i <= starNames.size(); ++i) {
|
||||
if (!starNames.hasValue<std::string>(std::to_string(i))) {
|
||||
return ghoul::lua::luaError(
|
||||
L, fmt::format("List item {} is of invalid type", i)
|
||||
L,
|
||||
fmt::format("List item {} is of invalid type", i)
|
||||
);
|
||||
}
|
||||
const std::string& starName = d.value<std::string>(std::to_string(i));
|
||||
const std::string& starName = starNames.value<std::string>(std::to_string(i));
|
||||
createExoplanetSystem(starName);
|
||||
}
|
||||
lua_pop(L, 1);
|
||||
}
|
||||
else {
|
||||
return ghoul::lua::luaError(L, "Invalid input");
|
||||
}
|
||||
|
||||
lua_settop(L, 0);
|
||||
ghoul_assert(lua_gettop(L) == 0, "Incorrect number of items left on stack");
|
||||
return 0;
|
||||
}
|
||||
|
||||
int removeExoplanetSystem(lua_State* L) {
|
||||
ghoul::lua::checkArgumentsAndThrow(L, 1, "lua::removeExoplanetSystem");
|
||||
std::string starName = ghoul::lua::value<std::string>(L);
|
||||
|
||||
const int StringLocation = -1;
|
||||
const std::string starName = luaL_checkstring(L, StringLocation);
|
||||
const std::string starIdentifier = createIdentifier(starName);
|
||||
|
||||
const std::string starIdentifier = createIdentifier(std::move(starName));
|
||||
openspace::global::scriptEngine->queueScript(
|
||||
"openspace.removeSceneGraphNode('" + starIdentifier + "');",
|
||||
scripting::ScriptEngine::RemoteScripting::Yes
|
||||
);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -656,7 +648,6 @@ std::vector<std::string> hostStarsWithSufficientData() {
|
||||
// For easier read, sort by names and remove duplicates
|
||||
std::sort(names.begin(), names.end());
|
||||
names.erase(std::unique(names.begin(), names.end()), names.end());
|
||||
|
||||
return names;
|
||||
}
|
||||
|
||||
@@ -664,15 +655,13 @@ int getListOfExoplanets(lua_State* L) {
|
||||
ghoul::lua::checkArgumentsAndThrow(L, 0, "lua::getListOfExoplanets");
|
||||
|
||||
std::vector<std::string> names = hostStarsWithSufficientData();
|
||||
|
||||
lua_newtable(L);
|
||||
int number = 1;
|
||||
for (const std::string& s : names) {
|
||||
lua_pushstring(L, s.c_str());
|
||||
ghoul::lua::push(L, s);
|
||||
lua_rawseti(L, -2, number);
|
||||
++number;
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
@@ -683,16 +672,15 @@ int listAvailableExoplanetSystems(lua_State* L) {
|
||||
|
||||
std::string output;
|
||||
for (auto it = names.begin(); it != names.end(); ++it) {
|
||||
if (it != names.end()) {
|
||||
output += *it + ", ";
|
||||
}
|
||||
output += *it + ", ";
|
||||
}
|
||||
output.pop_back();
|
||||
output.pop_back();
|
||||
|
||||
LINFO(fmt::format(
|
||||
"There is data available for the following {} exoplanet systems: {}",
|
||||
names.size(), output
|
||||
));
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
@@ -47,10 +47,8 @@ int addLayer(lua_State* L) {
|
||||
ZoneScoped
|
||||
|
||||
ghoul::lua::checkArgumentsAndThrow(L, 3, "lua::addLayer");
|
||||
|
||||
// String arguments
|
||||
const std::string& globeName = ghoul::lua::value<std::string>(L, 1);
|
||||
const std::string& layerGroupName = ghoul::lua::value<std::string>(L, 2);
|
||||
auto [globeName, layerGroupName, layerDict] =
|
||||
ghoul::lua::values<std::string, std::string, ghoul::Dictionary>(L);
|
||||
|
||||
// Get the node and make sure it exists
|
||||
SceneGraphNode* n = global::renderEngine->scene()->sceneGraphNode(globeName);
|
||||
@@ -73,23 +71,10 @@ int addLayer(lua_State* L) {
|
||||
}
|
||||
|
||||
// Get the dictionary defining the layer
|
||||
ghoul::Dictionary d;
|
||||
try {
|
||||
ghoul::lua::luaDictionaryFromState(L, d);
|
||||
}
|
||||
catch (const ghoul::lua::LuaFormatException& e) {
|
||||
LERRORC("addLayerFromDictionary", e.what());
|
||||
lua_settop(L, 0);
|
||||
return 0;
|
||||
}
|
||||
lua_settop(L, 0);
|
||||
|
||||
Layer* layer = globe->layerManager().addLayer(groupID, d);
|
||||
Layer* layer = globe->layerManager().addLayer(groupID, layerDict);
|
||||
if (layer) {
|
||||
layer->initialize();
|
||||
}
|
||||
|
||||
ghoul_assert(lua_gettop(L) == 0, "Incorrect number of items left on stack");
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -98,11 +83,8 @@ int addLayer(lua_State* L) {
|
||||
*/
|
||||
int deleteLayer(lua_State* L) {
|
||||
ghoul::lua::checkArgumentsAndThrow(L, 3, "lua::deleteLayer");
|
||||
|
||||
const std::string& globeName = luaL_checkstring(L, 1);
|
||||
const std::string& layerGroupName = luaL_checkstring(L, 2);
|
||||
const std::string& layerName = luaL_checkstring(L, 3);
|
||||
lua_pop(L, 3);
|
||||
auto [globeName, layerGroupName, layerName] =
|
||||
ghoul::lua::values<std::string, std::string, std::string>(L);
|
||||
|
||||
// Get the node and make sure it exists
|
||||
SceneGraphNode* n = global::renderEngine->scene()->sceneGraphNode(globeName);
|
||||
@@ -125,17 +107,12 @@ int deleteLayer(lua_State* L) {
|
||||
}
|
||||
|
||||
globe->layerManager().deleteLayer(groupID, layerName);
|
||||
|
||||
ghoul_assert(lua_gettop(L) == 0, "Incorrect number of items left on stack");
|
||||
return 0;
|
||||
}
|
||||
|
||||
int getLayers(lua_State* L) {
|
||||
ghoul::lua::checkArgumentsAndThrow(L, 2, "lua::getLayers");
|
||||
|
||||
const std::string& globeIdentifier = ghoul::lua::value<std::string>(L, 1);
|
||||
const std::string& layer = ghoul::lua::value<std::string>(L, 2);
|
||||
lua_pop(L, 2);
|
||||
auto [globeIdentifier, layer] = ghoul::lua::values<std::string, std::string>(L);
|
||||
|
||||
SceneGraphNode* n = sceneGraphNode(globeIdentifier);
|
||||
if (!n) {
|
||||
@@ -168,12 +145,8 @@ int getLayers(lua_State* L) {
|
||||
|
||||
int moveLayer(lua_State* L) {
|
||||
ghoul::lua::checkArgumentsAndThrow(L, 4, "lua::moveLayer");
|
||||
|
||||
const std::string& globeIdentifier = ghoul::lua::value<std::string>(L, 1);
|
||||
const std::string& layer = ghoul::lua::value<std::string>(L, 2);
|
||||
int oldPosition = ghoul::lua::value<int>(L, 3);
|
||||
int newPosition = ghoul::lua::value<int>(L, 4);
|
||||
lua_pop(L, 4);
|
||||
auto [globeIdentifier, layer, oldPosition, newPosition] =
|
||||
ghoul::lua::values<std::string, std::string, int, int>(L);
|
||||
|
||||
if (oldPosition == newPosition) {
|
||||
return 0;
|
||||
@@ -197,22 +170,16 @@ int moveLayer(lua_State* L) {
|
||||
|
||||
globebrowsing::LayerGroup& lg = globe->layerManager().layerGroup(group);
|
||||
lg.moveLayers(oldPosition, newPosition);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int goToChunk(lua_State* L) {
|
||||
ghoul::lua::checkArgumentsAndThrow(L, 4, "lua::goToChunk");
|
||||
auto [identifier, x, y, level] = ghoul::lua::values<std::string, int, int, int>(L);
|
||||
|
||||
const std::string& globeIdentifier = ghoul::lua::value<std::string>(L, 1);
|
||||
const int x = ghoul::lua::value<int>(L, 2);
|
||||
const int y = ghoul::lua::value<int>(L, 3);
|
||||
const int level = ghoul::lua::value<int>(L, 4);
|
||||
lua_pop(L, 4);
|
||||
|
||||
SceneGraphNode* n = sceneGraphNode(globeIdentifier);
|
||||
SceneGraphNode* n = sceneGraphNode(identifier);
|
||||
if (!n) {
|
||||
return ghoul::lua::luaError(L, "Unknown globe name: " + globeIdentifier);
|
||||
return ghoul::lua::luaError(L, "Unknown globe name: " + identifier);
|
||||
}
|
||||
|
||||
const RenderableGlobe* globe = dynamic_cast<const RenderableGlobe*>(n->renderable());
|
||||
@@ -221,22 +188,18 @@ int goToChunk(lua_State* L) {
|
||||
}
|
||||
|
||||
global::moduleEngine->module<GlobeBrowsingModule>()->goToChunk(*globe, x, y, level);
|
||||
|
||||
ghoul_assert(lua_gettop(L) == 0, "Incorrect number of items left on stack");
|
||||
return 0;
|
||||
}
|
||||
|
||||
int goToGeo(lua_State* L) {
|
||||
int nArguments = ghoul::lua::checkArgumentsAndThrow(L, { 2, 4 }, "lua::goToGeo");
|
||||
ghoul::lua::checkArgumentsAndThrow(L, { 2, 4 }, "lua::goToGeo");
|
||||
|
||||
// Check if the user provided a Scene graph node identifier as the first argument.
|
||||
// lua_isstring returns true for both numbers and strings, so better use !lua_isnumber
|
||||
const bool providedGlobeIdentifier = !lua_isnumber(L, 1);
|
||||
const int parameterOffset = providedGlobeIdentifier ? 1 : 0;
|
||||
|
||||
const SceneGraphNode* n;
|
||||
if (providedGlobeIdentifier) {
|
||||
const std::string& globeIdentifier = ghoul::lua::value<std::string>(L, 1);
|
||||
const std::string& globeIdentifier = ghoul::lua::value<std::string>(L);
|
||||
n = sceneGraphNode(globeIdentifier);
|
||||
if (!n) {
|
||||
return ghoul::lua::luaError(L, "Unknown globe name: " + globeIdentifier);
|
||||
@@ -249,8 +212,8 @@ int goToGeo(lua_State* L) {
|
||||
}
|
||||
}
|
||||
|
||||
const double latitude = ghoul::lua::value<double>(L, parameterOffset + 1);
|
||||
const double longitude = ghoul::lua::value<double>(L, parameterOffset + 2);
|
||||
auto [latitude, longitude, altitude] =
|
||||
ghoul::lua::values<double, double, std::optional<double>>(L);
|
||||
|
||||
const RenderableGlobe* globe = dynamic_cast<const RenderableGlobe*>(n->renderable());
|
||||
if (!globe) {
|
||||
@@ -258,32 +221,29 @@ int goToGeo(lua_State* L) {
|
||||
return ghoul::lua::luaError(L, "Identifier must be a RenderableGlobe");
|
||||
}
|
||||
else {
|
||||
return ghoul::lua::luaError(L,
|
||||
"Current anchor node is not a RenderableGlobe. "
|
||||
"Either change the anchor to a globe, or specify a globe identifier "
|
||||
"as the first argument"
|
||||
return ghoul::lua::luaError(
|
||||
L,
|
||||
"Current anchor node is not a RenderableGlobe. Either change the anchor "
|
||||
"to a globe, or specify a globe identifier as the first argument"
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
if (nArguments == parameterOffset + 2) {
|
||||
global::moduleEngine->module<GlobeBrowsingModule>()->goToGeo(
|
||||
*globe, latitude, longitude
|
||||
);
|
||||
}
|
||||
else if (nArguments == parameterOffset + 3) {
|
||||
const double altitude = ghoul::lua::value<double>(L, parameterOffset + 3);
|
||||
if (altitude.has_value()) {
|
||||
global::moduleEngine->module<GlobeBrowsingModule>()->goToGeo(
|
||||
*globe,
|
||||
latitude,
|
||||
longitude,
|
||||
altitude
|
||||
*altitude
|
||||
);
|
||||
}
|
||||
else {
|
||||
global::moduleEngine->module<GlobeBrowsingModule>()->goToGeo(
|
||||
*globe,
|
||||
latitude,
|
||||
longitude
|
||||
);
|
||||
}
|
||||
|
||||
lua_settop(L, 0);
|
||||
|
||||
ghoul_assert(lua_gettop(L) == 0, "Incorrect number of items left on stack");
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -394,12 +354,8 @@ int flyToGeo(lua_State* L) {
|
||||
|
||||
int getLocalPositionFromGeo(lua_State* L) {
|
||||
ghoul::lua::checkArgumentsAndThrow(L, 4, "lua::getLocalPositionFromGeo");
|
||||
|
||||
const std::string& globeIdentifier = ghoul::lua::value<std::string>(L, 1);
|
||||
const double latitude = ghoul::lua::value<double>(L, 2);
|
||||
const double longitude = ghoul::lua::value<double>(L, 3);
|
||||
const double altitude = ghoul::lua::value<double>(L, 4);
|
||||
lua_pop(L, 4);
|
||||
auto [globeIdentifier, latitude, longitude, altitude] =
|
||||
ghoul::lua::values<std::string, double, double, double>(L);
|
||||
|
||||
SceneGraphNode* n = sceneGraphNode(globeIdentifier);
|
||||
if (!n) {
|
||||
@@ -411,16 +367,8 @@ int getLocalPositionFromGeo(lua_State* L) {
|
||||
}
|
||||
|
||||
GlobeBrowsingModule& mod = *(global::moduleEngine->module<GlobeBrowsingModule>());
|
||||
glm::vec3 pos = mod.cartesianCoordinatesFromGeo(
|
||||
*globe,
|
||||
latitude,
|
||||
longitude,
|
||||
altitude
|
||||
);
|
||||
|
||||
ghoul::lua::push(L, pos.x, pos.y, pos.z);
|
||||
|
||||
ghoul_assert(lua_gettop(L) == 3, "Incorrect number of items left on stack");
|
||||
glm::vec3 p = mod.cartesianCoordinatesFromGeo(*globe, latitude, longitude, altitude);
|
||||
ghoul::lua::push(L, p.x, p.y, p.z);
|
||||
return 3;
|
||||
}
|
||||
|
||||
@@ -450,72 +398,48 @@ int getGeoPositionForCamera(lua_State* L) {
|
||||
posHandle.centerToReferenceSurface);
|
||||
|
||||
ghoul::lua::push(L, glm::degrees(geo2.lat), glm::degrees(geo2.lon), altitude);
|
||||
|
||||
ghoul_assert(lua_gettop(L) == 3, "Incorrect number of items left on stack");
|
||||
return 3;
|
||||
}
|
||||
|
||||
int loadWMSCapabilities(lua_State* L) {
|
||||
ghoul::lua::checkArgumentsAndThrow(L, 3, "lua::loadWMSCapabilities");
|
||||
|
||||
std::string name = ghoul::lua::value<std::string>(L, 1);
|
||||
std::string globe = ghoul::lua::value<std::string>(L, 2);
|
||||
std::string url = ghoul::lua::value<std::string>(L, 3);
|
||||
auto [name, globe, url] =
|
||||
ghoul::lua::values<std::string, std::string, std::string>(L);
|
||||
|
||||
global::moduleEngine->module<GlobeBrowsingModule>()->loadWMSCapabilities(
|
||||
std::move(name),
|
||||
std::move(globe),
|
||||
std::move(url)
|
||||
);
|
||||
|
||||
lua_pop(L, 3);
|
||||
|
||||
ghoul_assert(lua_gettop(L) == 0, "Incorrect number of items left on stack");
|
||||
return 0;
|
||||
}
|
||||
|
||||
int removeWMSServer(lua_State* L) {
|
||||
ghoul::lua::checkArgumentsAndThrow(L, 1, "lua::removeWMSServer");
|
||||
|
||||
const std::string& name = ghoul::lua::value<std::string>(
|
||||
L,
|
||||
1,
|
||||
ghoul::lua::PopValue::Yes
|
||||
);
|
||||
const std::string name = ghoul::lua::value<std::string>(L);
|
||||
|
||||
global::moduleEngine->module<GlobeBrowsingModule>()->removeWMSServer(name);
|
||||
|
||||
ghoul_assert(lua_gettop(L) == 0, "Incorrect number of items left on stack");
|
||||
return 0;
|
||||
}
|
||||
|
||||
int capabilities(lua_State* L) {
|
||||
ghoul::lua::checkArgumentsAndThrow(L, 1, "lua::capabilities");
|
||||
const std::string name = ghoul::lua::value<std::string>(L);
|
||||
|
||||
const std::string& name = ghoul::lua::value<std::string>(
|
||||
L,
|
||||
1,
|
||||
ghoul::lua::PopValue::Yes
|
||||
);
|
||||
GlobeBrowsingModule::Capabilities cap =
|
||||
global::moduleEngine->module<GlobeBrowsingModule>()->capabilities(name);
|
||||
|
||||
lua_newtable(L);
|
||||
for (unsigned long i = 0; i < cap.size(); ++i) {
|
||||
for (size_t i = 0; i < cap.size(); ++i) {
|
||||
const GlobeBrowsingModule::Layer& l = cap[i];
|
||||
|
||||
lua_newtable(L);
|
||||
|
||||
ghoul::lua::push(L, "Name", l.name);
|
||||
lua_settable(L, -3);
|
||||
|
||||
ghoul::lua::push(L, "URL", l.url);
|
||||
lua_settable(L, -3);
|
||||
|
||||
lua_rawseti(L, -2, i + 1);
|
||||
}
|
||||
|
||||
ghoul_assert(lua_gettop(L) == 1, "Incorrect number of items left on stack");
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
||||
@@ -30,48 +30,38 @@ int convertFromRaDec(lua_State* L) {
|
||||
ghoul::lua::checkArgumentsAndThrow(L, 3, "lua::convertFromRaDec");
|
||||
|
||||
glm::dvec2 degrees = glm::dvec2(0.0);
|
||||
if (lua_type(L, 1) == LUA_TSTRING && lua_type(L, 2) == LUA_TSTRING) {
|
||||
std::string ra = ghoul::lua::value<std::string>(L, 1);
|
||||
std::string dec = ghoul::lua::value<std::string>(L, 2);
|
||||
if (ghoul::lua::hasValue<std::string>(L, 1) &&
|
||||
ghoul::lua::hasValue<std::string>(L, 2))
|
||||
{
|
||||
auto [ra, dec] = ghoul::lua::values<std::string, std::string>(L);
|
||||
degrees = icrsToDecimalDegrees(ra, dec);
|
||||
}
|
||||
else if (lua_type(L, 1) == LUA_TNUMBER && lua_type(L, 2) == LUA_TNUMBER) {
|
||||
degrees.x = ghoul::lua::value<double>(L, 1);
|
||||
degrees.y = ghoul::lua::value<double>(L, 2);
|
||||
else if (ghoul::lua::hasValue<double>(L, 1) && ghoul::lua::hasValue<double>(L, 2)) {
|
||||
auto [x, y] = ghoul::lua::values<double, double>(L);
|
||||
degrees.x = x;
|
||||
degrees.y = y;
|
||||
}
|
||||
else {
|
||||
throw ghoul::lua::LuaRuntimeException("lua::convertFromRaDec: Ra and Dec have to "
|
||||
"be of the same type, either String or Number"
|
||||
throw ghoul::lua::LuaRuntimeException(
|
||||
"Ra and Dec have to be of the same type, either String or Number"
|
||||
);
|
||||
}
|
||||
|
||||
double distance = ghoul::lua::value<double>(L, 3);
|
||||
lua_settop(L, 0);
|
||||
|
||||
double distance = ghoul::lua::value<double>(L);
|
||||
glm::dvec3 pos = icrsToGalacticCartesian(degrees.x, degrees.y, distance);
|
||||
ghoul::lua::push(L, pos);
|
||||
|
||||
ghoul_assert(lua_gettop(L) == 1, "Incorrect number of items left on stack");
|
||||
return 1;
|
||||
}
|
||||
|
||||
int convertToRaDec(lua_State* L) {
|
||||
ghoul::lua::checkArgumentsAndThrow(L, 3, "lua::convertToRaDec");
|
||||
auto [x, y, z] = ghoul::lua::values<double, double, double>(L);
|
||||
|
||||
double x = ghoul::lua::value<double>(L, 1);
|
||||
double y = ghoul::lua::value<double>(L, 2);
|
||||
double z = ghoul::lua::value<double>(L, 3);
|
||||
lua_settop(L, 0);
|
||||
glm::dvec3 deg = galacticCartesianToIcrs(x, y, z);
|
||||
std::pair<std::string, std::string> raDecPair = decimalDegreesToIcrs(deg.x, deg.y);
|
||||
|
||||
glm::dvec3 degrees = galacticCartesianToIcrs(x, y, z);
|
||||
std::pair<std::string, std::string> raDecPair
|
||||
= decimalDegreesToIcrs(degrees.x, degrees.y);
|
||||
|
||||
ghoul::lua::push(L, raDecPair.first); // Ra
|
||||
ghoul::lua::push(L, raDecPair.second); // Dec
|
||||
ghoul::lua::push(L, degrees.z); // Distance
|
||||
|
||||
ghoul_assert(lua_gettop(L) == 3, "Incorrect number of items left on stack");
|
||||
// Ra, Dec, Distance
|
||||
ghoul::lua::push(L, raDecPair.first, raDecPair.second, deg.z);
|
||||
return 3;
|
||||
}
|
||||
|
||||
|
||||
@@ -33,95 +33,37 @@
|
||||
namespace openspace::luascriptfunctions {
|
||||
|
||||
int createStateMachine(lua_State* L) {
|
||||
const int nArguments = ghoul::lua::checkArgumentsAndThrow(
|
||||
L,
|
||||
{ 2, 3 },
|
||||
"lua::createStateMachine"
|
||||
);
|
||||
|
||||
// If three arguments, a start state was included
|
||||
std::optional<std::string> startState = std::nullopt;
|
||||
if (nArguments > 2) {
|
||||
startState = ghoul::lua::value<std::string>(L, 3, ghoul::lua::PopValue::Yes);
|
||||
}
|
||||
|
||||
// Last dictionary is on top of the stack
|
||||
ghoul::Dictionary transitions;
|
||||
try {
|
||||
ghoul::lua::luaDictionaryFromState(L, transitions);
|
||||
}
|
||||
catch (const ghoul::lua::LuaFormatException& e) {
|
||||
LERRORC("createStateMachine", e.what());
|
||||
return 0;
|
||||
}
|
||||
|
||||
// Pop, so that first dictionary is on top and can be read
|
||||
lua_pop(L, 1);
|
||||
ghoul::Dictionary states;
|
||||
try {
|
||||
ghoul::lua::luaDictionaryFromState(L, states);
|
||||
}
|
||||
catch (const ghoul::lua::LuaFormatException& e) {
|
||||
LERRORC("createStateMachine", e.what());
|
||||
return 0;
|
||||
}
|
||||
ghoul::lua::checkArgumentsAndThrow(L, { 2, 3 }, "lua::createStateMachine");
|
||||
auto [states, transitions, startState] = ghoul::lua::values<
|
||||
ghoul::Dictionary, ghoul::Dictionary, std::optional<std::string>
|
||||
>(L);
|
||||
|
||||
StateMachineModule* module = global::moduleEngine->module<StateMachineModule>();
|
||||
|
||||
module->initializeStateMachine(states, transitions, startState);
|
||||
|
||||
lua_settop(L, 0);
|
||||
ghoul_assert(lua_gettop(L) == 0, "Incorrect number of items left on stack");
|
||||
module->initializeStateMachine(
|
||||
std::move(states),
|
||||
std::move(transitions),
|
||||
std::move(startState)
|
||||
);
|
||||
return 0;
|
||||
}
|
||||
|
||||
int goToState(lua_State* L) {
|
||||
ghoul::lua::checkArgumentsAndThrow(L, 1, "lua::goToState");
|
||||
const bool isString = (lua_isstring(L, 1) != 0);
|
||||
std::string newState = ghoul::lua::value<std::string>(L);
|
||||
|
||||
if (!isString) {
|
||||
lua_settop(L, 0);
|
||||
const char* msg = lua_pushfstring(
|
||||
L,
|
||||
"%s expected, got %s",
|
||||
lua_typename(L, LUA_TSTRING),
|
||||
luaL_typename(L, 0)
|
||||
);
|
||||
return luaL_error(L, "bad argument #%d (%s)", 1, msg);
|
||||
}
|
||||
|
||||
const std::string newState = lua_tostring(L, 1);
|
||||
StateMachineModule* module = global::moduleEngine->module<StateMachineModule>();
|
||||
module->transitionTo(newState);
|
||||
LINFOC("StateMachine", "Transitioning to " + newState);
|
||||
|
||||
lua_settop(L, 0);
|
||||
ghoul_assert(lua_gettop(L) == 0, "Incorrect number of items left on stack");
|
||||
return 0;
|
||||
}
|
||||
|
||||
int setInitialState(lua_State* L) {
|
||||
ghoul::lua::checkArgumentsAndThrow(L, 1, "lua::setStartState");
|
||||
const bool isString = (lua_isstring(L, 1) != 0);
|
||||
std::string startState = ghoul::lua::value<std::string>(L);
|
||||
|
||||
if (!isString) {
|
||||
lua_settop(L, 0);
|
||||
const char* msg = lua_pushfstring(
|
||||
L,
|
||||
"%s expected, got %s",
|
||||
lua_typename(L, LUA_TSTRING),
|
||||
luaL_typename(L, 0)
|
||||
);
|
||||
return luaL_error(L, "bad argument #%d (%s)", 1, msg);
|
||||
}
|
||||
|
||||
const std::string startState = lua_tostring(L, 1);
|
||||
StateMachineModule* module = global::moduleEngine->module<StateMachineModule>();
|
||||
module->setInitialState(startState);
|
||||
LINFOC("StateMachine", "Initial state set to: " + startState);
|
||||
|
||||
lua_settop(L, 0);
|
||||
ghoul_assert(lua_gettop(L) == 0, "Incorrect number of items left on stack");
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -130,9 +72,7 @@ int currentState(lua_State* L) {
|
||||
|
||||
StateMachineModule* module = global::moduleEngine->module<StateMachineModule>();
|
||||
std::string currentState = module->currentState();
|
||||
|
||||
lua_pushstring(L, currentState.c_str());
|
||||
ghoul_assert(lua_gettop(L) == 1, "Incorrect number of items left on stack");
|
||||
ghoul::lua::push(L, std::move(currentState));
|
||||
return 1;
|
||||
}
|
||||
|
||||
@@ -141,32 +81,16 @@ int possibleTransitions(lua_State* L) {
|
||||
|
||||
StateMachineModule* module = global::moduleEngine->module<StateMachineModule>();
|
||||
std::vector<std::string> transitions = module->possibleTransitions();
|
||||
|
||||
ghoul::lua::push(L, transitions);
|
||||
ghoul_assert(lua_gettop(L) == 1, "Incorrect number of items left on stack");
|
||||
return 1;
|
||||
}
|
||||
|
||||
int canGoToState(lua_State* L) {
|
||||
ghoul::lua::checkArgumentsAndThrow(L, 1, "lua::canGoToState");
|
||||
const bool isString = (lua_isstring(L, 1) != 0);
|
||||
std::string state = ghoul::lua::value<std::string>(L);
|
||||
|
||||
if (!isString) {
|
||||
lua_settop(L, 0);
|
||||
const char* msg = lua_pushfstring(
|
||||
L,
|
||||
"%s expected, got %s",
|
||||
lua_typename(L, LUA_TSTRING),
|
||||
luaL_typename(L, 0)
|
||||
);
|
||||
return luaL_error(L, "bad argument #%d (%s)", 1, msg);
|
||||
}
|
||||
|
||||
const std::string state = lua_tostring(L, 1);
|
||||
StateMachineModule* module = global::moduleEngine->module<StateMachineModule>();
|
||||
ghoul::lua::push(L, module->canGoToState(state));
|
||||
|
||||
ghoul_assert(lua_gettop(L) == 1, "Incorrect number of items left on stack");
|
||||
return 1;
|
||||
}
|
||||
|
||||
@@ -174,7 +98,6 @@ int printCurrentStateInfo(lua_State* L) {
|
||||
ghoul::lua::checkArgumentsAndThrow(L, 0, "lua::printCurrentStateInfo");
|
||||
|
||||
StateMachineModule* module = global::moduleEngine->module<StateMachineModule>();
|
||||
|
||||
if (module->hasStateMachine()) {
|
||||
std::string currentState = module->currentState();
|
||||
std::vector<std::string> transitions = module->possibleTransitions();
|
||||
@@ -188,7 +111,6 @@ int printCurrentStateInfo(lua_State* L) {
|
||||
LINFOC("StateMachine", "No state machine has been created");
|
||||
}
|
||||
|
||||
ghoul_assert(lua_gettop(L) == 0, "Incorrect number of items left on stack");
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user