[PATCH 0/3] MR10951: wineandroid: Fix focus, activation and duplicate input issues
These changes fix several wineandroid focus and input handling bugs I discovered while tinkering with Wine Android, particularly while testing VirtualBox on Android 8.1. Changes included: - keep keyboard focus on whole Wine views instead of client rendering surfaces - request focus for the desktop view immediately after startup - ignore duplicate primary button motion events reported by some Android devices Together these changes fix issues such as: - keyboard input not working until focus changes externally - duplicate mouse button events breaking capture state - inconsistent focus behavior between client and whole views -- https://gitlab.winehq.org/wine/wine/-/merge_requests/10951
From: Twaik Yont <9674930+twaik@users.noreply.github.com> Client Wine views are rendering targets for GL/Vulkan client surfaces. They should not become independent Android keyboard focus targets, because input is dispatched by Wine window state, not by the rendering surface itself. Make client Wine views non-focusable and keep keyboard focus on the whole Wine view. Pointer/key input can then be handled by the parent Wine window while the client view remains only a drawable surface. Signed-off-by: Twaik Yont <9674930+twaik@users.noreply.github.com> --- dlls/wineandroid.drv/WineActivity.java | 9 ++------- 1 file changed, 2 insertions(+), 7 deletions(-) diff --git a/dlls/wineandroid.drv/WineActivity.java b/dlls/wineandroid.drv/WineActivity.java index 1ee99b8a037..1050349f536 100644 --- a/dlls/wineandroid.drv/WineActivity.java +++ b/dlls/wineandroid.drv/WineActivity.java @@ -615,11 +615,6 @@ public WineView create_view( boolean is_client ) if (content_view != null) return content_view; content_view = new WineView( WineActivity.this, win, is_client ); addView( content_view ); - if (!is_client) - { - content_view.setFocusable( true ); - content_view.setFocusableInTouchMode( true ); - } return content_view; } @@ -656,8 +651,8 @@ public WineView( Context c, WineWindow win, boolean client ) setSurfaceTextureListener( this ); setVisibility( VISIBLE ); setOpaque( false ); - setFocusable( true ); - setFocusableInTouchMode( true ); + setFocusable( !client ); + setFocusableInTouchMode( !client ); } public WineWindow get_window() -- GitLab https://gitlab.winehq.org/wine/wine/-/merge_requests/10951
From: Twaik Yont <9674930+twaik@users.noreply.github.com> Android key events are delivered to the focused view before Wine turns them into hardware input. Request focus for the desktop whole view after it is added, so keyboard input works immediately after activity startup without relying on a later focus transition such as switching through Recents. Signed-off-by: Twaik Yont <9674930+twaik@users.noreply.github.com> --- dlls/wineandroid.drv/WineActivity.java | 1 + 1 file changed, 1 insertion(+) diff --git a/dlls/wineandroid.drv/WineActivity.java b/dlls/wineandroid.drv/WineActivity.java index 1050349f536..5a1063f96cd 100644 --- a/dlls/wineandroid.drv/WineActivity.java +++ b/dlls/wineandroid.drv/WineActivity.java @@ -796,6 +796,7 @@ public void create_window( int hwnd, boolean is_desktop, boolean opengl, int par desktop_window = win; top_view.addView( desktop_window.create_whole_view() ); desktop_window.client_group.bringToFront(); + desktop_window.window_group.get_content_view().requestFocus(); } } if (opengl) win.create_client_view(); -- GitLab https://gitlab.winehq.org/wine/wine/-/merge_requests/10951
From: Twaik Yont <9674930+twaik@users.noreply.github.com> Some Android devices report primary mouse button clicks through both touch down/up and generic motion button press/release events. Forwarding both paths to Wine produces duplicate mouse button input, which can desynchronize button state and interfere with capture or window activation after dragging windows. Ignore generic motion primary button press/release events and keep using the touch path for the primary button. Leave non-primary buttons on the generic motion path, since they may not be reported as touch events. Signed-off-by: Twaik Yont <9674930+twaik@users.noreply.github.com> --- dlls/wineandroid.drv/WineActivity.java | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/dlls/wineandroid.drv/WineActivity.java b/dlls/wineandroid.drv/WineActivity.java index 5a1063f96cd..1f1d12d7ee4 100644 --- a/dlls/wineandroid.drv/WineActivity.java +++ b/dlls/wineandroid.drv/WineActivity.java @@ -704,6 +704,16 @@ public boolean onGenericMotionEvent( MotionEvent event ) if ((event.getSource() & InputDevice.SOURCE_CLASS_POINTER) != 0) { + /* Primary button press/release is also reported through touch down/up + * on some Android devices. Sending both paths to Wine leaves it with + * duplicate mouse button events, which can desynchronize button state + * and break capture/activation after window moves. + */ + if ((event.getActionMasked() == MotionEvent.ACTION_BUTTON_PRESS || + event.getActionMasked() == MotionEvent.ACTION_BUTTON_RELEASE) && + event.getActionButton() == MotionEvent.BUTTON_PRIMARY) + return true; + int[] pos = new int[2]; window.get_event_pos( event, pos ); Log.i( LOGTAG, String.format( "view motion event win %08x action %d pos %d,%d buttons %04x view %d,%d", -- GitLab https://gitlab.winehq.org/wine/wine/-/merge_requests/10951
participants (2)
-
Twaik Yont -
Twaik Yont (@twaik)