From b1cf6fcf63db218457c1249ba264e8f39816fcdb Mon Sep 17 00:00:00 2001 From: Ted John Date: Fri, 14 Feb 2020 23:36:24 +0000 Subject: [PATCH] Implement Widget API --- src/openrct2-ui/scripting/CustomWindow.cpp | 20 ++ src/openrct2-ui/scripting/CustomWindow.h | 17 ++ src/openrct2-ui/scripting/ScWidget.hpp | 235 +++++++++++++++++++++ src/openrct2-ui/scripting/ScWindow.hpp | 19 ++ src/openrct2-ui/scripting/UiExtensions.cpp | 2 + 5 files changed, 293 insertions(+) create mode 100644 src/openrct2-ui/scripting/CustomWindow.h create mode 100644 src/openrct2-ui/scripting/ScWidget.hpp diff --git a/src/openrct2-ui/scripting/CustomWindow.cpp b/src/openrct2-ui/scripting/CustomWindow.cpp index ebbbb7a2a9..a5d02962a0 100644 --- a/src/openrct2-ui/scripting/CustomWindow.cpp +++ b/src/openrct2-ui/scripting/CustomWindow.cpp @@ -234,6 +234,11 @@ namespace OpenRCT2::Ui::Windows } return nullptr; } + + CustomWidgetDesc* GetCustomWidgetDesc(size_t widgetIndex) + { + return const_cast(std::as_const(*this).GetCustomWidgetDesc(widgetIndex)); + } }; static rct_windownumber _nextWindowNumber; @@ -529,4 +534,19 @@ namespace OpenRCT2::Ui::Windows } } } + + void UpdateWidgetText(rct_window* w, rct_widgetindex widgetIndex, const std::string& value) + { + if (w->custom_info != nullptr) + { + auto &customInfo = GetInfo(w); + auto customWidgetInfo = customInfo.GetCustomWidgetDesc(widgetIndex); + if (customWidgetInfo != nullptr) + { + customWidgetInfo->Text = CustomWidgetDesc::ProcessString(value); + w->widgets[widgetIndex].string = customWidgetInfo->Text.data(); + } + } + } + } // namespace OpenRCT2::Ui::Windows diff --git a/src/openrct2-ui/scripting/CustomWindow.h b/src/openrct2-ui/scripting/CustomWindow.h new file mode 100644 index 0000000000..ba81fcd91c --- /dev/null +++ b/src/openrct2-ui/scripting/CustomWindow.h @@ -0,0 +1,17 @@ +/***************************************************************************** + * Copyright (c) 2014-2018 OpenRCT2 developers + * + * For a complete list of all authors, please refer to contributors.md + * Interested in contributing? Visit https://github.com/OpenRCT2/OpenRCT2 + * + * OpenRCT2 is licensed under the GNU General Public License version 3. + *****************************************************************************/ + +#include "../interface/Window.h" + +#include + +namespace OpenRCT2::Ui::Windows +{ + void UpdateWidgetText(rct_window* w, rct_widgetindex widget, const std::string& value); +} diff --git a/src/openrct2-ui/scripting/ScWidget.hpp b/src/openrct2-ui/scripting/ScWidget.hpp new file mode 100644 index 0000000000..d06141fbf4 --- /dev/null +++ b/src/openrct2-ui/scripting/ScWidget.hpp @@ -0,0 +1,235 @@ +/***************************************************************************** + * Copyright (c) 2014-2018 OpenRCT2 developers + * + * For a complete list of all authors, please refer to contributors.md + * Interested in contributing? Visit https://github.com/OpenRCT2/OpenRCT2 + * + * OpenRCT2 is licensed under the GNU General Public License version 3. + *****************************************************************************/ + +#pragma once + +#include "../interface/Widget.h" +#include "../interface/Window.h" +#include "CustomWindow.h" + +#include +#include +#include +#include +#include + +namespace OpenRCT2::Scripting +{ + class ScWidget + { + private: + rct_windowclass _class{}; + rct_windownumber _number{}; + rct_widgetindex _widgetIndex{}; + + public: + ScWidget(rct_windowclass c, rct_windownumber n, rct_widgetindex widgetIndex) + : _class(c) + , _number(n) + , _widgetIndex(widgetIndex) + { + } + + private: + std::string type_get() + { + auto widget = GetWidget(); + if (widget != nullptr) + { + switch (widget->type) + { + case WWT_FRAME: + return "frame"; + case WWT_RESIZE: + return "resize"; + case WWT_IMGBTN: + case WWT_COLOURBTN: + case WWT_TRNBTN: + case WWT_FLATBTN: + case WWT_BUTTON: + case WWT_CLOSEBOX: + return "button"; + case WWT_TAB: + return "tab"; + case WWT_LABEL_CENTRED: + case WWT_LABEL: + return "label"; + case WWT_TABLE_HEADER: + return "table_header"; + case WWT_SPINNER: + return "spinner"; + case WWT_DROPDOWN: + return "dropdown"; + case WWT_VIEWPORT: + return "viewport"; + case WWT_GROUPBOX: + return "groupbox"; + case WWT_CAPTION: + return "caption"; + case WWT_SCROLL: + return "scroll_view"; + case WWT_CHECKBOX: + return "checkbox"; + case WWT_TEXT_BOX: + return "textbox"; + } + } + return "unknown"; + } + + int32_t x_get() + { + auto widget = GetWidget(); + if (widget != nullptr) + { + return widget->left; + } + return 0; + } + void x_set(int32_t value) + { + auto widget = GetWidget(); + if (widget != nullptr) + { + Invalidate(); + widget->left = value; + Invalidate(); + } + } + + int32_t y_get() + { + auto widget = GetWidget(); + if (widget != nullptr) + { + return widget->top; + } + return 0; + } + void y_set(int32_t value) + { + auto widget = GetWidget(); + if (widget != nullptr) + { + Invalidate(); + widget->top = value; + Invalidate(); + } + } + + int32_t width_get() + { + auto widget = GetWidget(); + if (widget != nullptr) + { + return widget->right - widget->left; + } + return 0; + } + void width_set(int32_t value) + { + auto widget = GetWidget(); + if (widget != nullptr) + { + Invalidate(); + widget->right = widget->left + value; + Invalidate(); + } + } + + int32_t height_get() + { + auto widget = GetWidget(); + if (widget != nullptr) + { + return widget->bottom - widget->top; + } + return 0; + } + void height_set(int32_t value) + { + auto widget = GetWidget(); + if (widget != nullptr) + { + Invalidate(); + widget->bottom = widget->top + value; + Invalidate(); + } + } + + std::string text_get() + { + if (IsCustomWindow()) + { + auto widget = GetWidget(); + if (widget != nullptr && widget->string != nullptr) + { + return widget->string; + } + } + return ""; + } + void text_set(std::string value) + { + auto w = GetWindow(); + if (w != nullptr && IsCustomWindow()) + { + OpenRCT2::Ui::Windows::UpdateWidgetText(w, _widgetIndex, value); + } + } + + public: + static void Register(duk_context* ctx) + { + // Common + dukglue_register_property(ctx, &type_get, nullptr, "type"); + dukglue_register_property(ctx, &x_get, &x_set, "x"); + dukglue_register_property(ctx, &y_get, &y_set, "y"); + dukglue_register_property(ctx, &width_get, &width_set, "width"); + dukglue_register_property(ctx, &height_get, &height_set, "height"); + + // No so common + dukglue_register_property(ctx, &text_get, &text_set, "text"); + } + + private: + rct_window* GetWindow() + { + if (_class == WC_MAIN_WINDOW) + return window_get_main(); + else + return window_find_by_number(_class, _number); + } + + rct_widget* GetWidget() + { + auto w = GetWindow(); + if (w != nullptr) + { + return &w->widgets[_widgetIndex]; + } + return nullptr; + } + + bool IsCustomWindow() + { + auto w = GetWindow(); + if (w != nullptr) + { + return w->classification == WC_CUSTOM; + } + return false; + } + + void Invalidate() + { + widget_invalidate_by_number(_class, _number, _widgetIndex); + } + }; +} // namespace OpenRCT2::Scripting diff --git a/src/openrct2-ui/scripting/ScWindow.hpp b/src/openrct2-ui/scripting/ScWindow.hpp index 44ac133ed7..8bd94a0958 100644 --- a/src/openrct2-ui/scripting/ScWindow.hpp +++ b/src/openrct2-ui/scripting/ScWindow.hpp @@ -9,6 +9,8 @@ #pragma once +#include "ScWidget.hpp" + #include #include #include @@ -66,6 +68,22 @@ namespace OpenRCT2::Scripting return (flags & (WF_STICK_TO_BACK | WF_STICK_TO_FRONT)) != 0; } + std::vector> widgets_get() + { + std::vector> result; + auto w = GetWindow(); + if (w != nullptr) + { + rct_widgetindex widgetIndex = 0; + for (auto widget = w->widgets; widget->type != WWT_LAST; widget++) + { + result.push_back(std::make_shared(_class, _number, widgetIndex)); + widgetIndex++; + } + } + return result; + } + static void Register(duk_context* ctx) { dukglue_register_property(ctx, &ScWindow::x_get, &ScWindow::x_set, "x"); @@ -73,6 +91,7 @@ namespace OpenRCT2::Scripting dukglue_register_property(ctx, &ScWindow::width_get, nullptr, "width"); dukglue_register_property(ctx, &ScWindow::height_get, nullptr, "height"); dukglue_register_property(ctx, &ScWindow::isSticky_get, nullptr, "isSticky"); + dukglue_register_property(ctx, &ScWindow::widgets_get, nullptr, "widgets"); } private: diff --git a/src/openrct2-ui/scripting/UiExtensions.cpp b/src/openrct2-ui/scripting/UiExtensions.cpp index c2c959bb6f..0eb68ea9d6 100644 --- a/src/openrct2-ui/scripting/UiExtensions.cpp +++ b/src/openrct2-ui/scripting/UiExtensions.cpp @@ -11,6 +11,7 @@ #include "CustomMenu.h" #include "ScUi.hpp" +#include "ScWidget.hpp" #include "ScWindow.hpp" #include @@ -25,6 +26,7 @@ void UiScriptExtensions::Extend(ScriptEngine& scriptEngine) ScUi::Register(ctx); ScViewport::Register(ctx); + ScWidget::Register(ctx); ScWindow::Register(ctx); InitialiseCustomMenuItems(scriptEngine);