From 209a5946169c7e9e3dbdb001ef5d79f165dcfade Mon Sep 17 00:00:00 2001 From: Sebastian Date: Sun, 25 Nov 2018 20:36:55 +0000 Subject: [PATCH] Replaced module properties singleton with instance created as part of module manager: - Removed ImGui Module Properties singleton interface and released construction constraints. - Added ImGui Module Properties to ImGui Module Manager. - Moved ImGui Demo to ImGui Module Manager. - ImGui Demo and ImGui Module Commands keep reference to ImGui Module Manager that gives them access to properties. --- Source/ImGui/Private/ImGuiContextManager.cpp | 8 +++---- Source/ImGui/Private/ImGuiContextManager.h | 9 ++----- Source/ImGui/Private/ImGuiDemo.cpp | 4 +++- Source/ImGui/Private/ImGuiDemo.h | 8 +++++++ Source/ImGui/Private/ImGuiInputHandler.cpp | 2 +- Source/ImGui/Private/ImGuiModule.cpp | 24 ++++++++++++++----- Source/ImGui/Private/ImGuiModuleCommands.cpp | 14 ++++++----- Source/ImGui/Private/ImGuiModuleCommands.h | 13 ++++++---- Source/ImGui/Private/ImGuiModuleManager.cpp | 5 +++- Source/ImGui/Private/ImGuiModuleManager.h | 13 +++++++++- .../ImGui/Private/ImGuiModuleProperties.cpp | 6 +---- Source/ImGui/Private/ImGuiModuleProperties.h | 14 +---------- Source/ImGui/Private/ImGuiPrivatePCH.h | 1 - Source/ImGui/Private/SImGuiWidget.cpp | 7 +++--- 14 files changed, 74 insertions(+), 54 deletions(-) diff --git a/Source/ImGui/Private/ImGuiContextManager.cpp b/Source/ImGui/Private/ImGuiContextManager.cpp index dd3edd6..0a13bdb 100644 --- a/Source/ImGui/Private/ImGuiContextManager.cpp +++ b/Source/ImGui/Private/ImGuiContextManager.cpp @@ -121,7 +121,7 @@ FImGuiContextManager::FContextData& FImGuiContextManager::GetEditorContextData() if (UNLIKELY(!Data)) { - Data = &Contexts.Emplace(Utilities::EDITOR_CONTEXT_INDEX, FContextData{ GetEditorContextName(), Utilities::EDITOR_CONTEXT_INDEX, DrawMultiContextEvent, FontAtlas, ImGuiDemo, -1 }); + Data = &Contexts.Emplace(Utilities::EDITOR_CONTEXT_INDEX, FContextData{ GetEditorContextName(), Utilities::EDITOR_CONTEXT_INDEX, DrawMultiContextEvent, FontAtlas, -1 }); } return *Data; @@ -135,7 +135,7 @@ FImGuiContextManager::FContextData& FImGuiContextManager::GetStandaloneWorldCont if (UNLIKELY(!Data)) { - Data = &Contexts.Emplace(Utilities::STANDALONE_GAME_CONTEXT_INDEX, FContextData{ GetWorldContextName(), Utilities::STANDALONE_GAME_CONTEXT_INDEX, DrawMultiContextEvent, FontAtlas, ImGuiDemo }); + Data = &Contexts.Emplace(Utilities::STANDALONE_GAME_CONTEXT_INDEX, FContextData{ GetWorldContextName(), Utilities::STANDALONE_GAME_CONTEXT_INDEX, DrawMultiContextEvent, FontAtlas }); } return *Data; @@ -175,7 +175,7 @@ FImGuiContextManager::FContextData& FImGuiContextManager::GetWorldContextData(co #if WITH_EDITOR if (UNLIKELY(!Data)) { - Data = &Contexts.Emplace(Index, FContextData{ GetWorldContextName(World), Index, DrawMultiContextEvent, FontAtlas, ImGuiDemo, WorldContext->PIEInstance }); + Data = &Contexts.Emplace(Index, FContextData{ GetWorldContextName(World), Index, DrawMultiContextEvent, FontAtlas, WorldContext->PIEInstance }); } else { @@ -185,7 +185,7 @@ FImGuiContextManager::FContextData& FImGuiContextManager::GetWorldContextData(co #else if (UNLIKELY(!Data)) { - Data = &Contexts.Emplace(Index, FContextData{ GetWorldContextName(World), Index, DrawMultiContextEvent, FontAtlas, ImGuiDemo }); + Data = &Contexts.Emplace(Index, FContextData{ GetWorldContextName(World), Index, DrawMultiContextEvent, FontAtlas }); } #endif diff --git a/Source/ImGui/Private/ImGuiContextManager.h b/Source/ImGui/Private/ImGuiContextManager.h index c53b935..a66f086 100644 --- a/Source/ImGui/Private/ImGuiContextManager.h +++ b/Source/ImGui/Private/ImGuiContextManager.h @@ -3,7 +3,6 @@ #pragma once #include "ImGuiContextProxy.h" -#include "ImGuiDemo.h" // Manages ImGui context proxies. @@ -60,11 +59,10 @@ private: struct FContextData { - FContextData(const FString& ContextName, int32 ContextIndex, FSimpleMulticastDelegate& SharedDrawEvent, ImFontAtlas& FontAtlas, FImGuiDemo& Demo, int32 InPIEInstance = -1) + FContextData(const FString& ContextName, int32 ContextIndex, FSimpleMulticastDelegate& SharedDrawEvent, ImFontAtlas& FontAtlas, int32 InPIEInstance = -1) : PIEInstance(InPIEInstance) , ContextProxy(ContextName, &SharedDrawEvent, &FontAtlas) { - ContextProxy.OnDraw().AddLambda([&Demo, ContextIndex]() { Demo.DrawControls(ContextIndex); }); } FORCEINLINE bool CanTick() const { return PIEInstance < 0 || GEngine->GetWorldContextFromPIEInstance(PIEInstance); } @@ -77,10 +75,9 @@ private: struct FContextData { - FContextData(const FString& ContextName, int32 ContextIndex, FSimpleMulticastDelegate& SharedDrawEvent, ImFontAtlas& FontAtlas, FImGuiDemo& Demo) + FContextData(const FString& ContextName, int32 ContextIndex, FSimpleMulticastDelegate& SharedDrawEvent, ImFontAtlas& FontAtlas) : ContextProxy(ContextName, &SharedDrawEvent, &FontAtlas) { - ContextProxy.OnDraw().AddLambda([&Demo, ContextIndex]() { Demo.DrawControls(ContextIndex); }); } FORCEINLINE bool CanTick() const { return true; } @@ -108,8 +105,6 @@ private: TMap Contexts; - FImGuiDemo ImGuiDemo; - FSimpleMulticastDelegate DrawMultiContextEvent; ImFontAtlas FontAtlas; diff --git a/Source/ImGui/Private/ImGuiDemo.cpp b/Source/ImGui/Private/ImGuiDemo.cpp index 7bc3fee..6d4d036 100644 --- a/Source/ImGui/Private/ImGuiDemo.cpp +++ b/Source/ImGui/Private/ImGuiDemo.cpp @@ -4,11 +4,13 @@ #include "ImGuiDemo.h" +#include "ImGuiModuleManager.h" + // Demo copied (with minor modifications) from ImGui examples. See https://github.com/ocornut/imgui. void FImGuiDemo::DrawControls(int32 ContextIndex) { - if (FImGuiModuleProperties::Get().ShowDemo()) + if (ModuleManager.GetProperties().ShowDemo()) { const int32 ContextBit = ContextIndex < 0 ? 0 : 1 << ContextIndex; diff --git a/Source/ImGui/Private/ImGuiDemo.h b/Source/ImGui/Private/ImGuiDemo.h index 6534fb3..4507442 100644 --- a/Source/ImGui/Private/ImGuiDemo.h +++ b/Source/ImGui/Private/ImGuiDemo.h @@ -4,16 +4,24 @@ #include +class FImGuiModuleManager; // Widget drawing ImGui demo. class FImGuiDemo { public: + FImGuiDemo(FImGuiModuleManager& InModuleManager) + : ModuleManager(InModuleManager) + { + } + void DrawControls(int32 ContextIndex); private: + FImGuiModuleManager& ModuleManager; + ImVec4 ClearColor = ImColor{ 114, 144, 154 }; int32 ShowDemoWindowMask = 0; diff --git a/Source/ImGui/Private/ImGuiInputHandler.cpp b/Source/ImGui/Private/ImGuiInputHandler.cpp index 3c703d9..3d7a348 100644 --- a/Source/ImGui/Private/ImGuiInputHandler.cpp +++ b/Source/ImGui/Private/ImGuiInputHandler.cpp @@ -26,7 +26,7 @@ FImGuiInputResponse UImGuiInputHandler::OnKeyDown(const FKeyEvent& KeyEvent) // If this is an input mode switch event then handle it here and consume. if (IsToggleInputEvent(KeyEvent)) { - FImGuiModuleProperties::Get().ToggleInput(); + ModuleManager->GetProperties().ToggleInput(); return FImGuiInputResponse().RequestConsume(); } diff --git a/Source/ImGui/Private/ImGuiModule.cpp b/Source/ImGui/Private/ImGuiModule.cpp index 8f51c2f..63bb1ab 100644 --- a/Source/ImGui/Private/ImGuiModule.cpp +++ b/Source/ImGui/Private/ImGuiModule.cpp @@ -170,32 +170,44 @@ ImGuiContext** FImGuiModule::GetImGuiContextHandle() bool FImGuiModule::IsInputMode() const { - return FImGuiModuleProperties::Get().IsInputEnabled(); + return ImGuiModuleManager && ImGuiModuleManager->GetProperties().IsInputEnabled(); } void FImGuiModule::SetInputMode(bool bEnabled) { - return FImGuiModuleProperties::Get().SetInputEnabled(bEnabled); + if (ImGuiModuleManager) + { + ImGuiModuleManager->GetProperties().SetInputEnabled(bEnabled); + } } void FImGuiModule::ToggleInputMode() { - FImGuiModuleProperties::Get().ToggleInput(); + if (ImGuiModuleManager) + { + ImGuiModuleManager->GetProperties().ToggleInput(); + } } bool FImGuiModule::IsShowingDemo() const { - return FImGuiModuleProperties::Get().ShowDemo(); + return ImGuiModuleManager && ImGuiModuleManager->GetProperties().ShowDemo(); } void FImGuiModule::SetShowDemo(bool bShow) { - return FImGuiModuleProperties::Get().SetShowDemo(bShow); + if (ImGuiModuleManager) + { + ImGuiModuleManager->GetProperties().SetShowDemo(bShow); + } } void FImGuiModule::ToggleShowDemo() { - return FImGuiModuleProperties::Get().ToggleDemo(); + if (ImGuiModuleManager) + { + ImGuiModuleManager->GetProperties().ToggleDemo(); + } } diff --git a/Source/ImGui/Private/ImGuiModuleCommands.cpp b/Source/ImGui/Private/ImGuiModuleCommands.cpp index 78fe3e4..63de9b4 100644 --- a/Source/ImGui/Private/ImGuiModuleCommands.cpp +++ b/Source/ImGui/Private/ImGuiModuleCommands.cpp @@ -4,6 +4,7 @@ #include "ImGuiModuleCommands.h" +#include "ImGuiModuleManager.h" #include "ImGuiSettings.h" #include "Utilities/DebugExecBindings.h" @@ -19,8 +20,9 @@ namespace CommandNames } } -FImGuiModuleCommands::FImGuiModuleCommands() - : ToggleInputCommand(CommandNames::ToggleInput, +FImGuiModuleCommands::FImGuiModuleCommands(FImGuiModuleManager& InModuleManager) + : ModuleManager(InModuleManager) + , ToggleInputCommand(CommandNames::ToggleInput, TEXT("Toggle ImGui input mode."), FConsoleCommandDelegate::CreateRaw(this, &FImGuiModuleCommands::ToggleInput)) , ToggleKeyboardNavigationCommand(CommandNames::ToggleKeyboardNavigation, @@ -82,20 +84,20 @@ void FImGuiModuleCommands::UpdateToggleInputKeyBinding() void FImGuiModuleCommands::ToggleInput() { - FImGuiModuleProperties::Get().ToggleInput(); + ModuleManager.GetProperties().ToggleInput(); } void FImGuiModuleCommands::ToggleKeyboardNavigation() { - FImGuiModuleProperties::Get().ToggleKeyboardNavigation(); + ModuleManager.GetProperties().ToggleKeyboardNavigation(); } void FImGuiModuleCommands::ToggleGamepadNavigation() { - FImGuiModuleProperties::Get().ToggleGamepadNavigation(); + ModuleManager.GetProperties().ToggleGamepadNavigation(); } void FImGuiModuleCommands::ToggleDemo() { - FImGuiModuleProperties::Get().ToggleDemo(); + ModuleManager.GetProperties().ToggleDemo(); } diff --git a/Source/ImGui/Private/ImGuiModuleCommands.h b/Source/ImGui/Private/ImGuiModuleCommands.h index 6039250..192f23b 100644 --- a/Source/ImGui/Private/ImGuiModuleCommands.h +++ b/Source/ImGui/Private/ImGuiModuleCommands.h @@ -5,15 +5,18 @@ #include -// Wrapper for ImGui console commands. +class FImGuiModuleManager; + +// Manges ImGui module console commands. class FImGuiModuleCommands { - // Allow module manager to control life-cycle of this class. - friend class FImGuiModuleManager; +public: - FImGuiModuleCommands(); + FImGuiModuleCommands(FImGuiModuleManager& InModuleManager); ~FImGuiModuleCommands(); +private: + FImGuiModuleCommands(const FImGuiModuleCommands&) = delete; FImGuiModuleCommands& operator=(const FImGuiModuleCommands&) = delete; @@ -32,6 +35,8 @@ class FImGuiModuleCommands void ToggleGamepadNavigation(); void ToggleDemo(); + FImGuiModuleManager& ModuleManager; + FAutoConsoleCommand ToggleInputCommand; FAutoConsoleCommand ToggleKeyboardNavigationCommand; FAutoConsoleCommand ToggleGamepadNavigationCommand; diff --git a/Source/ImGui/Private/ImGuiModuleManager.cpp b/Source/ImGui/Private/ImGuiModuleManager.cpp index a0e9174..7990dc2 100644 --- a/Source/ImGui/Private/ImGuiModuleManager.cpp +++ b/Source/ImGui/Private/ImGuiModuleManager.cpp @@ -13,6 +13,8 @@ FImGuiModuleManager::FImGuiModuleManager() + : ModuleCommands(*this) + , ImGuiDemo(*this) { // Typically we will use viewport created events to add widget to new game viewports. ViewportCreatedHandle = UGameViewportClient::OnViewportCreated().AddRaw(this, &FImGuiModuleManager::OnViewportCreated); @@ -166,7 +168,8 @@ void FImGuiModuleManager::AddWidgetToViewport(UGameViewportClient* GameViewport) // Make sure that we have a context for this viewport's world and get its index. int32 ContextIndex; - auto& Proxy = ContextManager.GetWorldContextProxy(*GameViewport->GetWorld(), ContextIndex); + auto& ContextProxy = ContextManager.GetWorldContextProxy(*GameViewport->GetWorld(), ContextIndex); + ContextProxy.OnDraw().AddLambda([this, ContextIndex]() { ImGuiDemo.DrawControls(ContextIndex); }); // Make sure that textures are loaded before the first Slate widget is created. LoadTextures(); diff --git a/Source/ImGui/Private/ImGuiModuleManager.h b/Source/ImGui/Private/ImGuiModuleManager.h index 548560d..fb420fd 100644 --- a/Source/ImGui/Private/ImGuiModuleManager.h +++ b/Source/ImGui/Private/ImGuiModuleManager.h @@ -3,7 +3,9 @@ #pragma once #include "ImGuiContextManager.h" +#include "ImGuiDemo.h" #include "ImGuiModuleCommands.h" +#include "ImGuiModuleProperties.h" #include "SImGuiWidget.h" #include "TextureManager.h" @@ -16,6 +18,9 @@ class FImGuiModuleManager public: + // Get interface to module state properties. + FImGuiModuleProperties& GetProperties() { return Properties; } + // Get ImGui contexts manager. FImGuiContextManager& GetContextManager() { return ContextManager; } @@ -57,8 +62,14 @@ private: // Event that we call after ImGui is updated. FSimpleMulticastDelegate PostImGuiUpdateEvent; + // Collection of module state properties. + FImGuiModuleProperties Properties; + // Tying module console commands to life-cycle of this manager and module. - FImGuiModuleCommands Commands; + FImGuiModuleCommands ModuleCommands; + + // Widget that we add to all created contexts to draw ImGui demo. + FImGuiDemo ImGuiDemo; // Manager for ImGui contexts. FImGuiContextManager ContextManager; diff --git a/Source/ImGui/Private/ImGuiModuleProperties.cpp b/Source/ImGui/Private/ImGuiModuleProperties.cpp index cd21447..2c65bd6 100644 --- a/Source/ImGui/Private/ImGuiModuleProperties.cpp +++ b/Source/ImGui/Private/ImGuiModuleProperties.cpp @@ -5,8 +5,4 @@ #include "ImGuiModuleProperties.h" -FImGuiModuleProperties& FImGuiModuleProperties::Get() -{ - static FImGuiModuleProperties Instance; - return Instance; -} +// TODO: Initialize relevant properties from settings. diff --git a/Source/ImGui/Private/ImGuiModuleProperties.h b/Source/ImGui/Private/ImGuiModuleProperties.h index b133c5d..6bf68d3 100644 --- a/Source/ImGui/Private/ImGuiModuleProperties.h +++ b/Source/ImGui/Private/ImGuiModuleProperties.h @@ -6,15 +6,11 @@ // Collects and give access to module properties. -// TODO: For now singleton instance is initialized on the first use. Try to move it to the ImGui Manager. class FImGuiModuleProperties { public: - // Get the instance of the ImGui properties. - static FImGuiModuleProperties& Get(); - - // Check whether ImGui input is enabled. + // Check whether input is enabled. bool IsInputEnabled() const { return bInputEnabled; } // Enable or disable ImGui input. @@ -52,14 +48,6 @@ public: private: - FImGuiModuleProperties() = default; - - FImGuiModuleProperties(const FImGuiModuleProperties&) = delete; - FImGuiModuleProperties& operator=(const FImGuiModuleProperties&) = delete; - - FImGuiModuleProperties(FImGuiModuleProperties&&) = delete; - FImGuiModuleProperties& operator=(FImGuiModuleProperties&&) = delete; - bool bInputEnabled = false; bool bKeyboardNavigationEnabled = false; diff --git a/Source/ImGui/Private/ImGuiPrivatePCH.h b/Source/ImGui/Private/ImGuiPrivatePCH.h index 531f105..e193a86 100644 --- a/Source/ImGui/Private/ImGuiPrivatePCH.h +++ b/Source/ImGui/Private/ImGuiPrivatePCH.h @@ -3,7 +3,6 @@ // Module-wide macros #include "VersionCompatibility.h" #include "ImGuiModuleDebug.h" -#include "ImGuiModuleProperties.h" // Module #include "ImGuiModule.h" diff --git a/Source/ImGui/Private/SImGuiWidget.cpp b/Source/ImGui/Private/SImGuiWidget.cpp index 4b46c13..16a9464 100644 --- a/Source/ImGui/Private/SImGuiWidget.cpp +++ b/Source/ImGui/Private/SImGuiWidget.cpp @@ -503,7 +503,7 @@ void SImGuiWidget::SetVisibilityFromInputEnabled() void SImGuiWidget::UpdateInputEnabled() { - const bool bEnabled = FImGuiModuleProperties::Get().IsInputEnabled(); + const bool bEnabled = ModuleManager && ModuleManager->GetProperties().IsInputEnabled(); if (bInputEnabled != bEnabled) { bInputEnabled = bEnabled; @@ -552,9 +552,8 @@ void SImGuiWidget::UpdateInputEnabled() if (bInputEnabled) { - const auto& Properties = FImGuiModuleProperties::Get(); - InputState.SetKeyboardNavigationEnabled(Properties.IsKeyboardNavigationEnabled()); - InputState.SetGamepadNavigationEnabled(Properties.IsGamepadNavigationEnabled()); + InputState.SetKeyboardNavigationEnabled(ModuleManager && ModuleManager->GetProperties().IsKeyboardNavigationEnabled()); + InputState.SetGamepadNavigationEnabled(ModuleManager && ModuleManager->GetProperties().IsGamepadNavigationEnabled()); const auto& Application = FSlateApplication::Get().GetPlatformApplication(); InputState.SetGamepad(Application.IsValid() && Application->IsGamepadAttached()); }