From 814c4df261eb78ce5e1ffdaebc3cc7f6687f220e Mon Sep 17 00:00:00 2001 From: Mohmed abdel-fattah Date: Mon, 24 Jun 2024 18:16:28 +0300 Subject: [PATCH 1/2] The first stage of applying dark mode --- src/registry.h | 11 ++ src/rufus.c | 383 ++++++++++++++++++++++++++++++++++++++++++++++--- src/stdlg.c | 174 +++++++++++++++++++++- src/ui.c | 59 +++++--- src/ui.h | 15 +- 5 files changed, 602 insertions(+), 40 deletions(-) diff --git a/src/registry.h b/src/registry.h index db85ee3e..7e8312bc 100644 --- a/src/registry.h +++ b/src/registry.h @@ -202,6 +202,17 @@ static __inline BOOL WriteRegistryKey32(HKEY root, const char* key, int32_t val) DWORD tmp = (DWORD)val; return SetRegistryKey32(root, key, tmp); } +static __inline BOOL IsAppsUseDarkMode() { + char buffer [4] ; + DWORD cbData = (DWORD)(sizeof(buffer)); + LSTATUS res = RegGetValue(REGKEY_HKCU, L"Software\\Microsoft\\Windows\\CurrentVersion\\Themes\\Personalize", L"AppsUseLightTheme", RRF_RT_REG_DWORD, NULL, buffer, &cbData); + if (res == ERROR_SUCCESS) + { + int i = (int)(buffer[3] << 24 | buffer[2] << 16 | buffer[1] << 8 | buffer[0]); + return i == 0; + } + return FALSE; +} /* Helpers for boolean registry operations */ #define ReadRegistryKeyBool(root, key) (ReadRegistryKey32(root, key) != 0) diff --git a/src/rufus.c b/src/rufus.c index 74c73cbc..d106ec71 100755 --- a/src/rufus.c +++ b/src/rufus.c @@ -38,7 +38,7 @@ #include #include #include - +#include"ui_data.h" #include "rufus.h" #include "format.h" #include "missing.h" @@ -57,7 +57,10 @@ #include "cdio/logging.h" #include "../res/grub/grub_version.h" #include "../res/grub2/grub2_version.h" - +#include +#include +#pragma comment(lib,"UxTheme.lib") +#pragma comment(lib,"DwmApi.lib") enum bootcheck_return { BOOTCHECK_PROCEED = 0, BOOTCHECK_CANCEL = -1, @@ -147,6 +150,28 @@ const int nb_steps[FS_MAX] = { 5, 5, 12, 1, 10, 1, 1, 1, 1 }; const char* flash_type[BADLOCKS_PATTERN_TYPES] = { "SLC", "MLC", "TLC" }; RUFUS_DRIVE rufus_drive[MAX_DRIVES] = { 0 }; +// hdc is a memory DC with a 32bpp bitmap selected into it. +// This function sets the alpha channel to 255 without +// affecting any of the color channels. + +void MakeBitmapOpaque( + HDC hdc, int x, int y, int cx, int cy) +{ + BITMAPINFO bi = {0}; + bi.bmiHeader.biSize = sizeof(BITMAPINFOHEADER); + bi.bmiHeader.biWidth = 1; + bi.bmiHeader.biHeight = 1; + bi.bmiHeader.biPlanes = 1; + bi.bmiHeader.biBitCount = 32; + bi.bmiHeader.biCompression = BI_RGB; + + RGBQUAD bitmapBits = { 0x00, 0x00, 0x00, 0xFF }; + + StretchDIBits(hdc, x, y, cx, cy, + 0, 0, 1, 1, &bitmapBits, &bi, + DIB_RGB_COLORS, SRCPAINT); +} + // TODO: Remember to update copyright year in stdlg's AboutCallback() WM_INITDIALOG, // localization_data.sh and the .rc when the year changes! @@ -934,10 +959,283 @@ out: SetProposedLabel(device_index); return TRUE; } +/* + * DarkMode CheckBox Subclass Proc + */ +static LRESULT CALLBACK ButtonSubclassProc(HWND hWnd, UINT uMsg, WPARAM wParam, + LPARAM lParam, UINT_PTR uIdSubclass, DWORD_PTR dwRefData) +{ + if (!IsAppsUseDarkMode) + { + return DefSubclassProc(hWnd, uMsg, wParam, lParam); + } + + switch (uMsg) + { + + case WM_PAINT: + { + DefSubclassProc(hWnd, uMsg, wParam, lParam); + if (!IsWindowEnabled(hWnd)) + { + + return true; + } + HDC hDc = GetDC(hWnd); + RECT rc1; + GetClientRect(hWnd, &rc1); + SetBkMode(hDc, TRANSPARENT); + SetTextColor(hDc, RGB(255, 255, 255)); + HTHEME btnTheme = OpenThemeData(hWnd, L"Button"); + SIZE siz; + GetThemePartSize(btnTheme, hDc, 3, 1, NULL, TS_DRAW, &siz); + rc1.left += siz.cx + 2; + FillRect(hDc, &rc1, CreateSolidBrush(ColorControlDark)); + rc1.top += GetSystemMetrics(SM_CXPADDEDBORDER); + LPCWSTR* staticText[99] = {0}; + GetWindowText(hWnd, staticText, ARRAYSIZE(staticText)); + DTTOPTS opts; + opts.dwSize = sizeof(DTTOPTS); + opts.dwFlags = DTT_TEXTCOLOR; + opts.crText = RGB(255, 255, 255); + HFONT font = (HFONT)SendMessage(hWnd, WM_GETFONT, 0, 0); + SelectObject(hDc, font); + DrawThemeTextEx(btnTheme, hDc, 3, 0, &staticText, -1, DT_SINGLELINE | DT_LEFT, &rc1, &opts); + ReleaseDC(hWnd, hDc); + return true; + } + } + return DefSubclassProc(hWnd, uMsg, wParam, lParam); +} +/* + * Set DarkMode to all Child Windows + */ +static BOOL CALLBACK ThemeCallback(HWND hWnd, LPARAM lParam) +{ + const char* str[255] = {0}; + GetClassName(hWnd, &str, 255); + bool isDarkmode = IsAppsUseDarkMode(); + if (strcmp(str, L"Button") == 0) + { + LONG_PTR style = GetWindowLongPtr(hWnd, GWL_STYLE); + if ((style & BS_AUTOCHECKBOX) == BS_AUTOCHECKBOX) + { + if (!isDarkmode) + { + RemoveWindowSubclass(hWnd, ButtonSubclassProc, uIdSubclass); + return true; + } + else + SetWindowSubclass(hWnd, ButtonSubclassProc, uIdSubclass, 0); + } + + else + SetWindowTheme(hWnd, isDarkmode ? L"DarkMode_Explorer" : L"Explorer", NULL); + } + else if (strcmp(str, L"ComboBox") == 0) + { + SetWindowTheme(hWnd, isDarkmode ? L"DarkMode_CFD" : L"Explorer", NULL); + } + else if (strcmp(str, L"ToolBar") == 0) + { + wchar_t toolbarText[50]; + wchar_t multiToolbarText[50] ; + utf8_to_wchar_no_alloc(lmprintf(MSG_315), multiToolbarText, ARRAYSIZE(multiToolbarText)); + GetWindowText(hWnd, &toolbarText, 16); + if (strcmp(toolbarText, multiToolbarText) != 0) + SetWindowTheme(hWnd, isDarkmode ? L"DarkMode" : L"Explorer", NULL); + } + else if (strcmp(str, L"EDIT") == 0) + { + LONG_PTR style = GetWindowLongPtr(hWnd, GWL_STYLE); + if (((style & WS_VSCROLL) == WS_VSCROLL) || ((style & WS_HSCROLL) == WS_HSCROLL)) + SetWindowTheme(hWnd, isDarkmode ? L"DarkMode_Explorer" : L"Explorer", NULL); + else + SetWindowTheme(hWnd, isDarkmode ? L"DarkMode_CFD" : L"Explorer", NULL); + + + + } + + return TRUE; +} + +/* + * DarkMod Dialog Subclass Proc + */ + +static LRESULT CALLBACK DlgSubclassProc(HWND hDlg, UINT message, WPARAM wParam, + LPARAM lParam, UINT_PTR uIdSubclass, DWORD_PTR dwRefData) +{ + RECT rcDlg; + GetClientRect(hDlg, &rcDlg); + HDC dc; + switch (message) + { + case WM_NCPAINT: + { + LRESULT result = DefSubclassProc(hDlg, message, wParam, lParam); + HDC windowDC = GetWindowDC(hDlg); + RECT rcWin, rcClient; + GetWindowRect(hDlg, &rcWin); + GetClientRect(hDlg, &rcClient); + MapWindowPoints(hDlg, NULL, (LPPOINT)&rcWin, 2); + int rcWinWidth = rcWin.right - rcWin.left; + int rcWinHieght = rcWin.bottom - rcWin.top; + int rcrcClientWidth = rcClient.right - rcClient.left; + int rcrcClientHieght = rcClient.bottom - rcClient.top; + int borderWidth = (rcWinWidth - rcrcClientWidth) / 2; + int captionHight = rcWinHieght - rcrcClientHieght - borderWidth; + OffsetRect(&rcWin, -rcWin.left, -rcWin.top); + OffsetRect(&rcClient, borderWidth, captionHight); + HRGN updateRgn = wParam != 1 ?(HRGN)wParam : CreateRectRgnIndirect(&rcWin); + HRGN clipRgn = CreateRectRgn(0, 0, 0, 0); + HRGN ncRgn = CreateRectRgn(0, 0, 0, 0); + + if (wParam == 1) + clipRgn = CreateRectRgnIndirect(&rcClient); + else + GetClipRgn(windowDC, clipRgn); + CombineRgn(ncRgn, updateRgn, clipRgn, RGN_DIFF); + SelectClipRgn(windowDC, ncRgn); + FillRect(windowDC, &rcWin, CreateSolidBrush(RGB(63, 63, 63))); + HRGN hRgn= CreateRectRgnIndirect(&rcWin); + SelectClipRgn(windowDC, hRgn); + MakeBitmapOpaque(windowDC, 0, 0, rcWinWidth, rcWinHieght); + safe_release_dc(hDlg, windowDC); + return result; + } + case WM_NCCALCSIZE: + { + //TODO: get real caption Size + + if (wParam) + { + NCCALCSIZE_PARAMS* ncParma = (NCCALCSIZE_PARAMS*)(lParam); + ncParma->rgrc[0].left += 1;//pr++; + ncParma->rgrc[0].top += 31; + ncParma->rgrc[0].right -= 1; + ncParma->rgrc[0].bottom -= 1; + return 0; + } + else + { + RECT* rect = (RECT*)lParam; + rect->top += 31; + rect->left += 1; + rect->right -= 1; + rect->bottom -= 1; + return 0; + } + } + + case WM_SHOWWINDOW: + { + if (wParam) + { + EnumChildWindows(hDlg, ThemeCallback, lParam); + BOOL allowncpaint = TRUE; + COLORREF caption = RGB(0x0,0x0,0x0); + DwmSetWindowAttribute(hDlg, DWMWA_CAPTION_COLOR, &caption, sizeof caption); + DwmSetWindowAttribute(hDlg, DWMWA_BORDER_COLOR, &caption, sizeof caption); + DwmSetWindowAttribute(hDlg, DWMWA_ALLOW_NCPAINT, &allowncpaint, sizeof(int)); + RECT rcDlg; + GetWindowRect(hDlg, &rcDlg); + SetWindowPos(hDlg, 0, 0, 0, rcDlg.right-rcDlg.left, rcDlg.bottom-rcDlg.top, SWP_FRAMECHANGED | SWP_NOSIZE | SWP_NOMOVE); + + if (hLog) + { + RECT rcLog; + GetWindowRect(hLog, &rcLog); + GetClientRect(hDlg, &rcDlg); + rcLog.left = rcDlg.left + 1; + rcLog.right = rcDlg.right - 1; + SetWindowPos(hLog, NULL, 0, 0, rcLog.right - rcLog.left, rcLog.bottom - rcLog.top, SWP_NOMOVE | SWP_NOZORDER); + } + RedrawWindow(hDlg, NULL, NULL, RDW_ALLCHILDREN | RDW_UPDATENOW | RDW_INVALIDATE | RDW_FRAME | RDW_ERASENOW); + } + + return DefSubclassProc(hDlg, message, wParam, lParam); + + } + + case WM_CTLCOLORLISTBOX: + SetBkColor((HDC)wParam, RGB(25, 25, 25)); + SetTextColor((HDC)wParam, RGB(255, 255, 255)); + return (INT_PTR)CreateSolidBrush(RGB(25, 25, 25)); + case WM_CTLCOLOREDIT: + { + HDC hdc = (HDC)wParam; + SetBkColor((HDC)wParam, RGB(25, 25, 25)); + HBRUSH sysbrash = GetSysColorBrush(COLOR_WINDOWFRAME); + SetTextColor(hdc, RGB(255, 255, 255)); + return (INT_PTR)CreateSolidBrush(RGB(25, 25, 25)); + } + case WM_CTLCOLORBTN: + case WM_CTLCOLORDLG: + return (INT_PTR)CreateSolidBrush(ColorControlDark); + case WM_CTLCOLORSTATIC: + dc = GetDC((HWND)lParam); + RECT rcDlg; + GetClientRect((HWND)lParam, &rcDlg); + safe_release_dc((HWND)lParam, dc); + if ((HWND)lParam == GetDlgItem(hDlg, IDC_LABEL)) + { + + SetBkColor((HDC)wParam, GetSysColor(COLOR_WINDOWFRAME)); + + + return (INT_PTR)CreateSolidBrush(RGB(25, 25, 25)); + } + if ((HWND)lParam != GetDlgItem(hDlg, IDS_CSM_HELP_TXT)) + { + + SetBkMode((HDC)wParam, TRANSPARENT); + SetTextColor((HDC)wParam, TOOLBAR_ICON_COLOR); + //MakeBitmapOpaque((HDC)wParam, 0, 0, rcDlg.right - rcDlg.left, rcDlg.bottom - rcDlg.top); + + return (INT_PTR)CreateSolidBrush(ColorControlDark); + } + SetBkMode((HDC)wParam, TRANSPARENT); + SetTextColor((HDC)wParam, TOOLBAR_ICON_COLOR); + + return (INT_PTR)CreateSolidBrush(ColorControlDark); + case WM_SETTINGCHANGE: + { + if (IsAppsUseDarkMode()) + { + BOOL allowncpaint = TRUE; + COLORREF caption = RGB(0x0,0x0,0x0); + DWM_WINDOW_CORNER_PREFERENCE f = DWMWCP_DONOTROUND; + DwmSetWindowAttribute(hDlg, DWMWA_CAPTION_COLOR, &caption, sizeof caption); + DwmSetWindowAttribute(hDlg, DWMWA_BORDER_COLOR, &caption, sizeof caption); + DwmSetWindowAttribute(hDlg, DWMWA_WINDOW_CORNER_PREFERENCE, &f, sizeof(f)); + DwmSetWindowAttribute(hDlg, DWMWA_ALLOW_NCPAINT, &allowncpaint, sizeof(int)); + if (hLog) + { + RECT rcLog, rcDlg; + GetWindowRect(hLog, &rcLog); + GetClientRect(hDlg, &rcDlg); + rcLog.left = rcDlg.left + 1; + rcLog.right = rcDlg.right - 1; + SetWindowPos(hLog, NULL, 0, 0, rcLog.right - rcLog.left, rcLog.bottom - rcLog.top, SWP_NOMOVE | SWP_NOZORDER); + } + } + return DefSubclassProc(hDlg, message, wParam, lParam); + } + + default: + return DefSubclassProc(hDlg, message, wParam, lParam); + break; + } +} // Callback for the log window + BOOL CALLBACK LogCallback(HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam) { + BOOL resized_already = FALSE; + REQRESIZE* rsz; HDC hDC; HFONT hf; LONG lfHeight; @@ -948,10 +1246,14 @@ BOOL CALLBACK LogCallback(HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam) switch (message) { case WM_INITDIALOG: apply_localization(IDD_LOG, hDlg); + hLog = GetDlgItem(hDlg, IDC_LOG_EDIT); - // Increase the size of our log textbox to MAX_LOG_SIZE (unsigned word) PostMessage(hLog, EM_LIMITTEXT, MAX_LOG_SIZE , 0); + if (IsAppsUseDarkMode()) + { + SetWindowSubclass(hDlg, DlgSubclassProc, uIdSubclass, 0); + } // Set the font to Unicode so that we can display anything hDC = GetDC(NULL); lfHeight = -MulDiv(9, GetDeviceCaps(hDC, LOGPIXELSY), 72); @@ -973,6 +1275,7 @@ BOOL CALLBACK LogCallback(HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam) style &= ~(ES_RIGHT); SetWindowLongPtr(hLog, GWL_STYLE, style); break; + case WM_COMMAND: switch (LOWORD(wParam)) { case IDCANCEL: @@ -1018,7 +1321,34 @@ BOOL CALLBACK LogCallback(HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam) ResizeButtonHeight(hDlg, IDC_LOG_SAVE); ResizeButtonHeight(hDlg, IDC_LOG_CLEAR); return TRUE; + case WM_SETTINGCHANGE: + if (!IsAppsUseDarkMode()) + { + BOOL allowncpaint = FALSE; + COLORREF caption = DWMWA_COLOR_DEFAULT; + DWM_WINDOW_CORNER_PREFERENCE f = DWMWCP_DONOTROUND; + DwmSetWindowAttribute(hDlg, DWMWA_CAPTION_COLOR, &caption, sizeof caption); + DwmSetWindowAttribute(hDlg, DWMWA_ALLOW_NCPAINT, &allowncpaint, sizeof(int)); + DwmSetWindowAttribute(hDlg, DWMWA_BORDER_COLOR, &caption, sizeof caption); + DwmSetWindowAttribute(hDlg, DWMWA_WINDOW_CORNER_PREFERENCE, &f, sizeof(f)); + if (hLog) + { + RECT rcLog, rcDlg; + GetWindowRect(hLog, &rcLog); + GetClientRect(hDlg, &rcDlg); + rcLog.left = rcDlg.left + 1; + rcLog.right = rcDlg.right - 1; + SetWindowPos(hLog, NULL, 0, 0, rcLog.right - rcLog.left, rcLog.bottom - rcLog.top, SWP_NOMOVE | SWP_NOZORDER); + } + RemoveWindowSubclass(hDlg, DlgSubclassProc, uIdSubclass); + } + + else + SetWindowSubclass(hDlg, DlgSubclassProc, uIdSubclass, 0); + EnumChildWindows(hDlg, ThemeCallback, lParam); + return TRUE; } + return FALSE; } @@ -1232,6 +1562,7 @@ out: return ret; } + // The scanning process can be blocking for message processing => use a thread DWORD WINAPI ImageScanThread(LPVOID param) { @@ -2149,6 +2480,8 @@ static void PrintStatusTimeout(const char* str, BOOL val) /* * Main dialog callback */ + + static INT_PTR CALLBACK MainCallback(HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam) { static DWORD DeviceNum = 0; @@ -2178,7 +2511,7 @@ static INT_PTR CALLBACK MainCallback(HWND hDlg, UINT message, WPARAM wParam, LPA loc_cmd* lcmd = NULL; switch (message) { - + case WM_COMMAND: #ifdef RUFUS_TEST if (LOWORD(wParam) == IDC_TEST) { @@ -2704,6 +3037,8 @@ static INT_PTR CALLBACK MainCallback(HWND hDlg, UINT message, WPARAM wParam, LPA fScale = GetDeviceCaps(hDC, LOGPIXELSX) / 96.0f; safe_release_dc(hDlg, hDC); apply_localization(IDD_DIALOG, hDlg); + if (IsAppsUseDarkMode()) + SetWindowSubclass(hDlg, DlgSubclassProc, uIdSubclass, 0); // The AppStore version always enables Fido if (appstore_version) SetFidoCheck(); @@ -2713,6 +3048,7 @@ static INT_PTR CALLBACK MainCallback(HWND hDlg, UINT message, WPARAM wParam, LPA log_displayed = FALSE; hLogDialog = MyCreateDialog(hMainInstance, IDD_LOG, hDlg, (DLGPROC)LogCallback); InitDialog(hDlg); + GetDevices(0); EnableControls(TRUE, FALSE); UpdateImage(FALSE); @@ -2735,7 +3071,8 @@ static INT_PTR CALLBACK MainCallback(HWND hDlg, UINT message, WPARAM wParam, LPA // Set 'START' as the selected button if it's enabled, otherwise use 'SELECT', instead SendMessage(hDlg, WM_NEXTDLGCTL, (WPARAM)(IsWindowEnabled(hStart) ? hStart : hSelectImage), TRUE); - + + #if defined(ALPHA) // Add a VERY ANNOYING popup for Alpha releases, so that people don't start redistributing them MessageBoxA(NULL, "This is an Alpha version of " APPLICATION_NAME " - It is meant to be used for " @@ -2746,11 +3083,13 @@ static INT_PTR CALLBACK MainCallback(HWND hDlg, UINT message, WPARAM wParam, LPA "testing ONLY and should NOT be distributed as a release.", "TEST VERSION", MSG_INFO); #endif // Let's not take any risk: Ask Windows to redraw the whole dialog before we exit init + RedrawWindow(hMainDialog, NULL, NULL, RDW_ALLCHILDREN | RDW_UPDATENOW); InvalidateRect(hMainDialog, NULL, TRUE); - + + return (INT_PTR)FALSE; - + case WM_DRAWITEM: // The things one must do to get an ellipsis and text alignment on the status bar... if (wParam == IDC_STATUS) { @@ -2773,22 +3112,34 @@ static INT_PTR CALLBACK MainCallback(HWND hDlg, UINT message, WPARAM wParam, LPA return (INT_PTR)TRUE; } } + break; - + case WM_SETTINGCHANGE: + if (!IsAppsUseDarkMode()) + { + BOOL allowncpaint = FALSE; + COLORREF caption = DWMWA_COLOR_DEFAULT; + DWM_WINDOW_CORNER_PREFERENCE f = DWMWCP_ROUND; + DwmSetWindowAttribute(hDlg, DWMWA_CAPTION_COLOR, &caption, sizeof caption); + DwmSetWindowAttribute(hDlg, DWMWA_BORDER_COLOR, &caption, sizeof caption); + DwmSetWindowAttribute(hDlg, DWMWA_WINDOW_CORNER_PREFERENCE, &f, sizeof(f)); + DwmSetWindowAttribute(hDlg, DWMWA_ALLOW_NCPAINT, &allowncpaint, sizeof(int)); + RemoveWindowSubclass(hDlg, DlgSubclassProc, uIdSubclass); + } + else + { + SetWindowSubclass(hDlg, DlgSubclassProc, uIdSubclass, 0); + } + + EnumChildWindows(hDlg, ThemeCallback, lParam); + RedrawWindow(hMainDialog, NULL, NULL, RDW_ALLCHILDREN | RDW_UPDATENOW | RDW_ERASENOW); + return DefWindowProc(hDlg, message, wParam, lParam); case WM_PAINT: hDC = BeginPaint(hDlg, &ps); OnPaint(hDC); EndPaint(hDlg, &ps); break; - case WM_CTLCOLORSTATIC: - if ((HWND)lParam != GetDlgItem(hDlg, IDS_CSM_HELP_TXT)) - return FALSE; - SetBkMode((HDC)wParam, TRANSPARENT); - CreateStaticFont((HDC)wParam, &hyperlink_font, FALSE); - SelectObject((HDC)wParam, hyperlink_font); - SetTextColor((HDC)wParam, TOOLBAR_ICON_COLOR); - return (INT_PTR)CreateSolidBrush(GetSysColor(COLOR_BTNFACE)); case WM_NOTIFY: switch (((LPNMHDR)lParam)->code) { diff --git a/src/stdlg.c b/src/stdlg.c index e75987c4..532f81c5 100644 --- a/src/stdlg.c +++ b/src/stdlg.c @@ -43,6 +43,7 @@ #include "registry.h" #include "settings.h" #include "license.h" +#include /* Globals */ extern BOOL is_x86_64, appstore_version; @@ -83,6 +84,162 @@ void SetDialogFocus(HWND hDlg, HWND hCtrl) SendMessage(hDlg, WM_NEXTDLGCTL, (WPARAM)hCtrl, TRUE); } +/* + * DarkMode CheckBox Subclass Proc + */ + +static LRESULT CALLBACK ButtonSubclassProc(HWND hWnd, UINT uMsg, WPARAM wParam, + LPARAM lParam, UINT_PTR uIdSubclass, DWORD_PTR dwRefData) +{ + if (!IsAppsUseDarkMode) + { + return DefSubclassProc(hWnd, uMsg, wParam, lParam); + } + + switch (uMsg) + { + + case WM_PAINT: + { + DefSubclassProc(hWnd, uMsg, wParam, lParam); + if (!IsWindowEnabled(hWnd)) + { + + return TRUE; + } + HDC hDc = GetDC(hWnd); + RECT rc1; + GetClientRect(hWnd, &rc1); + SetBkMode(hDc, TRANSPARENT); + SetTextColor(hDc, RGB(255, 255, 255)); + HTHEME btnTheme = OpenThemeData(hWnd, L"Button"); + SIZE siz; + GetThemePartSize(btnTheme, hDc, 3, 1, NULL, TS_DRAW, &siz); + rc1.left += siz.cx + 2; + FillRect(hDc, &rc1, CreateSolidBrush(ColorControlDark)); + rc1.top += GetSystemMetrics(SM_CXPADDEDBORDER); + LPCWSTR* staticText[99] = {0}; + GetWindowText(hWnd, staticText, ARRAYSIZE(staticText)); + DTTOPTS opts; + opts.dwSize = sizeof(DTTOPTS); + opts.dwFlags = DTT_TEXTCOLOR; + opts.crText = RGB(255, 255, 255); + HFONT font = (HFONT)SendMessage(hWnd, WM_GETFONT, 0, 0); + SelectObject(hDc, font); + DrawThemeTextEx(btnTheme, hDc, 3, 0, &staticText, -1, DT_SINGLELINE | DT_LEFT, &rc1, &opts); + ReleaseDC(hWnd, hDc); + return TRUE; + } + } + return DefSubclassProc(hWnd, uMsg, wParam, lParam); +} + +/* + * Set DarkMode to all Child Windows + */ + +static BOOL CALLBACK ThemeCallback(HWND hWnd, LPARAM lParam) +{ + char* str[255]; + GetClassName(hWnd, &str, 255); + BOOL isDarkMode = IsAppsUseDarkMode(); + + if (strcmp(str, L"Button") == 0) + { + LONG_PTR style = GetWindowLongPtr(hWnd, GWL_STYLE); + if ((style & BS_AUTOCHECKBOX) == BS_AUTOCHECKBOX) + { + if (!isDarkMode) + { + RemoveWindowSubclass(hWnd, ButtonSubclassProc, uIdSubclass); + return TRUE; + } + else + SetWindowSubclass(hWnd, ButtonSubclassProc, uIdSubclass, 0); + } + + else + SetWindowTheme(hWnd, isDarkMode ? L"DarkMode_Explorer" : L"Explorer", NULL); + } + else if (strcmp(str, L"ComboBox") == 0) + { + SetWindowTheme(hWnd, isDarkMode ? L"DarkMode_CFD" : L"Explorer", NULL); + } + else if (strcmp(str, L"ToolBar") == 0) + { + char* title[16]; + GetWindowText(hWnd, &title, 16); + if (strcmp(title, L"Multiple buttons") != 0) + SetWindowTheme(hWnd, isDarkMode ? L"DarkMode" : L"Explorer", NULL); + } + else if (strcmp(str, L"EDIT") == 0) + { + LONG_PTR style = GetWindowLongPtr(hWnd, GWL_STYLE); + if(((style & WS_VSCROLL) == WS_VSCROLL) || ((style & WS_HSCROLL) == WS_HSCROLL)) + SetWindowTheme(hWnd, isDarkMode ? L"DarkMode_Explorer" : L"Explorer", NULL); + else + SetWindowTheme(hWnd, isDarkMode ? L"DarkMode_CFD" : L"Explorer", NULL); + + + } + else if (strcmp(str, L"RichEdit20W") == 0) + { + SendMessage(hWnd, EM_SETBKGNDCOLOR, 0, isDarkMode ? (LPARAM)ColorControlDark : (LPARAM)GetSysColor(COLOR_BTNFACE)); + CHARFORMAT cf; + cf.cbSize = sizeof(cf); + cf.dwMask = CFM_COLOR; + cf.crTextColor = isDarkMode ? RGB(255, 255, 255): RGB(0, 0, 0); + cf.dwEffects = 0; + SendMessage(hWnd, EM_SETCHARFORMAT, SCF_DEFAULT, (LPARAM)&cf); + //SetWindowTheme(hEdit[i], L"DarkMode_Explorer", NULL); + SetWindowTheme(hWnd, NULL, isDarkMode ? L"DarkMode_Explorer::ScrollBar" : L"Explorer::ScrollBar"); + + + } + + return TRUE; +} + +/* + * DarkMod Dialog Subclass Proc + */ + +static LRESULT CALLBACK DlgSubclassProc(HWND hDlg, UINT message, WPARAM wParam, + LPARAM lParam, UINT_PTR uIdSubclass, DWORD_PTR dwRefData) +{ + if (!IsAppsUseDarkMode()) + { + return DefSubclassProc(hDlg, message, wParam, lParam); + } + switch (message) + { + case WM_SHOWWINDOW: + EnumChildWindows(hDlg, ThemeCallback, lParam); + return DefWindowProc(hDlg, message, wParam, lParam); + case WM_CTLCOLORLISTBOX: + SetBkColor((HDC)wParam, RGB(25, 25, 25)); + SetTextColor((HDC)wParam, RGB(255, 255, 255)); + return (INT_PTR)CreateSolidBrush(RGB(25, 25, 25)); + case WM_CTLCOLOREDIT: + { + HDC hdc = (HDC)wParam; + SetBkColor((HDC)wParam, RGB(25, 25, 25)); + SetTextColor(hdc, RGB(255, 255, 255)); + return (INT_PTR)CreateSolidBrush(RGB(25, 25, 25)); + + } + case WM_CTLCOLORBTN: + case WM_CTLCOLORDLG: + return (INT_PTR)CreateSolidBrush(ColorControlDark); + case WM_CTLCOLORSTATIC: + SetBkMode((HDC)wParam, TRANSPARENT); + SetTextColor((HDC)wParam, TOOLBAR_ICON_COLOR); + return (INT_PTR)CreateSolidBrush(ColorControlDark); + default: + return DefSubclassProc(hDlg, message, wParam, lParam); + break; + } +} /* * Return the UTF8 path of a file selected through a load or save dialog * All string parameters are UTF-8 @@ -216,7 +373,6 @@ out: void CreateStatusBar(void) { RECT rect; - int edge[2]; HFONT hFont; // Create the status bar @@ -226,10 +382,10 @@ void CreateStatusBar(void) // Create 2 status areas GetClientRect(hMainDialog, &rect); - edge[0] = rect.right - (int)(SB_TIMER_SECTION_SIZE * fScale); - edge[1] = rect.right; - SendMessage(hStatus, SB_SETPARTS, (WPARAM)ARRAYSIZE(edge), (LPARAM)&edge); + int edge[] = { rect.right - (int)(SB_TIMER_SECTION_SIZE * fScale) , rect.right,-1}; + SendMessage(hStatus, SB_SETPARTS, (WPARAM)ARRAYSIZE(edge), (LPARAM)&edge); + //SendMessage(hStatus, WM_SIZE, 0, 0); // Set the font hFont = CreateFontA(-MulDiv(9, GetDeviceCaps(GetDC(hMainDialog), LOGPIXELSY), 72), 0, 0, 0, FW_MEDIUM, FALSE, FALSE, FALSE, DEFAULT_CHARSET, @@ -337,6 +493,7 @@ INT_PTR CALLBACK LicenseCallback(HWND hDlg, UINT message, WPARAM wParam, LPARAM style &= ~(ES_RIGHT); SetWindowLongPtr(hLicense, GWL_STYLE, style); SetDlgItemTextA(hDlg, IDC_LICENSE_TEXT, gplv3); + SetWindowSubclass(hDlg, DlgSubclassProc, uIdSubclass, 0); break; case WM_COMMAND: switch (LOWORD(wParam)) { @@ -403,6 +560,7 @@ INT_PTR CALLBACK AboutCallback(HWND hDlg, UINT message, WPARAM wParam, LPARAM lP // Need to send an explicit SetSel to avoid being positioned at the end of richedit control when tabstop is used SendMessage(hEdit[1], EM_SETSEL, 0, 0); SendMessage(hEdit[0], EM_REQUESTRESIZE, 0, 0); + SetWindowSubclass(hDlg, DlgSubclassProc, uIdSubclass, 0); break; case WM_NOTIFY: switch (((LPNMHDR)lParam)->code) { @@ -555,6 +713,7 @@ INT_PTR CALLBACK NotificationCallback(HWND hDlg, UINT message, WPARAM wParam, LP ResizeMoveCtrl(hDlg, GetDlgItem(hDlg, IDYES), 0, dh -cbh, 0, 0, 1.0f); ResizeMoveCtrl(hDlg, GetDlgItem(hDlg, IDNO), 0, dh -cbh, 0, 0, 1.0f); } + SetWindowSubclass(hDlg, DlgSubclassProc, uIdSubclass, 0); return (INT_PTR)TRUE; case WM_CTLCOLORSTATIC: // Change the background colour for static text and icon @@ -988,6 +1147,9 @@ INT_PTR CALLBACK TooltipCallback(HWND hDlg, UINT message, WPARAM wParam, LPARAM return (INT_PTR)FALSE; switch (message) { + case WM_NCPAINT: + SendMessageW(ttlist[i].hTip, TTM_SETWINDOWTHEME, 0, IsAppsUseDarkMode() ? ((LPARAM)&L"DarkMode_Explorer") : ((LPARAM)&L"Explorer")); + return CallWindowProc(ttlist[i].original_proc, hDlg, message, wParam, lParam); case WM_NOTIFY: switch (((LPNMHDR)lParam)->code) { case TTN_GETDISPINFOW: @@ -1318,6 +1480,7 @@ INT_PTR CALLBACK UpdateCallback(HWND hDlg, UINT message, WPARAM wParam, LPARAM l SendMessage(hPolicy, EM_SETEVENTMASK, 0, ENM_LINK|ENM_REQUESTRESIZE); SendMessageA(hPolicy, EM_SETBKGNDCOLOR, 0, (LPARAM)GetSysColor(COLOR_BTNFACE)); SendMessage(hPolicy, EM_REQUESTRESIZE, 0, 0); + SetWindowSubclass(hDlg, DlgSubclassProc, uIdSubclass, 0); break; case WM_NOTIFY: if ((((LPNMHDR)lParam)->code == EN_REQUESTRESIZE) && (!resized_already)) { @@ -1568,6 +1731,9 @@ INT_PTR CALLBACK NewVersionCallback(HWND hDlg, UINT message, WPARAM wParam, LPAR case WM_CTLCOLORSTATIC: if ((HWND)lParam != GetDlgItem(hDlg, IDC_WEBSITE)) return FALSE; + HDC hdcCtrl = GET_WM_CTLCOLOR_HDC(wParam, lParam, message); + HWND hWndCtrl = GET_WM_CTLCOLOR_HWND(wParam, lParam, message); + WORD cc = GET_WM_CTLCOLOR_TYPE(wParam, lParam, message); // Change the font for the hyperlink SetBkMode((HDC)wParam, TRANSPARENT); CreateStaticFont((HDC)wParam, &hyperlink_font, TRUE); diff --git a/src/ui.c b/src/ui.c index 166e2b0a..4b8e144b 100644 --- a/src/ui.c +++ b/src/ui.c @@ -38,10 +38,10 @@ #include "resource.h" #include "msapi_utf8.h" #include "localization.h" - +#include "WinUser.h" #include "ui.h" #include "ui_data.h" - +#include "registry.h" UINT_PTR UM_LANGUAGE_MENU_MAX = UM_LANGUAGE_MENU; HIMAGELIST hUpImageList, hDownImageList; extern BOOL use_vds, appstore_version; @@ -350,11 +350,18 @@ void PositionMainControls(HWND hDlg) GetWindowRect(hCtrl, &rc); MapWindowPoints(NULL, hDlg, (POINT*)&rc, 2); advanced_device_section_height = rc.top; + LONG_PTR style = GetWindowLongPtrW(hCtrl, GWL_STYLE); + /*if ((style & SS_OWNERDRAW) != SS_OWNERDRAW) + { + style |= SS_OWNERDRAW; + style |= ~BS_AUTOCHECKBOX; + SetWindowLongPtrW(hCtrl, GWL_STYLE, style); + }*/ hCtrl = GetDlgItem(hDlg, IDC_UEFI_MEDIA_VALIDATION); GetWindowRect(hCtrl, &rc); MapWindowPoints(NULL, hDlg, (POINT*)&rc, 2); advanced_device_section_height = rc.bottom - advanced_device_section_height; - + hCtrl = GetDlgItem(hDlg, IDC_QUICK_FORMAT); GetWindowRect(hCtrl, &rc); MapWindowPoints(NULL, hDlg, (POINT*)&rc, 2); @@ -893,14 +900,20 @@ static INT_PTR CALLBACK ProgressCallback(HWND hCtrl, UINT message, WPARAM wParam wchar_t winfo[128]; static BOOL marquee_mode = FALSE; static uint32_t pos = 0, min = 0, max = 0xFFFF; - static COLORREF color = PROGRESS_BAR_NORMAL_COLOR; + BOOL isDark = IsAppsUseDarkMode(); + COLORREF normalColor = isDark ? PROGRESS_BAR_DARK_NORMAL_COLOR : PROGRESS_BAR_NORMAL_COLOR; + COLORREF backgroundColor = isDark ? PROGRESS_BAR_DARK_BACKGROUND_COLOR : PROGRESS_BAR_BACKGROUND_COLOR; + COLORREF normalTextColor = isDark ? PROGRESS_BAR_DARK_NORMAL_TEXT_COLOR : PROGRESS_BAR_NORMAL_TEXT_COLOR; + COLORREF invertedlTextColor = isDark ? PROGRESS_BAR_DARK_INVERTED_TEXT_COLOR : PROGRESS_BAR_INVERTED_TEXT_COLOR; + COLORREF boxColor = isDark ? PROGRESS_BAR_DARK_BOX_COLOR : PROGRESS_BAR_BOX_COLOR; + COLORREF color = normalColor; switch (message) { case PBM_SETSTATE: switch (wParam) { case PBST_NORMAL: - color = PROGRESS_BAR_NORMAL_COLOR; + color = normalColor; break; case PBST_PAUSED: color = PROGRESS_BAR_PAUSED_COLOR; @@ -930,7 +943,7 @@ static INT_PTR CALLBACK ProgressCallback(HWND hCtrl, UINT message, WPARAM wParam if ((wParam == TRUE) && (!marquee_mode)) { marquee_mode = TRUE; pos = min; - color = PROGRESS_BAR_NORMAL_COLOR; + color = normalColor; SetTimer(hCtrl, TID_MARQUEE_TIMER, MARQUEE_TIMER_REFRESH, NULL); InvalidateRect(hProgress, NULL, TRUE); } else if ((wParam == FALSE) && (marquee_mode)) { @@ -971,7 +984,7 @@ static INT_PTR CALLBACK ProgressCallback(HWND hCtrl, UINT message, WPARAM wParam // Optional first segment if (pos + ((max - min) / 5) > max) { rc.right = MulDiv(pos + ((max - min) / 5) - max, rc.right, max - min); - SetTextColor(hDC, PROGRESS_BAR_INVERTED_TEXT_COLOR); + SetTextColor(hDC, invertedlTextColor); SetBkColor(hDC, color); ExtTextOut(hDC, (full_right - size.cx) / 2, (rc.bottom - size.cy) / 2, ETO_CLIPPED | ETO_OPAQUE | ETO_NUMERICSLOCAL, &rc, winfo, (int)wcslen(winfo), NULL); @@ -981,8 +994,8 @@ static INT_PTR CALLBACK ProgressCallback(HWND hCtrl, UINT message, WPARAM wParam // Optional second segment if (pos > min) { rc.right = MulDiv(pos - min, rc.right, max - min); - SetTextColor(hDC, PROGRESS_BAR_NORMAL_TEXT_COLOR); - SetBkColor(hDC, PROGRESS_BAR_BACKGROUND_COLOR); + SetTextColor(hDC, normalTextColor); + SetBkColor(hDC, backgroundColor); ExtTextOut(hDC, (full_right - size.cx) / 2, (rc.bottom - size.cy) / 2, ETO_CLIPPED | ETO_OPAQUE | ETO_NUMERICSLOCAL, &rc, winfo, (int)wcslen(winfo), NULL); rc.left = rc.right; @@ -990,14 +1003,14 @@ static INT_PTR CALLBACK ProgressCallback(HWND hCtrl, UINT message, WPARAM wParam } // Second to last segment rc.right = MulDiv(pos - min + ((max - min) / 5), rc.right, max - min); - SetTextColor(hDC, PROGRESS_BAR_INVERTED_TEXT_COLOR); + SetTextColor(hDC, invertedlTextColor); SetBkColor(hDC, color); ExtTextOut(hDC, (full_right - size.cx) / 2, (rc.bottom - size.cy) / 2, ETO_CLIPPED | ETO_OPAQUE | ETO_NUMERICSLOCAL, &rc, winfo, (int)wcslen(winfo), NULL); } else { // First segment rc.right = (pos > min) ? MulDiv(pos - min, rc.right, max - min) : rc.left; - SetTextColor(hDC, PROGRESS_BAR_INVERTED_TEXT_COLOR); + SetTextColor(hDC, invertedlTextColor); SetBkColor(hDC, color); ExtTextOut(hDC, (full_right - size.cx) / 2, (rc.bottom - size.cy) / 2, ETO_CLIPPED | ETO_OPAQUE | ETO_NUMERICSLOCAL, &rc, winfo, (int)wcslen(winfo), NULL); @@ -1005,12 +1018,12 @@ static INT_PTR CALLBACK ProgressCallback(HWND hCtrl, UINT message, WPARAM wParam // Last segment rc.left = rc.right; rc.right = full_right; - SetTextColor(hDC, PROGRESS_BAR_NORMAL_TEXT_COLOR); - SetBkColor(hDC, PROGRESS_BAR_BACKGROUND_COLOR); + SetTextColor(hDC, normalTextColor); + SetBkColor(hDC, backgroundColor); ExtTextOut(hDC, (full_right - size.cx) / 2, (rc.bottom - size.cy) / 2, ETO_CLIPPED | ETO_OPAQUE | ETO_NUMERICSLOCAL, &rc, winfo, (int)wcslen(winfo), NULL); // Bounding rectangle - SetDCPenColor(hDC, PROGRESS_BAR_BOX_COLOR); + SetDCPenColor(hDC, boxColor); Rectangle(hDC, rc2.left, rc2.top, rc2.right, rc2.bottom); EndPaint(hCtrl, &ps); return (INT_PTR)TRUE; @@ -1060,9 +1073,17 @@ void CreateAdditionalControls(HWND hDlg) hIconDown = (HICON)LoadImage(hDll, MAKEINTRESOURCE(16750), IMAGE_ICON, s16, s16, LR_DEFAULTCOLOR | LR_SHARED); hUpImageList = ImageList_Create(i16, i16, ILC_COLOR32 | ILC_HIGHQUALITYSCALE, 1, 0); hDownImageList = ImageList_Create(i16, i16, ILC_COLOR32 | ILC_HIGHQUALITYSCALE, 1, 0); - ImageList_AddIcon(hUpImageList, hIconUp); - ImageList_AddIcon(hDownImageList, hIconDown); - + if (!IsAppsUseDarkMode()) + { + ImageList_AddIcon(hUpImageList, hIconUp); + ImageList_AddIcon(hDownImageList, hIconDown); + } + else + { + ImageList_AddMasked(hUpImageList, LoadBitmap(0, MAKEINTRESOURCE(32753)), CLR_DEFAULT); + ImageList_AddMasked(hDownImageList, LoadBitmap(0, MAKEINTRESOURCE(32752)), CLR_DEFAULT); + } + // Create the advanced options toolbars memset(wtbtext, 0, sizeof(wtbtext)); utf8_to_wchar_no_alloc(lmprintf((advanced_mode_device) ? MSG_122 : MSG_121, lmprintf(MSG_119)), wtbtext[0], ARRAYSIZE(wtbtext[0])); @@ -1585,10 +1606,12 @@ void SetBootTypeDropdownWidth(void) void OnPaint(HDC hdc) { int i; - HPEN hp = CreatePen(0, (fScale < 1.5f) ? 2 : 3, RGB(0, 0, 0)); + + HPEN hp = CreatePen(0, (fScale < 1.5f) ? 2 : 3, IsAppsUseDarkMode() ? RGB(255,255,255) : RGB(0, 0, 0)); SelectObject(hdc, hp); for (i = 0; i < ARRAYSIZE(section_vpos); i++) { MoveToEx(hdc, mw + 10, section_vpos[i], NULL); LineTo(hdc, mw + fw, section_vpos[i]); } + } diff --git a/src/ui.h b/src/ui.h index 746aefc7..c0bb1a2c 100644 --- a/src/ui.h +++ b/src/ui.h @@ -21,7 +21,8 @@ #include #include "resource.h" #include "localization.h" - +//#include +//#include #pragma once // Progress bar colors @@ -33,8 +34,17 @@ #define PROGRESS_BAR_PAUSED_COLOR RGB(0xDA, 0xCB, 0x26) #define PROGRESS_BAR_ERROR_COLOR RGB(0xDA, 0x26, 0x26) +#define PROGRESS_BAR_DARK_NORMAL_TEXT_COLOR RGB(0xFF, 0xFF, 0xFF) +#define PROGRESS_BAR_DARK_INVERTED_TEXT_COLOR RGB(0x00, 0x00, 0x00) +#define PROGRESS_BAR_DARK_BACKGROUND_COLOR RGB(0x3F, 0x3F, 0x3F) +#define PROGRESS_BAR_DARK_BOX_COLOR RGB(192, 192,192) +#define PROGRESS_BAR_DARK_NORMAL_COLOR RGB(40,100,180) +#define PROGRESS_BAR_DARK_PAUSED_COLOR RGB(0xDA, 0xCB, 0x26) +#define PROGRESS_BAR_DARK_ERROR_COLOR RGB(0xDA, 0x26, 0x26) +#define ColorControlDark RGB(32, 32, 32) + // Toolbar icons main color -#define TOOLBAR_ICON_COLOR RGB(0x29, 0x80, 0xB9) +#define TOOLBAR_ICON_COLOR RGB(255, 255, 255) //(0x29, 0x80, 0xB9) // Toolbar default style #define TOOLBAR_STYLE ( WS_CHILD | WS_TABSTOP | WS_VISIBLE | \ @@ -106,3 +116,4 @@ extern void ShowLanguageMenu(RECT rcExclude); extern void SetPassesTooltip(void); extern void SetBootTypeDropdownWidth(void); extern void OnPaint(HDC hdc); +static UINT_PTR uIdSubclass = 1; From dba0b8c659bfcd66eef1be89c994ad0e6f4646f7 Mon Sep 17 00:00:00 2001 From: Mohmed abdel-fattah Date: Wed, 26 Jun 2024 12:50:04 +0300 Subject: [PATCH 2/2] fix MinGW build issues --- .mingw/Makefile.am | 2 +- .mingw/Makefile.in | 2 +- .mingw/dwmapi.def | 1 + .mingw/uxtheme.def | 79 ++++++++++++++++++++++++++++ .vs/rufus.vcxproj | 32 ++++++------ src/Makefile.in | 2 +- src/registry.h | 7 +++ src/rufus.c | 58 +++++++++----------- src/stdlg.c | 128 ++++++++++++++++++++++++++++++++++++++------- src/ui.h | 2 +- src/ui_data.h | 4 ++ 11 files changed, 244 insertions(+), 73 deletions(-) create mode 100644 .mingw/uxtheme.def diff --git a/.mingw/Makefile.am b/.mingw/Makefile.am index cb131d61..2326c9ca 100644 --- a/.mingw/Makefile.am +++ b/.mingw/Makefile.am @@ -19,7 +19,7 @@ TARGET := $(word 1,$(subst -, ,$(TUPLE))) DEF_SUFFIX := $(if $(TARGET:x86_64=),.def,.def64) .PHONY: all -all: dwmapi-delaylib.lib version-delaylib.lib wintrust-delaylib.lib +all: dwmapi-delaylib.lib version-delaylib.lib wintrust-delaylib.lib uxtheme-delaylib.lib %.def64: %.def $(AM_V_SED) "s/@.*//" $< >$@ diff --git a/.mingw/Makefile.in b/.mingw/Makefile.in index 0dda8fb1..877c4d83 100644 --- a/.mingw/Makefile.in +++ b/.mingw/Makefile.in @@ -367,7 +367,7 @@ uninstall-am: .PHONY: all -all: dwmapi-delaylib.lib version-delaylib.lib wintrust-delaylib.lib +all: dwmapi-delaylib.lib version-delaylib.lib wintrust-delaylib.lib uxtheme-delaylib.lib %.def64: %.def $(AM_V_SED) "s/@.*//" $< >$@ diff --git a/.mingw/dwmapi.def b/.mingw/dwmapi.def index 240e17c7..393c04e0 100644 --- a/.mingw/dwmapi.def +++ b/.mingw/dwmapi.def @@ -1,2 +1,3 @@ EXPORTS DwmGetWindowAttribute@16 + DwmSetWindowAttribute@16 diff --git a/.mingw/uxtheme.def b/.mingw/uxtheme.def new file mode 100644 index 00000000..3f772ac0 --- /dev/null +++ b/.mingw/uxtheme.def @@ -0,0 +1,79 @@ +; +; Definition file of UxTheme.dll +; Automatic generated by gendef +; written by Kai Tietz 2008 +; +LIBRARY "UxTheme.dll" +EXPORTS +BeginPanningFeedback@4 +EndPanningFeedback@8 +UpdatePanningFeedback@16 +BeginBufferedAnimation@32 +BeginBufferedPaint@20 +BufferedPaintClear@8 +BufferedPaintInit@0 +BufferedPaintRenderAnimation@8 +BufferedPaintSetAlpha@12 +DrawThemeBackgroundEx@24 +BufferedPaintStopAllAnimations@4 +BufferedPaintUnInit@0 +CloseThemeData@4 +DrawThemeBackground@24 +DrawThemeEdge@32 +DrawThemeIcon@28 +DrawThemeParentBackground@12 +DrawThemeParentBackgroundEx@16 +DrawThemeText@36 +OpenThemeDataEx@12 +DrawThemeTextEx@36 +EnableThemeDialogTexture@8 +EnableTheming@4 +EndBufferedAnimation@8 +EndBufferedPaint@8 +GetBufferedPaintBits@12 +GetBufferedPaintDC@4 +GetBufferedPaintTargetDC@4 +GetBufferedPaintTargetRect@8 +GetCurrentThemeName@24 +GetThemeAppProperties@0 +GetThemeBackgroundContentRect@24 +GetThemeBackgroundExtent@24 +GetThemeBackgroundRegion@24 +GetThemeBitmap@24 +GetThemeBool@20 +GetThemeColor@20 +GetThemeDocumentationProperty@16 +GetThemeEnumValue@20 +GetThemeFilename@24 +GetThemeFont@24 +GetThemeInt@20 +GetThemeIntList@20 +GetThemeMargins@28 +GetThemeMetric@24 +GetThemePartSize@28 +GetThemePosition@20 +GetThemePropertyOrigin@20 +GetThemeRect@20 +GetThemeStream@28 +GetThemeString@24 +GetThemeSysBool@8 +GetThemeSysColor@8 +GetThemeSysColorBrush@8 +GetThemeSysFont@12 +GetThemeSysInt@12 +GetThemeSysSize@8 +GetThemeSysString@16 +GetThemeTextExtent@36 +GetThemeTextMetrics@20 +GetThemeTransitionDuration@24 +GetWindowTheme@4 +HitTestThemeBackground@40 +IsAppThemed@0 +IsCompositionActive@0 +IsThemeActive@0 +IsThemeBackgroundPartiallyTransparent@12 +IsThemeDialogTextureEnabled@4 +IsThemePartDefined@12 +OpenThemeData@8 +SetThemeAppProperties@4 +SetWindowTheme@12 \ No newline at end of file diff --git a/.vs/rufus.vcxproj b/.vs/rufus.vcxproj index 7266623b..414c633f 100644 --- a/.vs/rufus.vcxproj +++ b/.vs/rufus.vcxproj @@ -133,12 +133,12 @@ /utf-8 $(ExternalCompilerOptions) %(AdditionalOptions) - advapi32.lib;comctl32.lib;crypt32.lib;gdi32.lib;ole32.lib;dwmapi.lib;setupapi.lib;shell32.lib;shlwapi.lib;version.lib;wintrust.lib;%(AdditionalDependencies) + advapi32.lib;comctl32.lib;crypt32.lib;gdi32.lib;ole32.lib;dwmapi.lib;setupapi.lib;uxtheme.lib;shell32.lib;shlwapi.lib;version.lib;wintrust.lib;%(AdditionalDependencies) RequireAdministrator true Windows MachineX86 - advapi32.dll;comctl32.dll;crypt32.dll;gdi32.dll;ole32.dll;dwmapi.dll;setupapi.dll;shell32.dll;shlwapi.dll;version.dll;wintrust.dll;%(DelayLoadDLLs) + advapi32.dll;comctl32.dll;crypt32.dll;gdi32.dll;ole32.dll;dwmapi.dll;setupapi.dll;uxtheme.dll;shell32.dll;shlwapi.dll;version.dll;wintrust.dll;%(DelayLoadDLLs) _UNICODE;UNICODE;%(PreprocessorDefinitions) @@ -162,12 +162,12 @@ /utf-8 $(ExternalCompilerOptions) %(AdditionalOptions) - advapi32.lib;comctl32.lib;crypt32.lib;gdi32.lib;ole32.lib;dwmapi.lib;setupapi.lib;shell32.lib;shlwapi.lib;version.lib;wintrust.lib;ole32.lib;advapi32.lib;gdi32.lib;shell32.lib;comdlg32.lib;%(AdditionalDependencies) + advapi32.lib;comctl32.lib;crypt32.lib;gdi32.lib;ole32.lib;dwmapi.lib;setupapi.lib;uxtheme.lib;shell32.lib;shlwapi.lib;version.lib;wintrust.lib;ole32.lib;advapi32.lib;gdi32.lib;shell32.lib;comdlg32.lib;%(AdditionalDependencies) RequireAdministrator true Windows C:\Program Files (x86)\Windows Kits\10\Lib\10.0.15063.0\um\arm - advapi32.dll;comctl32.dll;crypt32.dll;gdi32.dll;ole32.dll;dwmapi.dll;setupapi.dll;shell32.dll;shlwapi.dll;version.dll;wintrust.dll;ole32.dll;advapi32.dll;gdi32.dll;shell32.dll;comdlg32.dll;%(DelayLoadDLLs) + advapi32.dll;comctl32.dll;crypt32.dll;gdi32.dll;ole32.dll;dwmapi.dll;setupapi.dll;uxtheme.dll;shell32.dll;shlwapi.dll;version.dll;wintrust.dll;ole32.dll;advapi32.dll;gdi32.dll;shell32.dll;comdlg32.dll;%(DelayLoadDLLs) _UNICODE;UNICODE;%(PreprocessorDefinitions) @@ -193,12 +193,12 @@ /utf-8 $(ExternalCompilerOptions) %(AdditionalOptions) - advapi32.lib;comctl32.lib;crypt32.lib;gdi32.lib;ole32.lib;dwmapi.lib;setupapi.lib;shell32.lib;shlwapi.lib;version.lib;wintrust.lib;ole32.lib;advapi32.lib;gdi32.lib;shell32.lib;comdlg32.lib;%(AdditionalDependencies) + advapi32.lib;comctl32.lib;crypt32.lib;gdi32.lib;ole32.lib;dwmapi.lib;setupapi.lib;uxtheme.lib;shell32.lib;shlwapi.lib;version.lib;wintrust.lib;ole32.lib;advapi32.lib;gdi32.lib;shell32.lib;comdlg32.lib;%(AdditionalDependencies) RequireAdministrator true Windows C:\Program Files (x86)\Windows Kits\10\Lib\10.0.16299.0\um\arm64 - advapi32.dll;comctl32.dll;crypt32.dll;gdi32.dll;ole32.dll;dwmapi.dll;setupapi.dll;shell32.dll;shlwapi.dll;version.dll;wintrust.dll;ole32.dll;advapi32.dll;gdi32.dll;shell32.dll;comdlg32.dll;%(DelayLoadDLLs) + advapi32.dll;comctl32.dll;crypt32.dll;gdi32.dll;ole32.dll;dwmapi.dll;setupapi.dll;uxtheme.dll;shell32.dll;shlwapi.dll;version.dll;wintrust.dll;ole32.dll;advapi32.dll;gdi32.dll;shell32.dll;comdlg32.dll;%(DelayLoadDLLs) _UNICODE;UNICODE;%(PreprocessorDefinitions) @@ -229,12 +229,12 @@ /utf-8 $(ExternalCompilerOptions) %(AdditionalOptions) - advapi32.lib;comctl32.lib;crypt32.lib;gdi32.lib;ole32.lib;dwmapi.lib;setupapi.lib;shell32.lib;shlwapi.lib;version.lib;wintrust.lib;%(AdditionalDependencies) + advapi32.lib;comctl32.lib;crypt32.lib;gdi32.lib;ole32.lib;dwmapi.lib;setupapi.lib;uxtheme.lib;shell32.lib;shlwapi.lib;version.lib;wintrust.lib;%(AdditionalDependencies) RequireAdministrator true Windows MachineX64 - advapi32.dll;comctl32.dll;crypt32.dll;gdi32.dll;ole32.dll;dwmapi.dll;setupapi.dll;shell32.dll;shlwapi.dll;version.dll;wintrust.dll;%(DelayLoadDLLs) + advapi32.dll;comctl32.dll;crypt32.dll;gdi32.dll;ole32.dll;dwmapi.dll;setupapi.dll;uxtheme.dll;shell32.dll;shlwapi.dll;version.dll;wintrust.dll;%(DelayLoadDLLs) _UNICODE;UNICODE;%(PreprocessorDefinitions) @@ -260,13 +260,13 @@ true - advapi32.lib;comctl32.lib;crypt32.lib;gdi32.lib;ole32.lib;dwmapi.lib;setupapi.lib;shell32.lib;shlwapi.lib;version.lib;wintrust.lib;%(AdditionalDependencies) + advapi32.lib;comctl32.lib;crypt32.lib;gdi32.lib;ole32.lib;dwmapi.lib;setupapi.lib;uxtheme.lib;shell32.lib;shlwapi.lib;version.lib;wintrust.lib;%(AdditionalDependencies) RequireAdministrator false Windows MachineX86 /BREPRO %(AdditionalOptions) - advapi32.dll;comctl32.dll;crypt32.dll;gdi32.dll;ole32.dll;dwmapi.dll;setupapi.dll;shell32.dll;shlwapi.dll;version.dll;wintrust.dll;%(DelayLoadDLLs) + advapi32.dll;comctl32.dll;crypt32.dll;gdi32.dll;ole32.dll;dwmapi.dll;setupapi.dll;uxtheme.dll;shell32.dll;shlwapi.dll;version.dll;wintrust.dll;%(DelayLoadDLLs) _UNICODE;UNICODE;%(PreprocessorDefinitions) @@ -292,13 +292,13 @@ true - advapi32.lib;comctl32.lib;crypt32.lib;gdi32.lib;ole32.lib;dwmapi.lib;setupapi.lib;shell32.lib;shlwapi.lib;version.lib;wintrust.lib;ole32.lib;advapi32.lib;gdi32.lib;shell32.lib;comdlg32.lib;%(AdditionalDependencies) + advapi32.lib;comctl32.lib;crypt32.lib;gdi32.lib;ole32.lib;dwmapi.lib;setupapi.lib;uxtheme.lib;shell32.lib;shlwapi.lib;version.lib;wintrust.lib;ole32.lib;advapi32.lib;gdi32.lib;shell32.lib;comdlg32.lib;%(AdditionalDependencies) RequireAdministrator false Windows C:\Program Files (x86)\Windows Kits\10\Lib\10.0.15063.0\um\arm /BREPRO %(AdditionalOptions) - advapi32.dll;comctl32.dll;crypt32.dll;gdi32.dll;ole32.dll;dwmapi.dll;setupapi.dll;shell32.dll;shlwapi.dll;version.dll;wintrust.dll;ole32.dll;advapi32.dll;gdi32.dll;shell32.dll;comdlg32.dll;%(DelayLoadDLLs) + advapi32.dll;comctl32.dll;crypt32.dll;gdi32.dll;ole32.dll;dwmapi.dll;setupapi.dll;uxtheme.dll;shell32.dll;shlwapi.dll;version.dll;wintrust.dll;ole32.dll;advapi32.dll;gdi32.dll;shell32.dll;comdlg32.dll;%(DelayLoadDLLs) _UNICODE;UNICODE;%(PreprocessorDefinitions) @@ -326,13 +326,13 @@ true - advapi32.lib;comctl32.lib;crypt32.lib;gdi32.lib;ole32.lib;dwmapi.lib;setupapi.lib;shell32.lib;shlwapi.lib;version.lib;wintrust.lib;ole32.lib;advapi32.lib;gdi32.lib;shell32.lib;comdlg32.lib;%(AdditionalDependencies) + advapi32.lib;comctl32.lib;crypt32.lib;gdi32.lib;ole32.lib;dwmapi.lib;setupapi.lib;uxtheme.lib;shell32.lib;shlwapi.lib;version.lib;wintrust.lib;ole32.lib;advapi32.lib;gdi32.lib;shell32.lib;comdlg32.lib;%(AdditionalDependencies) RequireAdministrator false Windows C:\Program Files (x86)\Windows Kits\10\Lib\10.0.16299.0\um\arm64 /BREPRO %(AdditionalOptions) - advapi32.dll;comctl32.dll;crypt32.dll;gdi32.dll;ole32.dll;dwmapi.dll;setupapi.dll;shell32.dll;shlwapi.dll;version.dll;wintrust.dll;ole32.dll;advapi32.dll;gdi32.dll;shell32.dll;comdlg32.dll;%(DelayLoadDLLs) + advapi32.dll;comctl32.dll;crypt32.dll;gdi32.dll;ole32.dll;dwmapi.dll;setupapi.dll;uxtheme.dll;shell32.dll;shlwapi.dll;version.dll;wintrust.dll;ole32.dll;advapi32.dll;gdi32.dll;shell32.dll;comdlg32.dll;%(DelayLoadDLLs) _UNICODE;UNICODE;%(PreprocessorDefinitions) @@ -363,13 +363,13 @@ true - advapi32.lib;comctl32.lib;crypt32.lib;gdi32.lib;ole32.lib;dwmapi.lib;setupapi.lib;shell32.lib;shlwapi.lib;version.lib;wintrust.lib;%(AdditionalDependencies) + advapi32.lib;comctl32.lib;crypt32.lib;gdi32.lib;ole32.lib;dwmapi.lib;setupapi.lib;uxtheme.lib;uxtheme.lib;shell32.lib;shlwapi.lib;version.lib;wintrust.lib;%(AdditionalDependencies) RequireAdministrator false Windows MachineX64 /BREPRO %(AdditionalOptions) - advapi32.dll;comctl32.dll;crypt32.dll;gdi32.dll;ole32.dll;dwmapi.dll;setupapi.dll;shell32.dll;shlwapi.dll;version.dll;wintrust.dll;%(DelayLoadDLLs) + advapi32.dll;comctl32.dll;crypt32.dll;gdi32.dll;ole32.dll;dwmapi.dll;setupapi.dll;uxtheme.dll;shell32.dll;shlwapi.dll;version.dll;wintrust.dll;%(DelayLoadDLLs) _UNICODE;UNICODE;%(PreprocessorDefinitions) diff --git a/src/Makefile.in b/src/Makefile.in index 70d31a54..6c20da30 100644 --- a/src/Makefile.in +++ b/src/Makefile.in @@ -280,7 +280,7 @@ NONVULNERABLE_LIBS = -lsetupapi -lole32 -lgdi32 -lshlwapi -lcrypt32 -lcomctl32 - # Ideally there would also be virtdisk and wininet as delaylib's below, but the MinGW folks haven't quite sorted out delay-loading # for x86_32 so as soon as you try to call APIs from these, the application will crash! # See https://github.com/pbatard/rufus/issues/1877#issuecomment-1109683039 as well as https://github.com/pbatard/rufus/issues/2272 -VULNERABLE_LIBS = -ldwmapi-delaylib -lversion-delaylib -lwintrust-delaylib +VULNERABLE_LIBS = -ldwmapi-delaylib -lversion-delaylib -lwintrust-delaylib -luxtheme-delaylib AM_V_WINDRES_0 = @echo " RC $@";$(WINDRES) AM_V_WINDRES_1 = $(WINDRES) AM_V_WINDRES_ = $(AM_V_WINDRES_$(AM_DEFAULT_VERBOSITY)) diff --git a/src/registry.h b/src/registry.h index 7e8312bc..b6d401ea 100644 --- a/src/registry.h +++ b/src/registry.h @@ -26,10 +26,17 @@ #ifdef __cplusplus extern "C" { #endif + +// disable all warnings until fix theme +#ifdef __GNUC__ +#pragma GCC diagnostic ignored "-Wstrict-prototypes" +#pragma GCC diagnostic ignored "-Wunused-variable" +#endif #define REGKEY_HKCU HKEY_CURRENT_USER #define REGKEY_HKLM HKEY_LOCAL_MACHINE + /* Delete a registry key from \Software and all its values If the key has subkeys, this call will fail. */ static __inline BOOL DeleteRegistryKey(HKEY key_root, const char* key_name) diff --git a/src/rufus.c b/src/rufus.c index d106ec71..4d1c6f34 100755 --- a/src/rufus.c +++ b/src/rufus.c @@ -59,8 +59,9 @@ #include "../res/grub2/grub2_version.h" #include #include -#pragma comment(lib,"UxTheme.lib") -#pragma comment(lib,"DwmApi.lib") +#include + + enum bootcheck_return { BOOTCHECK_PROCEED = 0, BOOTCHECK_CANCEL = -1, @@ -106,7 +107,7 @@ extern const char* old_c32_name[NB_OLD_C32]; extern const char* cert_name[3]; extern const char* FileSystemLabel[FS_MAX]; extern const char *bootmgr_efi_name, *efi_dirname, *efi_bootname[ARCH_MAX]; - +static UINT_PTR uIdSubclass = 1; /* * Globals */ @@ -154,8 +155,7 @@ RUFUS_DRIVE rufus_drive[MAX_DRIVES] = { 0 }; // This function sets the alpha channel to 255 without // affecting any of the color channels. -void MakeBitmapOpaque( - HDC hdc, int x, int y, int cx, int cy) +void MakeBitmapOpaque( HDC hdc, int x, int y, int cx, int cy) { BITMAPINFO bi = {0}; bi.bmiHeader.biSize = sizeof(BITMAPINFOHEADER); @@ -164,12 +164,8 @@ void MakeBitmapOpaque( bi.bmiHeader.biPlanes = 1; bi.bmiHeader.biBitCount = 32; bi.bmiHeader.biCompression = BI_RGB; - RGBQUAD bitmapBits = { 0x00, 0x00, 0x00, 0xFF }; - - StretchDIBits(hdc, x, y, cx, cy, - 0, 0, 1, 1, &bitmapBits, &bi, - DIB_RGB_COLORS, SRCPAINT); + StretchDIBits(hdc, x, y, cx, cy, 0, 0, 1, 1, &bitmapBits, &bi,DIB_RGB_COLORS, SRCPAINT); } // TODO: Remember to update copyright year in stdlg's AboutCallback() WM_INITDIALOG, @@ -963,10 +959,9 @@ out: * DarkMode CheckBox Subclass Proc */ -static LRESULT CALLBACK ButtonSubclassProc(HWND hWnd, UINT uMsg, WPARAM wParam, - LPARAM lParam, UINT_PTR uIdSubclass, DWORD_PTR dwRefData) +static LRESULT CALLBACK ButtonSubclassProc(HWND hWnd, UINT uMsg, WPARAM wParam,LPARAM lParam, UINT_PTR idSubclass, DWORD_PTR dwRefData) { - if (!IsAppsUseDarkMode) + if (!IsAppsUseDarkMode()) { return DefSubclassProc(hWnd, uMsg, wParam, lParam); } @@ -993,15 +988,15 @@ static LRESULT CALLBACK ButtonSubclassProc(HWND hWnd, UINT uMsg, WPARAM wParam, rc1.left += siz.cx + 2; FillRect(hDc, &rc1, CreateSolidBrush(ColorControlDark)); rc1.top += GetSystemMetrics(SM_CXPADDEDBORDER); - LPCWSTR* staticText[99] = {0}; - GetWindowText(hWnd, staticText, ARRAYSIZE(staticText)); + WCHAR szCaption[60]; + GetWindowText(hWnd, szCaption, ARRAYSIZE(szCaption)); DTTOPTS opts; opts.dwSize = sizeof(DTTOPTS); opts.dwFlags = DTT_TEXTCOLOR; opts.crText = RGB(255, 255, 255); HFONT font = (HFONT)SendMessage(hWnd, WM_GETFONT, 0, 0); SelectObject(hDc, font); - DrawThemeTextEx(btnTheme, hDc, 3, 0, &staticText, -1, DT_SINGLELINE | DT_LEFT, &rc1, &opts); + DrawThemeTextEx(btnTheme, hDc, 3, 0, szCaption, -1, DT_SINGLELINE | DT_LEFT, &rc1, &opts); ReleaseDC(hWnd, hDc); return true; } @@ -1013,10 +1008,10 @@ static LRESULT CALLBACK ButtonSubclassProc(HWND hWnd, UINT uMsg, WPARAM wParam, */ static BOOL CALLBACK ThemeCallback(HWND hWnd, LPARAM lParam) { - const char* str[255] = {0}; - GetClassName(hWnd, &str, 255); + WCHAR str[20] = {0}; + GetClassName(hWnd, str, 20); bool isDarkmode = IsAppsUseDarkMode(); - if (strcmp(str, L"Button") == 0) + if (_wcsicmp(str, L"Button") == 0) { LONG_PTR style = GetWindowLongPtr(hWnd, GWL_STYLE); if ((style & BS_AUTOCHECKBOX) == BS_AUTOCHECKBOX) @@ -1033,20 +1028,20 @@ static BOOL CALLBACK ThemeCallback(HWND hWnd, LPARAM lParam) else SetWindowTheme(hWnd, isDarkmode ? L"DarkMode_Explorer" : L"Explorer", NULL); } - else if (strcmp(str, L"ComboBox") == 0) + else if (_wcsicmp(str, L"ComboBox") == 0) { SetWindowTheme(hWnd, isDarkmode ? L"DarkMode_CFD" : L"Explorer", NULL); } - else if (strcmp(str, L"ToolBar") == 0) + else if (_wcsicmp(str, L"ToolbarWindow32") == 0) { wchar_t toolbarText[50]; wchar_t multiToolbarText[50] ; utf8_to_wchar_no_alloc(lmprintf(MSG_315), multiToolbarText, ARRAYSIZE(multiToolbarText)); GetWindowText(hWnd, &toolbarText, 16); - if (strcmp(toolbarText, multiToolbarText) != 0) + if (_wcsicmp(toolbarText, multiToolbarText) != 0) SetWindowTheme(hWnd, isDarkmode ? L"DarkMode" : L"Explorer", NULL); } - else if (strcmp(str, L"EDIT") == 0) + else if (_wcsicmp(str, L"EDIT") == 0) { LONG_PTR style = GetWindowLongPtr(hWnd, GWL_STYLE); if (((style & WS_VSCROLL) == WS_VSCROLL) || ((style & WS_HSCROLL) == WS_HSCROLL)) @@ -1065,11 +1060,9 @@ static BOOL CALLBACK ThemeCallback(HWND hWnd, LPARAM lParam) * DarkMod Dialog Subclass Proc */ -static LRESULT CALLBACK DlgSubclassProc(HWND hDlg, UINT message, WPARAM wParam, - LPARAM lParam, UINT_PTR uIdSubclass, DWORD_PTR dwRefData) +static LRESULT CALLBACK DlgSubclassProc(HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam, UINT_PTR idSubclass, DWORD_PTR dwRefData) { - RECT rcDlg; - GetClientRect(hDlg, &rcDlg); + HDC dc; switch (message) { @@ -1088,16 +1081,17 @@ static LRESULT CALLBACK DlgSubclassProc(HWND hDlg, UINT message, WPARAM wParam, int borderWidth = (rcWinWidth - rcrcClientWidth) / 2; int captionHight = rcWinHieght - rcrcClientHieght - borderWidth; OffsetRect(&rcWin, -rcWin.left, -rcWin.top); - OffsetRect(&rcClient, borderWidth, captionHight); - HRGN updateRgn = wParam != 1 ?(HRGN)wParam : CreateRectRgnIndirect(&rcWin); + OffsetRect(&rcClient, -rcWin.left, -rcWin.top); + HRGN copy =CreateRectRgn(0, 0, 0, 0); + HRGN updateRgn = wParam != 1 ? copy : CreateRectRgnIndirect(&rcWin); HRGN clipRgn = CreateRectRgn(0, 0, 0, 0); HRGN ncRgn = CreateRectRgn(0, 0, 0, 0); - + CombineRgn(copy, copy, (HRGN)wParam, RGN_COPY); if (wParam == 1) clipRgn = CreateRectRgnIndirect(&rcClient); else GetClipRgn(windowDC, clipRgn); - CombineRgn(ncRgn, updateRgn, clipRgn, RGN_DIFF); + CombineRgn(ncRgn, updateRgn, clipRgn, RGN_OR); SelectClipRgn(windowDC, ncRgn); FillRect(windowDC, &rcWin, CreateSolidBrush(RGB(63, 63, 63))); HRGN hRgn= CreateRectRgnIndirect(&rcWin); @@ -1177,8 +1171,6 @@ static LRESULT CALLBACK DlgSubclassProc(HWND hDlg, UINT message, WPARAM wParam, return (INT_PTR)CreateSolidBrush(ColorControlDark); case WM_CTLCOLORSTATIC: dc = GetDC((HWND)lParam); - RECT rcDlg; - GetClientRect((HWND)lParam, &rcDlg); safe_release_dc((HWND)lParam, dc); if ((HWND)lParam == GetDlgItem(hDlg, IDC_LABEL)) { diff --git a/src/stdlg.c b/src/stdlg.c index 532f81c5..5d9afca8 100644 --- a/src/stdlg.c +++ b/src/stdlg.c @@ -44,6 +44,7 @@ #include "settings.h" #include "license.h" #include +#include /* Globals */ extern BOOL is_x86_64, appstore_version; @@ -61,6 +62,7 @@ static const char* notification_dont_display_setting; static WNDPROC update_original_proc = NULL; static HWINEVENTHOOK ap_weh = NULL; static char title_str[2][128], button_str[128]; +static UINT_PTR uIdSubclass = 1; HWND hFidoDlg = NULL; static int update_settings_reposition_ids[] = { @@ -76,6 +78,8 @@ static int update_settings_reposition_ids[] = { IDCANCEL, }; + + /* * https://blogs.msdn.microsoft.com/oldnewthing/20040802-00/?p=38283/ */ @@ -88,10 +92,9 @@ void SetDialogFocus(HWND hDlg, HWND hCtrl) * DarkMode CheckBox Subclass Proc */ -static LRESULT CALLBACK ButtonSubclassProc(HWND hWnd, UINT uMsg, WPARAM wParam, - LPARAM lParam, UINT_PTR uIdSubclass, DWORD_PTR dwRefData) +static LRESULT CALLBACK ButtonSubclassProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam, UINT_PTR idSubclass, DWORD_PTR dwRefData) { - if (!IsAppsUseDarkMode) + if (!IsAppsUseDarkMode()) { return DefSubclassProc(hWnd, uMsg, wParam, lParam); } @@ -118,15 +121,15 @@ static LRESULT CALLBACK ButtonSubclassProc(HWND hWnd, UINT uMsg, WPARAM wParam, rc1.left += siz.cx + 2; FillRect(hDc, &rc1, CreateSolidBrush(ColorControlDark)); rc1.top += GetSystemMetrics(SM_CXPADDEDBORDER); - LPCWSTR* staticText[99] = {0}; - GetWindowText(hWnd, staticText, ARRAYSIZE(staticText)); + WCHAR szCaption[60]; + GetWindowText(hWnd, szCaption, ARRAYSIZE(szCaption)); DTTOPTS opts; opts.dwSize = sizeof(DTTOPTS); opts.dwFlags = DTT_TEXTCOLOR; opts.crText = RGB(255, 255, 255); HFONT font = (HFONT)SendMessage(hWnd, WM_GETFONT, 0, 0); SelectObject(hDc, font); - DrawThemeTextEx(btnTheme, hDc, 3, 0, &staticText, -1, DT_SINGLELINE | DT_LEFT, &rc1, &opts); + DrawThemeTextEx(btnTheme, hDc, 3, 0, szCaption, -1, DT_SINGLELINE | DT_LEFT, &rc1, &opts); ReleaseDC(hWnd, hDc); return TRUE; } @@ -140,11 +143,11 @@ static LRESULT CALLBACK ButtonSubclassProc(HWND hWnd, UINT uMsg, WPARAM wParam, static BOOL CALLBACK ThemeCallback(HWND hWnd, LPARAM lParam) { - char* str[255]; - GetClassName(hWnd, &str, 255); + WCHAR str[30] = { 0 }; + GetClassName(hWnd, str, ARRAYSIZE(str)); BOOL isDarkMode = IsAppsUseDarkMode(); - if (strcmp(str, L"Button") == 0) + if (_wcsicmp(str, L"Button") == 0) { LONG_PTR style = GetWindowLongPtr(hWnd, GWL_STYLE); if ((style & BS_AUTOCHECKBOX) == BS_AUTOCHECKBOX) @@ -161,18 +164,18 @@ static BOOL CALLBACK ThemeCallback(HWND hWnd, LPARAM lParam) else SetWindowTheme(hWnd, isDarkMode ? L"DarkMode_Explorer" : L"Explorer", NULL); } - else if (strcmp(str, L"ComboBox") == 0) + else if (_wcsicmp(str, L"ComboBox") == 0) { SetWindowTheme(hWnd, isDarkMode ? L"DarkMode_CFD" : L"Explorer", NULL); } - else if (strcmp(str, L"ToolBar") == 0) + else if (_wcsicmp(str, L"ToolBar") == 0) { - char* title[16]; - GetWindowText(hWnd, &title, 16); - if (strcmp(title, L"Multiple buttons") != 0) + WCHAR title[30] = {0}; + GetWindowText(hWnd, title, ARRAYSIZE(title)); + if (_wcsicmp(title, L"Multiple buttons") != 0) SetWindowTheme(hWnd, isDarkMode ? L"DarkMode" : L"Explorer", NULL); } - else if (strcmp(str, L"EDIT") == 0) + else if (_wcsicmp(str, L"EDIT") == 0) { LONG_PTR style = GetWindowLongPtr(hWnd, GWL_STYLE); if(((style & WS_VSCROLL) == WS_VSCROLL) || ((style & WS_HSCROLL) == WS_HSCROLL)) @@ -182,7 +185,7 @@ static BOOL CALLBACK ThemeCallback(HWND hWnd, LPARAM lParam) } - else if (strcmp(str, L"RichEdit20W") == 0) + else if (_wcsicmp(str, L"RichEdit20W") == 0) { SendMessage(hWnd, EM_SETBKGNDCOLOR, 0, isDarkMode ? (LPARAM)ColorControlDark : (LPARAM)GetSysColor(COLOR_BTNFACE)); CHARFORMAT cf; @@ -204,8 +207,7 @@ static BOOL CALLBACK ThemeCallback(HWND hWnd, LPARAM lParam) * DarkMod Dialog Subclass Proc */ -static LRESULT CALLBACK DlgSubclassProc(HWND hDlg, UINT message, WPARAM wParam, - LPARAM lParam, UINT_PTR uIdSubclass, DWORD_PTR dwRefData) +static LRESULT CALLBACK DlgSubclassProc(HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam, UINT_PTR idSubclass, DWORD_PTR dwRefData) { if (!IsAppsUseDarkMode()) { @@ -213,9 +215,94 @@ static LRESULT CALLBACK DlgSubclassProc(HWND hDlg, UINT message, WPARAM wParam, } switch (message) { + case WM_NCPAINT: + { + LRESULT result = DefSubclassProc(hDlg, message, wParam, lParam); + HDC windowDC = GetWindowDC(hDlg); + RECT rcWin, rcClient; + GetWindowRect(hDlg, &rcWin); + GetClientRect(hDlg, &rcClient); + MapWindowPoints(hDlg, NULL, (LPPOINT)&rcWin, 2); + int rcWinWidth = rcWin.right - rcWin.left; + int rcWinHieght = rcWin.bottom - rcWin.top; + int rcrcClientWidth = rcClient.right - rcClient.left; + int rcrcClientHieght = rcClient.bottom - rcClient.top; + int borderWidth = (rcWinWidth - rcrcClientWidth) / 2; + int captionHight = rcWinHieght - rcrcClientHieght - borderWidth; + OffsetRect(&rcWin, -rcWin.left, -rcWin.top); + OffsetRect(&rcClient, -rcWin.left, -rcWin.top); + HRGN copy = CreateRectRgn(0, 0, 0, 0); + HRGN updateRgn = wParam != 1 ? copy : CreateRectRgnIndirect(&rcWin); + HRGN clipRgn = CreateRectRgn(0, 0, 0, 0); + HRGN ncRgn = CreateRectRgn(0, 0, 0, 0); + CombineRgn(copy, copy, (HRGN)wParam, RGN_COPY); + if (wParam == 1) + clipRgn = CreateRectRgnIndirect(&rcClient); + else + GetClipRgn(windowDC, clipRgn); + CombineRgn(ncRgn, updateRgn, clipRgn, RGN_OR); + SelectClipRgn(windowDC, ncRgn); + FillRect(windowDC, &rcWin, CreateSolidBrush(RGB(63, 63, 63))); + HRGN hRgn = CreateRectRgnIndirect(&rcWin); + SelectClipRgn(windowDC, hRgn); + MakeBitmapOpaque(windowDC, 0, 0, rcWinWidth, rcWinHieght); + safe_release_dc(hDlg, windowDC); + return result; + } + case WM_NCCALCSIZE: + { + //TODO: get real caption Size + + if (wParam) + { + NCCALCSIZE_PARAMS* ncParma = (NCCALCSIZE_PARAMS*)(lParam); + ncParma->rgrc[0].left += 1;//pr++; + ncParma->rgrc[0].top += 31; + ncParma->rgrc[0].right -= 1; + ncParma->rgrc[0].bottom -= 1; + return 0; + } + else + { + RECT* rect = (RECT*)lParam; + rect->top += 31; + rect->left += 1; + rect->right -= 1; + rect->bottom -= 1; + return 0; + } + } + case WM_SHOWWINDOW: - EnumChildWindows(hDlg, ThemeCallback, lParam); - return DefWindowProc(hDlg, message, wParam, lParam); + { + if (wParam) + { + EnumChildWindows(hDlg, ThemeCallback, lParam); + BOOL allowncpaint = TRUE; + COLORREF caption = RGB(0x0, 0x0, 0x0); + DwmSetWindowAttribute(hDlg, DWMWA_CAPTION_COLOR, &caption, sizeof caption); + DwmSetWindowAttribute(hDlg, DWMWA_BORDER_COLOR, &caption, sizeof caption); + DwmSetWindowAttribute(hDlg, DWMWA_ALLOW_NCPAINT, &allowncpaint, sizeof(int)); + RECT rcDlg; + GetWindowRect(hDlg, &rcDlg); + SetWindowPos(hDlg, 0, 0, 0, rcDlg.right - rcDlg.left, rcDlg.bottom - rcDlg.top, SWP_FRAMECHANGED | SWP_NOSIZE | SWP_NOMOVE); + + if (hLog) + { + RECT rcLog; + GetWindowRect(hLog, &rcLog); + GetClientRect(hDlg, &rcDlg); + rcLog.left = rcDlg.left + 1; + rcLog.right = rcDlg.right - 1; + SetWindowPos(hLog, NULL, 0, 0, rcLog.right - rcLog.left, rcLog.bottom - rcLog.top, SWP_NOMOVE | SWP_NOZORDER); + } + RedrawWindow(hDlg, NULL, NULL, RDW_ALLCHILDREN | RDW_UPDATENOW | RDW_INVALIDATE | RDW_FRAME | RDW_ERASENOW); + } + + return DefSubclassProc(hDlg, message, wParam, lParam); + + } + case WM_CTLCOLORLISTBOX: SetBkColor((HDC)wParam, RGB(25, 25, 25)); SetTextColor((HDC)wParam, RGB(255, 255, 255)); @@ -228,6 +315,7 @@ static LRESULT CALLBACK DlgSubclassProc(HWND hDlg, UINT message, WPARAM wParam, return (INT_PTR)CreateSolidBrush(RGB(25, 25, 25)); } + case WM_CTLCOLORBTN: case WM_CTLCOLORDLG: return (INT_PTR)CreateSolidBrush(ColorControlDark); diff --git a/src/ui.h b/src/ui.h index c0bb1a2c..0e2189be 100644 --- a/src/ui.h +++ b/src/ui.h @@ -116,4 +116,4 @@ extern void ShowLanguageMenu(RECT rcExclude); extern void SetPassesTooltip(void); extern void SetBootTypeDropdownWidth(void); extern void OnPaint(HDC hdc); -static UINT_PTR uIdSubclass = 1; +extern void MakeBitmapOpaque(HDC hdc, int x, int y, int cx, int cy); diff --git a/src/ui_data.h b/src/ui_data.h index be33e8c1..03dde1d7 100644 --- a/src/ui_data.h +++ b/src/ui_data.h @@ -20,6 +20,10 @@ #include #include "resource.h" + // disable all warnings about unused variable +#ifdef __GNUC__ +#pragma GCC diagnostic ignored "-Wunused-variable" +#endif #pragma once // GUIDs needed to set a control's accessibility props