From 78d9262b0515588769276aea142d8198fa626b81 Mon Sep 17 00:00:00 2001 From: nothingTVatYT Date: Fri, 1 Dec 2023 21:25:00 +0100 Subject: [PATCH 1/2] skip WM for non-regular windows and add mouse tracking --- .../Engine/Platform/Linux/LinuxPlatform.cpp | 33 ++++++++++++++++--- Source/Engine/Platform/Linux/LinuxPlatform.h | 2 ++ Source/Engine/Platform/Linux/LinuxWindow.cpp | 19 ++++++++--- 3 files changed, 45 insertions(+), 9 deletions(-) diff --git a/Source/Engine/Platform/Linux/LinuxPlatform.cpp b/Source/Engine/Platform/Linux/LinuxPlatform.cpp index a7634710f..83c3e3ae6 100644 --- a/Source/Engine/Platform/Linux/LinuxPlatform.cpp +++ b/Source/Engine/Platform/Linux/LinuxPlatform.cpp @@ -94,6 +94,7 @@ X11::XcursorImage* CursorsImg[(int32)CursorType::MAX]; Dictionary KeyNameMap; Array KeyCodeMap; Delegate LinuxPlatform::xEventRecieved; +const Window* mouseTrackingWindow; // Message boxes configuration #define LINUX_DIALOG_MIN_BUTTON_WIDTH 64 @@ -1917,6 +1918,8 @@ bool LinuxPlatform::Init() if (PlatformBase::Init()) return true; + mouseTrackingWindow = nullptr; + char fileNameBuffer[1024]; // Init timing @@ -2260,6 +2263,17 @@ bool LinuxPlatform::Init() return false; } +void LinuxPlatform::StartTrackingMouse(const Window* window) +{ + mouseTrackingWindow = window; +} + +void LinuxPlatform::EndTrackingMouse(const Window* window) +{ + if (mouseTrackingWindow == window) + mouseTrackingWindow = nullptr; +} + void LinuxPlatform::BeforeRun() { } @@ -2398,7 +2412,7 @@ void LinuxPlatform::Tick() // Update input context focus X11::XSetICFocus(IC); window = WindowsManager::GetByNativePtr((void*)event.xfocus.window); - if (window) + if (window && mouseTrackingWindow == nullptr) { window->OnGotFocus(); } @@ -2407,7 +2421,7 @@ void LinuxPlatform::Tick() // Update input context focus X11::XUnsetICFocus(IC); window = WindowsManager::GetByNativePtr((void*)event.xfocus.window); - if (window) + if (window && mouseTrackingWindow == nullptr) { window->OnLostFocus(); } @@ -2514,23 +2528,32 @@ void LinuxPlatform::Tick() break; case ButtonPress: window = WindowsManager::GetByNativePtr((void*)event.xbutton.window); - if (window) + if (mouseTrackingWindow) + ((LinuxWindow*)mouseTrackingWindow)->OnButtonPress(&event.xbutton); + else if (window) window->OnButtonPress(&event.xbutton); break; case ButtonRelease: window = WindowsManager::GetByNativePtr((void*)event.xbutton.window); - if (window) + if (mouseTrackingWindow) + ((LinuxWindow*)mouseTrackingWindow)->OnButtonRelease(&event.xbutton); + else if (window) window->OnButtonRelease(&event.xbutton); break; case MotionNotify: window = WindowsManager::GetByNativePtr((void*)event.xmotion.window); - if (window) + if (mouseTrackingWindow) + ((LinuxWindow*)mouseTrackingWindow)->OnMotionNotify(&event.xmotion); + else if (window) window->OnMotionNotify(&event.xmotion); break; case EnterNotify: + // nothing? break; case LeaveNotify: window = WindowsManager::GetByNativePtr((void*)event.xcrossing.window); + if (mouseTrackingWindow) + ((LinuxWindow*)mouseTrackingWindow)->OnLeaveNotify(&event.xcrossing); if (window) window->OnLeaveNotify(&event.xcrossing); break; diff --git a/Source/Engine/Platform/Linux/LinuxPlatform.h b/Source/Engine/Platform/Linux/LinuxPlatform.h index 54590adf2..00e7743d7 100644 --- a/Source/Engine/Platform/Linux/LinuxPlatform.h +++ b/Source/Engine/Platform/Linux/LinuxPlatform.h @@ -139,6 +139,8 @@ public: static String GetWorkingDirectory(); static bool SetWorkingDirectory(const String& path); static Window* CreateWindow(const CreateWindowSettings& settings); + static void StartTrackingMouse(const Window* window); + static void EndTrackingMouse(const Window *window); static void GetEnvironmentVariables(Dictionary& result); static bool GetEnvironmentVariable(const String& name, String& value); static bool SetEnvironmentVariable(const String& name, const String& value); diff --git a/Source/Engine/Platform/Linux/LinuxWindow.cpp b/Source/Engine/Platform/Linux/LinuxWindow.cpp index b3bae0276..9168beb29 100644 --- a/Source/Engine/Platform/Linux/LinuxWindow.cpp +++ b/Source/Engine/Platform/Linux/LinuxWindow.cpp @@ -54,7 +54,7 @@ LinuxWindow::LinuxWindow(const CreateWindowSettings& settings) return; auto screen = XDefaultScreen(display); - // Cache data + // Cache data int32 width = Math::TruncToInt(settings.Size.X); int32 height = Math::TruncToInt(settings.Size.Y); _clientSize = Float2((float)width, (float)height); @@ -111,6 +111,12 @@ LinuxWindow::LinuxWindow(const CreateWindowSettings& settings) windowAttributes.border_pixel = XBlackPixel(display, screen); windowAttributes.event_mask = KeyPressMask | KeyReleaseMask | StructureNotifyMask | ExposureMask; + if (!settings.IsRegularWindow) + { + windowAttributes.save_under = true; + windowAttributes.override_redirect = true; + } + // TODO: implement all window settings /* bool Fullscreen; @@ -118,11 +124,16 @@ LinuxWindow::LinuxWindow(const CreateWindowSettings& settings) bool AllowMaximize; */ + unsigned long valueMask = CWBackPixel | CWBorderPixel | CWEventMask | CWColormap; + if (!settings.IsRegularWindow) + { + valueMask |= CWOverrideRedirect | CWSaveUnder; + } const X11::Window window = X11::XCreateWindow( display, X11::XRootWindow(display, screen), x, y, width, height, 0, visualInfo->depth, InputOutput, visualInfo->visual, - CWBackPixel | CWBorderPixel | CWEventMask | CWColormap, &windowAttributes); + valueMask, &windowAttributes); _window = window; LinuxWindow::SetTitle(settings.Title); @@ -811,12 +822,12 @@ void LinuxWindow::SetTitle(const StringView& title) void LinuxWindow::StartTrackingMouse(bool useMouseScreenOffset) { - // TODO: impl this + LinuxPlatform::StartTrackingMouse(this); } void LinuxWindow::EndTrackingMouse() { - // TODO: impl this + LinuxPlatform::EndTrackingMouse(this); } void LinuxWindow::SetCursor(CursorType type) From c0ef2a1f5855d09d4f1a16da0d4cde01861d2bd5 Mon Sep 17 00:00:00 2001 From: Wojtek Figat Date: Sat, 16 Dec 2023 12:39:10 +0100 Subject: [PATCH 2/2] Cleamnup code for #2020 and use internal pointer for current tracking window --- .../Engine/Platform/Linux/LinuxPlatform.cpp | 36 ++++++------------- Source/Engine/Platform/Linux/LinuxPlatform.h | 2 -- Source/Engine/Platform/Linux/LinuxWindow.cpp | 6 ++-- 3 files changed, 15 insertions(+), 29 deletions(-) diff --git a/Source/Engine/Platform/Linux/LinuxPlatform.cpp b/Source/Engine/Platform/Linux/LinuxPlatform.cpp index 83c3e3ae6..41a2a33f6 100644 --- a/Source/Engine/Platform/Linux/LinuxPlatform.cpp +++ b/Source/Engine/Platform/Linux/LinuxPlatform.cpp @@ -94,7 +94,7 @@ X11::XcursorImage* CursorsImg[(int32)CursorType::MAX]; Dictionary KeyNameMap; Array KeyCodeMap; Delegate LinuxPlatform::xEventRecieved; -const Window* mouseTrackingWindow; +Window* MouseTrackingWindow = nullptr; // Message boxes configuration #define LINUX_DIALOG_MIN_BUTTON_WIDTH 64 @@ -1917,9 +1917,6 @@ bool LinuxPlatform::Init() { if (PlatformBase::Init()) return true; - - mouseTrackingWindow = nullptr; - char fileNameBuffer[1024]; // Init timing @@ -2263,17 +2260,6 @@ bool LinuxPlatform::Init() return false; } -void LinuxPlatform::StartTrackingMouse(const Window* window) -{ - mouseTrackingWindow = window; -} - -void LinuxPlatform::EndTrackingMouse(const Window* window) -{ - if (mouseTrackingWindow == window) - mouseTrackingWindow = nullptr; -} - void LinuxPlatform::BeforeRun() { } @@ -2412,7 +2398,7 @@ void LinuxPlatform::Tick() // Update input context focus X11::XSetICFocus(IC); window = WindowsManager::GetByNativePtr((void*)event.xfocus.window); - if (window && mouseTrackingWindow == nullptr) + if (window && MouseTrackingWindow == nullptr) { window->OnGotFocus(); } @@ -2421,7 +2407,7 @@ void LinuxPlatform::Tick() // Update input context focus X11::XUnsetICFocus(IC); window = WindowsManager::GetByNativePtr((void*)event.xfocus.window); - if (window && mouseTrackingWindow == nullptr) + if (window && MouseTrackingWindow == nullptr) { window->OnLostFocus(); } @@ -2528,22 +2514,22 @@ void LinuxPlatform::Tick() break; case ButtonPress: window = WindowsManager::GetByNativePtr((void*)event.xbutton.window); - if (mouseTrackingWindow) - ((LinuxWindow*)mouseTrackingWindow)->OnButtonPress(&event.xbutton); + if (MouseTrackingWindow) + MouseTrackingWindow->OnButtonPress(&event.xbutton); else if (window) window->OnButtonPress(&event.xbutton); break; case ButtonRelease: window = WindowsManager::GetByNativePtr((void*)event.xbutton.window); - if (mouseTrackingWindow) - ((LinuxWindow*)mouseTrackingWindow)->OnButtonRelease(&event.xbutton); + if (MouseTrackingWindow) + MouseTrackingWindow->OnButtonRelease(&event.xbutton); else if (window) window->OnButtonRelease(&event.xbutton); break; case MotionNotify: window = WindowsManager::GetByNativePtr((void*)event.xmotion.window); - if (mouseTrackingWindow) - ((LinuxWindow*)mouseTrackingWindow)->OnMotionNotify(&event.xmotion); + if (MouseTrackingWindow) + MouseTrackingWindow->OnMotionNotify(&event.xmotion); else if (window) window->OnMotionNotify(&event.xmotion); break; @@ -2552,8 +2538,8 @@ void LinuxPlatform::Tick() break; case LeaveNotify: window = WindowsManager::GetByNativePtr((void*)event.xcrossing.window); - if (mouseTrackingWindow) - ((LinuxWindow*)mouseTrackingWindow)->OnLeaveNotify(&event.xcrossing); + if (MouseTrackingWindow) + MouseTrackingWindow->OnLeaveNotify(&event.xcrossing); if (window) window->OnLeaveNotify(&event.xcrossing); break; diff --git a/Source/Engine/Platform/Linux/LinuxPlatform.h b/Source/Engine/Platform/Linux/LinuxPlatform.h index 00e7743d7..54590adf2 100644 --- a/Source/Engine/Platform/Linux/LinuxPlatform.h +++ b/Source/Engine/Platform/Linux/LinuxPlatform.h @@ -139,8 +139,6 @@ public: static String GetWorkingDirectory(); static bool SetWorkingDirectory(const String& path); static Window* CreateWindow(const CreateWindowSettings& settings); - static void StartTrackingMouse(const Window* window); - static void EndTrackingMouse(const Window *window); static void GetEnvironmentVariables(Dictionary& result); static bool GetEnvironmentVariable(const String& name, String& value); static bool SetEnvironmentVariable(const String& name, const String& value); diff --git a/Source/Engine/Platform/Linux/LinuxWindow.cpp b/Source/Engine/Platform/Linux/LinuxWindow.cpp index 9168beb29..9004ed84c 100644 --- a/Source/Engine/Platform/Linux/LinuxWindow.cpp +++ b/Source/Engine/Platform/Linux/LinuxWindow.cpp @@ -40,6 +40,7 @@ extern X11::Atom xAtomWmName; extern Dictionary KeyNameMap; extern Array KeyCodeMap; extern X11::Cursor Cursors[(int32)CursorType::MAX]; +extern Window* MouseTrackingWindow; static constexpr uint32 MouseDoubleClickTime = 500; static constexpr uint32 MaxDoubleClickDistanceSquared = 10; @@ -822,12 +823,13 @@ void LinuxWindow::SetTitle(const StringView& title) void LinuxWindow::StartTrackingMouse(bool useMouseScreenOffset) { - LinuxPlatform::StartTrackingMouse(this); + MouseTrackingWindow = this; } void LinuxWindow::EndTrackingMouse() { - LinuxPlatform::EndTrackingMouse(this); + if (MouseTrackingWindow == this) + MouseTrackingWindow = nullptr; } void LinuxWindow::SetCursor(CursorType type)