From 30ba3c347ced6676090496d31d85d3287adcd6da Mon Sep 17 00:00:00 2001 From: ocornut Date: Fri, 9 Feb 2024 15:40:14 +0100 Subject: [PATCH] Viewports: Fixed moving accross monitors when io.ConfigWindowsMoveFromTitleBarOnly is set. (#7299, #3071) --- docs/CHANGELOG.txt | 1 + imgui.cpp | 25 +++++++++++++++++++++---- imgui_internal.h | 1 + 3 files changed, 23 insertions(+), 4 deletions(-) diff --git a/docs/CHANGELOG.txt b/docs/CHANGELOG.txt index 42526d4a5..4dd3d4c9b 100644 --- a/docs/CHANGELOG.txt +++ b/docs/CHANGELOG.txt @@ -81,6 +81,7 @@ Docking+Viewports Branch: - Added ImGuiDockNodeFlags_DockedWindowsInFocusRoute to automatically make a dockspace connect the focus route of its docked window. This is provided a convenience in case you have windows where a connection is not explicit. (#6798) +- Viewports: Fixed moving accross monitors when io.ConfigWindowsMoveFromTitleBarOnly is set. (#7299, #3071) - Backends: OSX: Fixed not submitting Monitors info when viewports are not enabled, leading to missing e.g. DpiScale info. (#7257) [@actboy168] diff --git a/imgui.cpp b/imgui.cpp index 3ea3b80a7..5fede59fc 100644 --- a/imgui.cpp +++ b/imgui.cpp @@ -7172,10 +7172,19 @@ bool ImGui::Begin(const char* name, bool* p_open, ImGuiWindowFlags flags) } else if (window->ViewportOwned && g.PlatformIO.Monitors.Size > 0) { - // Lost windows (e.g. a monitor disconnected) will naturally moved to the fallback/dummy monitor aka the main viewport. - const ImGuiPlatformMonitor* monitor = GetViewportPlatformMonitor(window->Viewport); - visibility_rect.Min = monitor->WorkPos + visibility_padding; - visibility_rect.Max = monitor->WorkPos + monitor->WorkSize - visibility_padding; + if (g.MovingWindow != NULL && window->RootWindowDockTree == g.MovingWindow->RootWindowDockTree) + { + // While moving windows we allow them to straddle monitors (#7299, #3071) + visibility_rect = g.PlatformMonitorsFullWorkRect; + } + else + { + // When not moving ensure visible in its monitor + // Lost windows (e.g. a monitor disconnected) will naturally moved to the fallback/dummy monitor aka the main viewport. + const ImGuiPlatformMonitor* monitor = GetViewportPlatformMonitor(window->Viewport); + visibility_rect = ImRect(monitor->WorkPos, monitor->WorkPos + monitor->WorkSize); + } + visibility_rect.Expand(-visibility_padding); ClampWindowPos(window, visibility_rect); } } @@ -14818,6 +14827,7 @@ static void ImGui::UpdateViewportsNewFrame() } // Update fallback monitor + g.PlatformMonitorsFullWorkRect = ImRect(+FLT_MAX, +FLT_MAX, -FLT_MAX, -FLT_MAX); if (g.PlatformIO.Monitors.Size == 0) { ImGuiPlatformMonitor* monitor = &g.FallbackMonitor; @@ -14826,6 +14836,13 @@ static void ImGui::UpdateViewportsNewFrame() monitor->WorkPos = main_viewport->WorkPos; monitor->WorkSize = main_viewport->WorkSize; monitor->DpiScale = main_viewport->DpiScale; + g.PlatformMonitorsFullWorkRect.Add(monitor->WorkPos); + g.PlatformMonitorsFullWorkRect.Add(monitor->WorkPos + monitor->WorkSize); + } + for (ImGuiPlatformMonitor& monitor : g.PlatformIO.Monitors) + { + g.PlatformMonitorsFullWorkRect.Add(monitor.WorkPos); + g.PlatformMonitorsFullWorkRect.Add(monitor.WorkPos + monitor.WorkSize); } if (!viewports_enabled) diff --git a/imgui_internal.h b/imgui_internal.h index a4b17471b..8094b4e98 100644 --- a/imgui_internal.h +++ b/imgui_internal.h @@ -2230,6 +2230,7 @@ struct ImGuiContext ImGuiViewportP* MouseLastHoveredViewport; // Last known viewport that was hovered by mouse (even if we are not hovering any viewport any more) + honoring the _NoInputs flag. ImGuiID PlatformLastFocusedViewportId; ImGuiPlatformMonitor FallbackMonitor; // Virtual monitor used as fallback if backend doesn't provide monitor information. + ImRect PlatformMonitorsFullWorkRect; // Bounding box of all platform monitors int ViewportCreatedCount; // Unique sequential creation counter (mostly for testing/debugging) int PlatformWindowsCreatedCount; // Unique sequential creation counter (mostly for testing/debugging) int ViewportFocusedStampCount; // Every time the front-most window changes, we stamp its viewport with an incrementing counter