diff options
author | Andreas Kling <kling@serenityos.org> | 2021-06-07 10:20:50 +0200 |
---|---|---|
committer | Andreas Kling <kling@serenityos.org> | 2021-06-07 10:22:25 +0200 |
commit | cb295ab644875f87356df69385d2836dab8a1120 (patch) | |
tree | fe5102fe0eb306f6fad6f3ab335c7e80839c5408 | |
parent | 0ea1fd2d54771f9d24cca196a0ff26064aedc3ef (diff) | |
download | serenity-cb295ab644875f87356df69385d2836dab8a1120.zip |
WindowServer+Magnifier: Make Magnifier buttery smooth :^)
This patch moves the magnifier rect computation over to the server side
to ensure that the mouse cursor position and the screen image never get
out of sync.
5 files changed, 18 insertions, 9 deletions
diff --git a/Userland/Applications/Magnifier/MagnifierWidget.cpp b/Userland/Applications/Magnifier/MagnifierWidget.cpp index ef45843241..aa0ce2df88 100644 --- a/Userland/Applications/Magnifier/MagnifierWidget.cpp +++ b/Userland/Applications/Magnifier/MagnifierWidget.cpp @@ -39,13 +39,8 @@ void MagnifierWidget::set_scale_factor(int scale_factor) void MagnifierWidget::sync() { - m_mouse_position = GUI::WindowServerConnection::the().get_global_cursor_position(); - m_desktop_display_scale = GUI::WindowServerConnection::the().get_desktop_display_scale(); - - // Grab and paint our screenshot. - Gfx::IntSize region_size { size().width() / m_scale_factor, size().height() / m_scale_factor }; - Gfx::Rect region { (m_mouse_position.x() * m_desktop_display_scale) - (region_size.width() / 2), (m_mouse_position.y() * m_desktop_display_scale) - (region_size.height() / 2), region_size.width(), region_size.height() }; - m_grabbed_bitmap = GUI::WindowServerConnection::the().get_screen_bitmap(region).bitmap(); + Gfx::IntSize grab_size { size().width() / m_scale_factor, size().height() / m_scale_factor }; + m_grabbed_bitmap = GUI::WindowServerConnection::the().get_screen_bitmap_around_cursor(grab_size).bitmap(); update(); } diff --git a/Userland/Applications/Magnifier/MagnifierWidget.h b/Userland/Applications/Magnifier/MagnifierWidget.h index ba6d0b2c10..228667c082 100644 --- a/Userland/Applications/Magnifier/MagnifierWidget.h +++ b/Userland/Applications/Magnifier/MagnifierWidget.h @@ -23,8 +23,6 @@ private: void sync(); - Gfx::IntPoint m_mouse_position; int m_scale_factor { 2 }; - int m_desktop_display_scale { 1 }; RefPtr<Gfx::Bitmap> m_grabbed_bitmap; }; diff --git a/Userland/Services/WindowServer/ClientConnection.cpp b/Userland/Services/WindowServer/ClientConnection.cpp index af4e137b83..6fa36dd954 100644 --- a/Userland/Services/WindowServer/ClientConnection.cpp +++ b/Userland/Services/WindowServer/ClientConnection.cpp @@ -904,6 +904,20 @@ Messages::WindowServer::GetScreenBitmapResponse ClientConnection::get_screen_bit return bitmap.to_shareable_bitmap(); } +Messages::WindowServer::GetScreenBitmapAroundCursorResponse ClientConnection::get_screen_bitmap_around_cursor(Gfx::IntSize const& size) +{ + auto scale_factor = WindowManager::the().scale_factor(); + auto cursor_location = Screen::the().cursor_location(); + Gfx::Rect rect { (cursor_location.x() * scale_factor) - (size.width() / 2), (cursor_location.y() * scale_factor) - (size.height() / 2), size.width(), size.height() }; + + // Recompose the screen to make sure the cursor is painted in the location we think it is. + // FIXME: This is rather wasteful. We can probably think of a way to avoid this. + Compositor::the().compose(); + + auto bitmap = Compositor::the().front_bitmap_for_screenshot({}).cropped(rect); + return bitmap->to_shareable_bitmap(); +} + Messages::WindowServer::IsWindowModifiedResponse ClientConnection::is_window_modified(i32 window_id) { auto it = m_windows.find(window_id); diff --git a/Userland/Services/WindowServer/ClientConnection.h b/Userland/Services/WindowServer/ClientConnection.h index 3e21d9e866..4971b29359 100644 --- a/Userland/Services/WindowServer/ClientConnection.h +++ b/Userland/Services/WindowServer/ClientConnection.h @@ -147,6 +147,7 @@ private: virtual void set_scroll_step_size(u32) override; virtual Messages::WindowServer::GetScrollStepSizeResponse get_scroll_step_size() override; virtual Messages::WindowServer::GetScreenBitmapResponse get_screen_bitmap(Optional<Gfx::IntRect> const&) override; + virtual Messages::WindowServer::GetScreenBitmapAroundCursorResponse get_screen_bitmap_around_cursor(Gfx::IntSize const&) override; virtual void set_double_click_speed(i32) override; virtual Messages::WindowServer::GetDoubleClickSpeedResponse get_double_click_speed() override; virtual void set_window_modified(i32, bool) override; diff --git a/Userland/Services/WindowServer/WindowServer.ipc b/Userland/Services/WindowServer/WindowServer.ipc index ea80a98293..efddf3c2f2 100644 --- a/Userland/Services/WindowServer/WindowServer.ipc +++ b/Userland/Services/WindowServer/WindowServer.ipc @@ -121,6 +121,7 @@ endpoint WindowServer get_scroll_step_size() => (u32 step_size) get_screen_bitmap(Optional<Gfx::IntRect> rect) => (Gfx::ShareableBitmap bitmap) + get_screen_bitmap_around_cursor(Gfx::IntSize size) => (Gfx::ShareableBitmap bitmap) pong() =| |