From cbc03c0674eba2d0101c1b4e470b62e3c239c8cb Mon Sep 17 00:00:00 2001 From: omigamedev Date: Tue, 20 Jan 2026 20:30:08 +0100 Subject: [PATCH] fix scroll direction: use RmlUi native touch API Switch from mouse event emulation to RmlUi's native touch API (ProcessTouchStart/Move/End) for natural scrolling behavior. When dragging on scrollable content, the content now follows the finger/cursor direction instead of scrolling in reverse. - Designer: Use touch API when left mouse button is pressed - Android kernel: Use touch API for all touch events --- designer/main.cpp | 24 ++++++++++++++++++++++-- src/main/cpp/kernel.cpp | 23 +++++++++++++++++------ 2 files changed, 39 insertions(+), 8 deletions(-) diff --git a/designer/main.cpp b/designer/main.cpp index 0664edb..2fc375f 100644 --- a/designer/main.cpp +++ b/designer/main.cpp @@ -59,6 +59,11 @@ static std::string g_test_output_path; // Output file for record/screenshot/hie static mosis::testing::ActionRecorder* g_action_recorder = nullptr; static mosis::testing::ActionPlayer* g_action_player = nullptr; +// Touch simulation state for natural scrolling behavior +static bool g_touch_active = false; +static int g_touch_start_x = 0; +static int g_touch_start_y = 0; + // Logging and hierarchy dump for testing static std::string g_log_file_path; // Log file path (--log) static std::string g_hierarchy_file_path; // Continuous hierarchy dump path (--hierarchy) @@ -211,12 +216,20 @@ static void MouseButtonCallback(GLFWwindow* window, int button, int action, int if (g_action_recorder && g_action_recorder->IsRecording()) { g_action_recorder->RecordMouseDown(mouseX, mouseY); } - g_context->ProcessMouseButtonDown(0, key_modifier); + // Use touch API for natural scrolling behavior + g_touch_active = true; + g_touch_start_x = mouseX; + g_touch_start_y = mouseY; + Rml::TouchList touches = {{0, Rml::Vector2f(static_cast(mouseX), static_cast(mouseY))}}; + g_context->ProcessTouchStart(touches, 0); } else if (action == GLFW_RELEASE) { if (g_action_recorder && g_action_recorder->IsRecording()) { g_action_recorder->RecordMouseUp(mouseX, mouseY); } - g_context->ProcessMouseButtonUp(0, key_modifier); + // End touch for natural scrolling + g_touch_active = false; + Rml::TouchList touches = {{0, Rml::Vector2f(static_cast(mouseX), static_cast(mouseY))}}; + g_context->ProcessTouchEnd(touches, 0); } } } @@ -234,7 +247,14 @@ static void CursorPosCallback(GLFWwindow* window, double xpos, double ypos) { int mouseX = static_cast(xpos * fbWidth / winWidth); int mouseY = static_cast(ypos * fbHeight / winHeight); + // Always update mouse position for hover effects g_context->ProcessMouseMove(mouseX, mouseY, 0); + + // If touch is active (left button pressed), also send touch move for natural scrolling + if (g_touch_active) { + Rml::TouchList touches = {{0, Rml::Vector2f(static_cast(mouseX), static_cast(mouseY))}}; + g_context->ProcessTouchMove(touches, 0); + } } static void ScrollCallback(GLFWwindow* window, double xoffset, double yoffset) { diff --git a/src/main/cpp/kernel.cpp b/src/main/cpp/kernel.cpp index 379b313..0f84c9e 100644 --- a/src/main/cpp/kernel.cpp +++ b/src/main/cpp/kernel.cpp @@ -761,9 +761,13 @@ void Kernel::on_touch_down(float x, float y) m_tasks.emplace_back([x, y](Rml::Context* context){ int px = static_cast(x * 540); int py = static_cast(y * 960); - bool move_handled = context->ProcessMouseMove(px, py, 0); - bool down_handled = context->ProcessMouseButtonDown(0, 0); - Logger::Log(std::format("Touch at ({}, {}): move={}, down={}", px, py, move_handled, down_handled)); + + // Use native touch API for proper scroll direction (natural scrolling) + // Touch ID 0 for primary touch point + Rml::TouchList touches = {{0, Rml::Vector2f(static_cast(px), static_cast(py))}}; + context->ProcessTouchStart(touches, 0); + + Logger::Log(std::format("Touch start at ({}, {})", px, py)); // Debug: Check if there's a hover element auto* hover_elem = context->GetHoverElement(); @@ -782,7 +786,11 @@ void Kernel::on_touch_move(float x, float y) Logger::Log(std::format("on_touch_move {} - {}", x, y)); std::lock_guard _lock(m_mutex); m_tasks.emplace_back([x, y](Rml::Context* context){ - context->ProcessMouseMove(static_cast(x * 540), static_cast(y * 960), 0); + int px = static_cast(x * 540); + int py = static_cast(y * 960); + // Use native touch API for proper scroll direction + Rml::TouchList touches = {{0, Rml::Vector2f(static_cast(px), static_cast(py))}}; + context->ProcessTouchMove(touches, 0); }); } @@ -791,8 +799,11 @@ void Kernel::on_touch_up(float x, float y) Logger::Log(std::format("on_touch_up {} - {}", x, y)); std::lock_guard _lock(m_mutex); m_tasks.emplace_back([x, y](Rml::Context* context){ - context->ProcessMouseMove(static_cast(x * 540), static_cast(y * 960), 0); - context->ProcessMouseButtonUp(0, 0); + int px = static_cast(x * 540); + int py = static_cast(y * 960); + // Use native touch API for proper scroll direction + Rml::TouchList touches = {{0, Rml::Vector2f(static_cast(px), static_cast(py))}}; + context->ProcessTouchEnd(touches, 0); }); }