summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAndreas Kling <kling@serenityos.org>2021-03-30 23:30:50 +0200
committerAndreas Kling <kling@serenityos.org>2021-03-30 23:43:24 +0200
commit0cd60a28ba0496e829f00b1e9f6d0c4052c637f4 (patch)
tree7c6d592cd953d0b963bd0ebeffdd58c320e57c3c
parent9bbc1c9c930157ba89eb0c3554a67bf4bd6fe7cb (diff)
downloadserenity-0cd60a28ba0496e829f00b1e9f6d0c4052c637f4.zip
WindowServer+LibGUI: Plumb mouse/enter/leave events to applet windows
Since applet windows live in the applet area window, the AppletManager has to keep track of which applet is hovered and send the appropriate enter/leave events to the applet windows. This makes applet tooltips work again. :^)
-rw-r--r--Userland/Libraries/LibGUI/Widget.cpp2
-rw-r--r--Userland/Libraries/LibGUI/Window.cpp4
-rw-r--r--Userland/Libraries/LibGUI/Window.h2
-rw-r--r--Userland/MenuApplets/Audio/main.cpp6
-rw-r--r--Userland/Services/WindowServer/AppletManager.cpp26
-rw-r--r--Userland/Services/WindowServer/AppletManager.h2
-rw-r--r--Userland/Services/WindowServer/ClientConnection.cpp11
-rw-r--r--Userland/Services/WindowServer/ClientConnection.h2
-rw-r--r--Userland/Services/WindowServer/WindowServer.ipc2
9 files changed, 44 insertions, 13 deletions
diff --git a/Userland/Libraries/LibGUI/Widget.cpp b/Userland/Libraries/LibGUI/Widget.cpp
index 86bf5c8b9f..0a4b406949 100644
--- a/Userland/Libraries/LibGUI/Widget.cpp
+++ b/Userland/Libraries/LibGUI/Widget.cpp
@@ -599,7 +599,7 @@ Gfx::IntRect Widget::window_relative_rect() const
Gfx::IntRect Widget::screen_relative_rect() const
{
auto window_position = window()->window_type() == WindowType::MenuApplet
- ? window()->rect_in_menubar().location()
+ ? window()->applet_rect_on_screen().location()
: window()->rect().location();
return window_relative_rect().translated(window_position);
}
diff --git a/Userland/Libraries/LibGUI/Window.cpp b/Userland/Libraries/LibGUI/Window.cpp
index 23332112b1..e0ddab3d25 100644
--- a/Userland/Libraries/LibGUI/Window.cpp
+++ b/Userland/Libraries/LibGUI/Window.cpp
@@ -235,10 +235,10 @@ String Window::title() const
return WindowServerConnection::the().send_sync<Messages::WindowServer::GetWindowTitle>(m_window_id)->title();
}
-Gfx::IntRect Window::rect_in_menubar() const
+Gfx::IntRect Window::applet_rect_on_screen() const
{
VERIFY(m_window_type == WindowType::MenuApplet);
- return WindowServerConnection::the().send_sync<Messages::WindowServer::GetWindowRectInMenubar>(m_window_id)->rect();
+ return WindowServerConnection::the().send_sync<Messages::WindowServer::GetAppletRectOnScreen>(m_window_id)->rect();
}
Gfx::IntRect Window::rect() const
diff --git a/Userland/Libraries/LibGUI/Window.h b/Userland/Libraries/LibGUI/Window.h
index 306788d8e7..06bea7ef55 100644
--- a/Userland/Libraries/LibGUI/Window.h
+++ b/Userland/Libraries/LibGUI/Window.h
@@ -101,7 +101,7 @@ public:
int height() const { return rect().height(); }
Gfx::IntRect rect() const;
- Gfx::IntRect rect_in_menubar() const;
+ Gfx::IntRect applet_rect_on_screen() const;
Gfx::IntSize size() const { return rect().size(); }
void set_rect(const Gfx::IntRect&);
void set_rect(int x, int y, int width, int height) { set_rect({ x, y, width, height }); }
diff --git a/Userland/MenuApplets/Audio/main.cpp b/Userland/MenuApplets/Audio/main.cpp
index 4bdcaa7d86..414f40bef2 100644
--- a/Userland/MenuApplets/Audio/main.cpp
+++ b/Userland/MenuApplets/Audio/main.cpp
@@ -189,7 +189,11 @@ private:
VERIFY_NOT_REACHED();
}
- void reposition_slider_window() { m_slider_window->set_rect(window()->rect_in_menubar().x() - 20, 19, 50, 100); }
+ void reposition_slider_window()
+ {
+ auto applet_rect = window()->applet_rect_on_screen();
+ m_slider_window->set_rect(applet_rect.x() - 20, applet_rect.y() - 106, 50, 100);
+ }
struct VolumeBitmapPair {
int volume_threshold { 0 };
diff --git a/Userland/Services/WindowServer/AppletManager.cpp b/Userland/Services/WindowServer/AppletManager.cpp
index cbe7723223..a2d2d648e3 100644
--- a/Userland/Services/WindowServer/AppletManager.cpp
+++ b/Userland/Services/WindowServer/AppletManager.cpp
@@ -27,6 +27,7 @@
#include "AppletManager.h"
#include <AK/QuickSort.h>
+#include <LibCore/EventLoop.h>
#include <LibGfx/Painter.h>
#include <WindowServer/MenuManager.h>
@@ -60,21 +61,40 @@ void AppletManager::set_position(const Gfx::IntPoint& position)
m_window->set_visible(true);
}
+void AppletManager::set_hovered_applet(Window* applet)
+{
+ if (m_hovered_applet == applet)
+ return;
+
+ if (m_hovered_applet)
+ Core::EventLoop::current().post_event(*m_hovered_applet, make<Event>(Event::WindowLeft));
+
+ m_hovered_applet = applet;
+
+ if (m_hovered_applet)
+ Core::EventLoop::current().post_event(*m_hovered_applet, make<Event>(Event::WindowEntered));
+}
+
void AppletManager::event(Core::Event& event)
{
+ if (event.type() == Event::WindowLeft && m_hovered_applet) {
+ set_hovered_applet(nullptr);
+ return;
+ }
+
if (!is<MouseEvent>(event))
return;
auto& mouse_event = static_cast<MouseEvent&>(event);
- dbgln("mouse_event: {}", mouse_event.position());
-
for (auto& applet : m_applets) {
if (!applet)
continue;
if (!applet->rect_in_applet_area().contains(mouse_event.position()))
continue;
auto local_event = mouse_event.translated(-applet->rect_in_applet_area().location());
- applet->dispatch_event(local_event);
+ set_hovered_applet(applet);
+ Core::EventLoop::current().post_event(*applet, make<MouseEvent>(local_event));
+ return;
}
}
diff --git a/Userland/Services/WindowServer/AppletManager.h b/Userland/Services/WindowServer/AppletManager.h
index e55a14adfd..2b3cdd2757 100644
--- a/Userland/Services/WindowServer/AppletManager.h
+++ b/Userland/Services/WindowServer/AppletManager.h
@@ -54,9 +54,11 @@ public:
private:
void draw_applet(const Window& applet);
+ void set_hovered_applet(Window*);
Vector<WeakPtr<Window>> m_applets;
RefPtr<Window> m_window;
+ WeakPtr<Window> m_hovered_applet;
};
}
diff --git a/Userland/Services/WindowServer/ClientConnection.cpp b/Userland/Services/WindowServer/ClientConnection.cpp
index b16b708d0f..77ff8e1ab7 100644
--- a/Userland/Services/WindowServer/ClientConnection.cpp
+++ b/Userland/Services/WindowServer/ClientConnection.cpp
@@ -475,15 +475,20 @@ OwnPtr<Messages::WindowServer::GetWindowMinimumSizeResponse> ClientConnection::h
return make<Messages::WindowServer::GetWindowMinimumSizeResponse>(it->value->minimum_size());
}
-OwnPtr<Messages::WindowServer::GetWindowRectInMenubarResponse> ClientConnection::handle(const Messages::WindowServer::GetWindowRectInMenubar& message)
+OwnPtr<Messages::WindowServer::GetAppletRectOnScreenResponse> ClientConnection::handle(const Messages::WindowServer::GetAppletRectOnScreen& message)
{
int window_id = message.window_id();
auto it = m_windows.find(window_id);
if (it == m_windows.end()) {
- did_misbehave("GetWindowRectInMenubar: Bad window ID");
+ did_misbehave("GetAppletRectOnScreen: Bad window ID");
return {};
}
- return make<Messages::WindowServer::GetWindowRectInMenubarResponse>(it->value->rect_in_applet_area());
+
+ Gfx::IntRect applet_area_rect;
+ if (auto* applet_area_window = AppletManager::the().window())
+ applet_area_rect = applet_area_window->rect();
+
+ return make<Messages::WindowServer::GetAppletRectOnScreenResponse>(it->value->rect_in_applet_area().translated(applet_area_rect.location()));
}
Window* ClientConnection::window_from_id(i32 window_id)
diff --git a/Userland/Services/WindowServer/ClientConnection.h b/Userland/Services/WindowServer/ClientConnection.h
index 73650acc31..198775adc9 100644
--- a/Userland/Services/WindowServer/ClientConnection.h
+++ b/Userland/Services/WindowServer/ClientConnection.h
@@ -126,7 +126,7 @@ private:
virtual OwnPtr<Messages::WindowServer::GetWindowRectResponse> handle(const Messages::WindowServer::GetWindowRect&) override;
virtual OwnPtr<Messages::WindowServer::SetWindowMinimumSizeResponse> handle(const Messages::WindowServer::SetWindowMinimumSize&) override;
virtual OwnPtr<Messages::WindowServer::GetWindowMinimumSizeResponse> handle(const Messages::WindowServer::GetWindowMinimumSize&) override;
- virtual OwnPtr<Messages::WindowServer::GetWindowRectInMenubarResponse> handle(const Messages::WindowServer::GetWindowRectInMenubar&) override;
+ virtual OwnPtr<Messages::WindowServer::GetAppletRectOnScreenResponse> handle(const Messages::WindowServer::GetAppletRectOnScreen&) override;
virtual void handle(const Messages::WindowServer::InvalidateRect&) override;
virtual void handle(const Messages::WindowServer::DidFinishPainting&) override;
virtual OwnPtr<Messages::WindowServer::SetGlobalCursorTrackingResponse> handle(const Messages::WindowServer::SetGlobalCursorTracking&) override;
diff --git a/Userland/Services/WindowServer/WindowServer.ipc b/Userland/Services/WindowServer/WindowServer.ipc
index 13618fb1ee..fa8d70462f 100644
--- a/Userland/Services/WindowServer/WindowServer.ipc
+++ b/Userland/Services/WindowServer/WindowServer.ipc
@@ -62,7 +62,7 @@ endpoint WindowServer = 2
SetWindowMinimumSize(i32 window_id, Gfx::IntSize size) => ()
GetWindowMinimumSize(i32 window_id) => (Gfx::IntSize size)
- GetWindowRectInMenubar(i32 window_id) => (Gfx::IntRect rect)
+ GetAppletRectOnScreen(i32 window_id) => (Gfx::IntRect rect)
StartWindowResize(i32 window_id) =|