aboutsummaryrefslogtreecommitdiff
path: root/src/openvic-simulation/interface/GUI.cpp
diff options
context:
space:
mode:
author hop311 <hop3114@gmail.com>2024-02-04 15:09:06 +0100
committer hop311 <hop3114@gmail.com>2024-02-04 15:09:06 +0100
commit87fa1c74281a651b23089079c4c1621d4fb66d73 (patch)
tree4e343f81b13f166ad4a478962348d4734ea7e11b /src/openvic-simulation/interface/GUI.cpp
parent3f6d7351816b0e089495b2f15dc1c956f3151f5a (diff)
Added support for loading all gui filesgui-loading
Diffstat (limited to 'src/openvic-simulation/interface/GUI.cpp')
-rw-r--r--src/openvic-simulation/interface/GUI.cpp208
1 files changed, 174 insertions, 34 deletions
diff --git a/src/openvic-simulation/interface/GUI.cpp b/src/openvic-simulation/interface/GUI.cpp
index 7aebfe8..94e1fe3 100644
--- a/src/openvic-simulation/interface/GUI.cpp
+++ b/src/openvic-simulation/interface/GUI.cpp
@@ -6,6 +6,16 @@ using namespace OpenVic;
using namespace OpenVic::GUI;
using namespace OpenVic::NodeTools;
+Position::Position() : position {} {}
+
+bool Position::_fill_key_map(NodeTools::case_insensitive_key_map_t& key_map) {
+ bool ret = Named::_fill_key_map(key_map);
+ ret &= add_key_map_entry(key_map,
+ "position", ONE_EXACTLY, expect_fvec2(assign_variable_callback(position))
+ );
+ return ret;
+}
+
Element::Element() : position {}, orientation { orientation_t::UPPER_LEFT } {}
bool Element::_fill_key_map(NodeTools::case_insensitive_key_map_t& key_map, UIManager const& ui_manager) {
@@ -14,11 +24,14 @@ bool Element::_fill_key_map(NodeTools::case_insensitive_key_map_t& key_map, UIMa
static const string_map_t<orientation_t> orientation_map = {
{ "UPPER_LEFT", UPPER_LEFT }, { "LOWER_LEFT", LOWER_LEFT },
{ "LOWER_RIGHT", LOWER_RIGHT }, { "UPPER_RIGHT", UPPER_RIGHT },
- { "CENTER", CENTER }
+ { "CENTER", CENTER }, { "CENTER_UP", CENTER_UP }, { "CENTER_DOWN", CENTER_DOWN }
};
ret &= add_key_map_entries(key_map,
- "position", ONE_EXACTLY, expect_fvec2(assign_variable_callback(position)),
- "orientation", ZERO_OR_ONE, expect_string(expect_mapped_string(orientation_map, assign_variable_callback(orientation)))
+ "position", ZERO_OR_ONE, expect_fvec2(assign_variable_callback(position)),
+ "orientation", ZERO_OR_ONE, expect_identifier_or_string(expect_mapped_string(
+ orientation_map, assign_variable_callback(orientation),
+ true /* Warn if the key here is invalid, leaving the default orientation UPPER_LEFT unchanged. */
+ ))
);
return ret;
}
@@ -29,22 +42,31 @@ bool Element::_fill_elements_key_map(
bool ret = true;
ret &= add_key_map_entries(key_map,
"iconType", ZERO_OR_MORE, _expect_instance<Element, Icon>(callback, ui_manager),
+ "shieldtype", ZERO_OR_MORE, _expect_instance<Element, Icon>(callback, ui_manager),
"guiButtonType", ZERO_OR_MORE, _expect_instance<Element, Button>(callback, ui_manager),
"checkboxType", ZERO_OR_MORE, _expect_instance<Element, Checkbox>(callback, ui_manager),
"textBoxType", ZERO_OR_MORE, _expect_instance<Element, Text>(callback, ui_manager),
"instantTextBoxType", ZERO_OR_MORE, _expect_instance<Element, Text>(callback, ui_manager),
"OverlappingElementsBoxType", ZERO_OR_MORE, _expect_instance<Element, OverlappingElementsBox>(callback, ui_manager),
"listboxType", ZERO_OR_MORE, _expect_instance<Element, ListBox>(callback, ui_manager),
+ "editBoxType", ZERO_OR_MORE, _expect_instance<Element, TextEditBox>(callback, ui_manager),
+ "scrollbarType", ZERO_OR_MORE, _expect_instance<Element, Scrollbar>(callback, ui_manager),
"windowType", ZERO_OR_MORE, _expect_instance<Element, Window>(callback, ui_manager),
- "positionType", ZERO_OR_MORE, success_callback // TODO - load this as a marker for placing sub-scenes
+ "eu3dialogtype", ZERO_OR_MORE, _expect_instance<Element, Window>(callback, ui_manager)
);
return ret;
}
bool Scene::_fill_key_map(NodeTools::case_insensitive_key_map_t& key_map, UIManager const& ui_manager) {
- return Element::_fill_elements_key_map(key_map, [this](std::unique_ptr<Element>&& element) -> bool {
+ bool ret = Element::_fill_elements_key_map(key_map, [this](std::unique_ptr<Element>&& element) -> bool {
return scene_elements.add_item(std::move(element));
}, ui_manager);
+ ret &= add_key_map_entry(key_map,
+ "positionType", ZERO_OR_MORE, Position::_expect_value<Position>([this](Position&& position) -> bool {
+ return scene_positions.add_item(std::move(position));
+ })
+ );
+ return ret;
}
node_callback_t Scene::expect_scene(
@@ -56,7 +78,7 @@ node_callback_t Scene::expect_scene(
}, ui_manager);
}
-Window::Window() : moveable { false }, fullscreen { false } {}
+Window::Window() : background {}, size {}, moveable { false }, fullscreen { false } {}
bool Window::_fill_key_map(NodeTools::case_insensitive_key_map_t& key_map, UIManager const& ui_manager) {
bool ret = Element::_fill_elements_key_map(key_map, [this](std::unique_ptr<Element>&& element) -> bool {
@@ -64,55 +86,71 @@ bool Window::_fill_key_map(NodeTools::case_insensitive_key_map_t& key_map, UIMan
}, ui_manager);
ret &= Element::_fill_key_map(key_map, ui_manager);
ret &= add_key_map_entries(key_map,
- "backGround", ZERO_OR_ONE, success_callback, // TODO - load as potential panel texture (almost always empty)
"size", ONE_EXACTLY, expect_fvec2(assign_variable_callback(size)),
- "moveable", ONE_EXACTLY, expect_int_bool(assign_variable_callback(moveable)),
+ "moveable", ZERO_OR_ONE, expect_int_bool(assign_variable_callback(moveable)),
+ "fullScreen", ZERO_OR_ONE, expect_bool(assign_variable_callback(fullscreen)),
+ "backGround", ZERO_OR_ONE, expect_string(assign_variable_callback_string(background), true),
+
"dontRender", ZERO_OR_ONE, success_callback, // always empty string?
"horizontalBorder", ZERO_OR_ONE, success_callback,
"verticalBorder", ZERO_OR_ONE, success_callback,
- "fullScreen", ZERO_OR_ONE, expect_bool(assign_variable_callback(fullscreen))
+ "upsound", ZERO_OR_ONE, success_callback,
+ "downsound", ZERO_OR_ONE, success_callback
);
return ret;
}
-Icon::Icon() : sprite { nullptr }, frame { GFX::NO_FRAMES } {}
+Icon::Icon() : sprite { nullptr }, frame { GFX::NO_FRAMES }, scale { 1 }, rotation { 0 } {}
bool Icon::_fill_key_map(NodeTools::case_insensitive_key_map_t& key_map, UIManager const& ui_manager) {
bool ret = Element::_fill_key_map(key_map, ui_manager);
ret &= add_key_map_entries(key_map,
- "spriteType", ONE_EXACTLY, expect_string(ui_manager.expect_sprite_str(assign_variable_callback_pointer(sprite))),
- "frame", ZERO_OR_ONE, expect_uint(assign_variable_callback(frame))
+ // TODO - make these share a ONE_EXACTLY count
+ "spriteType", ZERO_OR_ONE, ui_manager.expect_sprite_string(assign_variable_callback_pointer(sprite)),
+ "buttonMesh", ZERO_OR_ONE, ui_manager.expect_sprite_string(assign_variable_callback_pointer(sprite)),
+
+ "frame", ZERO_OR_ONE, expect_uint(assign_variable_callback(frame)),
+ "scale", ZERO_OR_ONE, expect_fixed_point(assign_variable_callback(scale)),
+ "rotation", ZERO_OR_ONE, expect_fixed_point(assign_variable_callback(rotation))
);
return ret;
}
-BaseButton::BaseButton() : sprite { nullptr } {}
+BaseButton::BaseButton() : sprite { nullptr }, text {}, font { nullptr } {}
bool BaseButton::_fill_key_map(NodeTools::case_insensitive_key_map_t& key_map, UIManager const& ui_manager) {
bool ret = Element::_fill_key_map(key_map, ui_manager);
// look up sprite registry for texture sprite with name...
ret &= add_key_map_entries(key_map,
+ // TODO - make these share a ONE_EXACTLY count
"quadTextureSprite", ZERO_OR_ONE,
- expect_string(ui_manager.expect_sprite_str(assign_variable_callback_pointer(sprite)), true),
+ ui_manager.expect_sprite_string(assign_variable_callback_pointer(sprite), true),
"spriteType", ZERO_OR_ONE,
- expect_string(ui_manager.expect_sprite_str(assign_variable_callback_pointer(sprite)), true),
- "shortcut", ZERO_OR_ONE, success_callback // TODO - load and use shortcuts (how to integrate with custom keybinds?)
+ ui_manager.expect_sprite_string(assign_variable_callback_pointer(sprite)),
+
+ "buttonText", ZERO_OR_ONE, expect_string(assign_variable_callback_string(text), true),
+ /* Some buttons have multiple fonts listed with the last one being used. */
+ "buttonFont", ZERO_OR_MORE, ui_manager.expect_font_string(assign_variable_callback_pointer(font), true),
+
+ "shortcut", ZERO_OR_ONE, success_callback, // TODO - load and use shortcuts (how to integrate with custom keybinds?)
+ "tooltip", ZERO_OR_ONE, success_callback,
+ "tooltipText", ZERO_OR_ONE, success_callback,
+ "delayedTooltipText", ZERO_OR_ONE, success_callback
);
return ret;
}
-Button::Button() : text {}, font { nullptr} {}
+Button::Button() : size {}, rotation { 0 } {}
bool Button::_fill_key_map(NodeTools::case_insensitive_key_map_t& key_map, UIManager const& ui_manager) {
bool ret = BaseButton::_fill_key_map(key_map, ui_manager);
ret &= add_key_map_entries(key_map,
- "buttonText", ZERO_OR_ONE, expect_string(assign_variable_callback_string(text), true),
- "buttonFont", ZERO_OR_ONE, expect_string(ui_manager.expect_font_str(assign_variable_callback_pointer(font))),
- "clicksound", ZERO_OR_ONE, success_callback,
- /* These are always empty in the base defines */
- "tooltip", ZERO_OR_ONE, success_callback,
- "tooltipText", ZERO_OR_ONE, success_callback,
- "delayedTooltipText", ZERO_OR_ONE, success_callback
+ "size", ZERO_OR_ONE, expect_fvec2(assign_variable_callback(size)),
+ "rotation", ZERO_OR_ONE, expect_fixed_point(assign_variable_callback(rotation)),
+
+ "format", ZERO_OR_ONE, success_callback, /* Is always left from what I've seen. */
+ "clicksound", ZERO_OR_ONE, success_callback, // TODO - clicksound!!!
+ "parent", ZERO_OR_ONE, success_callback /* Links buttons to a scrollbar, not needed thanks to contextual info. */
);
return ret;
}
@@ -128,7 +166,7 @@ bool AlignedElement::_fill_key_map(NodeTools::case_insensitive_key_map_t& key_ma
bool ret = Element::_fill_key_map(key_map, ui_manager);
using enum format_t;
static const string_map_t<format_t> format_map = {
- { "left", left }, { "right", right }, { "centre", centre }, { "center", centre }
+ { "left", left }, { "right", right }, { "centre", centre }, { "center", centre }, { "justified", justified }
};
ret &= add_key_map_entries(key_map,
"format", ZERO_OR_ONE, expect_identifier(expect_mapped_string(format_map, assign_variable_callback(format))
@@ -136,18 +174,19 @@ bool AlignedElement::_fill_key_map(NodeTools::case_insensitive_key_map_t& key_ma
return ret;
}
-Text::Text() : text {}, font { nullptr } {}
+Text::Text() : text {}, font { nullptr }, max_size {} {}
bool Text::_fill_key_map(NodeTools::case_insensitive_key_map_t& key_map, UIManager const& ui_manager) {
bool ret = AlignedElement::_fill_key_map(key_map, ui_manager);
ret &= add_key_map_entries(key_map,
"text", ZERO_OR_ONE, expect_string(assign_variable_callback_string(text), true),
- "font", ONE_EXACTLY, expect_string(ui_manager.expect_font_str(assign_variable_callback_pointer(font))),
- "maxWidth", ONE_EXACTLY, expect_fixed_point(assign_variable_callback(max_size.x)),
- "maxHeight", ONE_EXACTLY, expect_fixed_point(assign_variable_callback(max_size.y)),
+ "font", ONE_EXACTLY, ui_manager.expect_font_string(assign_variable_callback_pointer(font)),
+ "maxWidth", ZERO_OR_ONE, expect_fixed_point(assign_variable_callback(max_size.x)),
+ "maxHeight", ZERO_OR_ONE, expect_fixed_point(assign_variable_callback(max_size.y)),
"borderSize", ZERO_OR_ONE, success_callback,
"fixedsize", ZERO_OR_ONE, success_callback,
+ "allwaystransparent", ZERO_OR_ONE, success_callback,
// Add warning about redundant key?
"textureFile", ZERO_OR_ONE, success_callback
@@ -155,7 +194,7 @@ bool Text::_fill_key_map(NodeTools::case_insensitive_key_map_t& key_map, UIManag
return ret;
}
-OverlappingElementsBox::OverlappingElementsBox() : size {} {}
+OverlappingElementsBox::OverlappingElementsBox() : size {}, spacing {} {}
bool OverlappingElementsBox::_fill_key_map(NodeTools::case_insensitive_key_map_t& key_map, UIManager const& ui_manager) {
bool ret = AlignedElement::_fill_key_map(key_map, ui_manager);
@@ -166,16 +205,117 @@ bool OverlappingElementsBox::_fill_key_map(NodeTools::case_insensitive_key_map_t
return ret;
}
-ListBox::ListBox() : size {} {}
+ListBox::ListBox() : size {}, offset {}, spacing {}, scrollbar_name {} {}
bool ListBox::_fill_key_map(NodeTools::case_insensitive_key_map_t& key_map, UIManager const& ui_manager) {
bool ret = Element::_fill_key_map(key_map, ui_manager);
ret &= add_key_map_entries(key_map,
+ "size", ONE_EXACTLY, expect_fvec2(assign_variable_callback(size)),
+ "offset", ZERO_OR_ONE, expect_fvec2(assign_variable_callback(offset)),
+ "spacing", ZERO_OR_ONE, expect_fixed_point(assign_variable_callback(spacing)),
+ "scrollbartype", ZERO_OR_ONE, expect_string(assign_variable_callback_string(scrollbar_name)),
+
"backGround", ZERO_OR_ONE, success_callback,
+ "borderSize", ZERO_OR_ONE, success_callback,
+ "horizontal", ZERO_OR_ONE, success_callback,
+ "priority", ZERO_OR_ONE, success_callback,
+ "allwaystransparent", ZERO_OR_ONE, success_callback
+ );
+ return ret;
+}
+
+TextEditBox::TextEditBox() : text {}, font { nullptr }, texture_file {}, size {}, border_size {} {}
+
+bool TextEditBox::_fill_key_map(NodeTools::case_insensitive_key_map_t& key_map, UIManager const& ui_manager) {
+ bool ret = Element::_fill_key_map(key_map, ui_manager);
+ ret &= add_key_map_entries(key_map,
+ "text", ONE_EXACTLY, expect_string(assign_variable_callback_string(text), true),
+ "font", ONE_EXACTLY, ui_manager.expect_font_string(assign_variable_callback_pointer(font)),
+ "textureFile", ZERO_OR_ONE, expect_string(assign_variable_callback_string(texture_file), true),
+ "size", ONE_EXACTLY, expect_fvec2(assign_variable_callback(size)),
+ "borderSize", ONE_EXACTLY, expect_fvec2(assign_variable_callback(border_size))
+ );
+ return ret;
+}
+
+Scrollbar::Scrollbar()
+ : slider_button_name {}, track_button_name {}, less_button_name{}, more_button_name {}, size {}, border_size {},
+ min_value {}, max_value {}, step_size {}, start_value {}, horizontal { false }, use_range_limit { false },
+ range_limit_min {}, range_limit_max {}, range_limit_min_icon_name {}, range_limit_max_icon_name {} {
+ scrollbar_elements.reserve(4); /* Space for 4 buttons, might need 2 more for range limit icons. */
+}
+
+bool Scrollbar::_fill_key_map(NodeTools::case_insensitive_key_map_t& key_map, UIManager const& ui_manager) {
+ bool ret = Element::_fill_key_map(key_map, ui_manager);
+ const auto add_element = [this](std::unique_ptr<Element>&& element) -> bool {
+ return scrollbar_elements.add_item(std::move(element));
+ };
+ ret &= add_key_map_entries(key_map,
+ "slider", ONE_EXACTLY, expect_string(assign_variable_callback_string(slider_button_name)),
+ "track", ONE_EXACTLY, expect_string(assign_variable_callback_string(track_button_name)),
+ "leftbutton", ONE_EXACTLY, expect_string(assign_variable_callback_string(less_button_name)),
+ "rightbutton", ONE_EXACTLY, expect_string(assign_variable_callback_string(more_button_name)),
"size", ONE_EXACTLY, expect_fvec2(assign_variable_callback(size)),
- "spacing", ZERO_OR_ONE, success_callback,
- "scrollbartype", ZERO_OR_ONE, success_callback, // TODO - implement modable listbox scrollbars
- "borderSize", ZERO_OR_ONE, success_callback
+ "borderSize", ZERO_OR_ONE, expect_fvec2(assign_variable_callback(border_size)),
+ "minValue", ONE_EXACTLY, expect_fixed_point(assign_variable_callback(min_value)),
+ "maxValue", ONE_EXACTLY, expect_fixed_point(assign_variable_callback(max_value)),
+ "stepSize", ONE_EXACTLY, expect_fixed_point(assign_variable_callback(step_size)),
+ "startValue", ONE_EXACTLY, expect_fixed_point(assign_variable_callback(start_value)),
+ "horizontal", ONE_EXACTLY, expect_int_bool(assign_variable_callback(horizontal)),
+ "useRangeLimit", ZERO_OR_ONE, expect_bool(assign_variable_callback(use_range_limit)),
+ "rangeLimitMin", ZERO_OR_ONE, expect_fixed_point(assign_variable_callback(range_limit_min)),
+ "rangeLimitMax", ZERO_OR_ONE, expect_fixed_point(assign_variable_callback(range_limit_max)),
+ "rangeLimitMinIcon", ZERO_OR_ONE, expect_string(assign_variable_callback_string(range_limit_min_icon_name)),
+ "rangeLimitMaxIcon", ZERO_OR_ONE, expect_string(assign_variable_callback_string(range_limit_max_icon_name)),
+
+ "guiButtonType", ONE_OR_MORE, _expect_instance<Element, Button>(add_element, ui_manager),
+ "iconType", ZERO_OR_MORE, _expect_instance<Element, Icon>(add_element, ui_manager),
+
+ "priority", ZERO_OR_ONE, success_callback
);
return ret;
}
+
+template<std::derived_from<Element> T>
+T const* Scrollbar::get_element(std::string_view name, std::string_view type) const {
+ Element const* element = scrollbar_elements.get_item_by_identifier(name);
+ if (element != nullptr) {
+ T const* cast_element = element->cast_to<T>();
+ if (cast_element != nullptr) {
+ return cast_element;
+ } else {
+ Logger::error(
+ "GUI Scrollbar ", get_name(), " ", type, " element ", name, " has wrong type: ", element->get_type(),
+ " (expected ", T::get_type_static(), ")"
+ );
+ return nullptr;
+ }
+ } else {
+ Logger::error("GUI Scrollbar ", get_name(), " has no ", type, " element named ", name, "!");
+ return nullptr;
+ }
+}
+
+Button const* Scrollbar::get_slider_button() const {
+ return get_element<Button>(slider_button_name, "slider button");
+}
+
+Button const* Scrollbar::get_track_button() const {
+ return get_element<Button>(track_button_name, "track button");
+}
+
+Button const* Scrollbar::get_less_button() const {
+ return get_element<Button>(less_button_name, "less button");
+}
+
+Button const* Scrollbar::get_more_button() const {
+ return get_element<Button>(more_button_name, "more button");
+}
+
+Icon const* Scrollbar::get_range_limit_min_icon() const {
+ return get_element<Icon>(range_limit_min_icon_name, "range limit min icon");
+}
+
+Icon const* Scrollbar::get_range_limit_max_icon() const {
+ return get_element<Icon>(range_limit_max_icon_name, "range limit max icon");
+}