diff --git a/openrct2.common.props b/openrct2.common.props index e62f3ea129..f8228d5e25 100644 --- a/openrct2.common.props +++ b/openrct2.common.props @@ -54,6 +54,7 @@ C4555: expression has no effect; expected expression with side-effect --> __AVX2__;__SSE4_1__;OPENGL_NO_LINK;_CRT_SECURE_NO_WARNINGS;_USE_MATH_DEFINES;SDL_MAIN_HANDLED;_WINSOCK_DEPRECATED_NO_WARNINGS;NOMINMAX;%(PreprocessorDefinitions) + __ENABLE_SCRIPTING__;%(PreprocessorDefinitions) MultiThreaded MultiThreadedDLL true diff --git a/src/openrct2-ui/UiContext.cpp b/src/openrct2-ui/UiContext.cpp index 1f75eac344..78d8b9ee75 100644 --- a/src/openrct2-ui/UiContext.cpp +++ b/src/openrct2-ui/UiContext.cpp @@ -120,8 +120,10 @@ public: void Initialise() override { +#ifdef __ENABLE_SCRIPTING__ auto& scriptEngine = GetContext()->GetScriptEngine(); UiScriptExtensions::Extend(scriptEngine); +#endif } void Update() override diff --git a/src/openrct2-ui/scripting/CustomMenu.cpp b/src/openrct2-ui/scripting/CustomMenu.cpp index 63e79e3b67..542a0366b6 100644 --- a/src/openrct2-ui/scripting/CustomMenu.cpp +++ b/src/openrct2-ui/scripting/CustomMenu.cpp @@ -7,7 +7,9 @@ * OpenRCT2 is licensed under the GNU General Public License version 3. *****************************************************************************/ -#include "CustomMenu.h" +#ifdef __ENABLE_SCRIPTING__ + +# include "CustomMenu.h" namespace OpenRCT2::Scripting { @@ -34,3 +36,5 @@ namespace OpenRCT2::Scripting scriptEngine.SubscribeToPluginStoppedEvent([](std::shared_ptr plugin) -> void { RemoveMenuItems(plugin); }); } } // namespace OpenRCT2::Scripting + +#endif diff --git a/src/openrct2-ui/scripting/CustomMenu.h b/src/openrct2-ui/scripting/CustomMenu.h index 74f1a009bd..05300ac894 100644 --- a/src/openrct2-ui/scripting/CustomMenu.h +++ b/src/openrct2-ui/scripting/CustomMenu.h @@ -9,12 +9,14 @@ #pragma once -#include -#include -#include -#include -#include -#include +#ifdef __ENABLE_SCRIPTING__ + +# include +# include +# include +# include +# include +# include namespace OpenRCT2::Scripting { @@ -50,3 +52,5 @@ namespace OpenRCT2::Scripting void InitialiseCustomMenuItems(ScriptEngine& scriptEngine); } // namespace OpenRCT2::Scripting + +#endif diff --git a/src/openrct2-ui/scripting/CustomWindow.cpp b/src/openrct2-ui/scripting/CustomWindow.cpp index d93b512d13..28c5af6a66 100644 --- a/src/openrct2-ui/scripting/CustomWindow.cpp +++ b/src/openrct2-ui/scripting/CustomWindow.cpp @@ -7,21 +7,23 @@ * OpenRCT2 is licensed under the GNU General Public License version 3. *****************************************************************************/ -#include "../interface/Dropdown.h" -#include "ScUi.hpp" -#include "ScWindow.hpp" +#ifdef __ENABLE_SCRIPTING__ -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include +# include "../interface/Dropdown.h" +# include "ScUi.hpp" +# include "ScWindow.hpp" + +# include +# include +# include +# include +# include +# include +# include +# include +# include +# include +# include using namespace OpenRCT2; using namespace OpenRCT2::Scripting; @@ -711,3 +713,5 @@ namespace OpenRCT2::Ui::Windows } } // namespace OpenRCT2::Ui::Windows + +#endif diff --git a/src/openrct2-ui/scripting/UiExtensions.cpp b/src/openrct2-ui/scripting/UiExtensions.cpp index 0eb68ea9d6..b70f9552fc 100644 --- a/src/openrct2-ui/scripting/UiExtensions.cpp +++ b/src/openrct2-ui/scripting/UiExtensions.cpp @@ -7,14 +7,16 @@ * OpenRCT2 is licensed under the GNU General Public License version 3. *****************************************************************************/ -#include "UiExtensions.h" +#ifdef __ENABLE_SCRIPTING__ -#include "CustomMenu.h" -#include "ScUi.hpp" -#include "ScWidget.hpp" -#include "ScWindow.hpp" +# include "UiExtensions.h" -#include +# include "CustomMenu.h" +# include "ScUi.hpp" +# include "ScWidget.hpp" +# include "ScWindow.hpp" + +# include using namespace OpenRCT2::Scripting; @@ -31,3 +33,5 @@ void UiScriptExtensions::Extend(ScriptEngine& scriptEngine) InitialiseCustomMenuItems(scriptEngine); } + +#endif diff --git a/src/openrct2-ui/windows/TopToolbar.cpp b/src/openrct2-ui/windows/TopToolbar.cpp index 48c81d0643..0ddd5ade53 100644 --- a/src/openrct2-ui/windows/TopToolbar.cpp +++ b/src/openrct2-ui/windows/TopToolbar.cpp @@ -3282,6 +3282,7 @@ static void top_toolbar_init_map_menu(rct_window* w, rct_widget* widget) gDropdownItemsFormat[i++] = STR_MAPGEN_WINDOW_TITLE; } +#ifdef __ENABLE_SCRIPTING__ const auto& customMenuItems = OpenRCT2::Scripting::CustomMenuItems; if (!customMenuItems.empty()) { @@ -3293,6 +3294,7 @@ static void top_toolbar_init_map_menu(rct_window* w, rct_widget* widget) i++; } } +#endif window_dropdown_show_text( w->windowPos.x + widget->left, w->windowPos.y + widget->top, widget->bottom - widget->top + 1, w->colours[1] | 0x80, 0, @@ -3325,12 +3327,14 @@ static void top_toolbar_map_menu_dropdown(int16_t dropdownIndex) } else { +#ifdef __ENABLE_SCRIPTING__ const auto& customMenuItems = OpenRCT2::Scripting::CustomMenuItems; auto customIndex = static_cast(dropdownIndex - customStartIndex); if (customMenuItems.size() > customIndex) { customMenuItems[customIndex].Invoke(); } +#endif } } diff --git a/src/openrct2/Context.cpp b/src/openrct2/Context.cpp index 7dd8edf040..0a04bea93b 100644 --- a/src/openrct2/Context.cpp +++ b/src/openrct2/Context.cpp @@ -103,7 +103,9 @@ namespace OpenRCT2 std::unique_ptr _discordService; #endif StdInOutConsole _stdInOutConsole; +#ifdef __ENABLE_SCRIPTING__ ScriptEngine _scriptEngine; +#endif // Game states std::unique_ptr _titleScreen; @@ -138,7 +140,9 @@ namespace OpenRCT2 , _audioContext(audioContext) , _uiContext(uiContext) , _localisationService(std::make_unique(env)) +#ifdef __ENABLE_SCRIPTING__ , _scriptEngine(_stdInOutConsole, *env) +#endif , _painter(std::make_unique(uiContext)) { // Can't have more than one context currently. @@ -181,10 +185,12 @@ namespace OpenRCT2 return _uiContext; } +#ifdef __ENABLE_SCRIPTING__ Scripting::ScriptEngine& GetScriptEngine() override { return _scriptEngine; } +#endif GameState* GetGameState() override { @@ -1026,7 +1032,10 @@ namespace OpenRCT2 Twitch::Update(); chat_update(); +#ifdef __ENABLE_SCRIPTING__ _scriptEngine.Update(); +#endif + _stdInOutConsole.ProcessEvalQueue(); _uiContext->Update(); } diff --git a/src/openrct2/Context.h b/src/openrct2/Context.h index c8ee6181ed..0ec9465f13 100644 --- a/src/openrct2/Context.h +++ b/src/openrct2/Context.h @@ -114,7 +114,9 @@ namespace OpenRCT2 virtual Localisation::LocalisationService& GetLocalisationService() abstract; virtual IObjectManager& GetObjectManager() abstract; virtual IObjectRepository& GetObjectRepository() abstract; +#ifdef __ENABLE_SCRIPTING__ virtual Scripting::ScriptEngine& GetScriptEngine() abstract; +#endif virtual ITrackDesignRepository* GetTrackDesignRepository() abstract; virtual IScenarioRepository* GetScenarioRepository() abstract; virtual IReplayManager* GetReplayManager() abstract; diff --git a/src/openrct2/Game.cpp b/src/openrct2/Game.cpp index 7526bb5d2c..cdbf7ff8bc 100644 --- a/src/openrct2/Game.cpp +++ b/src/openrct2/Game.cpp @@ -592,12 +592,16 @@ void game_load_init() void game_load_scripts() { +#ifdef __ENABLE_SCRIPTING__ GetContext()->GetScriptEngine().LoadPlugins(); +#endif } void game_finish() { +#ifdef __ENABLE_SCRIPTING__ GetContext()->GetScriptEngine().UnloadPlugins(); +#endif } /** diff --git a/src/openrct2/GameState.cpp b/src/openrct2/GameState.cpp index 568fdb2183..4e9de175a2 100644 --- a/src/openrct2/GameState.cpp +++ b/src/openrct2/GameState.cpp @@ -269,18 +269,22 @@ void GameState::UpdateLogic() } } +#ifdef __ENABLE_SCRIPTING__ auto& hookEngine = GetContext()->GetScriptEngine().GetHookEngine(); hookEngine.Call(HOOK_TYPE::INTERVAL_TICK, true); auto day = _date.GetDay(); +#endif date_update(); _date = Date(gDateMonthsElapsed, gDateMonthTicks); +#ifdef __ENABLE_SCRIPTING__ if (day != _date.GetDay()) { hookEngine.Call(HOOK_TYPE::INTERVAL_DAY, true); } +#endif scenario_update(); climate_update(); diff --git a/src/openrct2/interface/InteractiveConsole.h b/src/openrct2/interface/InteractiveConsole.h index ce35d74e1d..136c135eb8 100644 --- a/src/openrct2/interface/InteractiveConsole.h +++ b/src/openrct2/interface/InteractiveConsole.h @@ -13,6 +13,7 @@ #include "../localisation/FormatCodes.h" #include +#include #include struct rct_drawpixelinfo; @@ -50,9 +51,13 @@ public: class StdInOutConsole final : public InteractiveConsole { +private: + std::queue, std::string>> _evalQueue; + public: void Start(); std::future Eval(const std::string& s); + void ProcessEvalQueue(); void Clear() override; void Close() override; diff --git a/src/openrct2/interface/StdInOutConsole.cpp b/src/openrct2/interface/StdInOutConsole.cpp index 9491b00cd7..9fc0ac896a 100644 --- a/src/openrct2/interface/StdInOutConsole.cpp +++ b/src/openrct2/interface/StdInOutConsole.cpp @@ -55,8 +55,35 @@ void StdInOutConsole::Start() std::future StdInOutConsole::Eval(const std::string& s) { +#ifdef __ENABLE_SCRIPTING__ auto& scriptEngine = GetContext()->GetScriptEngine(); return scriptEngine.Eval(s); +#else + // Push on-demand evaluations onto a queue so that it can be processed deterministically + // on the main thead at the right time. + std::promise barrier; + auto future = barrier.get_future(); + _evalQueue.emplace(std::move(barrier), s); + return future; +#endif +} + +void StdInOutConsole::ProcessEvalQueue() +{ +#ifndef __ENABLE_SCRIPTING__ + while (_evalQueue.size() > 0) + { + auto item = std::move(_evalQueue.front()); + _evalQueue.pop(); + auto promise = std::move(std::get<0>(item)); + auto command = std::move(std::get<1>(item)); + + Execute(command); + + // Signal the promise so caller can continue + promise.set_value(); + } +#endif } void StdInOutConsole::Clear() diff --git a/src/openrct2/network/Network.cpp b/src/openrct2/network/Network.cpp index 10f36d33a6..8ced55ee05 100644 --- a/src/openrct2/network/Network.cpp +++ b/src/openrct2/network/Network.cpp @@ -1472,6 +1472,9 @@ void Network::Server_Send_OBJECTS(NetworkConnection& connection, const std::vect void Network::Server_Send_SCRIPTS(NetworkConnection& connection) const { + std::unique_ptr packet(NetworkPacket::Allocate()); + *packet << (uint32_t)NETWORK_COMMAND_SCRIPTS; +# ifdef __ENABLE_SCRIPTING__ using namespace OpenRCT2::Scripting; auto& scriptEngine = GetContext()->GetScriptEngine(); @@ -1487,8 +1490,7 @@ void Network::Server_Send_SCRIPTS(NetworkConnection& connection) const } log_verbose("Server sends %u scripts", pluginsToSend.size()); - std::unique_ptr packet(NetworkPacket::Allocate()); - *packet << (uint32_t)NETWORK_COMMAND_SCRIPTS << (uint32_t)pluginsToSend.size(); + *packet << (uint32_t)pluginsToSend.size(); for (const auto& plugin : pluginsToSend) { const auto& metadata = plugin->GetMetadata(); @@ -1498,6 +1500,9 @@ void Network::Server_Send_SCRIPTS(NetworkConnection& connection) const *packet << (uint32_t)code.size(); packet->Write((const uint8_t*)code.c_str(), code.size()); } +# else + *packet << (uint32_t)0; +# endif connection.QueuePacket(std::move(packet)); } @@ -2437,10 +2442,11 @@ void Network::Client_Handle_OBJECTS(NetworkConnection& connection, NetworkPacket void Network::Client_Handle_SCRIPTS(NetworkConnection& connection, NetworkPacket& packet) { - auto& scriptEngine = GetContext()->GetScriptEngine(); - uint32_t numScripts{}; packet >> numScripts; + +# ifdef __ENABLE_SCRIPTING__ + auto& scriptEngine = GetContext()->GetScriptEngine(); for (uint32_t i = 0; i < numScripts; i++) { uint32_t codeLength{}; @@ -2448,6 +2454,13 @@ void Network::Client_Handle_SCRIPTS(NetworkConnection& connection, NetworkPacket auto code = std::string_view((const char*)packet.Read(codeLength), codeLength); scriptEngine.AddNetworkPlugin(code); } +# else + if (numScripts > 0) + { + connection.SetLastDisconnectReason("The server requires plugin support."); + Close(); + } +# endif } void Network::Client_Handle_GAMESTATE(NetworkConnection& connection, NetworkPacket& packet) @@ -2891,6 +2904,7 @@ void Network::Server_Handle_CHAT(NetworkConnection& connection, NetworkPacket& p std::string text = szText; if (connection.Player != nullptr) { +# ifdef __ENABLE_SCRIPTING__ auto& hookEngine = GetContext()->GetScriptEngine().GetHookEngine(); if (hookEngine.HasSubscriptions(OpenRCT2::Scripting::HOOK_TYPE::NETWORK_CHAT)) { @@ -2920,6 +2934,7 @@ void Network::Server_Handle_CHAT(NetworkConnection& connection, NetworkPacket& p return; } } +# endif } const char* formatted = FormatChat(connection.Player, text.c_str()); diff --git a/src/openrct2/scripting/HookEngine.cpp b/src/openrct2/scripting/HookEngine.cpp index 1e6801d189..ee554fd75a 100644 --- a/src/openrct2/scripting/HookEngine.cpp +++ b/src/openrct2/scripting/HookEngine.cpp @@ -1,5 +1,5 @@ /***************************************************************************** - * Copyright (c) 2014-2018 OpenRCT2 developers + * Copyright (c) 2014-2020 OpenRCT2 developers * * For a complete list of all authors, please refer to contributors.md * Interested in contributing? Visit https://github.com/OpenRCT2/OpenRCT2 @@ -7,11 +7,13 @@ * OpenRCT2 is licensed under the GNU General Public License version 3. *****************************************************************************/ -#include "HookEngine.h" +#ifdef __ENABLE_SCRIPTING__ -#include "ScriptEngine.h" +# include "HookEngine.h" -#include +# include "ScriptEngine.h" + +# include using namespace OpenRCT2::Scripting; @@ -171,3 +173,5 @@ const HookList& HookEngine::GetHookList(HOOK_TYPE type) const auto index = static_cast(type); return _hookMap[index]; } + +#endif diff --git a/src/openrct2/scripting/ScriptEngine.cpp b/src/openrct2/scripting/ScriptEngine.cpp index e067791114..796cb96e02 100644 --- a/src/openrct2/scripting/ScriptEngine.cpp +++ b/src/openrct2/scripting/ScriptEngine.cpp @@ -7,28 +7,30 @@ * OpenRCT2 is licensed under the GNU General Public License version 3. *****************************************************************************/ -#include "ScriptEngine.h" +#ifdef __ENABLE_SCRIPTING__ -#include "../PlatformEnvironment.h" -#include "../config/Config.h" -#include "../core/FileScanner.h" -#include "../core/Path.hpp" -#include "../interface/InteractiveConsole.h" -#include "../platform/Platform2.h" -#include "Duktape.hpp" -#include "ScConsole.hpp" -#include "ScContext.hpp" -#include "ScDate.hpp" -#include "ScDisposable.hpp" -#include "ScMap.hpp" -#include "ScNetwork.hpp" -#include "ScPark.hpp" -#include "ScRide.hpp" -#include "ScThing.hpp" -#include "ScTile.hpp" +# include "ScriptEngine.h" -#include -#include +# include "../PlatformEnvironment.h" +# include "../config/Config.h" +# include "../core/FileScanner.h" +# include "../core/Path.hpp" +# include "../interface/InteractiveConsole.h" +# include "../platform/Platform2.h" +# include "Duktape.hpp" +# include "ScConsole.hpp" +# include "ScContext.hpp" +# include "ScDate.hpp" +# include "ScDisposable.hpp" +# include "ScMap.hpp" +# include "ScNetwork.hpp" +# include "ScPark.hpp" +# include "ScRide.hpp" +# include "ScThing.hpp" +# include "ScTile.hpp" + +# include +# include using namespace OpenRCT2; using namespace OpenRCT2::Scripting; @@ -398,3 +400,5 @@ void OpenRCT2::Scripting::ThrowIfGameStateNotMutable() duk_error(ctx, DUK_ERR_ERROR, "Game state is not mutable in this context."); } } + +#endif diff --git a/src/openrct2/scripting/ScriptEngine.h b/src/openrct2/scripting/ScriptEngine.h index da6517f699..6ebce0af41 100644 --- a/src/openrct2/scripting/ScriptEngine.h +++ b/src/openrct2/scripting/ScriptEngine.h @@ -9,18 +9,20 @@ #pragma once -#include "../common.h" -#include "../core/FileWatcher.h" -#include "HookEngine.h" -#include "Plugin.h" +#ifdef __ENABLE_SCRIPTING__ -#include -#include -#include -#include -#include -#include -#include +# include "../common.h" +# include "../core/FileWatcher.h" +# include "HookEngine.h" +# include "Plugin.h" + +# include +# include +# include +# include +# include +# include +# include struct duk_hthread; typedef struct duk_hthread duk_context; @@ -168,3 +170,5 @@ namespace OpenRCT2::Scripting void ThrowIfGameStateNotMutable(); } // namespace OpenRCT2::Scripting + +#endif