mirror of
https://github.com/OpenSpace/OpenSpace.git
synced 2026-01-06 03:29:44 -06:00
Add a new panel to the Launcher to control which WebUI button appears on the bottom bar (#3569)
- Add markNodes to the profiletopic --------- Co-authored-by: Ylva Selling <ylva.selling@gmail.com>
This commit is contained in:
@@ -48,6 +48,7 @@ set(HEADER_FILES
|
||||
include/profile/timedialog.h
|
||||
include/profile/profileedit.h
|
||||
include/profile/propertiesdialog.h
|
||||
include/profile/uipanelsdialog.h
|
||||
include/sgctedit/displaywindowunion.h
|
||||
include/sgctedit/monitorbox.h
|
||||
include/sgctedit/sgctedit.h
|
||||
@@ -78,6 +79,7 @@ set(SOURCE_FILES
|
||||
src/profile/timedialog.cpp
|
||||
src/profile/profileedit.cpp
|
||||
src/profile/propertiesdialog.cpp
|
||||
src/profile/uipanelsdialog.cpp
|
||||
src/sgctedit/sgctedit.cpp
|
||||
src/sgctedit/displaywindowunion.cpp
|
||||
src/sgctedit/monitorbox.cpp
|
||||
|
||||
@@ -86,16 +86,17 @@ signals:
|
||||
void raiseExitWindow();
|
||||
|
||||
private slots:
|
||||
void openMeta();
|
||||
void openProperties();
|
||||
void openModules();
|
||||
void openKeybindings();
|
||||
void openAssets();
|
||||
void openTime();
|
||||
void openAddedScripts();
|
||||
void openKeybindings();
|
||||
void openMeta();
|
||||
void openMarkNodes();
|
||||
void openDeltaTimes();
|
||||
void openCamera();
|
||||
void openMarkNodes();
|
||||
void openTime();
|
||||
void openModules();
|
||||
void openUiPanels();
|
||||
void openAddedScripts();
|
||||
void approved();
|
||||
|
||||
private:
|
||||
@@ -112,18 +113,19 @@ private:
|
||||
std::string _profileFilename;
|
||||
|
||||
QLineEdit* _profileEdit = nullptr;
|
||||
QLabel* _modulesLabel = nullptr;
|
||||
QLabel* _assetsLabel = nullptr;
|
||||
QTextEdit* _assetsEdit = nullptr;
|
||||
QLabel* _propertiesLabel = nullptr;
|
||||
QTextEdit* _propertiesEdit = nullptr;
|
||||
QLabel* _assetsLabel = nullptr;
|
||||
QTextEdit* _assetsEdit = nullptr;
|
||||
QLabel* _keybindingsLabel = nullptr;
|
||||
QTextEdit* _keybindingsEdit = nullptr;
|
||||
QLabel* _deltaTimesLabel = nullptr;
|
||||
QLabel* _metaLabel = nullptr;
|
||||
QLabel* _interestingNodesLabel = nullptr;
|
||||
QLabel* _deltaTimesLabel = nullptr;
|
||||
QLabel* _cameraLabel = nullptr;
|
||||
QLabel* _timeLabel = nullptr;
|
||||
QLabel* _metaLabel = nullptr;
|
||||
QLabel* _modulesLabel = nullptr;
|
||||
QLabel* _uiPanelVisibilityLabel = nullptr;
|
||||
QLabel* _additionalScriptsLabel = nullptr;
|
||||
};
|
||||
|
||||
|
||||
51
apps/OpenSpace/ext/launcher/include/profile/uipanelsdialog.h
Normal file
51
apps/OpenSpace/ext/launcher/include/profile/uipanelsdialog.h
Normal file
@@ -0,0 +1,51 @@
|
||||
/*****************************************************************************************
|
||||
* *
|
||||
* OpenSpace *
|
||||
* *
|
||||
* Copyright (c) 2014-2025 *
|
||||
* *
|
||||
* 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. *
|
||||
****************************************************************************************/
|
||||
|
||||
#ifndef __OPENSPACE_UI_LAUNCHER___UIPANELSDIALOG___H__
|
||||
#define __OPENSPACE_UI_LAUNCHER___UIPANELSDIALOG___H__
|
||||
|
||||
#include <QDialog>
|
||||
|
||||
class QCheckBox;
|
||||
|
||||
class UiPanelsDialog final : public QDialog {
|
||||
Q_OBJECT
|
||||
public:
|
||||
/**
|
||||
* Constructor for UiPanelsDialog class.
|
||||
*
|
||||
* \param parent Pointer to parent Qt widget
|
||||
* \param uiPanels The list of ui panels and their visibility
|
||||
*/
|
||||
UiPanelsDialog(QWidget* parent, std::map<std::string, bool>* uiPanels);
|
||||
|
||||
private slots:
|
||||
void parseSelections();
|
||||
|
||||
private:
|
||||
std::map<std::string, bool>* _uiPanels;
|
||||
std::map<QCheckBox*, std::string> _checkboxToId;
|
||||
};
|
||||
|
||||
#endif // __OPENSPACE_UI_LAUNCHER___UIPANELSDIALOG___H__
|
||||
@@ -35,6 +35,7 @@
|
||||
#include "profile/modulesdialog.h"
|
||||
#include "profile/propertiesdialog.h"
|
||||
#include "profile/timedialog.h"
|
||||
#include "profile/uipanelsdialog.h"
|
||||
#include <openspace/scene/profile.h>
|
||||
#include <ghoul/format.h>
|
||||
#include <QDialogButtonBox>
|
||||
@@ -305,6 +306,21 @@ void ProfileEdit::createWidgets() {
|
||||
rightLayout->addLayout(container);
|
||||
}
|
||||
rightLayout->addWidget(new Line);
|
||||
{
|
||||
QBoxLayout* container = new QVBoxLayout;
|
||||
_uiPanelVisibilityLabel = new QLabel("User Interface Panels");
|
||||
_uiPanelVisibilityLabel->setObjectName("heading");
|
||||
_uiPanelVisibilityLabel->setWordWrap(true);
|
||||
container->addWidget(_uiPanelVisibilityLabel);
|
||||
|
||||
QPushButton* uiPanelEdit = new QPushButton("Edit");
|
||||
connect(uiPanelEdit, &QPushButton::clicked, this, &ProfileEdit::openUiPanels);
|
||||
uiPanelEdit->setLayoutDirection(Qt::RightToLeft);
|
||||
uiPanelEdit->setAccessibleName("Edit user interface panels");
|
||||
container->addWidget(uiPanelEdit);
|
||||
rightLayout->addLayout(container);
|
||||
}
|
||||
rightLayout->addWidget(new Line);
|
||||
{
|
||||
QBoxLayout* container = new QVBoxLayout;
|
||||
_additionalScriptsLabel = new QLabel("Additional Scripts");
|
||||
@@ -375,6 +391,10 @@ void ProfileEdit::openModules() {
|
||||
_modulesLabel->setText(labelText(_profile.modules.size(), "Modules"));
|
||||
}
|
||||
|
||||
void ProfileEdit::openUiPanels() {
|
||||
UiPanelsDialog(this, &_profile.uiPanelVisibility).exec();
|
||||
}
|
||||
|
||||
void ProfileEdit::openProperties() {
|
||||
PropertiesDialog(this, &_profile.properties).exec();
|
||||
_propertiesLabel->setText(labelText(_profile.properties.size(), "Properties"));
|
||||
|
||||
130
apps/OpenSpace/ext/launcher/src/profile/uipanelsdialog.cpp
Normal file
130
apps/OpenSpace/ext/launcher/src/profile/uipanelsdialog.cpp
Normal file
@@ -0,0 +1,130 @@
|
||||
/*****************************************************************************************
|
||||
* *
|
||||
* OpenSpace *
|
||||
* *
|
||||
* Copyright (c) 2014-2025 *
|
||||
* *
|
||||
* 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. *
|
||||
****************************************************************************************/
|
||||
|
||||
#include "profile/uipanelsdialog.h"
|
||||
|
||||
#include "profile/line.h"
|
||||
#include <openspace/json.h>
|
||||
#include <ghoul/filesystem/filesystem.h>
|
||||
#include <QCheckBox>
|
||||
#include <QDialogButtonBox>
|
||||
#include <QLabel>
|
||||
#include <QVBoxLayout>
|
||||
#include <fstream>
|
||||
#include <string_view>
|
||||
|
||||
namespace {
|
||||
constexpr std::string_view DefaultPanelPath = "${DATA}/web/default_ui_panels.json";
|
||||
|
||||
struct Panel {
|
||||
std::string id;
|
||||
std::string name;
|
||||
bool isVisible;
|
||||
};
|
||||
|
||||
void from_json(const nlohmann::json& j, Panel& layout) {
|
||||
j["id"].get_to(layout.id);
|
||||
j["name"].get_to(layout.name);
|
||||
j["visible"].get_to(layout.isVisible);
|
||||
}
|
||||
|
||||
std::vector<Panel> loadPanels() {
|
||||
std::ifstream panelFile = std::ifstream(absPath(DefaultPanelPath));
|
||||
const std::string panelContent = std::string(
|
||||
std::istreambuf_iterator<char>(panelFile),
|
||||
std::istreambuf_iterator<char>()
|
||||
);
|
||||
const nlohmann::json panel = nlohmann::json::parse(panelContent);
|
||||
std::map<std::string, Panel> panels = panel.get<std::map<std::string, Panel>>();
|
||||
|
||||
std::vector<Panel> result;
|
||||
for (const auto& [key, value] : panels) {
|
||||
result.push_back(value);
|
||||
}
|
||||
|
||||
std::sort(
|
||||
result.begin(),
|
||||
result.end(),
|
||||
[](const Panel& lhs, const Panel& rhs) { return lhs.name < rhs.name; }
|
||||
);
|
||||
|
||||
return result;
|
||||
}
|
||||
} // namespace
|
||||
|
||||
UiPanelsDialog::UiPanelsDialog(QWidget* parent, std::map<std::string, bool>* uiPanels)
|
||||
: QDialog(parent)
|
||||
, _uiPanels(uiPanels)
|
||||
{
|
||||
setWindowTitle("User Interface Panels");
|
||||
|
||||
std::vector<Panel> panels = loadPanels();
|
||||
|
||||
QBoxLayout* layout = new QVBoxLayout(this);
|
||||
|
||||
QLabel* info = new QLabel(
|
||||
"Select the user interface panels that should be visible by default in the "
|
||||
"current profile."
|
||||
);
|
||||
info->setWordWrap(true);
|
||||
layout->addWidget(info);
|
||||
|
||||
for (const Panel& panel : panels) {
|
||||
QCheckBox* box = new QCheckBox(QString::fromStdString(panel.name));
|
||||
|
||||
// If the profile already has a desired value for the checkbox, use it. Otherwise
|
||||
// use the default values
|
||||
auto it = _uiPanels->find(panel.id);
|
||||
if (it != _uiPanels->end()) {
|
||||
box->setChecked(it->second);
|
||||
}
|
||||
else {
|
||||
box->setChecked(panel.isVisible);
|
||||
}
|
||||
|
||||
layout->addWidget(box);
|
||||
_checkboxToId[box] = panel.id;
|
||||
}
|
||||
|
||||
layout->addWidget(new Line);
|
||||
|
||||
{
|
||||
QDialogButtonBox* buttons = new QDialogButtonBox;
|
||||
buttons->setStandardButtons(QDialogButtonBox::Save | QDialogButtonBox::Cancel);
|
||||
connect(
|
||||
buttons, &QDialogButtonBox::accepted,
|
||||
this, &UiPanelsDialog::parseSelections
|
||||
);
|
||||
connect(buttons, &QDialogButtonBox::rejected, this, &UiPanelsDialog::reject);
|
||||
layout->addWidget(buttons);
|
||||
}
|
||||
}
|
||||
|
||||
void UiPanelsDialog::parseSelections() {
|
||||
_uiPanels->clear();
|
||||
for (const auto& [key, value] : _checkboxToId) {
|
||||
_uiPanels->emplace(value, key->isChecked());
|
||||
}
|
||||
accept();
|
||||
}
|
||||
17
data/web/default_ui_panels.json
Normal file
17
data/web/default_ui_panels.json
Normal file
@@ -0,0 +1,17 @@
|
||||
{
|
||||
"0": { "id": "scene", "name": "Scene", "visible": true, "enabled": true },
|
||||
"1": { "id": "settings", "name": "Settings", "visible": false, "enabled": true },
|
||||
"2": { "id": "navigation", "name": "Navigation", "visible": true, "enabled": true },
|
||||
"3": { "id": "timePanel", "name": "Date & Time", "visible": true, "enabled": true },
|
||||
"4": { "id": "sessionRecording", "name": "Session Recording", "visible": true, "enabled": true },
|
||||
"5": { "id": "geoLocation", "name": "Geo Location", "visible": true, "enabled": true },
|
||||
"6": { "id": "screenSpaceRenderables", "name": "ScreenSpace Renderables", "visible": true, "enabled": true },
|
||||
"7": { "id": "exoplanets", "name": "Exoplanets", "visible": true, "enabled": true },
|
||||
"8": { "id": "userPanels", "name": "User Panels", "visible": true, "enabled": true },
|
||||
"9": { "id": "actions", "name": "Actions", "visible": true, "enabled": true },
|
||||
"10": { "id": "skyBrowser", "name": "SkyBrowser", "visible": true, "enabled": true },
|
||||
"11": { "id": "mission", "name": "Mission", "visible": false, "enabled": false },
|
||||
"12": { "id": "flightControl", "name": "Flight Control", "visible": false, "enabled": true },
|
||||
"13": { "id": "keybindingsLayout", "name": "Keybindings", "visible": true, "enabled": true },
|
||||
"14": { "id": "gettingStartedTour", "name": "Getting Started Tour", "visible": true, "enabled": true }
|
||||
}
|
||||
@@ -178,7 +178,7 @@ public:
|
||||
/// Removes an asset unless the `ignoreUpdates` member is set to `true`
|
||||
void removeAsset(const std::string& path);
|
||||
|
||||
static constexpr Version CurrentVersion = Version{ 1, 3 };
|
||||
static constexpr Version CurrentVersion = Version{ 1, 4 };
|
||||
|
||||
Version version = CurrentVersion;
|
||||
std::vector<Module> modules;
|
||||
@@ -192,6 +192,7 @@ public:
|
||||
std::optional<CameraType> camera;
|
||||
std::vector<std::string> markNodes;
|
||||
std::vector<std::string> additionalScripts;
|
||||
std::map<std::string, bool> uiPanelVisibility;
|
||||
|
||||
bool ignoreUpdates = false;
|
||||
|
||||
|
||||
@@ -43,6 +43,7 @@ set(HEADER_FILES
|
||||
include/topics/getpropertytopic.h
|
||||
include/topics/luascripttopic.h
|
||||
include/topics/missiontopic.h
|
||||
include/topics/profiletopic.h
|
||||
include/topics/sessionrecordingtopic.h
|
||||
include/topics/setpropertytopic.h
|
||||
include/topics/shortcuttopic.h
|
||||
@@ -73,6 +74,7 @@ set(SOURCE_FILES
|
||||
src/topics/getpropertytopic.cpp
|
||||
src/topics/luascripttopic.cpp
|
||||
src/topics/missiontopic.cpp
|
||||
src/topics/profiletopic.cpp
|
||||
src/topics/sessionrecordingtopic.cpp
|
||||
src/topics/setpropertytopic.cpp
|
||||
src/topics/shortcuttopic.cpp
|
||||
|
||||
45
modules/server/include/topics/profiletopic.h
Normal file
45
modules/server/include/topics/profiletopic.h
Normal file
@@ -0,0 +1,45 @@
|
||||
/*****************************************************************************************
|
||||
* *
|
||||
* OpenSpace *
|
||||
* *
|
||||
* Copyright (c) 2014-2025 *
|
||||
* *
|
||||
* 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. *
|
||||
****************************************************************************************/
|
||||
|
||||
#ifndef __OPENSPACE_MODULE_SERVER___PROFILETOPIC___H__
|
||||
#define __OPENSPACE_MODULE_SERVER___PROFILETOPIC___H__
|
||||
|
||||
#include <modules/server/include/topics/topic.h>
|
||||
|
||||
using nlohmann::json;
|
||||
|
||||
namespace openspace {
|
||||
|
||||
class ProfileTopic : public Topic {
|
||||
public:
|
||||
ProfileTopic() = default;
|
||||
~ProfileTopic() override = default;
|
||||
|
||||
void handleJson(const nlohmann::json& json) override;
|
||||
bool isDone() const override;
|
||||
};
|
||||
|
||||
} // namespace openspace
|
||||
|
||||
#endif // __OPENSPACE_MODULE_SERVER___PROFILETOPIC___H__
|
||||
@@ -53,6 +53,7 @@
|
||||
#include <ghoul/io/socket/tcpsocketserver.h>
|
||||
#include <ghoul/io/socket/websocketserver.h>
|
||||
#include <ghoul/misc/profiling.h>
|
||||
#include <include/topics/profiletopic.h>
|
||||
|
||||
namespace {
|
||||
constexpr std::string_view _loggerCat = "ServerModule: Connection";
|
||||
@@ -97,6 +98,7 @@ Connection::Connection(std::unique_ptr<ghoul::io::Socket> s, std::string address
|
||||
_topicFactory.registerClass<GetPropertyTopic>("get");
|
||||
_topicFactory.registerClass<LuaScriptTopic>("luascript");
|
||||
_topicFactory.registerClass<MissionTopic>("missions");
|
||||
_topicFactory.registerClass<ProfileTopic>("profile");
|
||||
_topicFactory.registerClass<SessionRecordingTopic>("sessionRecording");
|
||||
_topicFactory.registerClass<SetPropertyTopic>("set");
|
||||
_topicFactory.registerClass<ShortcutTopic>("shortcuts");
|
||||
|
||||
46
modules/server/src/topics/profiletopic.cpp
Normal file
46
modules/server/src/topics/profiletopic.cpp
Normal file
@@ -0,0 +1,46 @@
|
||||
/*****************************************************************************************
|
||||
* *
|
||||
* OpenSpace *
|
||||
* *
|
||||
* Copyright (c) 2014-2025 *
|
||||
* *
|
||||
* 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. *
|
||||
****************************************************************************************/
|
||||
|
||||
#include <modules/server/include/topics/profiletopic.h>
|
||||
|
||||
#include <modules/server/include/connection.h>
|
||||
#include <modules/server/include/jsonconverters.h>
|
||||
#include <openspace/engine/globals.h>
|
||||
#include <openspace/scene/profile.h>
|
||||
|
||||
namespace openspace {
|
||||
|
||||
bool ProfileTopic::isDone() const {
|
||||
return true;
|
||||
}
|
||||
|
||||
void ProfileTopic::handleJson(const nlohmann::json&) {
|
||||
const nlohmann::json data = {
|
||||
{ "uiPanelVisibility", global::profile->uiPanelVisibility },
|
||||
{ "markNodes", global::profile->markNodes }
|
||||
};
|
||||
_connection->sendJson(wrappedPayload(data));
|
||||
}
|
||||
|
||||
} // namespace openspace
|
||||
@@ -623,6 +623,15 @@ void convertVersion12to13(nlohmann::json& profile) {
|
||||
|
||||
} // namespace version12
|
||||
|
||||
namespace version13 {
|
||||
|
||||
void convertVersion13to14(nlohmann::json& profile) {
|
||||
// Version 1.4 introduced the ui panel view
|
||||
profile["version"] = Profile::Version{ 1, 4 };
|
||||
}
|
||||
|
||||
} // namespace version13
|
||||
|
||||
Profile::ParsingError::ParsingError(Severity severity_, std::string msg)
|
||||
: ghoul::RuntimeError(std::move(msg), "profile")
|
||||
, severity(severity_)
|
||||
@@ -737,6 +746,9 @@ std::string Profile::serialize() const {
|
||||
if (!additionalScripts.empty()) {
|
||||
r["additional_scripts"] = additionalScripts;
|
||||
}
|
||||
if (!uiPanelVisibility.empty()) {
|
||||
r["panel_visibility"] = uiPanelVisibility;
|
||||
}
|
||||
|
||||
return r.dump(2);
|
||||
}
|
||||
@@ -779,6 +791,11 @@ Profile::Profile(const std::filesystem::path& path) {
|
||||
profile["version"].get_to(version);
|
||||
}
|
||||
|
||||
if (version.major == 1 && version.minor == 3) {
|
||||
version13::convertVersion13to14(profile);
|
||||
profile["version"].get_to(version);
|
||||
}
|
||||
|
||||
|
||||
if (profile.find("modules") != profile.end()) {
|
||||
profile["modules"].get_to(modules);
|
||||
@@ -827,6 +844,9 @@ Profile::Profile(const std::filesystem::path& path) {
|
||||
if (profile.find("additional_scripts") != profile.end()) {
|
||||
profile["additional_scripts"].get_to(additionalScripts);
|
||||
}
|
||||
if (profile.find("panel_visibility") != profile.end()) {
|
||||
profile["panel_visibility"].get_to(uiPanelVisibility);
|
||||
}
|
||||
}
|
||||
catch (const nlohmann::json::exception& e) {
|
||||
std::string err = e.what();
|
||||
|
||||
131
tests/profile/conversion/version_14.profile
Normal file
131
tests/profile/conversion/version_14.profile
Normal file
@@ -0,0 +1,131 @@
|
||||
{
|
||||
"version": { "major": 1, "minor": 4 },
|
||||
"meta": {
|
||||
"name": "name",
|
||||
"version": "version",
|
||||
"description": "description",
|
||||
"author": "author",
|
||||
"url": "url",
|
||||
"license": "license"
|
||||
},
|
||||
"modules": [
|
||||
{ "name": "abs-module" },
|
||||
{
|
||||
"name": "def-module",
|
||||
"loadedInstruction": "instr"
|
||||
},
|
||||
{
|
||||
"name": "ghi-module",
|
||||
"notLoadedInstruction": "not_instr"
|
||||
},
|
||||
{
|
||||
"name": "jkl-module",
|
||||
"loadedInstruction": "instr",
|
||||
"notLoadedInstruction": "not_instr"
|
||||
}
|
||||
],
|
||||
"assets": [
|
||||
"scene/solarsystem/planets/earth/earth",
|
||||
"scene/solarsystem/planets/earth/satellites/satellites",
|
||||
"folder1/folder2/asset",
|
||||
"folder3/folder4/asset2",
|
||||
"folder5/folder6/asset3"
|
||||
],
|
||||
"properties": [
|
||||
{
|
||||
"type": "setPropertyValue",
|
||||
"name": "{earth_satellites}.Renderable.Enabled",
|
||||
"value": "false"
|
||||
},
|
||||
{
|
||||
"type": "setPropertyValue",
|
||||
"name": "property_name_1",
|
||||
"value": "property_value_1"
|
||||
},
|
||||
{
|
||||
"type": "setPropertyValue",
|
||||
"name": "property_name_2",
|
||||
"value": "property_value_2"
|
||||
},
|
||||
{
|
||||
"type": "setPropertyValue",
|
||||
"name": "property_name_3",
|
||||
"value": "property_value_3"
|
||||
},
|
||||
{
|
||||
"type": "setPropertyValueSingle",
|
||||
"name": "property_name_4",
|
||||
"value": "property_value_4"
|
||||
},
|
||||
{
|
||||
"type": "setPropertyValueSingle",
|
||||
"name": "property_name_5",
|
||||
"value": "property_value_5"
|
||||
},
|
||||
{
|
||||
"type": "setPropertyValueSingle",
|
||||
"name": "property_name_6",
|
||||
"value": "property_value_6"
|
||||
}
|
||||
],
|
||||
"actions": [
|
||||
{
|
||||
"identifier": "profile.keybind.0",
|
||||
"documentation": "T documentation",
|
||||
"name": "T name",
|
||||
"gui_path": "T Gui-Path",
|
||||
"is_local": true,
|
||||
"script": "T script"
|
||||
},
|
||||
{
|
||||
"identifier": "profile.keybind.1",
|
||||
"documentation": "U documentation",
|
||||
"name": "U name",
|
||||
"gui_path": "U Gui-Path",
|
||||
"is_local": false,
|
||||
"script": "U script"
|
||||
},
|
||||
{
|
||||
"identifier": "profile.keybind.2",
|
||||
"documentation": "CTRL+V documentation",
|
||||
"name": "CTRL+V name",
|
||||
"gui_path": "CTRL+V Gui-Path",
|
||||
"is_local": false,
|
||||
"script": "CTRL+V script"
|
||||
}
|
||||
],
|
||||
"keybindings": [
|
||||
{
|
||||
"action": "profile.keybind.0",
|
||||
"key": "T"
|
||||
},
|
||||
{
|
||||
"action": "profile.keybind.1",
|
||||
"key": "U"
|
||||
},
|
||||
{
|
||||
"action": "profile.keybind.2",
|
||||
"key": "CTRL+V"
|
||||
}
|
||||
],
|
||||
"time": {
|
||||
"type": "relative",
|
||||
"value": "-1d",
|
||||
"is_paused": false
|
||||
},
|
||||
"camera": {
|
||||
"type": "goToGeo",
|
||||
"anchor": "Earth",
|
||||
"latitude": 58.5877,
|
||||
"longitude": 16.1924,
|
||||
"altitude": 2.0e+07
|
||||
},
|
||||
"mark_nodes": [
|
||||
"Earth", "Mars", "Moon", "Sun"
|
||||
],
|
||||
"additional_scripts": [
|
||||
"script-1",
|
||||
"script-2",
|
||||
"script-3"
|
||||
]
|
||||
}
|
||||
@@ -888,6 +888,15 @@ TEST_CASE("Version 1.0 -> 1.3", "[profile]") {
|
||||
CHECK(src == dst);
|
||||
}
|
||||
|
||||
TEST_CASE("Version 1.0 -> 1.4", "[profile]") {
|
||||
constexpr std::string_view Src = "${TESTDIR}/profile/conversion/version_10.profile";
|
||||
constexpr std::string_view Dest = "${TESTDIR}/profile/conversion/version_14.profile";
|
||||
|
||||
Profile src = Profile(absPath(Src));
|
||||
Profile dst = Profile(absPath(Dest));
|
||||
CHECK(src == dst);
|
||||
}
|
||||
|
||||
TEST_CASE("Version 1.1 -> 1.2", "[profile]") {
|
||||
constexpr std::string_view Src = "${TESTDIR}/profile/conversion/version_11.profile";
|
||||
constexpr std::string_view Dest = "${TESTDIR}/profile/conversion/version_12.profile";
|
||||
@@ -906,6 +915,15 @@ TEST_CASE("Version 1.1 -> 1.3", "[profile]") {
|
||||
CHECK(src == dst);
|
||||
}
|
||||
|
||||
TEST_CASE("Version 1.1 -> 1.4", "[profile]") {
|
||||
constexpr std::string_view Src = "${TESTDIR}/profile/conversion/version_11.profile";
|
||||
constexpr std::string_view Dest = "${TESTDIR}/profile/conversion/version_14.profile";
|
||||
|
||||
Profile src = Profile(absPath(Src));
|
||||
Profile dst = Profile(absPath(Dest));
|
||||
CHECK(src == dst);
|
||||
}
|
||||
|
||||
TEST_CASE("Version 1.2 -> 1.3", "[profile]") {
|
||||
constexpr std::string_view Src = "${TESTDIR}/profile/conversion/version_12.profile";
|
||||
constexpr std::string_view Dest = "${TESTDIR}/profile/conversion/version_13.profile";
|
||||
@@ -915,6 +933,24 @@ TEST_CASE("Version 1.2 -> 1.3", "[profile]") {
|
||||
CHECK(src == dst);
|
||||
}
|
||||
|
||||
TEST_CASE("Version 1.2 -> 1.4", "[profile]") {
|
||||
constexpr std::string_view Src = "${TESTDIR}/profile/conversion/version_12.profile";
|
||||
constexpr std::string_view Dest = "${TESTDIR}/profile/conversion/version_14.profile";
|
||||
|
||||
Profile src = Profile(absPath(Src));
|
||||
Profile dst = Profile(absPath(Dest));
|
||||
CHECK(src == dst);
|
||||
}
|
||||
|
||||
TEST_CASE("Version 1.3 -> 1.4", "[profile]") {
|
||||
constexpr std::string_view Src = "${TESTDIR}/profile/conversion/version_13.profile";
|
||||
constexpr std::string_view Dest = "${TESTDIR}/profile/conversion/version_14.profile";
|
||||
|
||||
Profile src = Profile(absPath(Src));
|
||||
Profile dst = Profile(absPath(Dest));
|
||||
CHECK(src == dst);
|
||||
}
|
||||
|
||||
|
||||
|
||||
//
|
||||
|
||||
Reference in New Issue
Block a user