[PATCH v2 1/3] user32/tests: Add color tests for static controls.

Jeff Smith whydoubt at gmail.com
Tue Oct 20 10:35:13 CDT 2020


Signed-off-by: Jeff Smith <whydoubt at gmail.com>
---
v2:
- Moved tests in with existing static tests.
- Quit using macro for shortening CLR_INVALID.
- Added const char *'s for common class names in tests.
- Created struct for style tests.

 dlls/user32/tests/static.c | 191 ++++++++++++++++++++++++++++++++++++-
 1 file changed, 189 insertions(+), 2 deletions(-)

diff --git a/dlls/user32/tests/static.c b/dlls/user32/tests/static.c
index 0c453d08a67..d42fc757c5d 100644
--- a/dlls/user32/tests/static.c
+++ b/dlls/user32/tests/static.c
@@ -52,9 +52,14 @@ static void flush_events(void)
     }
 }
 
-static HWND build_static(DWORD style)
+static const char *CLS_STATIC = "static";
+static const char *CLS_BUTTON = "button";
+
+#define build_static(style) build_child(CLS_STATIC, style)
+static HWND build_child(const char *class, DWORD style)
 {
-    return CreateWindowA("static", "Test", WS_VISIBLE|WS_CHILD|style, 5, 5, 100, 100, hMainWnd, (HMENU)CTRL_ID, NULL, 0);
+    return CreateWindowA(class, "Test", WS_VISIBLE|WS_CHILD|style, 5, 5, 100, 100, hMainWnd,
+            (HMENU)CTRL_ID, NULL, 0);
 }
 
 static LRESULT CALLBACK WndProc(HWND hwnd, UINT msg, WPARAM wparam, LPARAM lparam)
@@ -189,6 +194,187 @@ static void test_set_image(void)
     DeleteObject(image);
 }
 
+struct color_values
+{
+    HBRUSH brush;
+    COLORREF brushcolor;
+    COLORREF altbrushcolor;
+    COLORREF pencolor;
+    COLORREF textcolor;
+    COLORREF bkcolor;
+    int bkmode;
+};
+
+struct user_data
+{
+    UINT msg_expect;
+    struct color_values *color_test;
+};
+
+static LRESULT CALLBACK styles_wndproc(HWND hwnd, UINT msg, WPARAM wparam, LPARAM lparam)
+{
+    struct user_data *ud = (struct user_data *)GetWindowLongPtrA(hwnd, GWLP_USERDATA);
+
+    if (!ud || !ud->color_test)
+        return DefWindowProcA(hwnd, msg, wparam, lparam);
+
+    switch (msg)
+    {
+    case WM_CTLCOLORBTN:
+    case WM_CTLCOLORSTATIC:
+        ok(msg == ud->msg_expect, "Expected message %#x got %#x\n", msg, ud->msg_expect);
+        if (msg == ud->msg_expect)
+        {
+            HDC hdc = (HDC)wparam;
+            if (ud->color_test->bkmode)
+                SetBkMode(hdc, ud->color_test->bkmode);
+            if (ud->color_test->altbrushcolor != CLR_INVALID)
+                SetDCBrushColor(hdc, ud->color_test->altbrushcolor);
+            if (ud->color_test->pencolor != CLR_INVALID)
+                SetDCPenColor(hdc, ud->color_test->pencolor);
+            if (ud->color_test->textcolor != CLR_INVALID)
+                SetTextColor(hdc, ud->color_test->textcolor);
+            if (ud->color_test->bkcolor != CLR_INVALID)
+                SetBkColor(hdc, ud->color_test->bkcolor);
+
+            return (LRESULT)ud->color_test->brush;
+        }
+    }
+
+    return DefWindowProcA(hwnd, msg, wparam, lparam);
+}
+
+static void test_style_colors(const char *class, int style, POINT *inside, POINT *outside)
+{
+    struct color_values color_tests[] =
+    {
+        /* wndproc will return NULL */
+        {NULL, CLR_INVALID, CLR_INVALID, CLR_INVALID, CLR_INVALID, CLR_INVALID},
+        /* wndproc will return non-object */
+        {(HBRUSH)(COLOR_HIGHLIGHT+1), CLR_INVALID, CLR_INVALID, CLR_INVALID, CLR_INVALID, CLR_INVALID},
+        /* wndproc will return object */
+        {NULL, RGB(255,0,0), CLR_INVALID, CLR_INVALID, CLR_INVALID, CLR_INVALID},
+        {NULL, RGB(255,0,0), CLR_INVALID, CLR_INVALID, CLR_INVALID, CLR_INVALID, TRANSPARENT},
+        {NULL, RGB(255,0,0), RGB(0,255,0), RGB(0,0,255), RGB(255,255,0), RGB(255,0,255)},
+        {NULL, RGB(255,0,0), RGB(0,255,0), RGB(0,0,255), RGB(255,255,0), RGB(255,0,255), TRANSPARENT},
+    };
+    struct user_data ud;
+    COLORREF icolor0, ocolor0;
+    COLORREF icolor, ocolor;
+    COLORREF icolor_exp, ocolor_exp;
+    HWND hChild;
+    HDC hdc;
+    int i;
+
+    int is_simple = (class == CLS_STATIC) && (style == SS_SIMPLE);
+    int is_groupbox = (class == CLS_BUTTON) && (style == BS_GROUPBOX);
+    int is_pushbutton = (class == CLS_BUTTON) &&
+        (style == BS_PUSHBUTTON || style == BS_DEFPUSHBUTTON || style == BS_USERBUTTON);
+
+    /* Setup child window */
+    hChild = build_child(class, style);
+    SetWindowTextA(hChild, "____");
+    ud.msg_expect = is_pushbutton ? WM_CTLCOLORBTN : WM_CTLCOLORSTATIC;
+    ud.color_test = NULL;
+    SetWindowLongPtrA(hMainWnd, GWLP_USERDATA, (LONG_PTR)&ud);
+
+    /* Get system colors for child window */
+    InvalidateRect(hChild, NULL, FALSE);
+    UpdateWindow(hChild);
+    hdc = GetDC(hChild);
+    icolor0 = GetPixel(hdc, inside->x, inside->y);
+    ocolor0 = GetPixel(hdc, outside->x, outside->y);
+    ReleaseDC(hChild, hdc);
+
+    ocolor_exp = (is_simple || is_groupbox) ? RGB(255, 255, 255) : icolor0;
+    ok(ocolor0 == ocolor_exp, "(%s,%#x) Expected color %#x outside text area, got %#x\n",
+            class, style, ocolor_exp, ocolor0);
+
+    for (i = 0; i < ARRAY_SIZE(color_tests); i++)
+    {
+        /* Update child window with default colors */
+        InvalidateRect(hChild, NULL, FALSE);
+        UpdateWindow(hChild);
+
+        /* Update child window to exercise control color message */
+        if (color_tests[i].brushcolor != CLR_INVALID)
+            color_tests[i].brush = CreateSolidBrush(color_tests[i].brushcolor);
+        ud.color_test = &color_tests[i];
+        InvalidateRect(hChild, NULL, FALSE);
+        UpdateWindow(hChild);
+        ud.color_test = NULL;
+        if (color_tests[i].brushcolor != CLR_INVALID)
+            DeleteObject(color_tests[i].brush);
+
+        /* Get updated colors for child window */
+        hdc = GetDC(hChild);
+        icolor = GetPixel(hdc, inside->x, inside->y);
+        ocolor = GetPixel(hdc, outside->x, outside->y);
+        ReleaseDC(hChild, hdc);
+
+        icolor_exp =
+            (color_tests[i].brushcolor == CLR_INVALID || is_pushbutton) ? icolor0 :
+            (is_simple && color_tests[i].bkmode == TRANSPARENT) ? icolor0 :
+            (color_tests[i].bkmode == TRANSPARENT) ? color_tests[i].brushcolor :
+            (color_tests[i].bkcolor != CLR_INVALID) ? color_tests[i].bkcolor :
+            RGB(255, 255, 255);
+        ocolor_exp =
+            (color_tests[i].brushcolor == CLR_INVALID || is_pushbutton) ? ocolor0 :
+            (is_simple || is_groupbox) ? ocolor0 :
+            color_tests[i].brushcolor;
+        todo_wine_if(color_tests[i].brush != NULL && color_tests[i].brushcolor == CLR_INVALID && !is_pushbutton)
+        ok(icolor == icolor_exp, "(%s,%#x,%d) Expected color %#x inside text area, got %#x\n",
+                class, style, i, icolor_exp, icolor);
+        todo_wine_if(color_tests[i].brush != NULL && color_tests[i].brushcolor == CLR_INVALID && !is_pushbutton &&
+                     !is_simple && !is_groupbox)
+        ok(ocolor == ocolor_exp, "(%s,%#x,%d) Expected color %#x outside text area, got %#x\n",
+                class, style, i, ocolor_exp, ocolor);
+    }
+
+    DestroyWindow(hChild);
+}
+
+static void test_styles(void)
+{
+    struct {
+        const char *class;
+        int style;
+        /* A point that should always land inside the text area */
+        POINT test_point_inside;
+        /* A point that should always land outside the text area */
+        POINT test_point_outside;
+    } style_tests[] = {
+        /* Test basic static styles */
+        {CLS_STATIC, SS_SIMPLE,          {5, 5},   {90, 90}},
+        {CLS_STATIC, SS_LEFT,            {5, 5},   {90, 90}},
+        {CLS_STATIC, SS_RIGHT,           {95, 5},  {90, 90}},
+        {CLS_STATIC, SS_CENTER,          {50, 5},  {90, 90}},
+        {CLS_STATIC, SS_LEFTNOWORDWRAP,  {5, 5},   {90, 90}},
+        /* Test the static area inside push-buttons */
+        {CLS_BUTTON, BS_PUSHBUTTON,      {50, 50}, {90, 90}},
+        {CLS_BUTTON, BS_DEFPUSHBUTTON,   {50, 50}, {90, 90}},
+        {CLS_BUTTON, BS_USERBUTTON,      {50, 50}, {90, 90}},
+        /* Test the static area beside checkbox and radio buttons */
+        {CLS_BUTTON, BS_CHECKBOX,        {25, 50}, {90, 90}},
+        {CLS_BUTTON, BS_AUTOCHECKBOX,    {25, 50}, {90, 90}},
+        {CLS_BUTTON, BS_RADIOBUTTON,     {25, 50}, {90, 90}},
+        {CLS_BUTTON, BS_AUTORADIOBUTTON, {25, 50}, {90, 90}},
+        {CLS_BUTTON, BS_3STATE,          {25, 50}, {90, 90}},
+        {CLS_BUTTON, BS_AUTO3STATE,      {25, 50}, {90, 90}},
+        {CLS_BUTTON, BS_GROUPBOX,        {20, 5},  {90, 90}},
+    };
+    int i;
+    WNDPROC oldwndproc;
+
+    oldwndproc = (WNDPROC)SetWindowLongPtrA(hMainWnd, GWLP_WNDPROC, (LONG_PTR)styles_wndproc);
+    for (i = 0; i < ARRAY_SIZE(style_tests); i++)
+    {
+        test_style_colors(style_tests[i].class, style_tests[i].style,
+                &style_tests[i].test_point_inside, &style_tests[i].test_point_outside);
+    }
+    SetWindowLongPtrA(hMainWnd, GWLP_WNDPROC, (LONG_PTR)oldwndproc);
+}
+
 START_TEST(static)
 {
     static const char szClassName[] = "testclass";
@@ -222,6 +408,7 @@ START_TEST(static)
     test_updates(SS_ETCHEDVERT, TODO_COUNT);
     test_set_text();
     test_set_image();
+    test_styles();
 
     DestroyWindow(hMainWnd);
 }
-- 
2.23.0




More information about the wine-devel mailing list