diff --git a/Base/etc/WindowServer/WindowServer.ini b/Base/etc/WindowServer/WindowServer.ini index ff231f06ef..f1132609a3 100644 --- a/Base/etc/WindowServer/WindowServer.ini +++ b/Base/etc/WindowServer/WindowServer.ini @@ -5,6 +5,10 @@ Height=768 [Theme] Name=Default +[Mouse] +AccelerationFactor=1.0 +ScrollStepSize=4 + [Cursor] Hidden=/res/cursors/hidden.png Arrow=/res/cursors/arrow.x2y2.png diff --git a/Services/WindowServer/Screen.cpp b/Services/WindowServer/Screen.cpp index 9071ec6115..f929586c50 100644 --- a/Services/WindowServer/Screen.cpp +++ b/Services/WindowServer/Screen.cpp @@ -116,11 +116,23 @@ void Screen::set_buffer(int index) ASSERT(rc == 0); } +void Screen::set_acceleration_factor(double factor) +{ + ASSERT(factor >= mouse_accel_min && factor <= mouse_accel_max); + m_acceleration_factor = factor; +} + +void Screen::set_scroll_step_size(unsigned step_size) +{ + ASSERT(step_size >= scroll_step_size_min); + m_scroll_step_size = step_size; +} + void Screen::on_receive_mouse_data(const MousePacket& packet) { auto prev_location = m_cursor_location; if (packet.is_relative) { - m_cursor_location.move_by(packet.x, packet.y); + m_cursor_location.move_by(packet.x * m_acceleration_factor, packet.y * m_acceleration_factor); #ifdef WSSCREEN_DEBUG dbgprintf("Screen: New Relative mouse point @ X %d, Y %d\n", m_cursor_location.x(), m_cursor_location.y()); #endif @@ -154,7 +166,7 @@ void Screen::on_receive_mouse_data(const MousePacket& packet) } if (packet.z) { - auto message = make(Event::MouseWheel, m_cursor_location, buttons, MouseButton::None, m_modifiers, packet.z); + auto message = make(Event::MouseWheel, m_cursor_location, buttons, MouseButton::None, m_modifiers, packet.z * m_scroll_step_size); Core::EventLoop::current().post_event(WindowManager::the(), move(message)); } diff --git a/Services/WindowServer/Screen.h b/Services/WindowServer/Screen.h index 79b4010e31..c435bc62c9 100644 --- a/Services/WindowServer/Screen.h +++ b/Services/WindowServer/Screen.h @@ -35,6 +35,10 @@ struct MousePacket; namespace WindowServer { +const double mouse_accel_max = 3.5; +const double mouse_accel_min = 0.5; +const unsigned scroll_step_size_min = 1; + class Screen { public: Screen(unsigned width, unsigned height); @@ -57,6 +61,12 @@ public: Gfx::IntPoint cursor_location() const { return m_cursor_location; } unsigned mouse_button_state() const { return m_mouse_button_state; } + double acceleration_factor() const { return m_acceleration_factor; } + void set_acceleration_factor(double); + + unsigned scroll_step_size() const { return m_scroll_step_size; } + void set_scroll_step_size(unsigned); + void on_receive_mouse_data(const MousePacket&); void on_receive_keyboard_data(::KeyEvent); @@ -76,6 +86,8 @@ private: Gfx::IntPoint m_cursor_location; unsigned m_mouse_button_state { 0 }; unsigned m_modifiers { 0 }; + double m_acceleration_factor { 1.0 }; + unsigned m_scroll_step_size { 1 }; }; inline Gfx::RGBA32* Screen::scanline(int y) diff --git a/Services/WindowServer/WindowManager.cpp b/Services/WindowServer/WindowManager.cpp index 568fde9190..1924525cc9 100644 --- a/Services/WindowServer/WindowManager.cpp +++ b/Services/WindowServer/WindowManager.cpp @@ -163,6 +163,22 @@ Gfx::IntSize WindowManager::resolution() const return Screen::the().size(); } +void WindowManager::set_acceleration_factor(double factor) +{ + Screen::the().set_acceleration_factor(factor); + dbgln("Saving acceleration factor {} to config file at {}", factor, m_config->file_name()); + m_config->write_entry("Mouse", "AccelerationFactor", String::formatted("{}", factor)); + m_config->sync(); +} + +void WindowManager::set_scroll_step_size(unsigned step_size) +{ + Screen::the().set_scroll_step_size(step_size); + dbgln("Saving scroll step size {} to config file at {}", step_size, m_config->file_name()); + m_config->write_entry("Mouse", "ScrollStepSize", String::number(step_size)); + m_config->sync(); +} + void WindowManager::add_window(Window& window) { bool is_first_window = m_windows_in_order.is_empty(); diff --git a/Services/WindowServer/WindowManager.h b/Services/WindowServer/WindowManager.h index 7350efe437..69386da1e3 100644 --- a/Services/WindowServer/WindowManager.h +++ b/Services/WindowServer/WindowManager.h @@ -145,6 +145,9 @@ public: bool set_resolution(int width, int height); Gfx::IntSize resolution() const; + void set_acceleration_factor(double); + void set_scroll_step_size(unsigned); + Window* set_active_input_window(Window*); void restore_active_input_window(Window*); void set_active_window(Window*, bool make_input = true); diff --git a/Services/WindowServer/main.cpp b/Services/WindowServer/main.cpp index 17d2d3796a..d063be9665 100644 --- a/Services/WindowServer/main.cpp +++ b/Services/WindowServer/main.cpp @@ -91,6 +91,8 @@ int main(int, char**) WindowServer::Screen screen(wm_config->read_num_entry("Screen", "Width", 1024), wm_config->read_num_entry("Screen", "Height", 768)); + screen.set_acceleration_factor(atof(wm_config->read_entry("Mouse", "AccelerationFactor", "1.0").characters())); + screen.set_scroll_step_size(wm_config->read_num_entry("Mouse", "ScrollStepSize", 4)); WindowServer::Compositor::the(); auto wm = WindowServer::WindowManager::construct(*palette); auto am = WindowServer::AppletManager::construct();