From: Sergei Chernyadyev serg.cherniadjev@gmail.com
--- dlls/win32u/driver.c | 46 ++++++++++++++++++++++++++++++---- dlls/win32u/systray.c | 10 ++++++-- dlls/winemac.drv/gdi.c | 5 +++- dlls/winemac.drv/macdrv.h | 5 +++- dlls/winemac.drv/systray.c | 49 ++++++++++++++----------------------- dlls/wow64win/user.c | 3 ++- include/ntuser.h | 5 +++- include/wine/gdi_driver.h | 5 +++- programs/explorer/systray.c | 33 +++++++++++++++++++++++-- 9 files changed, 117 insertions(+), 44 deletions(-)
diff --git a/dlls/win32u/driver.c b/dlls/win32u/driver.c index 3b6187d678e..ab7faf436c3 100644 --- a/dlls/win32u/driver.c +++ b/dlls/win32u/driver.c @@ -766,7 +766,22 @@ static BOOL nulldrv_ClipCursor( const RECT *clip, BOOL reset ) return TRUE; }
-static LRESULT nulldrv_NotifyIcon( HWND hwnd, UINT msg, NOTIFYICONDATAW *data ) +static LRESULT nulldrv_AddNotifyIcon( HWND hwnd, NOTIFYICONDATAW *data ) +{ + return -1; +} + +static LRESULT nulldrv_ModifyNotifyIcon( HWND hwnd, NOTIFYICONDATAW *data ) +{ + return -1; +} + +static LRESULT nulldrv_DeleteNotifyIcon( HWND hwnd, UINT uID ) +{ + return -1; +} + +static LRESULT nulldrv_SetNotifyIconVersion( HWND hwnd, UINT uID, UINT uVersion ) { return -1; } @@ -1189,9 +1204,24 @@ static BOOL loaderdrv_ClipCursor( const RECT *clip, BOOL reset ) return load_driver()->pClipCursor( clip, reset ); }
-static LRESULT loaderdrv_NotifyIcon( HWND hwnd, UINT msg, NOTIFYICONDATAW *data ) +static LRESULT loaderdrv_AddNotifyIcon( HWND hwnd, NOTIFYICONDATAW *data ) +{ + return load_driver()->pAddNotifyIcon( hwnd, data ); +} + +static LRESULT loaderdrv_ModifyNotifyIcon( HWND hwnd, NOTIFYICONDATAW *data ) +{ + return load_driver()->pModifyNotifyIcon( hwnd, data ); +} + +static LRESULT loaderdrv_DeleteNotifyIcon( HWND hwnd, UINT uID ) +{ + return load_driver()->pDeleteNotifyIcon( hwnd, uID ); +} + +static LRESULT loaderdrv_SetNotifyIconVersion( HWND hwnd, UINT uID, UINT uVersion ) { - return load_driver()->pNotifyIcon( hwnd, msg, data ); + return load_driver()->pSetNotifyIconVersion( hwnd, uID, uVersion ); }
static void loaderdrv_CleanupIcons( HWND hwnd ) @@ -1311,7 +1341,10 @@ static const struct user_driver_funcs lazy_load_driver = loaderdrv_SetCursorPos, loaderdrv_ClipCursor, /* systray functions */ - loaderdrv_NotifyIcon, + loaderdrv_AddNotifyIcon, + loaderdrv_ModifyNotifyIcon, + loaderdrv_DeleteNotifyIcon, + loaderdrv_SetNotifyIconVersion, loaderdrv_CleanupIcons, loaderdrv_SystrayDockInit, loaderdrv_SystrayDockInsert, @@ -1402,7 +1435,10 @@ void __wine_set_user_driver( const struct user_driver_funcs *funcs, UINT version SET_USER_FUNC(GetCursorPos); SET_USER_FUNC(SetCursorPos); SET_USER_FUNC(ClipCursor); - SET_USER_FUNC(NotifyIcon); + SET_USER_FUNC(AddNotifyIcon); + SET_USER_FUNC(ModifyNotifyIcon); + SET_USER_FUNC(DeleteNotifyIcon); + SET_USER_FUNC(SetNotifyIconVersion); SET_USER_FUNC(CleanupIcons); SET_USER_FUNC(SystrayDockInit); SET_USER_FUNC(SystrayDockInsert); diff --git a/dlls/win32u/systray.c b/dlls/win32u/systray.c index 73e344e90e7..3a62fa7c986 100644 --- a/dlls/win32u/systray.c +++ b/dlls/win32u/systray.c @@ -35,8 +35,14 @@ LRESULT system_tray_call( HWND hwnd, UINT msg, WPARAM wparam, LPARAM lparam, voi { switch (msg) { - case WINE_SYSTRAY_NOTIFY_ICON: - return user_driver->pNotifyIcon( hwnd, wparam, data ); + case WINE_SYSTRAY_ADD_NOTIFY_ICON: + return user_driver->pAddNotifyIcon( hwnd, data ); + case WINE_SYSTRAY_MODIFY_NOTIFY_ICON: + return user_driver->pModifyNotifyIcon( hwnd, data ); + case WINE_SYSTRAY_DELETE_NOTIFY_ICON: + return user_driver->pDeleteNotifyIcon( hwnd, wparam ); + case WINE_SYSTRAY_SET_NOTIFY_ICON_VERSION: + return user_driver->pSetNotifyIconVersion( hwnd, wparam, lparam ); case WINE_SYSTRAY_CLEANUP_ICONS: user_driver->pCleanupIcons( hwnd ); return 0; diff --git a/dlls/winemac.drv/gdi.c b/dlls/winemac.drv/gdi.c index 6c2241514a9..648e0f7e2f7 100644 --- a/dlls/winemac.drv/gdi.c +++ b/dlls/winemac.drv/gdi.c @@ -269,7 +269,10 @@ static const struct user_driver_funcs macdrv_funcs = .pBeep = macdrv_Beep, .pChangeDisplaySettings = macdrv_ChangeDisplaySettings, .pClipCursor = macdrv_ClipCursor, - .pNotifyIcon = macdrv_NotifyIcon, + .pAddNotifyIcon = macdrv_AddNotifyIcon, + .pModifyNotifyIcon = macdrv_ModifyNotifyIcon, + .pDeleteNotifyIcon = macdrv_DeleteNotifyIcon, + .pSetNotifyIconVersion = macdrv_SetNotifyIconVersion, .pCleanupIcons = macdrv_CleanupIcons, .pClipboardWindowProc = macdrv_ClipboardWindowProc, .pDesktopWindowProc = macdrv_DesktopWindowProc, diff --git a/dlls/winemac.drv/macdrv.h b/dlls/winemac.drv/macdrv.h index e1dd1c61b3f..6574091950f 100644 --- a/dlls/winemac.drv/macdrv.h +++ b/dlls/winemac.drv/macdrv.h @@ -134,7 +134,10 @@ extern BOOL macdrv_UpdateDisplayDevices( const struct gdi_device_manager *device extern BOOL macdrv_GetDeviceGammaRamp(PHYSDEV dev, LPVOID ramp); extern BOOL macdrv_SetDeviceGammaRamp(PHYSDEV dev, LPVOID ramp); extern BOOL macdrv_ClipCursor(const RECT *clip, BOOL reset); -extern LRESULT macdrv_NotifyIcon(HWND hwnd, UINT msg, NOTIFYICONDATAW *data); +extern LRESULT macdrv_AddNotifyIcon(HWND hwnd, NOTIFYICONDATAW *data); +extern LRESULT macdrv_ModifyNotifyIcon(HWND hwnd, NOTIFYICONDATAW *data); +extern LRESULT macdrv_DeleteNotifyIcon(HWND hwnd, UINT uID); +extern LRESULT macdrv_SetNotifyIconVersion(HWND hwnd, UINT uID, UINT uVersion); extern void macdrv_CleanupIcons(HWND hwnd); extern LRESULT macdrv_DesktopWindowProc(HWND hwnd, UINT msg, WPARAM wparam, LPARAM lparam); extern void macdrv_DestroyWindow(HWND hwnd); diff --git a/dlls/winemac.drv/systray.c b/dlls/winemac.drv/systray.c index 0231e08e82b..4852530055e 100644 --- a/dlls/winemac.drv/systray.c +++ b/dlls/winemac.drv/systray.c @@ -88,16 +88,19 @@ static struct tray_icon *get_icon(HWND owner, UINT id)
/*********************************************************************** - * modify_icon + * macdrv_ModifyNotifyIcon * * Modifies an existing tray icon and updates its status item as needed. */ -static BOOL modify_icon(struct tray_icon *icon, NOTIFYICONDATAW *nid) +LRESULT macdrv_ModifyNotifyIcon(HWND hwnd, NOTIFYICONDATAW *nid) { BOOL update_image = FALSE, update_tooltip = FALSE; + struct tray_icon *icon = get_icon(nid->hWnd, nid->uID);
TRACE("hwnd %p id 0x%x flags %x\n", nid->hWnd, nid->uID, nid->uFlags);
+ if (!icon) return FALSE; + if (nid->uFlags & NIF_STATE) { DWORD changed = (icon->state ^ nid->dwState) & nid->dwStateMask; @@ -185,7 +188,7 @@ static BOOL modify_icon(struct tray_icon *icon, NOTIFYICONDATAW *nid) * * Creates a new tray icon structure and adds it to the list. */ -static BOOL add_icon(NOTIFYICONDATAW *nid) +LRESULT macdrv_AddNotifyIcon(HWND hwnd, NOTIFYICONDATAW *nid) { NOTIFYICONDATAW new_nid; struct tray_icon *icon; @@ -218,7 +221,7 @@ static BOOL add_icon(NOTIFYICONDATAW *nid) new_nid.dwStateMask |= NIS_HIDDEN; nid = &new_nid; } - return modify_icon(icon, nid); + return macdrv_ModifyNotifyIcon(hwnd, nid); }
@@ -242,38 +245,24 @@ static BOOL delete_icon(struct tray_icon *icon) return TRUE; }
+LRESULT macdrv_DeleteNotifyIcon(HWND hwnd, UINT uID) +{ + struct tray_icon *icon = get_icon(hwnd, uID); + if (!icon) return FALSE;
+ return delete_icon(icon); +} /*********************************************************************** * NotifyIcon (MACDRV.@) */ -LRESULT macdrv_NotifyIcon(HWND hwnd, UINT msg, NOTIFYICONDATAW *data) +LRESULT macdrv_SetNotifyIconVersion(HWND hwnd, UINT uID, UINT uVersion) { - BOOL ret = FALSE; - struct tray_icon *icon; + struct tray_icon *icon = get_icon(hwnd, uID);
- switch (msg) - { - case NIM_ADD: - ret = add_icon(data); - break; - case NIM_DELETE: - if ((icon = get_icon(data->hWnd, data->uID))) ret = delete_icon(icon); - break; - case NIM_MODIFY: - if ((icon = get_icon(data->hWnd, data->uID))) ret = modify_icon(icon, data); - break; - case NIM_SETVERSION: - if ((icon = get_icon(data->hWnd, data->uID))) - { - icon->version = data->uVersion; - ret = TRUE; - } - break; - default: - ERR("Unexpected NotifyIconProc call\n"); - return -1; - } - return ret; + if (!icon) return FALSE; + + icon->version = uVersion; + return TRUE; }
static BOOL notify_owner(struct tray_icon *icon, UINT msg, int x, int y) diff --git a/dlls/wow64win/user.c b/dlls/wow64win/user.c index ff78e74cc7a..aee16e5261f 100644 --- a/dlls/wow64win/user.c +++ b/dlls/wow64win/user.c @@ -3624,7 +3624,8 @@ NTSTATUS WINAPI wow64_NtUserMessageCall( UINT *args )
return NtUserMessageCall( hwnd, msg, wparam, lparam, &balloon_params, type, ansi ); } - case WINE_SYSTRAY_NOTIFY_ICON: + case WINE_SYSTRAY_ADD_NOTIFY_ICON: + case WINE_SYSTRAY_MODIFY_NOTIFY_ICON: { struct { diff --git a/include/ntuser.h b/include/ntuser.h index eb416df71cb..d188c7bb92c 100644 --- a/include/ntuser.h +++ b/include/ntuser.h @@ -524,7 +524,10 @@ struct ime_driver_call_params /* NtUserSystemTrayCall calls */ enum wine_systray_call { - WINE_SYSTRAY_NOTIFY_ICON, + WINE_SYSTRAY_ADD_NOTIFY_ICON, + WINE_SYSTRAY_MODIFY_NOTIFY_ICON, + WINE_SYSTRAY_DELETE_NOTIFY_ICON, + WINE_SYSTRAY_SET_NOTIFY_ICON_VERSION, WINE_SYSTRAY_CLEANUP_ICONS, WINE_SYSTRAY_DOCK_INIT, WINE_SYSTRAY_DOCK_INSERT, diff --git a/include/wine/gdi_driver.h b/include/wine/gdi_driver.h index 9e9b2886bfa..608b5494b0f 100644 --- a/include/wine/gdi_driver.h +++ b/include/wine/gdi_driver.h @@ -307,7 +307,10 @@ struct user_driver_funcs BOOL (*pSetCursorPos)(INT,INT); BOOL (*pClipCursor)(const RECT*,BOOL); /* notify icon functions */ - LRESULT (*pNotifyIcon)(HWND,UINT,NOTIFYICONDATAW *); + LRESULT (*pAddNotifyIcon)(HWND,NOTIFYICONDATAW *); + LRESULT (*pModifyNotifyIcon)(HWND,NOTIFYICONDATAW *); + LRESULT (*pDeleteNotifyIcon)(HWND,UINT); + LRESULT (*pSetNotifyIconVersion)(HWND,UINT,UINT); void (*pCleanupIcons)(HWND); void (*pSystrayDockInit)(HWND); BOOL (*pSystrayDockInsert)(HWND,UINT,UINT,void *); diff --git a/programs/explorer/systray.c b/programs/explorer/systray.c index 75a857ac583..9da95af6bac 100644 --- a/programs/explorer/systray.c +++ b/programs/explorer/systray.c @@ -847,8 +847,37 @@ static BOOL handle_incoming(HWND hwndSource, COPYDATASTRUCT *cds) /* try forwarding to the display driver first */ if (cds->dwData == NIM_ADD || !(icon = get_icon( nid.hWnd, nid.uID ))) { - if ((ret = NtUserMessageCall( hwndSource, WINE_SYSTRAY_NOTIFY_ICON, cds->dwData, 0, - &nid, NtUserSystemTrayCall, FALSE )) != -1) + switch (cds->dwData) + { + case NIM_ADD: + { + ret = NtUserMessageCall( hwndSource, WINE_SYSTRAY_ADD_NOTIFY_ICON, 0, 0, + &nid, NtUserSystemTrayCall, FALSE ); + break; + } + case NIM_MODIFY: + { + ret = NtUserMessageCall( hwndSource, WINE_SYSTRAY_MODIFY_NOTIFY_ICON, 0, 0, + &nid, NtUserSystemTrayCall, FALSE ); + break; + } + case NIM_DELETE: + { + ret = NtUserMessageCall( hwndSource, WINE_SYSTRAY_DELETE_NOTIFY_ICON, nid.uID, 0, + NULL, NtUserSystemTrayCall, FALSE ); + break; + } + case NIM_SETVERSION: + { + ret = NtUserMessageCall( hwndSource, WINE_SYSTRAY_SET_NOTIFY_ICON_VERSION, nid.uID, + nid.uVersion, NULL, NtUserSystemTrayCall, FALSE ); + break; + } + default: + ret = -1; + break; + } + if (ret != -1) goto done; ret = FALSE; }