2023-08-09 01:48:52 -07:00
|
|
|
From 7149a4637b34e291dd5a9003b6f4a421d6c1781b Mon Sep 17 00:00:00 2001
|
2014-09-21 22:47:26 -07:00
|
|
|
From: Felix Yan <felixonmars@gmail.com>
|
2014-09-23 08:30:26 -07:00
|
|
|
Date: Tue, 23 Sep 2014 23:22:17 +0800
|
2021-05-06 16:40:21 -07:00
|
|
|
Subject: [PATCH] winex11.drv: Update a candidate window's position with
|
|
|
|
over-the-spot style. (try 2)
|
2014-09-21 22:47:26 -07:00
|
|
|
|
|
|
|
In the current implementation, the candidate window position of a input
|
|
|
|
method is fixed because XNSpotLocation isn't updated after an input
|
|
|
|
context (XIC) is created in X11DRV_CreateIC().
|
|
|
|
X11DRV_UpdateCandidatePos() in this patch updates the position. You can
|
2014-09-23 08:30:26 -07:00
|
|
|
see the change of a position with ibus, scim or fcitx when input style
|
|
|
|
is set to "over the spot" in the registry key:
|
2014-09-21 22:47:26 -07:00
|
|
|
|
|
|
|
[HKEY_CURRENT_USER\Software\Wine\X11 Driver]
|
|
|
|
"InputStyle"="OverTheSpot"
|
|
|
|
|
2014-09-23 08:30:26 -07:00
|
|
|
This patch was based on the original work by Muneyuki Noguchi, and
|
|
|
|
received a lot of help from Sebastian Lackner.
|
2014-09-21 22:47:26 -07:00
|
|
|
---
|
2022-04-07 16:08:08 -07:00
|
|
|
dlls/win32u/driver.c | 7 ++++
|
2023-08-09 01:48:52 -07:00
|
|
|
dlls/win32u/input.c | 4 +++
|
2021-11-11 22:54:41 -08:00
|
|
|
dlls/winex11.drv/init.c | 1 +
|
2022-04-12 15:45:41 -07:00
|
|
|
dlls/winex11.drv/x11drv.h | 1 +
|
2023-04-03 17:40:07 -07:00
|
|
|
dlls/winex11.drv/xim.c | 70 +++++++++++++++++++++++++++++++++++++++
|
2022-04-07 16:08:08 -07:00
|
|
|
include/wine/gdi_driver.h | 2 ++
|
2023-08-09 01:48:52 -07:00
|
|
|
6 files changed, 85 insertions(+)
|
2014-09-21 22:47:26 -07:00
|
|
|
|
2021-11-11 22:54:41 -08:00
|
|
|
diff --git a/dlls/win32u/driver.c b/dlls/win32u/driver.c
|
2023-08-09 01:48:52 -07:00
|
|
|
index ed2e0973d39..2965f5f0090 100644
|
2021-11-11 22:54:41 -08:00
|
|
|
--- a/dlls/win32u/driver.c
|
|
|
|
+++ b/dlls/win32u/driver.c
|
2023-08-09 01:48:52 -07:00
|
|
|
@@ -923,6 +923,11 @@ static struct opengl_funcs *nulldrv_wine_get_wgl_driver( UINT version )
|
2022-03-02 15:13:09 -08:00
|
|
|
return (void *)-1;
|
2021-12-08 14:43:18 -08:00
|
|
|
}
|
|
|
|
|
2022-04-07 16:08:08 -07:00
|
|
|
+static void nulldrv_UpdateCandidatePos( HWND hwnd, const RECT *caret_rect )
|
2014-09-23 08:30:26 -07:00
|
|
|
+{
|
2021-12-08 14:43:18 -08:00
|
|
|
+
|
2014-09-23 08:30:26 -07:00
|
|
|
+}
|
|
|
|
+
|
2022-04-07 16:08:08 -07:00
|
|
|
static void nulldrv_ThreadDetach( void )
|
2014-09-23 08:30:26 -07:00
|
|
|
{
|
2021-11-11 22:54:41 -08:00
|
|
|
}
|
2023-08-09 01:48:52 -07:00
|
|
|
@@ -1261,6 +1266,7 @@ static const struct user_driver_funcs lazy_load_driver =
|
2022-03-19 14:45:32 -07:00
|
|
|
loaderdrv_wine_get_vulkan_driver,
|
|
|
|
/* opengl support */
|
|
|
|
nulldrv_wine_get_wgl_driver,
|
|
|
|
+ nulldrv_UpdateCandidatePos,
|
|
|
|
/* thread management */
|
|
|
|
nulldrv_ThreadDetach,
|
|
|
|
};
|
2023-08-09 01:48:52 -07:00
|
|
|
@@ -1337,6 +1343,7 @@ void __wine_set_user_driver( const struct user_driver_funcs *funcs, UINT version
|
2021-11-11 22:54:41 -08:00
|
|
|
SET_USER_FUNC(SystemParametersInfo);
|
2021-12-08 14:43:18 -08:00
|
|
|
SET_USER_FUNC(wine_get_vulkan_driver);
|
2022-03-02 15:13:09 -08:00
|
|
|
SET_USER_FUNC(wine_get_wgl_driver);
|
2021-11-11 22:54:41 -08:00
|
|
|
+ SET_USER_FUNC(UpdateCandidatePos);
|
|
|
|
SET_USER_FUNC(ThreadDetach);
|
|
|
|
#undef SET_USER_FUNC
|
|
|
|
|
2022-04-26 14:59:17 -07:00
|
|
|
diff --git a/dlls/win32u/input.c b/dlls/win32u/input.c
|
2023-08-09 01:48:52 -07:00
|
|
|
index 1f9e48423fc..9eba12c37bd 100644
|
2022-04-26 14:59:17 -07:00
|
|
|
--- a/dlls/win32u/input.c
|
|
|
|
+++ b/dlls/win32u/input.c
|
2023-08-09 01:48:52 -07:00
|
|
|
@@ -2330,6 +2330,8 @@ BOOL set_caret_pos( int x, int y )
|
2022-04-26 14:59:17 -07:00
|
|
|
r.left = x;
|
|
|
|
r.top = y;
|
|
|
|
display_caret( hwnd, &r );
|
2023-08-09 01:48:52 -07:00
|
|
|
+ if (user_driver->pUpdateCandidatePos)
|
|
|
|
+ user_driver->pUpdateCandidatePos( hwnd, &r );
|
2022-04-26 14:59:17 -07:00
|
|
|
NtUserSetSystemTimer( hwnd, SYSTEM_TIMER_CARET, caret.timeout );
|
|
|
|
}
|
|
|
|
return ret;
|
2023-08-09 01:48:52 -07:00
|
|
|
@@ -2367,6 +2369,8 @@ BOOL WINAPI NtUserShowCaret( HWND hwnd )
|
2022-04-26 14:59:17 -07:00
|
|
|
if (ret && hidden == 1) /* hidden was 1 so it's now 0 */
|
|
|
|
{
|
|
|
|
display_caret( hwnd, &r );
|
2023-08-09 01:48:52 -07:00
|
|
|
+ if (user_driver->pUpdateCandidatePos)
|
|
|
|
+ user_driver->pUpdateCandidatePos( hwnd, &r );
|
2022-04-26 14:59:17 -07:00
|
|
|
NtUserSetSystemTimer( hwnd, SYSTEM_TIMER_CARET, caret.timeout );
|
|
|
|
}
|
|
|
|
return ret;
|
2021-11-11 22:54:41 -08:00
|
|
|
diff --git a/dlls/winex11.drv/init.c b/dlls/winex11.drv/init.c
|
2023-08-09 01:48:52 -07:00
|
|
|
index c3d54da1d4d..8e277ba0003 100644
|
2021-11-11 22:54:41 -08:00
|
|
|
--- a/dlls/winex11.drv/init.c
|
|
|
|
+++ b/dlls/winex11.drv/init.c
|
2023-08-09 01:48:52 -07:00
|
|
|
@@ -437,6 +437,7 @@ static const struct user_driver_funcs x11drv_funcs =
|
2021-11-11 22:54:41 -08:00
|
|
|
.pSystemParametersInfo = X11DRV_SystemParametersInfo,
|
2021-12-08 14:43:18 -08:00
|
|
|
.pwine_get_vulkan_driver = X11DRV_wine_get_vulkan_driver,
|
2022-03-02 15:13:09 -08:00
|
|
|
.pwine_get_wgl_driver = X11DRV_wine_get_wgl_driver,
|
2021-11-11 22:54:41 -08:00
|
|
|
+ .pUpdateCandidatePos = X11DRV_UpdateCandidatePos,
|
|
|
|
.pThreadDetach = X11DRV_ThreadDetach,
|
2014-09-23 08:30:26 -07:00
|
|
|
};
|
2014-09-21 22:47:26 -07:00
|
|
|
|
2022-04-12 15:45:41 -07:00
|
|
|
diff --git a/dlls/winex11.drv/x11drv.h b/dlls/winex11.drv/x11drv.h
|
2023-08-09 01:48:52 -07:00
|
|
|
index 9ee6498a02e..ef88221202f 100644
|
2022-04-12 15:45:41 -07:00
|
|
|
--- a/dlls/winex11.drv/x11drv.h
|
|
|
|
+++ b/dlls/winex11.drv/x11drv.h
|
2023-05-23 19:06:20 -07:00
|
|
|
@@ -256,6 +256,7 @@ extern void X11DRV_WindowPosChanged( HWND hwnd, HWND insert_after, UINT swp_flag
|
2022-04-12 15:45:41 -07:00
|
|
|
struct window_surface *surface ) DECLSPEC_HIDDEN;
|
|
|
|
extern BOOL X11DRV_SystemParametersInfo( UINT action, UINT int_param, void *ptr_param,
|
|
|
|
UINT flags ) DECLSPEC_HIDDEN;
|
|
|
|
+extern void X11DRV_UpdateCandidatePos( HWND hwnd, const RECT *caret_rect ) DECLSPEC_HIDDEN;
|
|
|
|
extern void X11DRV_ThreadDetach(void) DECLSPEC_HIDDEN;
|
|
|
|
|
|
|
|
/* X11 driver internal functions */
|
2014-09-21 22:47:26 -07:00
|
|
|
diff --git a/dlls/winex11.drv/xim.c b/dlls/winex11.drv/xim.c
|
2023-08-09 01:48:52 -07:00
|
|
|
index 209d63f0402..32e5fef58db 100644
|
2014-09-21 22:47:26 -07:00
|
|
|
--- a/dlls/winex11.drv/xim.c
|
|
|
|
+++ b/dlls/winex11.drv/xim.c
|
2023-05-23 19:06:20 -07:00
|
|
|
@@ -36,6 +36,7 @@
|
2014-09-23 08:30:26 -07:00
|
|
|
#include "x11drv.h"
|
|
|
|
#include "imm.h"
|
|
|
|
#include "wine/debug.h"
|
|
|
|
+#include "wine/server.h"
|
2014-09-21 22:47:26 -07:00
|
|
|
|
2014-09-23 08:30:26 -07:00
|
|
|
WINE_DEFAULT_DEBUG_CHANNEL(xim);
|
2022-05-06 22:51:15 -07:00
|
|
|
|
2023-08-09 01:48:52 -07:00
|
|
|
@@ -438,6 +439,49 @@ void xim_thread_attach( struct x11drv_thread_data *data )
|
2023-05-23 19:06:20 -07:00
|
|
|
XRegisterIMInstantiateCallback( display, NULL, NULL, NULL, xim_open, (XPointer)data );
|
2014-09-21 22:47:26 -07:00
|
|
|
}
|
2014-09-23 08:30:26 -07:00
|
|
|
|
|
|
|
+/***********************************************************************
|
|
|
|
+ * X11DRV_UpdateCandidatePos
|
|
|
|
+ */
|
2022-04-07 16:08:08 -07:00
|
|
|
+void X11DRV_UpdateCandidatePos( HWND hwnd, const RECT *caret_rect )
|
2014-09-21 22:47:26 -07:00
|
|
|
+{
|
2023-04-05 16:14:54 -07:00
|
|
|
+ if (input_style & XIMPreeditPosition)
|
2014-09-21 22:47:26 -07:00
|
|
|
+ {
|
2014-09-23 08:30:26 -07:00
|
|
|
+ struct x11drv_win_data *data;
|
|
|
|
+ HWND parent;
|
2014-09-21 22:47:26 -07:00
|
|
|
+
|
2022-04-26 16:02:07 -07:00
|
|
|
+ for (parent = hwnd; parent && parent != NtUserGetDesktopWindow(); parent = NtUserGetAncestor( parent, GA_PARENT ))
|
2014-09-23 08:30:26 -07:00
|
|
|
+ {
|
|
|
|
+ if (!(data = get_win_data( parent ))) continue;
|
|
|
|
+ if (data->xic)
|
|
|
|
+ {
|
|
|
|
+ XVaNestedList preedit;
|
|
|
|
+ XPoint xpoint;
|
|
|
|
+ POINT pt;
|
|
|
|
+
|
|
|
|
+ pt.x = caret_rect->left;
|
|
|
|
+ pt.y = caret_rect->bottom;
|
|
|
|
+
|
|
|
|
+ if (hwnd != data->hwnd)
|
2022-04-26 16:02:07 -07:00
|
|
|
+ NtUserMapWindowPoints( hwnd, data->hwnd, &pt, 1 );
|
2014-09-23 08:30:26 -07:00
|
|
|
+
|
2022-04-26 16:02:07 -07:00
|
|
|
+ if (NtUserGetWindowLongW( data->hwnd, GWL_EXSTYLE ) & WS_EX_LAYOUTRTL)
|
2014-09-23 08:30:26 -07:00
|
|
|
+ pt.x = data->client_rect.right - data->client_rect.left - 1 - pt.x;
|
|
|
|
+
|
|
|
|
+ xpoint.x = pt.x + data->client_rect.left - data->whole_rect.left;
|
|
|
|
+ xpoint.y = pt.y + data->client_rect.top - data->whole_rect.top;
|
|
|
|
+
|
|
|
|
+ preedit = XVaCreateNestedList( 0, XNSpotLocation, &xpoint, NULL );
|
|
|
|
+ if (preedit)
|
|
|
|
+ {
|
|
|
|
+ XSetICValues( data->xic, XNPreeditAttributes, preedit, NULL );
|
|
|
|
+ XFree( preedit );
|
|
|
|
+ }
|
2014-09-21 22:47:26 -07:00
|
|
|
+ }
|
2014-09-23 08:30:26 -07:00
|
|
|
+ release_win_data( data );
|
2014-09-21 22:47:26 -07:00
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+}
|
2023-04-03 17:40:07 -07:00
|
|
|
+
|
2023-04-05 16:14:54 -07:00
|
|
|
static BOOL xic_destroy( XIC xic, XPointer user, XPointer arg )
|
2014-09-23 08:30:26 -07:00
|
|
|
{
|
2023-04-05 16:14:54 -07:00
|
|
|
struct x11drv_win_data *data;
|
2023-08-09 01:48:52 -07:00
|
|
|
@@ -491,6 +535,32 @@ static XIC xic_create( XIM xim, HWND hwnd, Window win )
|
2023-04-03 17:40:07 -07:00
|
|
|
XFree( preedit );
|
|
|
|
XFree( status );
|
2014-09-23 08:30:26 -07:00
|
|
|
|
2023-04-05 16:14:54 -07:00
|
|
|
+ if (xic != NULL && (input_style & XIMPreeditPosition))
|
2014-09-23 08:30:26 -07:00
|
|
|
+ {
|
|
|
|
+ SERVER_START_REQ( set_caret_info )
|
|
|
|
+ {
|
|
|
|
+ req->flags = 0; /* don't set anything */
|
|
|
|
+ req->handle = 0;
|
|
|
|
+ req->x = 0;
|
|
|
|
+ req->y = 0;
|
|
|
|
+ req->hide = 0;
|
|
|
|
+ req->state = 0;
|
|
|
|
+ if (!wine_server_call_err( req ))
|
|
|
|
+ {
|
|
|
|
+ HWND hwnd;
|
|
|
|
+ RECT r;
|
|
|
|
+
|
|
|
|
+ hwnd = wine_server_ptr_handle( reply->full_handle );
|
|
|
|
+ r.left = reply->old_rect.left;
|
|
|
|
+ r.top = reply->old_rect.top;
|
|
|
|
+ r.right = reply->old_rect.right;
|
|
|
|
+ r.bottom = reply->old_rect.bottom;
|
|
|
|
+ X11DRV_UpdateCandidatePos( hwnd, &r );
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+ SERVER_END_REQ;
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
return xic;
|
|
|
|
}
|
2023-04-05 16:14:54 -07:00
|
|
|
|
2021-11-11 22:54:41 -08:00
|
|
|
diff --git a/include/wine/gdi_driver.h b/include/wine/gdi_driver.h
|
2023-08-09 01:48:52 -07:00
|
|
|
index c4e859f21e5..fba67f9873e 100644
|
2021-11-11 22:54:41 -08:00
|
|
|
--- a/include/wine/gdi_driver.h
|
|
|
|
+++ b/include/wine/gdi_driver.h
|
2023-08-09 01:48:52 -07:00
|
|
|
@@ -343,6 +343,8 @@ struct user_driver_funcs
|
2022-04-07 16:08:08 -07:00
|
|
|
const struct vulkan_funcs * (*pwine_get_vulkan_driver)(UINT);
|
2022-03-02 15:13:09 -08:00
|
|
|
/* opengl support */
|
2022-04-07 16:08:08 -07:00
|
|
|
struct opengl_funcs * (*pwine_get_wgl_driver)(UINT);
|
2021-11-11 22:54:41 -08:00
|
|
|
+ /* IME functions */
|
2022-04-07 16:08:08 -07:00
|
|
|
+ void (*pUpdateCandidatePos)(HWND, const RECT *);
|
2021-11-11 22:54:41 -08:00
|
|
|
/* thread management */
|
2022-04-07 16:08:08 -07:00
|
|
|
void (*pThreadDetach)(void);
|
2021-11-11 22:54:41 -08:00
|
|
|
};
|
2014-09-21 22:47:26 -07:00
|
|
|
--
|
2023-05-23 19:06:20 -07:00
|
|
|
2.40.1
|
2014-09-21 22:47:26 -07:00
|
|
|
|