Aric Stewart : comctl32: TTM_SETTOOLINFO does not change subclassing flags.

Alexandre Julliard julliard at wine.codeweavers.com
Mon Apr 27 07:45:11 CDT 2015


Module: wine
Branch: master
Commit: aba3b131bc6ab9f74e9ffcaaad0019253cb3f70d
URL:    http://source.winehq.org/git/wine.git/?a=commit;h=aba3b131bc6ab9f74e9ffcaaad0019253cb3f70d

Author: Aric Stewart <aric at codeweavers.com>
Date:   Fri Apr 24 07:34:59 2015 -0500

comctl32: TTM_SETTOOLINFO does not change subclassing flags.

---

 dlls/comctl32/tests/tooltips.c | 149 +++++++++++++++++++++++++++++++++++++++++
 dlls/comctl32/tooltips.c       |  24 ++++---
 2 files changed, 162 insertions(+), 11 deletions(-)

diff --git a/dlls/comctl32/tests/tooltips.c b/dlls/comctl32/tests/tooltips.c
index a07a054..3382fce 100644
--- a/dlls/comctl32/tests/tooltips.c
+++ b/dlls/comctl32/tests/tooltips.c
@@ -839,6 +839,154 @@ static void test_track(void)
     DestroyWindow(parent);
 }
 
+static LRESULT CALLBACK info_wnd_proc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam)
+{
+    switch(msg) {
+
+    case WM_DESTROY:
+        PostQuitMessage(0);
+        break;
+
+    default:
+        return DefWindowProcA(hWnd, msg, wParam, lParam);
+    }
+    return 0;
+}
+
+static void test_setinfo(void)
+{
+   WNDCLASSA wc;
+   LRESULT   lResult;
+   HWND parent, parent2, hwndTip, hwndTip2;
+   TTTOOLINFOA toolInfo = { 0 };
+   TTTOOLINFOA toolInfo2 = { 0 };
+   WNDPROC wndProc;
+
+   /* Create a class to use the custom draw wndproc */
+   wc.style = CS_HREDRAW | CS_VREDRAW;
+   wc.cbClsExtra = 0;
+   wc.cbWndExtra = 0;
+   wc.hInstance = GetModuleHandleA(NULL);
+   wc.hIcon = NULL;
+   wc.hCursor = LoadCursorA(NULL, (LPCSTR)IDC_ARROW);
+   wc.hbrBackground = GetSysColorBrush(COLOR_WINDOW);
+   wc.lpszMenuName = NULL;
+   wc.lpszClassName = "SetInfoClass";
+   wc.lpfnWndProc = info_wnd_proc;
+   RegisterClassA(&wc);
+
+   /* Create a main window */
+   parent = CreateWindowExA(0, "SetInfoClass", NULL,
+                           WS_CAPTION | WS_SYSMENU | WS_MINIMIZEBOX |
+                           WS_MAXIMIZEBOX | WS_VISIBLE,
+                           50, 50,
+                           300, 300,
+                           NULL, NULL, NULL, 0);
+   ok(parent != NULL, "Creation of main window failed\n");
+
+   parent2 = CreateWindowExA(0, "SetInfoClass", NULL,
+                           WS_CAPTION | WS_SYSMENU | WS_MINIMIZEBOX |
+                           WS_MAXIMIZEBOX | WS_VISIBLE,
+                           50, 50,
+                           300, 300,
+                           NULL, NULL, NULL, 0);
+   ok(parent2 != NULL, "Creation of main window failed\n");
+
+   /* Make it show */
+   ShowWindow(parent2, SW_SHOWNORMAL);
+   flush_events(100);
+
+   /* Create Tooltip */
+   hwndTip = CreateWindowExA(WS_EX_TOPMOST, TOOLTIPS_CLASSA,
+                            NULL, TTS_NOPREFIX | TTS_ALWAYSTIP,
+                            CW_USEDEFAULT, CW_USEDEFAULT,
+                            CW_USEDEFAULT, CW_USEDEFAULT,
+                            parent, NULL, GetModuleHandleA(NULL), 0);
+   ok(hwndTip != NULL, "Creation of tooltip window failed\n");
+
+   hwndTip2 = CreateWindowExA(WS_EX_TOPMOST, TOOLTIPS_CLASSA,
+                            NULL, TTS_NOPREFIX | TTS_ALWAYSTIP,
+                            CW_USEDEFAULT, CW_USEDEFAULT,
+                            CW_USEDEFAULT, CW_USEDEFAULT,
+                            parent, NULL, GetModuleHandleA(NULL), 0);
+   ok(hwndTip2 != NULL, "Creation of tooltip window failed\n");
+
+
+   /* Make it topmost, as per the MSDN */
+   SetWindowPos(hwndTip, HWND_TOPMOST, 0, 0, 0, 0,
+         SWP_NOMOVE | SWP_NOSIZE | SWP_NOACTIVATE);
+
+   /* Create a tool */
+   toolInfo.cbSize = TTTOOLINFOA_V1_SIZE;
+   toolInfo.hwnd = parent;
+   toolInfo.hinst = GetModuleHandleA(NULL);
+   toolInfo.uFlags = TTF_SUBCLASS;
+   toolInfo.uId = 0x1234ABCD;
+   toolInfo.lpszText = (LPSTR)"This is a test tooltip";
+   toolInfo.lParam = 0xdeadbeef;
+   GetClientRect (parent, &toolInfo.rect);
+   lResult = SendMessageA(hwndTip, TTM_ADDTOOLA, 0, (LPARAM)&toolInfo);
+   ok(lResult, "Adding the tool to the tooltip failed\n");
+
+   toolInfo.cbSize = TTTOOLINFOA_V1_SIZE;
+   toolInfo.hwnd = parent2;
+   toolInfo.hinst = GetModuleHandleA(NULL);
+   toolInfo.uFlags = 0;
+   toolInfo.uId = 0x1234ABCE;
+   toolInfo.lpszText = (LPSTR)"This is a test tooltip";
+   toolInfo.lParam = 0xdeadbeef;
+   GetClientRect (parent, &toolInfo.rect);
+   lResult = SendMessageA(hwndTip, TTM_ADDTOOLA, 0, (LPARAM)&toolInfo);
+   ok(lResult, "Adding the tool to the tooltip failed\n");
+
+   /* Try to Remove Subclass */
+   toolInfo2.cbSize = TTTOOLINFOA_V1_SIZE;
+   toolInfo2.hwnd = parent;
+   toolInfo2.uId = 0x1234ABCD;
+   lResult = SendMessageA(hwndTip, TTM_GETTOOLINFOA, 0, (LPARAM)&toolInfo2);
+   ok(lResult, "GetToolInfo failed\n");
+   ok(toolInfo2.uFlags & TTF_SUBCLASS, "uFlags does not have subclass\n");
+   wndProc = (WNDPROC)GetWindowLongPtrA(parent, GWLP_WNDPROC);
+   ok (wndProc != info_wnd_proc, "Window Proc is wrong\n");
+
+   toolInfo2.uFlags &= ~TTF_SUBCLASS;
+   SendMessageA(hwndTip, TTM_SETTOOLINFOA, 0, (LPARAM)&toolInfo2);
+   lResult = SendMessageA(hwndTip, TTM_GETTOOLINFOA, 0, (LPARAM)&toolInfo2);
+   ok(lResult, "GetToolInfo failed\n");
+   ok(!(toolInfo2.uFlags & TTF_SUBCLASS), "uFlags has subclass\n");
+   wndProc = (WNDPROC)GetWindowLongPtrA(parent, GWLP_WNDPROC);
+   ok (wndProc != info_wnd_proc, "Window Proc is wrong\n");
+
+   /* Try to Add Subclass */
+
+   /* Make it topmost, as per the MSDN */
+   SetWindowPos(hwndTip2, HWND_TOPMOST, 0, 0, 0, 0,
+         SWP_NOMOVE | SWP_NOSIZE | SWP_NOACTIVATE);
+
+   toolInfo2.cbSize = TTTOOLINFOA_V1_SIZE;
+   toolInfo2.hwnd = parent2;
+   toolInfo2.uId = 0x1234ABCE;
+   lResult = SendMessageA(hwndTip, TTM_GETTOOLINFOA, 0, (LPARAM)&toolInfo2);
+   ok(lResult, "GetToolInfo failed\n");
+   ok(!(toolInfo2.uFlags & TTF_SUBCLASS), "uFlags has subclass\n");
+   wndProc = (WNDPROC)GetWindowLongPtrA(parent2, GWLP_WNDPROC);
+   ok (wndProc == info_wnd_proc, "Window Proc is wrong\n");
+
+   toolInfo2.uFlags |= TTF_SUBCLASS;
+   SendMessageA(hwndTip, TTM_SETTOOLINFOA, 0, (LPARAM)&toolInfo2);
+   lResult = SendMessageA(hwndTip, TTM_GETTOOLINFOA, 0, (LPARAM)&toolInfo2);
+   ok(lResult, "GetToolInfo failed\n");
+   ok(toolInfo2.uFlags & TTF_SUBCLASS, "uFlags does not have subclass\n");
+   wndProc = (WNDPROC)GetWindowLongPtrA(parent2, GWLP_WNDPROC);
+   ok (wndProc == info_wnd_proc, "Window Proc is wrong\n");
+
+   /* Clean up */
+   DestroyWindow(hwndTip);
+   DestroyWindow(hwndTip2);
+   DestroyWindow(parent);
+   DestroyWindow(parent2);
+}
+
 START_TEST(tooltips)
 {
     InitCommonControls();
@@ -850,4 +998,5 @@ START_TEST(tooltips)
     test_longtextA();
     test_longtextW();
     test_track();
+    test_setinfo();
 }
diff --git a/dlls/comctl32/tooltips.c b/dlls/comctl32/tooltips.c
index 5423ca5..8bf6919 100644
--- a/dlls/comctl32/tooltips.c
+++ b/dlls/comctl32/tooltips.c
@@ -111,6 +111,7 @@ static HICON hTooltipIcons[TTI_ERROR+1];
 typedef struct
 {
     UINT      uFlags;
+    UINT      uInternalFlags;
     HWND      hwnd;
     BOOL      bNotifyUnicode;
     UINT_PTR  uId;
@@ -1057,11 +1058,12 @@ TOOLTIPS_AddToolT (TOOLTIPS_INFO *infoPtr, const TTTOOLINFOW *ti, BOOL isW)
     infoPtr->uNumTools++;
 
     /* copy tool data */
-    toolPtr->uFlags = ti->uFlags;
-    toolPtr->hwnd   = ti->hwnd;
-    toolPtr->uId    = ti->uId;
-    toolPtr->rect   = ti->rect;
-    toolPtr->hinst  = ti->hinst;
+    toolPtr->uFlags         = ti->uFlags;
+    toolPtr->uInternalFlags = (ti->uFlags & (TTF_SUBCLASS | TTF_IDISHWND));
+    toolPtr->hwnd           = ti->hwnd;
+    toolPtr->uId            = ti->uId;
+    toolPtr->rect           = ti->rect;
+    toolPtr->hinst          = ti->hinst;
 
     if (ti->cbSize >= TTTOOLINFOW_V1_SIZE) {
         if (IS_INTRESOURCE(ti->lpszText)) {
@@ -1092,8 +1094,8 @@ TOOLTIPS_AddToolT (TOOLTIPS_INFO *infoPtr, const TTTOOLINFOW *ti, BOOL isW)
 	toolPtr->lParam = ti->lParam;
 
     /* install subclassing hook */
-    if (toolPtr->uFlags & TTF_SUBCLASS) {
-	if (toolPtr->uFlags & TTF_IDISHWND) {
+    if (toolPtr->uInternalFlags & TTF_SUBCLASS) {
+	if (toolPtr->uInternalFlags & TTF_IDISHWND) {
 	    SetWindowSubclass((HWND)toolPtr->uId, TOOLTIPS_SubclassProc, 1,
 			      (DWORD_PTR)infoPtr->hwndSelf);
 	}
@@ -1152,8 +1154,8 @@ TOOLTIPS_DelToolT (TOOLTIPS_INFO *infoPtr, const TTTOOLINFOW *ti, BOOL isW)
     }
 
     /* remove subclassing */
-    if (toolPtr->uFlags & TTF_SUBCLASS) {
-	if (toolPtr->uFlags & TTF_IDISHWND) {
+    if (toolPtr->uInternalFlags & TTF_SUBCLASS) {
+	if (toolPtr->uInternalFlags & TTF_IDISHWND) {
 	    RemoveWindowSubclass((HWND)toolPtr->uId, TOOLTIPS_SubclassProc, 1);
 	}
 	else {
@@ -1918,8 +1920,8 @@ TOOLTIPS_Destroy (TOOLTIPS_INFO *infoPtr)
 	    }
 
 	    /* remove subclassing */
-        if (toolPtr->uFlags & TTF_SUBCLASS) {
-            if (toolPtr->uFlags & TTF_IDISHWND) {
+        if (toolPtr->uInternalFlags & TTF_SUBCLASS) {
+            if (toolPtr->uInternalFlags & TTF_IDISHWND) {
                 RemoveWindowSubclass((HWND)toolPtr->uId, TOOLTIPS_SubclassProc, 1);
             }
             else {




More information about the wine-cvs mailing list