Skip to content

Commit

Permalink
Removed native child windowing (Windows Only!)
Browse files Browse the repository at this point in the history
  • Loading branch information
dacuster committed Mar 28, 2024
1 parent e21d366 commit fd629d7
Show file tree
Hide file tree
Showing 6 changed files with 26 additions and 189 deletions.
1 change: 0 additions & 1 deletion CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,6 @@ target_sources(
${CMAKE_CURRENT_SOURCE_DIR}/imgui_tables.cpp
${CMAKE_CURRENT_SOURCE_DIR}/imgui_widgets.cpp
${CMAKE_CURRENT_SOURCE_DIR}/misc/cpp/imgui_stdlib.cpp
${CMAKE_CURRENT_SOURCE_DIR}/microstrain/NativeChildWindow.cpp
)

target_compile_features(${PROJECT_NAME} PUBLIC cxx_std_11)
Expand Down
138 changes: 4 additions & 134 deletions backends/imgui_impl_sdl2.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -83,13 +83,6 @@
#include "imgui.h"
#ifndef IMGUI_DISABLE
#include "imgui_impl_sdl2.h"
#include "microstrain/NativeChildWindow.hpp"
#include <SDL2/SDL.h>
#include <SDL_syswm.h> // Must be after mip command includes due to #define Status

#if defined __linux__
#include <X11/Xlib.h>
#endif

// Clang warnings with -Weverything
#if defined(__clang__)
Expand Down Expand Up @@ -855,7 +848,6 @@ struct ImGui_ImplSDL2_ViewportData
Uint32 WindowID;
bool WindowOwned;
SDL_GLContext GLContext;
NativeChildWindow *ChildWindow = nullptr;
ImGui_ImplSDL2_ViewportData() { Window = nullptr; WindowID = 0; WindowOwned = false; GLContext = nullptr; }
~ImGui_ImplSDL2_ViewportData() { IM_ASSERT(Window == nullptr && GLContext == nullptr); }
};
Expand Down Expand Up @@ -892,83 +884,10 @@ static void ImGui_ImplSDL2_CreateWindow(ImGuiViewport* viewport)
#if SDL_HAS_ALWAYS_ON_TOP
sdl_flags |= (viewport->Flags & ImGuiViewportFlags_TopMost) ? SDL_WINDOW_ALWAYS_ON_TOP : 0;
#endif

//Microstrain Custom
if(viewport->Flags & ImGuiViewportFlags_NativeChild)
{
float x_pos = viewport->Pos.x - main_viewport->Pos.x;
float y_pos = viewport->Pos.y - main_viewport->Pos.y;

NativeChildWindow *child_window = new NativeChildWindow;

ImGuiViewport *parent_viewport = ImGui::FindViewportByID(viewport->ParentViewportId);

while (parent_viewport->Flags & ImGuiViewportFlags_NativeChild)
parent_viewport = ImGui::FindViewportByID(parent_viewport->ParentViewportId);

ImGui_ImplSDL2_ViewportData *parent_viewport_data = (ImGui_ImplSDL2_ViewportData *)parent_viewport->PlatformUserData;

void *parent_ptr = nullptr;
SDL_Window *parent_window = parent_viewport_data->Window;

#ifdef __linux__
parent_ptr = parent_window;
#else
if (parent_window != nullptr)
{
SDL_SysWMinfo wmInfo;
SDL_VERSION(&wmInfo.version);
SDL_GetWindowWMInfo(parent_window, &wmInfo);

#if defined _WIN32
parent_ptr = wmInfo.info.win.window;
#endif
vd->Window = SDL_CreateWindow("No Title Yet", (int)viewport->Pos.x, (int)viewport->Pos.y, (int)viewport->Size.x, (int)viewport->Size.y, sdl_flags);

#if defined __APPLE__
parent_ptr = wmInfo.info.cocoa.window;
#endif
}
else
{
parent_ptr = main_viewport->PlatformHandleRaw;
}

#endif

if(child_window->create(parent_ptr, (int)(x_pos), (int)(y_pos), (int)viewport->Size.x, (int)viewport->Size.y))
{
void *native_child_window = child_window->get();

//#ifdef __linux__

//SDL_SysWMinfo info = SDL_SysWMinfo();
//SDL_VERSION(&info.version);

//vd->Window = (SDL_Window *)native_child_window;
//#else
char address[100];

sprintf(address, "%p", (SDL_Window*)main_viewport->PlatformHandle);
SDL_SetHint(SDL_HINT_VIDEO_WINDOW_SHARE_PIXEL_FORMAT, address);
SDL_SetHint(SDL_HINT_VIDEO_FOREIGN_WINDOW_OPENGL, "1");

vd->Window = SDL_CreateWindowFrom(native_child_window);

child_window->enableHighDpi();
//#endif
vd->ChildWindow = child_window;
}
else
return;
}
//Standard window creation
else
{
vd->Window = SDL_CreateWindow("No Title Yet", (int)viewport->Pos.x, (int)viewport->Pos.y, (int)viewport->Size.x, (int)viewport->Size.y, sdl_flags);
}

vd->WindowOwned = true;

if (use_opengl)
{
vd->GLContext = SDL_GL_CreateContext(vd->Window);
Expand All @@ -978,10 +897,10 @@ static void ImGui_ImplSDL2_CreateWindow(ImGuiViewport* viewport)
SDL_GL_MakeCurrent(vd->Window, backup_context);

viewport->PlatformHandle = (void*)vd->Window;

viewport->PlatformHandleRaw = nullptr;

SDL_SysWMinfo info;
SDL_VERSION(&info.version);

if (SDL_GetWindowWMInfo(vd->Window, &info))
{
#if defined(SDL_VIDEO_DRIVER_WINDOWS)
Expand All @@ -1000,14 +919,6 @@ static void ImGui_ImplSDL2_DestroyWindow(ImGuiViewport* viewport)
SDL_GL_DeleteContext(vd->GLContext);
if (vd->Window && vd->WindowOwned)
SDL_DestroyWindow(vd->Window);

if(vd->ChildWindow != nullptr)
{
NativeChildWindow *child_window = (NativeChildWindow *)vd->ChildWindow;
child_window->destroy();
delete child_window;
}

vd->GLContext = nullptr;
vd->Window = nullptr;
IM_DELETE(vd);
Expand Down Expand Up @@ -1053,38 +964,7 @@ static ImVec2 ImGui_ImplSDL2_GetWindowPos(ImGuiViewport* viewport)
static void ImGui_ImplSDL2_SetWindowPos(ImGuiViewport* viewport, ImVec2 pos)
{
ImGui_ImplSDL2_ViewportData* vd = (ImGui_ImplSDL2_ViewportData*)viewport->PlatformUserData;

int pos_x = (int)pos.x, pos_y = (int)pos.y;

ImGuiViewport *parent_viewport = ImGui::FindViewportByID(viewport->ParentViewportId);

while (parent_viewport->Flags & ImGuiViewportFlags_NativeChild)
parent_viewport = ImGui::FindViewportByID(parent_viewport->ParentViewportId);

//Microstrain edit (use child coordinates for child windows)
#if defined(_WIN32)
if(vd->ChildWindow != nullptr)
{
pos_x = (int)(viewport->Pos.x - parent_viewport->Pos.x);
pos_y = (int)(viewport->Pos.y - parent_viewport->Pos.y);

SetWindowPos((HWND)vd->ChildWindow->get(), HWND_TOP, pos_x, pos_y, 0, 0, SWP_NOCOPYBITS | SWP_NOACTIVATE | SWP_NOSIZE);
}
#elif defined __linux__
if(vd->ChildWindow != nullptr)
{
pos_x = viewport->Pos.x - parent_viewport->Pos.x;
pos_y = viewport->Pos.y - parent_viewport->Pos.y;

if(vd->ChildWindow)
{
vd->ChildWindow->setSize(pos_x, pos_y, viewport->Size.x, viewport->Size.y);
}
}

#else
SDL_SetWindowPosition(vd->Window, pos_x, pos_y);
#endif
SDL_SetWindowPosition(vd->Window, (int)pos.x, (int)pos.y);
}

static ImVec2 ImGui_ImplSDL2_GetWindowSize(ImGuiViewport* viewport)
Expand All @@ -1098,17 +978,7 @@ static ImVec2 ImGui_ImplSDL2_GetWindowSize(ImGuiViewport* viewport)
static void ImGui_ImplSDL2_SetWindowSize(ImGuiViewport* viewport, ImVec2 size)
{
ImGui_ImplSDL2_ViewportData* vd = (ImGui_ImplSDL2_ViewportData*)viewport->PlatformUserData;

//Microstrain edit (use child coordinates for child windows)
#if defined(_WIN32)
if (vd->ChildWindow != nullptr)
{
SetWindowPos((HWND)vd->ChildWindow->get(), HWND_TOP, 0, 0, size.x, size.y, SWP_NOCOPYBITS | SWP_NOACTIVATE | SWP_NOMOVE);
}
#else

SDL_SetWindowSize(vd->Window, (int)size.x, (int)size.y);
#endif
}

static void ImGui_ImplSDL2_SetWindowTitle(ImGuiViewport* viewport, const char* title)
Expand Down
6 changes: 4 additions & 2 deletions imconfig.h
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,9 @@
// Using Dear ImGui via a shared library is not recommended, because of function call overhead and because we don't guarantee backward nor forward ABI compatibility.
// DLL users: heaps and globals are not shared across DLL boundaries! You will need to call SetCurrentContext() + SetAllocatorFunctions()
// for each static/DLL boundary you are calling from. Read "Context and Memory Allocators" section of imgui.cpp for more details.
//#define IMGUI_API __declspec( dllexport )
#ifdef WIN32_
#define IMGUI_API __declspec( dllexport )
#endif
//#define IMGUI_API __declspec( dllimport )

//---- Don't define obsolete functions/enums/behaviors. Consider enabling from time to time after updating to clean your code of obsolete function/names.
Expand Down Expand Up @@ -100,7 +102,7 @@
operator MyVec4() const { return MyVec4(x,y,z,w); }
*/
//---- ...Or use Dear ImGui's own very basic math operators.
//#define IMGUI_DEFINE_MATH_OPERATORS
#define IMGUI_DEFINE_MATH_OPERATORS

//---- Use 32-bit vertex indices (default is 16-bit) is one way to allow large meshes with more than 64K vertices.
// Your renderer backend will need to support it (most example renderer backends support both 16/32-bit indices).
Expand Down
51 changes: 13 additions & 38 deletions imgui.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -5097,7 +5097,7 @@ static void AddWindowToDrawData(ImGuiWindow* window, int layer)

static inline int GetWindowDisplayLayer(ImGuiWindow* window)
{
return (window->Flags & ImGuiWindowFlags_Tooltip)? 1 : 0;
return (window->Flags & ImGuiWindowFlags_Tooltip) ? 1 : 0;
}

// Layer is locked for the root window, however child windows may use a different viewport (e.g. extruding menu)
Expand Down Expand Up @@ -6082,8 +6082,7 @@ static ImVec2 CalcWindowAutoFitSize(ImGuiWindow* window, const ImVec2& size_cont
ImVec2 size_pad = window->WindowPadding * 2.0f;
ImVec2 size_desired = size_contents + size_pad + ImVec2(decoration_w_without_scrollbars, decoration_h_without_scrollbars);

//Microstrain custom!
if ((window->Flags & ImGuiWindowFlags_Tooltip) || (window->Flags & ImGuiWindowFlags_Native_Child_Window))
if (window->Flags & ImGuiWindowFlags_Tooltip)
{
// Tooltip always resize
return size_desired;
Expand Down Expand Up @@ -7145,18 +7144,12 @@ bool ImGui::Begin(const char* name, bool* p_open, ImGuiWindowFlags flags)
window->Pos = FindBestWindowPosForPopup(window);

// Late create viewport if we don't fit within our current host viewport.
//Microstrain custom!
if (window->ViewportAllowPlatformMonitorExtend >= 0 && !window->ViewportOwned && !(window->Viewport->Flags & ImGuiViewportFlags_IsMinimized))
if (!window->Viewport->GetMainRect().Contains(window->Rect()) || (flags & ImGuiWindowFlags_Native_Child_Window))
if ((window->WindowClass.ViewportFlagsOverrideSet & ImGuiViewportFlags_NoAutoMerge) || !window->Viewport->GetMainRect().Contains(window->Rect()))
{
ImGuiViewportFlags viewport_flags = ImGuiViewportFlags_NoFocusOnAppearing;

if(flags & ImGuiWindowFlags_Native_Child_Window)
viewport_flags |= ImGuiViewportFlags_NativeChild;

// This is based on the assumption that the DPI will be known ahead (same as the DPI of the selection done in UpdateSelectWindowViewport)
//ImGuiViewport* old_viewport = window->Viewport;
window->Viewport = AddUpdateViewport(window, window->ID, window->Pos, window->Size, viewport_flags);
window->Viewport = AddUpdateViewport(window, window->ID, window->Pos, window->Size, ImGuiViewportFlags_NoFocusOnAppearing);

// FIXME-DPI
//IM_ASSERT(old_viewport->DpiScale == window->Viewport->DpiScale); // FIXME-DPI: Something went wrong
Expand Down Expand Up @@ -11076,8 +11069,7 @@ bool ImGui::BeginTooltipEx(ImGuiTooltipFlags tooltip_flags, ImGuiWindowFlags ext
SetWindowHiddendAndSkipItemsForCurrentFrame(window);
ImFormatString(window_name, IM_ARRAYSIZE(window_name), "##Tooltip_%02d", ++g.TooltipOverrideCount);
}
//Microstrain custom!
ImGuiWindowFlags flags = ImGuiWindowFlags_Native_Child_Window | ImGuiWindowFlags_Tooltip | ImGuiWindowFlags_NoInputs | ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoMove | ImGuiWindowFlags_NoResize | ImGuiWindowFlags_NoSavedSettings | ImGuiWindowFlags_AlwaysAutoResize | ImGuiWindowFlags_NoDocking;
ImGuiWindowFlags flags = ImGuiWindowFlags_Tooltip | ImGuiWindowFlags_NoInputs | ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoMove | ImGuiWindowFlags_NoResize | ImGuiWindowFlags_NoSavedSettings | ImGuiWindowFlags_AlwaysAutoResize | ImGuiWindowFlags_NoDocking;
Begin(window_name, NULL, flags | extra_window_flags);
// 2023-03-09: Added bool return value to the API, but currently always returning true.
// If this ever returns false we need to update BeginDragDropSource() accordingly.
Expand Down Expand Up @@ -11404,9 +11396,7 @@ bool ImGui::BeginPopup(const char* str_id, ImGuiWindowFlags flags)
g.NextWindowData.ClearFlags(); // We behave like Begin() and need to consume those values
return false;
}

//Microstrain Edit
flags |= ImGuiWindowFlags_Native_Child_Window | ImGuiWindowFlags_AlwaysAutoResize | ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoSavedSettings;
flags |= ImGuiWindowFlags_AlwaysAutoResize | ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoSavedSettings;
ImGuiID id = g.CurrentWindow->GetID(str_id);
return BeginPopupEx(id, flags);
}
Expand Down Expand Up @@ -14768,12 +14758,6 @@ static void ImGui::WindowSelectViewport(ImGuiWindow* window)
ImGuiWindowFlags flags = window->Flags;
window->ViewportAllowPlatformMonitorExtend = -1;

ImGuiViewportFlags viewport_flags = ImGuiViewportFlags_None;

if(flags & ImGuiWindowFlags_Native_Child_Window)
viewport_flags |= ImGuiViewportFlags_NativeChild;


// Restore main viewport if multi-viewport is not supported by the backend
ImGuiViewportP* main_viewport = (ImGuiViewportP*)(void*)GetMainViewport();
if (!(g.ConfigFlagsCurrFrame & ImGuiConfigFlags_ViewportsEnable))
Expand Down Expand Up @@ -14801,12 +14785,10 @@ static void ImGui::WindowSelectViewport(ImGuiWindow* window)
{
window->Viewport = (ImGuiViewportP*)FindViewportByID(window->ViewportId);
if (window->Viewport == NULL && window->ViewportPos.x != FLT_MAX && window->ViewportPos.y != FLT_MAX)
window->Viewport = AddUpdateViewport(window, window->ID, window->ViewportPos, window->Size, viewport_flags);
window->Viewport = AddUpdateViewport(window, window->ID, window->ViewportPos, window->Size, ImGuiViewportFlags_None);
}
}



bool lock_viewport = false;
if (g.NextWindowData.Flags & ImGuiNextWindowDataFlags_HasViewport)
{
Expand Down Expand Up @@ -14838,12 +14820,12 @@ static void ImGui::WindowSelectViewport(ImGuiWindow* window)
}
else if (GetWindowAlwaysWantOwnViewport(window))
{
window->Viewport = AddUpdateViewport(window, window->ID, window->Pos, window->Size, viewport_flags);
window->Viewport = AddUpdateViewport(window, window->ID, window->Pos, window->Size, ImGuiViewportFlags_None);
}
else if (g.MovingWindow && g.MovingWindow->RootWindowDockTree == window && IsMousePosValid())
{
if (window->Viewport != NULL && window->Viewport->Window == window)
window->Viewport = AddUpdateViewport(window, window->ID, window->Pos, window->Size, viewport_flags);
window->Viewport = AddUpdateViewport(window, window->ID, window->Pos, window->Size, ImGuiViewportFlags_None);
}
else
{
Expand All @@ -14858,7 +14840,7 @@ static void ImGui::WindowSelectViewport(ImGuiWindow* window)
// Fallback: merge in default viewport if z-order matches, otherwise create a new viewport
if (window->Viewport == NULL)
if (!UpdateTryMergeWindowIntoHostViewport(window, main_viewport))
window->Viewport = AddUpdateViewport(window, window->ID, window->Pos, window->Size, viewport_flags);
window->Viewport = AddUpdateViewport(window, window->ID, window->Pos, window->Size, ImGuiViewportFlags_None);

// Mark window as allowed to protrude outside of its viewport and into the current monitor
if (!lock_viewport)
Expand Down Expand Up @@ -14890,7 +14872,7 @@ static void ImGui::WindowSelectViewport(ImGuiWindow* window)
else if (!UpdateTryMergeWindowIntoHostViewports(window)) // Merge?
{
// New viewport
window->Viewport = AddUpdateViewport(window, window->ID, window->Pos, window->Size, viewport_flags | ImGuiViewportFlags_NoFocusOnAppearing);
window->Viewport = AddUpdateViewport(window, window->ID, window->Pos, window->Size, ImGuiViewportFlags_NoFocusOnAppearing);
}
}
else if (window->ViewportAllowPlatformMonitorExtend < 0 && (flags & ImGuiWindowFlags_ChildWindow) == 0)
Expand Down Expand Up @@ -14951,10 +14933,8 @@ void ImGui::WindowSyncOwnedViewport(ImGuiWindow* window, ImGuiWindow* parent_win
ImGuiViewportFlags viewport_flags = window->Viewport->Flags & ~viewport_flags_to_clear;
ImGuiWindowFlags window_flags = window->Flags;
const bool is_modal = (window_flags & ImGuiWindowFlags_Modal) != 0;

//Microstrain custom!
const bool is_short_lived_floating_window = (window_flags & (ImGuiWindowFlags_ChildMenu | ImGuiWindowFlags_Tooltip | ImGuiWindowFlags_Popup | ImGuiWindowFlags_Native_Child_Window)) != 0;
if ((window_flags & ImGuiWindowFlags_Tooltip) || (window_flags & ImGuiWindowFlags_Native_Child_Window))
const bool is_short_lived_floating_window = (window_flags & (ImGuiWindowFlags_ChildMenu | ImGuiWindowFlags_Tooltip | ImGuiWindowFlags_Popup)) != 0;
if (window_flags & ImGuiWindowFlags_Tooltip)
viewport_flags |= ImGuiViewportFlags_TopMost;
if ((g.IO.ConfigViewportsNoTaskBarIcon || is_short_lived_floating_window) && !is_modal)
viewport_flags |= ImGuiViewportFlags_NoTaskBarIcon;
Expand Down Expand Up @@ -15035,11 +15015,6 @@ void ImGui::UpdatePlatformWindows()
if (is_new_platform_window)
{
IMGUI_DEBUG_LOG_VIEWPORT("[viewport] Create Platform Window %08X '%s'\n", viewport->ID, viewport->Window ? viewport->Window->Name : "n/a");

//Microstrain Custom Edit
if(viewport->Window->Flags & ImGuiWindowFlags_Native_Child_Window)
viewport->Flags |= ImGuiViewportFlags_NativeChild;

g.PlatformIO.Platform_CreateWindow(viewport);
if (g.PlatformIO.Renderer_CreateWindow != NULL)
g.PlatformIO.Renderer_CreateWindow(viewport);
Expand Down
8 changes: 1 addition & 7 deletions imgui.h
Original file line number Diff line number Diff line change
Expand Up @@ -1065,11 +1065,9 @@ enum ImGuiWindowFlags_
ImGuiWindowFlags_ChildMenu = 1 << 28, // Don't use! For internal use by BeginMenu()
ImGuiWindowFlags_DockNodeHost = 1 << 29, // Don't use! For internal use by Begin()/NewFrame()

// [Microstrain Custom!]
ImGuiWindowFlags_Native_Child_Window = 1 << 30, // Microstrain Custom!!!
// Obsolete names
#ifndef IMGUI_DISABLE_OBSOLETE_FUNCTIONS
ImGuiWindowFlags_AlwaysUseWindowPadding = 1 << 31, // Obsoleted in 1.90: Use ImGuiChildFlags_AlwaysUseWindowPadding in BeginChild() call.
ImGuiWindowFlags_AlwaysUseWindowPadding = 1 << 30, // Obsoleted in 1.90: Use ImGuiChildFlags_AlwaysUseWindowPadding in BeginChild() call.
#endif
};

Expand Down Expand Up @@ -3242,10 +3240,6 @@ enum ImGuiViewportFlags_
// Output status flags (from Platform)
ImGuiViewportFlags_IsMinimized = 1 << 12, // Platform Window: Window is minimized, can skip render. When minimized we tend to avoid using the viewport pos/size for clipping window or testing if they are contained in the viewport.
ImGuiViewportFlags_IsFocused = 1 << 13, // Platform Window: Window is focused (last call to Platform_GetWindowFocus() returned true)

//Microstrain Custom
ImGuiViewportFlags_NativeChild = 1 << 14, // Platform Window: Create window as native child

};

// - Currently represents the Platform Window created by the application which is hosting our Dear ImGui windows.
Expand Down
Loading

0 comments on commit fd629d7

Please sign in to comment.