diff --git a/dlls/user32/input.c b/dlls/user32/input.c index eca8c3f115a..210cc368527 100644 --- a/dlls/user32/input.c +++ b/dlls/user32/input.c @@ -359,37 +359,6 @@ BOOL WINAPI GetCursorInfo( PCURSORINFO pci ) } -/*********************************************************************** - * SetCursorPos (USER32.@) - */ -BOOL WINAPI DECLSPEC_HOTPATCH SetCursorPos( INT x, INT y ) -{ - POINT pt = { x, y }; - BOOL ret; - INT prev_x, prev_y, new_x, new_y; - UINT dpi; - - if ((dpi = get_thread_dpi())) - pt = map_dpi_point( pt, dpi, get_monitor_dpi( MonitorFromPoint( pt, MONITOR_DEFAULTTOPRIMARY ))); - - SERVER_START_REQ( set_cursor ) - { - req->flags = SET_CURSOR_POS; - req->x = pt.x; - req->y = pt.y; - if ((ret = !wine_server_call( req ))) - { - prev_x = reply->prev_x; - prev_y = reply->prev_y; - new_x = reply->new_x; - new_y = reply->new_y; - } - } - SERVER_END_REQ; - if (ret && (prev_x != new_x || prev_y != new_y)) USER_Driver->pSetCursorPos( new_x, new_y ); - return ret; -} - /********************************************************************** * SetCapture (USER32.@) */ diff --git a/dlls/user32/sysparams.c b/dlls/user32/sysparams.c index 1b26098a413..3907c876176 100644 --- a/dlls/user32/sysparams.c +++ b/dlls/user32/sysparams.c @@ -1184,7 +1184,7 @@ BOOL WINAPI GetPhysicalCursorPos( POINT *point ) */ BOOL WINAPI SetPhysicalCursorPos( INT x, INT y ) { - return SetCursorPos( x, y ); + return NtUserSetCursorPos( x, y ); } /*********************************************************************** diff --git a/dlls/user32/user32.spec b/dlls/user32/user32.spec index c8484d0e362..47a5db3bd8f 100644 --- a/dlls/user32/user32.spec +++ b/dlls/user32/user32.spec @@ -659,7 +659,7 @@ # @ stub SetConsoleReserveKeys @ stdcall SetCursor(long) @ stub SetCursorContents -@ stdcall SetCursorPos(long long) +@ stdcall -import SetCursorPos(long long) NtUserSetCursorPos @ stdcall SetDebugErrorLevel(long) @ stdcall SetDeskWallPaper(str) # @ stub SetDeskWallpaper diff --git a/dlls/user32/winpos.c b/dlls/user32/winpos.c index 9f3303fecc0..abf9c25e6c6 100644 --- a/dlls/user32/winpos.c +++ b/dlls/user32/winpos.c @@ -2816,7 +2816,7 @@ static LONG start_size_move( HWND hwnd, WPARAM wParam, POINT *capturePoint, LONG } *capturePoint = pt; } - SetCursorPos( pt.x, pt.y ); + NtUserSetCursorPos( pt.x, pt.y ); SendMessageW( hwnd, WM_SETCURSOR, (WPARAM)hwnd, MAKELONG( hittest, WM_MOUSEMOVE )); return hittest; } @@ -2991,7 +2991,7 @@ void WINPOS_SysCommandSizeMove( HWND hwnd, WPARAM wParam ) draw_moving_frame( parent, hdc, &sizingRect, thickframe ); } - if (msg.message == WM_KEYDOWN) SetCursorPos( pt.x, pt.y ); + if (msg.message == WM_KEYDOWN) NtUserSetCursorPos( pt.x, pt.y ); else { if (!DragFullWindows) draw_moving_frame( parent, hdc, &sizingRect, thickframe ); diff --git a/dlls/win32u/driver.c b/dlls/win32u/driver.c index 58c814556c6..2caacd2b2a6 100644 --- a/dlls/win32u/driver.c +++ b/dlls/win32u/driver.c @@ -1005,6 +1005,11 @@ static void CDECL loaderdrv_SetCursor( HCURSOR cursor ) load_driver()->pSetCursor( cursor ); } +static BOOL CDECL loaderdrv_SetCursorPos( INT x, INT y ) +{ + return load_driver()->pSetCursorPos( x, y ); +} + static BOOL CDECL loaderdrv_ClipCursor( const RECT *clip ) { return load_driver()->pClipCursor( clip ); @@ -1039,6 +1044,7 @@ static const struct user_driver_funcs lazy_load_driver = .pEnumDisplaySettingsEx = loaderdrv_EnumDisplaySettingsEx, .pUpdateDisplayDevices = loaderdrv_UpdateDisplayDevices, .pSetCursor = loaderdrv_SetCursor, + .pSetCursorPos = loaderdrv_SetCursorPos, .pClipCursor = loaderdrv_ClipCursor, .pUpdateClipboard = loaderdrv_UpdateClipboard, .pScrollDC = nulldrv_ScrollDC, diff --git a/dlls/win32u/gdiobj.c b/dlls/win32u/gdiobj.c index 6a7bf2d6044..e7fbcfcbf47 100644 --- a/dlls/win32u/gdiobj.c +++ b/dlls/win32u/gdiobj.c @@ -1167,6 +1167,7 @@ static struct unix_funcs unix_funcs = NtUserMapVirtualKeyEx, NtUserScrollDC, NtUserSelectPalette, + NtUserSetCursorPos, NtUserSetSysColors, NtUserShowCursor, NtUserSystemParametersInfo, diff --git a/dlls/win32u/input.c b/dlls/win32u/input.c index 90a77639d1a..493efcd605b 100644 --- a/dlls/win32u/input.c +++ b/dlls/win32u/input.c @@ -62,6 +62,40 @@ BOOL WINAPI NtUserAttachThreadInput( DWORD from, DWORD to, BOOL attach ) return ret; } +/*********************************************************************** + * NtUserSetCursorPos (win32u.@) + */ +BOOL WINAPI NtUserSetCursorPos( INT x, INT y ) +{ + POINT pt = { x, y }; + BOOL ret; + INT prev_x, prev_y, new_x, new_y; + UINT dpi; + + if ((dpi = get_thread_dpi())) + { + HMONITOR monitor = monitor_from_point( pt, MONITOR_DEFAULTTOPRIMARY, get_thread_dpi() ); + pt = map_dpi_point( pt, dpi, get_monitor_dpi( monitor )); + } + + SERVER_START_REQ( set_cursor ) + { + req->flags = SET_CURSOR_POS; + req->x = pt.x; + req->y = pt.y; + if ((ret = !wine_server_call( req ))) + { + prev_x = reply->prev_x; + prev_y = reply->prev_y; + new_x = reply->new_x; + new_y = reply->new_y; + } + } + SERVER_END_REQ; + if (ret && (prev_x != new_x || prev_y != new_y)) user_driver->pSetCursorPos( new_x, new_y ); + return ret; +} + /*********************************************************************** * get_locale_kbd_layout */ diff --git a/dlls/win32u/sysparams.c b/dlls/win32u/sysparams.c index f409921785f..e29a05661dc 100644 --- a/dlls/win32u/sysparams.c +++ b/dlls/win32u/sysparams.c @@ -1411,6 +1411,19 @@ RECT map_dpi_rect( RECT rect, UINT dpi_from, UINT dpi_to ) return rect; } +/********************************************************************** + * map_dpi_point + */ +POINT map_dpi_point( POINT pt, UINT dpi_from, UINT dpi_to ) +{ + if (dpi_from && dpi_to && dpi_from != dpi_to) + { + pt.x = muldiv( pt.x, dpi_to, dpi_from ); + pt.y = muldiv( pt.y, dpi_to, dpi_from ); + } + return pt; +} + /* map value from system dpi to standard 96 dpi for storing in the registry */ static int map_from_system_dpi( int val ) { @@ -2002,6 +2015,13 @@ HMONITOR monitor_from_rect( const RECT *rect, DWORD flags, UINT dpi ) return ret; } +HMONITOR monitor_from_point( POINT pt, DWORD flags, UINT dpi ) +{ + RECT rect; + SetRect( &rect, pt.x, pt.y, pt.x + 1, pt.y + 1 ); + return monitor_from_rect( &rect, flags, dpi ); +} + /*********************************************************************** * NtUserGetSystemDpiForProcess (win32u.@) */ diff --git a/dlls/win32u/win32u.spec b/dlls/win32u/win32u.spec index aa2ed8ab460..fb2fcb3f293 100644 --- a/dlls/win32u/win32u.spec +++ b/dlls/win32u/win32u.spec @@ -1181,7 +1181,7 @@ @ stub NtUserSetCursor @ stub NtUserSetCursorContents @ stub NtUserSetCursorIconData -@ stub NtUserSetCursorPos +@ stdcall NtUserSetCursorPos(long long) @ stub NtUserSetDesktopColorTransform @ stub NtUserSetDesktopVisualInputSink @ stub NtUserSetDialogControlDpiChangeBehavior diff --git a/dlls/win32u/win32u_private.h b/dlls/win32u/win32u_private.h index 6594d7b10b7..0a5f6ce10b8 100644 --- a/dlls/win32u/win32u_private.h +++ b/dlls/win32u/win32u_private.h @@ -214,6 +214,7 @@ struct unix_funcs BOOL (WINAPI *pNtUserScrollDC)( HDC hdc, INT dx, INT dy, const RECT *scroll, const RECT *clip, HRGN ret_update_rgn, RECT *update_rect ); HPALETTE (WINAPI *pNtUserSelectPalette)( HDC hdc, HPALETTE hpal, WORD bkg ); + BOOL (WINAPI *pNtUserSetCursorPos)( INT x, INT y ); BOOL (WINAPI *pNtUserSetSysColors)( INT count, const INT *colors, const COLORREF *values ); INT (WINAPI *pNtUserShowCursor)( BOOL show ); BOOL (WINAPI *pNtUserSystemParametersInfo)( UINT action, UINT val, PVOID ptr, UINT winini ); @@ -251,7 +252,9 @@ extern UINT get_system_dpi(void) DECLSPEC_HIDDEN; extern int get_system_metrics( int index ) DECLSPEC_HIDDEN; extern UINT get_thread_dpi(void) DECLSPEC_HIDDEN; extern RECT get_virtual_screen_rect( UINT dpi ) DECLSPEC_HIDDEN; +extern POINT map_dpi_point( POINT pt, UINT dpi_from, UINT dpi_to ) DECLSPEC_HIDDEN; extern RECT map_dpi_rect( RECT rect, UINT dpi_from, UINT dpi_to ) DECLSPEC_HIDDEN; +extern HMONITOR monitor_from_point( POINT pt, DWORD flags, UINT dpi ) DECLSPEC_HIDDEN; extern HMONITOR monitor_from_rect( const RECT *rect, DWORD flags, UINT dpi ) DECLSPEC_HIDDEN; extern void wrappers_init( unixlib_handle_t handle ) DECLSPEC_HIDDEN; diff --git a/dlls/win32u/wrappers.c b/dlls/win32u/wrappers.c index 9dcfed5b802..8d2b553ba7b 100644 --- a/dlls/win32u/wrappers.c +++ b/dlls/win32u/wrappers.c @@ -808,6 +808,12 @@ HPALETTE WINAPI NtUserSelectPalette( HDC hdc, HPALETTE hpal, WORD bkg ) return unix_funcs->pNtUserSelectPalette( hdc, hpal, bkg ); } +BOOL WINAPI NtUserSetCursorPos( INT x, INT y ) +{ + if (!unix_funcs) return FALSE; + return unix_funcs->pNtUserSetCursorPos( x, y ); +} + BOOL WINAPI NtUserSetSysColors( INT count, const INT *colors, const COLORREF *values ) { if (!unix_funcs) return FALSE; diff --git a/include/ntuser.h b/include/ntuser.h index 11bc0bbcb44..929d773cc97 100644 --- a/include/ntuser.h +++ b/include/ntuser.h @@ -185,6 +185,7 @@ HANDLE WINAPI NtUserRemoveProp( HWND hwnd, const WCHAR *str ); BOOL WINAPI NtUserScrollDC( HDC hdc, INT dx, INT dy, const RECT *scroll, const RECT *clip, HRGN ret_update_rgn, RECT *update_rect ); HPALETTE WINAPI NtUserSelectPalette( HDC hdc, HPALETTE palette, WORD force_background ); +BOOL WINAPI NtUserSetCursorPos( INT x, INT y ); BOOL WINAPI NtUserSetKeyboardState( BYTE *state ); BOOL WINAPI NtUserSetProcessDpiAwarenessContext( ULONG awareness, ULONG unknown ); BOOL WINAPI NtUserSetProcessWindowStation( HWINSTA handle );