Search code examples
winapithemesvisual-styles

Visual Style for Windows Explorer hover and selection


The last three versions of Windows have all had translucent highlight and hover effects in Windows Explorer listview:

enter image description here

Using a theme explorer I see that the ListItem has no state that matches what i see in Windows:

enter image description here

Is there a:

  • class
  • part
  • state

that represents the ListView in Windows?


Solution

  • For compatibility reasons ListView still has the old style look by default. DrawThemeBackground(htheme, hdc, LVP_LISTITEM, ...) will simply draw a solid rectangle with border, for all item states, as shown in above image. GetSysColor should be used to get the right colors for this listview.

    A call to SetWindowTheme(hwnd, L"Explorer", NULL) will load the new theme data and draw the list items similar to Explorer. Example:

    LRESULT CALLBACK WndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
    {
        switch(msg)
        {
        case WM_CREATE:
            SetWindowTheme(hwnd, L"Explorer", NULL);
            break;
        case WM_PAINT:
        {
            PAINTSTRUCT ps;
            auto hdc = BeginPaint(hwnd, &ps);
            HTHEME ht = OpenThemeData(hwnd, L"LISTVIEW");
            if(ht)
            {
                RECT rc = { 10, 10, 100, 50 };
                DrawThemeBackground(ht, hdc, LVP_LISTITEM, LISS_SELECTED, &rc, NULL); OffsetRect(&rc, 0, 55);
                DrawThemeBackground(ht, hdc, LVP_LISTITEM, LISS_DISABLED, &rc, NULL); OffsetRect(&rc, 0, 55);
                DrawThemeBackground(ht, hdc, LVP_LISTITEM, LISS_SELECTED, &rc, NULL); OffsetRect(&rc, 0, 55);
                DrawThemeBackground(ht, hdc, LVP_LISTITEM, LISS_HOT, &rc, NULL); OffsetRect(&rc, 0, 55);
                DrawThemeBackground(ht, hdc, LVP_LISTITEM, LISS_HOTSELECTED, &rc, NULL); OffsetRect(&rc, 0, 55);
                DrawThemeBackground(ht, hdc, LVP_LISTITEM, LISS_SELECTEDNOTFOCUS, &rc, NULL);
                CloseThemeData(ht);
            }
    
            EndPaint(hwnd, &ps);
            return 0;
        }
        case WM_DESTROY:
            PostQuitMessage(0);
            return 0;
        }
        return DefWindowProc(hwnd, msg, wParam, lParam);
    }
    

    Output:

    enter image description here