Jump to content

UEZ

MVPs
  • Posts

    7,443
  • Joined

  • Last visited

  • Days Won

    94

UEZ last won the day on February 27

UEZ had the most liked content!

About UEZ

  • Birthday 12/03/2007

Profile Information

  • Member Title
    Never say never
  • Location
    Germany
  • Interests
    Computer, watching movies, football (soccer), being lazy :-)

Recent Profile Visitors

10,836 profile views

UEZ's Achievements

  1. This works in my example: Func _SetDarkTreeViewCheckboxes($hTreeView) Local $hImageList = _GUIImageList_Create(16, 16, 5, 3) Local $hBmp_GDI = _WinAPI_ExtractThemeBackground($g_hGUI, 2) ;thanks to WildByDesign for the idea! _GUIImageList_Add($hImageList, $hBmp_GDI) _WinAPI_DeleteObject($hBmp_GDI) $hBmp_GDI = _WinAPI_ExtractThemeBackground($g_hGUI, 5) _GUIImageList_Add($hImageList, $hBmp_GDI) _WinAPI_DeleteObject($hBmp_GDI) _GUICtrlTreeView_SetStateImageList($hTreeView, $hImageList) Return True EndFunc ;==>_SetDarkTreeViewCheckboxes Func _WinAPI_ExtractThemeBackground($hGUI, $iState, $iPart = 3, $iWidth = 16, $iHeight = 16) Local $hTheme = _WinAPI_OpenThemeData($hGUI, "DarkMode_DarkTheme::Button") If @error Then Return SetError(1, 0, 0) Local $hDC = _WinAPI_GetDC($hGUI) Local $hHBitmap = _WinAPI_CreateCompatibleBitmap($hDC, $iWidth, $iHeight) Local $hMemDC = _WinAPI_CreateCompatibleDC($hDC) Local $hObjOld = _WinAPI_SelectObject($hMemDC, $hHBitmap) Local $tRECT = _WinAPI_CreateRectEx(0, 0, $iWidth, $iHeight) _WinAPI_DrawThemeBackground($hTheme, $iPart, $iState, $hMemDC, $tRECT) If @error Then _WinAPI_CloseThemeData($hTheme) Return SetError(2, 0, 0) EndIf _WinAPI_SelectObject($hMemDC, $hObjOld) _WinAPI_ReleaseDC($hGUI, $hDC) _WinAPI_DeleteDC($hMemDC) _WinAPI_CloseThemeData($hTheme) Return $hHBitmap EndFunc ;==>_WinAPI_ExtractThemeBackground Important is to use: "DarkMode_DarkTheme::Button"
  2. I changed in my example the drawing from GDI to GDI+ completely. Func _GDIPlus_DrawRoundRect($hGfx, $iX, $iY, $iW, $iH, $iDiameter, $iBrushARGB, $iPenARGB, $fPenWidth = 1.0) Local Const $hPath = _GDIPlus_PathCreate() ; Top-left arc _GDIPlus_PathAddArc($hPath, $iX, $iY, $iDiameter, $iDiameter, 180, 90) ; Top-right arc _GDIPlus_PathAddArc($hPath, $iX + $iW - $iDiameter, $iY, $iDiameter, $iDiameter, 270, 90) ; Bottom-right arc _GDIPlus_PathAddArc($hPath, $iX + $iW - $iDiameter, $iY + $iH - $iDiameter, $iDiameter, $iDiameter, 0, 90) ; Bottom-left arc _GDIPlus_PathAddArc($hPath, $iX, $iY + $iH - $iDiameter, $iDiameter, $iDiameter, 90, 90) _GDIPlus_PathCloseFigure($hPath) If $iBrushARGB <> 0 Then Local Const $hBrush = _GDIPlus_BrushCreateSolid($iBrushARGB) _GDIPlus_GraphicsFillPath($hGfx, $hPath, $hBrush) _GDIPlus_BrushDispose($hBrush) EndIf If $iPenARGB <> 0 Then Local Const $hPen = _GDIPlus_PenCreate($iPenARGB, $fPenWidth) _GDIPlus_GraphicsDrawPath($hGfx, $hPath, $hPen) _GDIPlus_PenDispose($hPen) EndIf _GDIPlus_PathDispose($hPath) EndFunc ;==>_GDIPlus_DrawRoundRect Func _SetDarkTreeViewCheckboxes($hTreeView, $iW = 16, $iH = 16) Local $hImageList = _GUIImageList_Create($iW, $iH, 5, 3) Local $hBmp = _GDIPlus_BitmapCreateFromScan0($iW, $iH) Local $hGfx = _GDIPlus_ImageGetGraphicsContext($hBmp) _GDIPlus_GraphicsSetSmoothingMode($hGfx, $GDIP_SMOOTHINGMODE_HIGHQUALITY) ; --- Index 0: Unchecked --- _GDIPlus_GraphicsClear($hGfx, 0xFF000000 + $COLOR_EDIT_BG) _GDIPlus_DrawRoundRect($hGfx, 2 / 16 * $iW, 2 / 16 * $iH, 12 / 16 * $iW, 12 / 16 * $iH, 3, 0, 0xFF000000 + $COLOR_BORDER2, 1.5) Local $hBmp_GDI = _GDIPlus_BitmapCreateHBITMAPFromBitmap($hBmp, 0) _GUIImageList_Add($hImageList, $hBmp_GDI) _WinAPI_DeleteObject($hBmp_GDI) ; --- Index 1: Checked --- _GDIPlus_GraphicsClear($hGfx, 0xFF000000 + $COLOR_EDIT_BG) _GDIPlus_DrawRoundRect($hGfx, 2 / 16 * $iW, 2 / 16 * $iH, 12 / 16 * $iW, 12 / 16 * $iH, 3, 0xFF60CDFF, 0xFF60CDFF, 1.0) Local $hCheckPen = _GDIPlus_PenCreate(0xFF0F2028, 1.5) _GDIPlus_GraphicsDrawLine($hGfx, 5 / 16 * $iW, 8 / 16 * $iH, 7 / 16 * $iW, 10 / 16 * $iH, $hCheckPen) _GDIPlus_GraphicsDrawLine($hGfx, 7 / 16 * $iW, 10 / 16 * $iH, 11 / 16 * $iW, 6 / 16 * $iH, $hCheckPen) $hBmp_GDI = _GDIPlus_BitmapCreateHBITMAPFromBitmap($hBmp, 0) _GUIImageList_Add($hImageList, $hBmp_GDI) _WinAPI_DeleteObject($hBmp_GDI) ; --- Cleanup --- _GDIPlus_PenDispose($hCheckPen) _GDIPlus_GraphicsDispose($hGfx) _GDIPlus_ImageDispose($hBmp) _GUICtrlTreeView_SetStateImageList($hTreeView, $hImageList) Return True EndFunc ;==>_SetDarkTreeViewCheckboxes It gives much more smoother drawings with aa. To your new idea - I like it. You can draw to a GDI bitmap and add it to ImageList. Let me check it and add it to the example...
  3. _WM_INITMENUPOPUP() is useless and can be removed.
  4. I updated also my example by drawing the checkbox using GDI+ with aa. It uses GDI and GDIPlus to create it -> see _SetDarkTreeViewCheckboxes() function. Next step is to add DPI using _WinAPI_DPI.au3 from here: Let's see how complicated it will be to draw all the controls on DPI changes...
  5. GUIDarkTheme.au3 incl. base64 icons: #include-once #AutoIt3Wrapper_Au3Check_Parameters=-q -d -w 1 -w 2 -w 3 -w 4 -w 5 -w 6 -w 7 #include <GDIPlus.au3> ; #INDEX# ======================================================================================================================= ; Title .........: GUIDarkTheme UDF Library for AutoIt3 ; AutoIt Version : 3.3.18.0 ; Language ......: English ; Description ...: UDF library for applying dark theme to win32 controls ; Author(s) .....: WildByDesign (including previous code from NoNameCode, argumentum, UEZ) ; Version .......: 0.9 ; =============================================================================================================================== ; Windows messages used by GUIDarkTheme: (only when relevant controls are detected) ; $WM_CTLCOLORLISTBOX ; $WM_CTLCOLOREDIT ; $WM_NOTIFY ; Windows messages used by GUIDarkMenu: (activated only if GUI has a menubar) ; $WM_DRAWITEM ; $WM_MEASUREITEM ; $WM_NCPAINT ; $WM_ACTIVATE #Region Functions list ; #CURRENT# ===================================================================================================================== ; _GUISetDarkTheme ; _GUICtrlSetDarkTheme ; _GUICtrlAllSetDarkTheme ; _ApplyDarkTheme ; _ApplyLightTheme ; =============================================================================================================================== #EndRegion Functions list #Region API Functions list ; #CURRENT# ===================================================================================================================== ; _WinAPI_ShouldAppsUseDarkMode ; _WinAPI_AllowDarkModeForWindow ; _WinAPI_AllowDarkModeForApp ; _WinAPI_FlushMenuThemes ; _WinAPI_RefreshImmersiveColorPolicyState ; _WinAPI_IsDarkModeAllowedForWindow ; _WinAPI_GetIsImmersiveColorUsingHighContrast ; _WinAPI_OpenNcThemeData ; =============================================================================================================================== #EndRegion API Functions list #include <GuiMonthCal.au3> #include <GuiDateTimePicker.au3> #include <WindowsConstants.au3> #include <GuiListView.au3> #include <TabConstants.au3> #include <GuiImageList.au3> #include <GuiTreeView.au3> #include <GuiMenu.au3> #include "GUIDarkInternal.au3" #include "GUIDarkMenu.au3" #Region Global Variables and Constants ; #VARIABLES# =================================================================================================================== ; Windows build information Global $iOSBuild = @OSBuild Global $iRevision = RegRead("HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows NT\CurrentVersion", "UBR") Global $b24H2Plus = False If $iOSBuild >= 26100 And $iRevision >= 6899 Then $b24H2Plus = True ; Fake lower build number to test DarkMode_Explorer ;$b24H2Plus = False ; Declare edit brush Global $g_hBrushEdit = 0 ; Global variable for tab subclassing Global $g_hTab_CB, $g_pTab_CB, $g_hProc, $g_hTab ; Set global variable placeholders in the case SysListView32 control is detected ; TODO: need better method if there are multiple ListView controls Global $hWndListViewHeader, $hWndListView Global $g__ListView_wProcNew = 0, $g__ListView_wProcOld = 0 ; DateTimePicker Global $g_hDateProc_CB, $g_pDateProc_CB, $g_hDateOldProc, $g_hDate Global Const $PRF_CLIENT = 0x0004, $DTP_BORDER = 0x404040, $DTP_BG_DARK = $COLOR_CONTROL_BG, $DTP_TEXT_LIGHT = $COLOR_TEXT_LIGHT, $DTP_BORDER_LIGHT = 0xD8D8D8 Global $g_bHover = False ; Structure for NM_CUSTOMDRAW notification Global Const $tagNMCUSTOMDRAW = _ $tagNMHDR & ";" & _ ; Contains NM_CUSTOMDRAW / NMHDR header among other things "dword dwDrawStage;" & _ ; Current drawing stage (CDDS_*) "handle hdc;" & _ ; Device Context Handle "long left;long top;long right;long bottom;" & _ ; Drawing rectangle "dword_ptr dwItemSpec;" & _ ; Item index or other info (depending on the control) "uint uItemState;" & _ ; State Flags (CDIS_SELECTED, CDIS_FOCUS etc.) "lparam lItemlParam" ; lParam set by the item (e.g., via LVITEM.lParam) #Region ; GUIStyles.inc.au3 ;~ #include "GUIStyles.inc.au3" Global Const $_g__Style_Gui[32][2] = _ [[0x80000000, 'WS_POPUP'], _ [0x40000000, 'WS_CHILD'], _ [0x20000000, 'WS_MINIMIZE'], _ [0x10000000, 'WS_VISIBLE'], _ [0x08000000, 'WS_DISABLED'], _ [0x04000000, 'WS_CLIPSIBLINGS'], _ [0x02000000, 'WS_CLIPCHILDREN'], _ [0x01000000, 'WS_MAXIMIZE'], _ [0x00CF0000, 'WS_OVERLAPPEDWINDOW'], _ ; (WS_CAPTION | WS_SYSMENU | WS_SIZEBOX | WS_MINIMIZEBOX | WS_MAXIMIZEBOX) aka 'WS_TILEDWINDOW' [0x00C00000, 'WS_CAPTION'], _ ; (WS_BORDER | WS_DLGFRAME) [0x00800000, 'WS_BORDER'], _ [0x00400000, 'WS_DLGFRAME'], _ [0x00200000, 'WS_VSCROLL'], _ [0x00100000, 'WS_HSCROLL'], _ [0x00080000, 'WS_SYSMENU'], _ [0x00040000, 'WS_SIZEBOX'], _ [0x00020000, '! WS_MINIMIZEBOX ! WS_GROUP'], _ ; ! GUI ! Control [0x00010000, '! WS_MAXIMIZEBOX ! WS_TABSTOP'], _ ; ! GUI ! Control [0x00002000, 'DS_CONTEXTHELP'], _ [0x00001000, 'DS_CENTERMOUSE'], _ [0x00000800, 'DS_CENTER'], _ [0x00000400, 'DS_CONTROL'], _ [0x00000200, 'DS_SETFOREGROUND'], _ [0x00000100, 'DS_NOIDLEMSG'], _ [0x00000080, 'DS_MODALFRAME'], _ [0x00000040, 'DS_SETFONT'], _ [0x00000020, 'DS_LOCALEDIT'], _ [0x00000010, 'DS_NOFAILCREATE'], _ [0x00000008, 'DS_FIXEDSYS'], _ [0x00000004, 'DS_3DLOOK'], _ [0x00000002, 'DS_SYSMODAL'], _ [0x00000001, 'DS_ABSALIGN']] ; ; [0x80880000, 'WS_POPUPWINDOW'] ; [0x20000000, 'WS_ICONIC'] ; [0x00040000, 'WS_THICKFRAME'] ; ; [0x00000000, 'WS_OVERLAPPED'] ; also named 'WS_TILED' Global Const $_g__Style_GuiExtended[21][2] = _ [[0x08000000, 'WS_EX_NOACTIVATE'], _ [0x02000000, 'WS_EX_COMPOSITED'], _ [0x00400000, 'WS_EX_LAYOUTRTL'], _ [0x00100000, '! WS_EX_NOINHERITLAYOUT ! GUI_WS_EX_PARENTDRAG'], _ ; ! GUI ! Control (label or pic, AutoIt "draggable" feature on 2 controls) [0x00080000, 'WS_EX_LAYERED'], _ [0x00040000, 'WS_EX_APPWINDOW'], _ [0x00020000, 'WS_EX_STATICEDGE'], _ [0x00010000, 'WS_EX_CONTROLPARENT'], _ ; AutoIt adds a "draggable" feature to this GUI extended style behavior [0x00004000, 'WS_EX_LEFTSCROLLBAR'], _ [0x00002000, 'WS_EX_RTLREADING'], _ [0x00001000, 'WS_EX_RIGHT'], _ [0x00000400, 'WS_EX_CONTEXTHELP'], _ [0x00000200, 'WS_EX_CLIENTEDGE'], _ [0x00000100, 'WS_EX_WINDOWEDGE'], _ [0x00000080, 'WS_EX_TOOLWINDOW'], _ [0x00000040, 'WS_EX_MDICHILD'], _ [0x00000020, 'WS_EX_TRANSPARENT'], _ [0x00000010, 'WS_EX_ACCEPTFILES'], _ [0x00000008, 'WS_EX_TOPMOST'], _ [0x00000004, 'WS_EX_NOPARENTNOTIFY'], _ [0x00000001, 'WS_EX_DLGMODALFRAME']] ; ; [0x00000300, 'WS_EX_OVERLAPPEDWINDOW'] ; [0x00000188, 'WS_EX_PALETTEWINDOW'] ; ; [0x00000000, 'WS_EX_LEFT'] ; [0x00000000, 'WS_EX_LTRREADING'] ; [0x00000000, 'WS_EX_RIGHTSCROLLBAR'] Global Const $_g__Style_Avi[5][2] = _ [[0x0010, 'ACS_NONTRANSPARENT'], _ [0x0008, 'ACS_TIMER'], _ [0x0004, 'ACS_AUTOPLAY'], _ [0x0002, 'ACS_TRANSPARENT'], _ [0x0001, 'ACS_CENTER']] Global Const $_g__Style_Button[20][2] = _ [[0x8000, 'BS_FLAT'], _ [0x4000, 'BS_NOTIFY'], _ [0x2000, 'BS_MULTILINE'], _ [0x1000, 'BS_PUSHLIKE'], _ [0x0C00, 'BS_VCENTER'], _ [0x0800, 'BS_BOTTOM'], _ [0x0400, 'BS_TOP'], _ [0x0300, 'BS_CENTER'], _ [0x0200, 'BS_RIGHT'], _ [0x0100, 'BS_LEFT'], _ [0x0080, 'BS_BITMAP'], _ [0x0040, 'BS_ICON'], _ [0x0020, 'BS_RIGHTBUTTON'], _ [0x0009, 'BS_AUTORADIOBUTTON'] , _ [0x0007, 'BS_GROUPBOX'], _ [0x0006, 'BS_AUTO3STATE'], _ [0x0005, 'BS_3STATE'], _ [0x0003, 'BS_AUTOCHECKBOX'], _ [0x0002, 'BS_CHECKBOX'], _ [0x0001, 'BS_DEFPUSHBUTTON']] Global Const $_g__Style_Combo[13][2] = _ [[0x4000, 'CBS_LOWERCASE'], _ [0x2000, 'CBS_UPPERCASE'], _ [0x0800, 'CBS_DISABLENOSCROLL'], _ [0x0400, 'CBS_NOINTEGRALHEIGHT'], _ [0x0200, 'CBS_HASSTRINGS'], _ [0x0100, 'CBS_SORT'], _ [0x0080, 'CBS_OEMCONVERT'], _ [0x0040, 'CBS_AUTOHSCROLL'], _ [0x0020, 'CBS_OWNERDRAWVARIABLE'], _ [0x0010, 'CBS_OWNERDRAWFIXED'], _ [0x0003, 'CBS_DROPDOWNLIST'], _ [0x0002, 'CBS_DROPDOWN'], _ [0x0001, 'CBS_SIMPLE']] Global Const $_g__Style_Common[12][2] = _ ; "for rebar controls, toolbar controls, and status windows (msdn)" [[0x0083, 'CCS_RIGHT'], _ [0x0082, 'CCS_NOMOVEX'], _ [0x0081, 'CCS_LEFT'], _ [0x0080, 'CCS_VERT'], _ [0x0040, 'CCS_NODIVIDER'], _ [0x0020, 'CCS_ADJUSTABLE'], _ [0x0010, 'CCS_NOHILITE'], _ [0x0008, 'CCS_NOPARENTALIGN'], _ [0x0004, 'CCS_NORESIZE'], _ [0x0003, 'CCS_BOTTOM'], _ [0x0002, 'CCS_NOMOVEY'], _ [0x0001, 'CCS_TOP']] Global Const $_g__Style_DateTime[7][2] = _ [[0x0020, 'DTS_RIGHTALIGN'], _ [0x0010, 'DTS_APPCANPARSE'], _ [0x000C, 'DTS_SHORTDATECENTURYFORMAT'], _ [0x0009, 'DTS_TIMEFORMAT'], _ [0x0004, 'DTS_LONGDATEFORMAT'], _ [0x0002, 'DTS_SHOWNONE'], _ [0x0001, 'DTS_UPDOWN']] ; ; [0x0000, 'DTS_SHORTDATEFORMAT'] Global Const $_g__Style_Edit[13][2] = _ [[0x2000, 'ES_NUMBER'], _ [0x1000, 'ES_WANTRETURN'], _ [0x0800, 'ES_READONLY'], _ [0x0400, 'ES_OEMCONVERT'], _ [0x0100, 'ES_NOHIDESEL'], _ [0x0080, 'ES_AUTOHSCROLL'], _ [0x0040, 'ES_AUTOVSCROLL'], _ [0x0020, 'ES_PASSWORD'], _ [0x0010, 'ES_LOWERCASE'], _ [0x0008, 'ES_UPPERCASE'], _ [0x0004, 'ES_MULTILINE'], _ [0x0002, 'ES_RIGHT'], _ [0x0001, 'ES_CENTER']] Global Const $_g__Style_Header[10][2] = _ [[0x1000, 'HDS_OVERFLOW'], _ [0x0800, 'HDS_NOSIZING'], _ [0x0400, 'HDS_CHECKBOXES'], _ [0x0200, 'HDS_FLAT'], _ [0x0100, 'HDS_FILTERBAR'], _ [0x0080, 'HDS_FULLDRAG'], _ [0x0040, 'HDS_DRAGDROP'], _ [0x0008, 'HDS_HIDDEN'], _ [0x0004, 'HDS_HOTTRACK'], _ [0x0002, 'HDS_BUTTONS']] ; ; [0x0000, '$HDS_HORZ'] Global Const $_g__Style_ListBox[16][2] = _ [[0x8000, 'LBS_COMBOBOX'], _ [0x4000, 'LBS_NOSEL'], _ [0x2000, 'LBS_NODATA'], _ [0x1000, 'LBS_DISABLENOSCROLL'], _ [0x0800, 'LBS_EXTENDEDSEL'], _ [0x0400, 'LBS_WANTKEYBOARDINPUT'], _ [0x0200, 'LBS_MULTICOLUMN'], _ [0x0100, 'LBS_NOINTEGRALHEIGHT'], _ [0x0080, 'LBS_USETABSTOPS'], _ [0x0040, 'LBS_HASSTRINGS'], _ [0x0020, 'LBS_OWNERDRAWVARIABLE'], _ [0x0010, 'LBS_OWNERDRAWFIXED'], _ [0x0008, 'LBS_MULTIPLESEL'], _ [0x0004, 'LBS_NOREDRAW'], _ [0x0002, 'LBS_SORT'], _ [0x0001, 'LBS_NOTIFY']] ; ; [0xA00003, 'LBS_STANDARD'] ; i.e. (LBS_NOTIFY | LBS_SORT | WS_VSCROLL | WS_BORDER) help file correct, ListBoxConstants.au3 incorrect Global Const $_g__Style_ListView[17][2] = _ [[0x8000, 'LVS_NOSORTHEADER'], _ [0x4000, 'LVS_NOCOLUMNHEADER'], _ [0x2000, 'LVS_NOSCROLL'], _ [0x1000, 'LVS_OWNERDATA'], _ [0x0800, 'LVS_ALIGNLEFT'], _ [0x0400, 'LVS_OWNERDRAWFIXED'], _ [0x0200, 'LVS_EDITLABELS'], _ [0x0100, 'LVS_AUTOARRANGE'], _ [0x0080, 'LVS_NOLABELWRAP'], _ [0x0040, 'LVS_SHAREIMAGELISTS'], _ [0x0020, 'LVS_SORTDESCENDING'], _ [0x0010, 'LVS_SORTASCENDING'], _ [0x0008, 'LVS_SHOWSELALWAYS'], _ [0x0004, 'LVS_SINGLESEL'], _ [0x0003, 'LVS_LIST'], _ [0x0002, 'LVS_SMALLICON'], _ [0x0001, 'LVS_REPORT']] ; ; [0x0000, 'LVS_ICON'] ; [0x0000, 'LVS_ALIGNTOP'] Global Const $_g__Style_ListViewExtended[20][2] = _ [[0x00100000, 'LVS_EX_SIMPLESELECT'], _ [0x00080000, 'LVS_EX_SNAPTOGRID'], _ [0x00020000, 'LVS_EX_HIDELABELS'], _ [0x00010000, 'LVS_EX_DOUBLEBUFFER'], _ [0x00008000, 'LVS_EX_BORDERSELECT'], _ [0x00004000, 'LVS_EX_LABELTIP'], _ [0x00002000, 'LVS_EX_MULTIWORKAREAS'], _ [0x00001000, 'LVS_EX_UNDERLINECOLD'], _ [0x00000800, 'LVS_EX_UNDERLINEHOT'], _ [0x00000400, 'LVS_EX_INFOTIP'], _ [0x00000200, 'LVS_EX_REGIONAL'], _ [0x00000100, 'LVS_EX_FLATSB'], _ [0x00000080, 'LVS_EX_TWOCLICKACTIVATE'], _ [0x00000040, 'LVS_EX_ONECLICKACTIVATE'], _ [0x00000020, 'LVS_EX_FULLROWSELECT'], _ [0x00000010, 'LVS_EX_HEADERDRAGDROP'], _ [0x00000008, 'LVS_EX_TRACKSELECT'], _ [0x00000004, 'LVS_EX_CHECKBOXES'], _ [0x00000002, 'LVS_EX_SUBITEMIMAGES'], _ [0x00000001, 'LVS_EX_GRIDLINES']] Global Const $_g__Style_MonthCal[8][2] = _ [[0x0100, 'MCS_NOSELCHANGEONNAV'], _ [0x0080, 'MCS_SHORTDAYSOFWEEK'], _ [0x0040, 'MCS_NOTRAILINGDATES'], _ [0x0010, 'MCS_NOTODAY'], _ [0x0008, 'MCS_NOTODAYCIRCLE'], _ [0x0004, 'MCS_WEEKNUMBERS'], _ [0x0002, 'MCS_MULTISELECT'], _ [0x0001, 'MCS_DAYSTATE']] Global Const $_g__Style_Pager[3][2] = _ [[0x0004, 'PGS_DRAGNDROP'], _ [0x0002, 'PGS_AUTOSCROLL'], _ [0x0001, 'PGS_HORZ']] ; ; [0x0000, 'PGS_VERT'] Global Const $_g__Style_Progress[4][2] = _ [[0x0010, 'PBS_SMOOTHREVERSE'], _ [0x0008, 'PBS_MARQUEE'], _ [0x0004, 'PBS_VERTICAL'], _ [0x0001, 'PBS_SMOOTH']] Global Const $_g__Style_Rebar[8][2] = _ [[0x8000, 'RBS_DBLCLKTOGGLE'], _ [0x4000, 'RBS_VERTICALGRIPPER'], _ [0x2000, 'RBS_AUTOSIZE'], _ [0x1000, 'RBS_REGISTERDROP'], _ [0x0800, 'RBS_FIXEDORDER'], _ [0x0400, 'RBS_BANDBORDERS'], _ [0x0200, 'RBS_VARHEIGHT'], _ [0x0100, 'RBS_TOOLTIPS']] Global Const $_g__Style_RichEdit[8][2] = _ ; will also use plenty (not all) of Edit styles [[0x01000000, 'ES_SELECTIONBAR'], _ [0x00400000, 'ES_VERTICAL'], _ ; Asian-language support only (msdn) [0x00080000, 'ES_NOIME'], _ ; ditto [0x00040000, 'ES_SELFIME'], _ ; ditto [0x00008000, 'ES_SAVESEL'], _ [0x00004000, 'ES_SUNKEN'], _ [0x00002000, 'ES_DISABLENOSCROLL'], _ ; same value as 'ES_NUMBER' => issue ? [0x00000008, 'ES_NOOLEDRAGDROP']] ; same value as 'ES_UPPERCASE' but RichRdit controls do not support 'ES_UPPERCASE' style (msdn) Global Const $_g__Style_Scrollbar[5][2] = _ [[0x0010, 'SBS_SIZEGRIP'], _ [0x0008, 'SBS_SIZEBOX'], _ [0x0004, 'SBS_RIGHTALIGN or SBS_BOTTOMALIGN'], _ ; i.e. use SBS_RIGHTALIGN with SBS_VERT, use SBS_BOTTOMALIGN with SBS_HORZ (msdn) [0x0002, 'SBS_LEFTALIGN or SBS_TOPALIGN'], _ ; i.e. use SBS_LEFTALIGN with SBS_VERT, use SBS_TOPALIGN with SBS_HORZ (msdn) [0x0001, 'SBS_VERT']] ; ; [0x0000, 'SBS_HORZ'] Global Const $_g__Style_Slider[13][2] = _ ; i.e. trackbar [[0x1000, 'TBS_TRANSPARENTBKGND'], _ [0x0800, 'TBS_NOTIFYBEFOREMOVE'], _ [0x0400, 'TBS_DOWNISLEFT'], _ [0x0200, 'TBS_REVERSED'], _ [0x0100, 'TBS_TOOLTIPS'], _ [0x0080, 'TBS_NOTHUMB'], _ [0x0040, 'TBS_FIXEDLENGTH'], _ [0x0020, 'TBS_ENABLESELRANGE'], _ [0x0010, 'TBS_NOTICKS'], _ [0x0008, 'TBS_BOTH'], _ [0x0004, 'TBS_LEFT or TBS_TOP'], _ ; i.e. TBS_LEFT tick marks when vertical slider, or TBS_TOP tick marks when horizontal slider [0x0002, 'TBS_VERT'], _ [0x0001, 'TBS_AUTOTICKS']] ; ; [0x0000, 'TBS_RIGHT'] ; [0x0000, 'TBS_BOTTOM'] ; [0x0000, 'TBS_HORZ'] Global Const $_g__Style_Static[18][2] = _ [[0x1000, 'SS_SUNKEN'], _ [0x0400, 'SS_RIGHTJUST'], _ [0x0200, 'SS_CENTERIMAGE'], _ [0x0100, 'SS_NOTIFY'], _ [0x0080, 'SS_NOPREFIX'], _ [0x0012, 'SS_ETCHEDFRAME'], _ [0x0011, 'SS_ETCHEDVERT'], _ [0x0010, 'SS_ETCHEDHORZ'], _ [0x000C, 'SS_LEFTNOWORDWRAP'], _ [0x000B, 'SS_SIMPLE'], _ [0x0009, 'SS_WHITEFRAME'], _ [0x0008, 'SS_GRAYFRAME'], _ [0x0007, 'SS_BLACKFRAME'], _ [0x0006, 'SS_WHITERECT'], _ [0x0005, 'SS_GRAYRECT'], _ [0x0004, 'SS_BLACKRECT'], _ [0x0002, 'SS_RIGHT'], _ [0x0001, 'SS_CENTER']] ; ; [0x0000, 'SS_LEFT'] Global Const $_g__Style_StatusBar[2][2] = _ [[0x0800, 'SBARS_TOOLTIPS'], _ [0x0100, 'SBARS_SIZEGRIP']] ; ; [0x0800, 'SBT_TOOLTIPS'] Global Const $_g__Style_Tab[17][2] = _ [[0x8000, 'TCS_FOCUSNEVER'], _ [0x4000, 'TCS_TOOLTIPS'], _ [0x2000, 'TCS_OWNERDRAWFIXED'], _ [0x1000, 'TCS_FOCUSONBUTTONDOWN'], _ [0x0800, 'TCS_RAGGEDRIGHT'], _ [0x0400, 'TCS_FIXEDWIDTH'], _ [0x0200, 'TCS_MULTILINE'], _ [0x0100, 'TCS_BUTTONS'], _ [0x0080, 'TCS_VERTICAL'], _ [0x0040, 'TCS_HOTTRACK'], _ [0x0020, 'TCS_FORCELABELLEFT'], _ [0x0010, 'TCS_FORCEICONLEFT'], _ [0x0008, 'TCS_FLATBUTTONS'], _ [0x0004, 'TCS_MULTISELECT'], _ [0x0002, 'TCS_RIGHT'], _ [0x0002, 'TCS_BOTTOM'], _ [0x0001, 'TCS_SCROLLOPPOSITE']] ; ; [0x0000, 'TCS_TABS'] ; [0x0000, 'TCS_SINGLELINE'] ; [0x0000, 'TCS_RIGHTJUSTIFY'] Global Const $_g__Style_Toolbar[8][2] = _ [[0x8000, 'TBSTYLE_TRANSPARENT'], _ [0x4000, 'TBSTYLE_REGISTERDROP'], _ [0x2000, 'TBSTYLE_CUSTOMERASE'], _ [0x1000, 'TBSTYLE_LIST'], _ [0x0800, 'TBSTYLE_FLAT'], _ [0x0400, 'TBSTYLE_ALTDRAG'], _ [0x0200, 'TBSTYLE_WRAPABLE'], _ [0x0100, 'TBSTYLE_TOOLTIPS']] Global Const $_g__Style_TreeView[16][2] = _ [[0x8000, 'TVS_NOHSCROLL'], _ [0x4000, 'TVS_NONEVENHEIGHT'], _ [0x2000, 'TVS_NOSCROLL'], _ [0x1000, 'TVS_FULLROWSELECT'], _ [0x0800, 'TVS_INFOTIP'], _ [0x0400, 'TVS_SINGLEEXPAND'], _ [0x0200, 'TVS_TRACKSELECT'], _ [0x0100, 'TVS_CHECKBOXES'], _ [0x0080, 'TVS_NOTOOLTIPS'], _ [0x0040, 'TVS_RTLREADING'], _ [0x0020, 'TVS_SHOWSELALWAYS'], _ [0x0010, 'TVS_DISABLEDRAGDROP'], _ [0x0008, 'TVS_EDITLABELS'], _ [0x0004, 'TVS_LINESATROOT'], _ [0x0002, 'TVS_HASLINES'], _ [0x0001, 'TVS_HASBUTTONS']] Global Const $_g__Style_UpDown[9][2] = _ [[0x0100, 'UDS_HOTTRACK'], _ [0x0080, 'UDS_NOTHOUSANDS'], _ [0x0040, 'UDS_HORZ'], _ [0x0020, 'UDS_ARROWKEYS'], _ [0x0010, 'UDS_AUTOBUDDY'], _ [0x0008, 'UDS_ALIGNLEFT'], _ [0x0004, 'UDS_ALIGNRIGHT'], _ [0x0002, 'UDS_SETBUDDYINT'], _ [0x0001, 'UDS_WRAP']] #EndRegion ; GUIStyles.inc.au3 ; =============================================================================================================================== ; #CONSTANTS# =================================================================================================================== ;Global Const $DWMWA_USE_IMMERSIVE_DARK_MODE = (@OSBuild <= 18985) ? 19 : 20 ; before this build set to 19, otherwise set to 20, no thanks Windaube to document anything ?? ; _WinAPI_GetIsImmersiveColorUsingHighContrast($IMMERSIVE_HC_CACHE_MODE) Global Const $IHCM_USE_CACHED_VALUE = 0 Global Const $IIHCM_REFRESH = 1 ; _WinAPI_SetPreferredAppMode($PREFERREDAPPMODE) Global Const $APPMODE_DEFAULT = 0 Global Const $APPMODE_ALLOWDARK = 1 Global Const $APPMODE_FORCEDARK = 2 Global Const $APPMODE_FORCELIGHT = 3 Global Const $APPMODE_MAX = 4 OnAutoItExitRegister(_CleanExit) Func _CleanExit() If $g_hDateOldProc Then __WinAPI_SetWindowLong($g_hDate, $GWL_WNDPROC, $g_hDateOldProc) If $g_hDateProc_CB Then DllCallbackFree($g_hDateProc_CB) If $g_hBrushEdit Then __WinAPI_DeleteObject($g_hBrushEdit) If $g__ListView_wProcOld Then __WinAPI_SetWindowLong($hWndListView, $GWL_WNDPROC, $g__ListView_wProcOld) If $g__ListView_wProcNew Then DllCallbackFree($g__ListView_wProcNew) ; Restore the original window procedure for the tab control If $g_hProc Then __WinAPI_SetWindowLong($g_hTab, $GWL_WNDPROC, $g_hProc) If $g_hTab_CB Then DllCallbackFree($g_hTab_CB) EndFunc ; =============================================================================================================================== #EndRegion Global Variables and Constants #Region API Functions ; #FUNCTION# ==================================================================================================================== ; Name ..........: _WinAPI_ShouldAppsUseDarkMode ; Description ...: Checks if apps should use the dark mode. ; Syntax ........: _WinAPI_ShouldAppsUseDarkMode() ; Parameters ....: None ; Return values .: Success: Returns True if apps should use dark mode. ; Failure: Returns False and sets @error: ; -1: Operating system version is earlier than Windows 10 (version 1809, build 17763). ; Other values: DllCall error, check @error @extended for more information. ; Author ........: NoNameCode ; Modified ......: ; Remarks .......: Requires Windows 10 (version 1809, build 17763) or later. ; Related .......: ; Link ..........: http://www.opengate.at/blog/2021/08/dark-mode-win32/ ; Example .......: No ; =============================================================================================================================== Func _WinAPI_ShouldAppsUseDarkMode() If @OSBuild < 17763 Then Return SetError(-1, 0, False) Local $fnShouldAppsUseDarkMode = 132 Local $aResult = DllCall($hUxthemeDll, 'bool', $fnShouldAppsUseDarkMode) If @error Then Return SetError(@error, @extended, False) Return $aResult[0] EndFunc ;==>_WinAPI_ShouldAppsUseDarkMode ; #FUNCTION# ==================================================================================================================== ; Name ..........: _WinAPI_AllowDarkModeForWindow ; Description ...: Allows or disallows dark mode for a specific window handle. ; Syntax ........: _WinAPI_AllowDarkModeForWindow($hWnd, $bAllow = True) ; Parameters ....: $hWnd - Handle to the window. ; $bAllow - [optional] If True, allows dark mode; if False, disallows dark mode. Default is True. ; Return values .: Success: Returns True if the operation succeeded. ; Failure: Returns False and sets @error: ; -1: Operating system version is earlier than Windows 10 (version 1809, build 17763). ; Other values: DllCall error, check @error @extended for more information. ; Author ........: NoNameCode ; Modified ......: ; Remarks .......: Requires Windows 10 (version 1809, build 17763) or later. ; Related .......: ; Link ..........: http://www.opengate.at/blog/2021/08/dark-mode-win32/ ; Example .......: No ; =============================================================================================================================== Func _WinAPI_AllowDarkModeForWindow($hWnd, $bAllow = True) If @OSBuild < 17763 Then Return SetError(-1, 0, False) Local $fnAllowDarkModeForWindow = 133 Local $aResult = DllCall($hUxthemeDll, 'bool', $fnAllowDarkModeForWindow, 'hwnd', $hWnd, 'bool', $bAllow) If @error Then Return SetError(@error, @extended, False) Return $aResult[0] EndFunc ;==>_WinAPI_AllowDarkModeForWindow ; #FUNCTION# ==================================================================================================================== ; Name ..........: _WinAPI_AllowDarkModeForApp ; Description ...: Allows or disallows dark mode for the entire application. ; Syntax ........: _WinAPI_AllowDarkModeForApp($bAllow = True) ; Parameters ....: $bAllow - [optional] If True, allows dark mode for the application; if False, disallows dark mode. Default is True. ; Return values .: Success: Returns True if the operation succeeded. ; Failure: Returns False and sets @error: ; -1: Operating system version is earlier than Windows 10 (version 1809, build 17763). ; -2: Operating system version is later than or equal to Windows 10 (version 1903, build 18362). (Use _WinAPI_SetPreferredAppMode instat!) ; Other values: DllCall error, check @error @extended for more information. ; Author ........: NoNameCode ; Modified ......: ; Remarks .......: Requires Windows 10 (version 1809, build 17763) and earlier than Windows 10 (version 1903, build 18362). ; Related .......: _WinAPI_SetPreferredAppMode ; Link ..........: http://www.opengate.at/blog/2021/08/dark-mode-win32/ ; Example .......: No ; =============================================================================================================================== Func _WinAPI_AllowDarkModeForApp($bAllow = True) If @OSBuild < 17763 Then Return SetError(-1, 0, False) If @OSBuild >= 18362 Then Return SetError(-2, 0, False) Local $fnAllowDarkModeForApp = 135 Local $aResult = DllCall($hUxthemeDll, 'bool', $fnAllowDarkModeForApp, 'bool', $bAllow) If @error Then Return SetError(@error, @extended, False) Return $aResult[0] EndFunc ;==>_WinAPI_AllowDarkModeForApp ; #FUNCTION# ==================================================================================================================== ; Name ..........: _WinAPI_FlushMenuThemes ; Description ...: Refreshes the system's immersive color policy state, allowing changes to take effect. ; Syntax ........: _WinAPI_FlushMenuThemes() ; Parameters ....: None ; Return values .: Success: True ; Failure: False and sets the @error flag: ; -1: Operating system version is earlier than Windows 10 (version 17763) ; Other values: DllCall error, check @error @extended for more information. ; Author ........: NoNameCode ; Modified ......: ; Remarks .......: This function is applicable for Windows 10 (version 17763) and later. ; Related .......: ; Link ..........: http://www.opengate.at/blog/2021/08/dark-mode-win32/ ; Example .......: No ; =============================================================================================================================== Func _WinAPI_FlushMenuThemes() If @OSBuild < 17763 Then Return SetError(-1, 0, False) Local $fnFlushMenuThemes = 136 DllCall($hUxthemeDll, 'none', $fnFlushMenuThemes) If @error Then Return SetError(@error, @extended, False) Return True EndFunc ;==>_WinAPI_FlushMenuThemes ; #FUNCTION# ==================================================================================================================== ; Name ..........: _WinAPI_RefreshImmersiveColorPolicyState ; Description ...: Refreshes the system's immersive color policy state, allowing changes to take effect. ; Syntax ........: _WinAPI_RefreshImmersiveColorPolicyState() ; Parameters ....: None ; Return values .: Success: True ; Failure: False and sets the @error flag: ; -1: Operating system version is earlier than Windows 10 (version 17763) ; Other values: DllCall error, check @error @extended for more information. ; Author ........: NoNameCode ; Modified ......: ; Remarks .......: This function is applicable for Windows 10 (version 17763) and later. ; Related .......: ; Link ..........: http://www.opengate.at/blog/2021/08/dark-mode-win32/ ; Example .......: No ; =============================================================================================================================== Func _WinAPI_RefreshImmersiveColorPolicyState() If @OSBuild < 17763 Then Return SetError(-1, 0, False) Local $fnRefreshImmersiveColorPolicyState = 104 DllCall($hUxthemeDll, 'none', $fnRefreshImmersiveColorPolicyState) If @error Then Return SetError(@error, @extended, False) Return True EndFunc ;==>_WinAPI_RefreshImmersiveColorPolicyState ; #FUNCTION# ==================================================================================================================== ; Name ..........: _WinAPI_IsDarkModeAllowedForWindow ; Description ...: Checks if the dark mode is allowed for the specified window. ; Syntax ........: _WinAPI_IsDarkModeAllowedForWindow() ; Parameters ....: None ; Return values .: Success: True if dark mode is allowed for the window, False otherwise. ; Failure: False and sets the @error flag: ; -1: Operating system version is earlier than Windows 10 (version 17763) ; Other values: DllCall error, check @error @extended for more information. ; Author ........: NoNameCode ; Modified ......: ; Remarks .......: This function is applicable for Windows 10 (version 17763) and later. ; Related .......: ; Link ..........: http://www.opengate.at/blog/2021/08/dark-mode-win32/ ; Example .......: No ; =============================================================================================================================== Func _WinAPI_IsDarkModeAllowedForWindow() If @OSBuild < 17763 Then Return SetError(-1, 0, False) Local $fnIsDarkModeAllowedForWindow = 137 Local $aResult = DllCall($hUxthemeDll, 'bool', $fnIsDarkModeAllowedForWindow) If @error Then Return SetError(@error, @extended, False) Return $aResult[0] EndFunc ;==>_WinAPI_IsDarkModeAllowedForWindow ; #FUNCTION# ==================================================================================================================== ; Name ..........: _WinAPI_GetIsImmersiveColorUsingHighContrast ; Description ...: Retrieves whether immersive color is using high contrast. ; Syntax ........: _WinAPI_GetIsImmersiveColorUsingHighContrast($IMMERSIVE_HC_CACHE_MODE) ; Parameters ....: $IMMERSIVE_HC_CACHE_MODE - The cache mode. Use one of the following values: ; $IHCM_USE_CACHED_VALUE (0) - Use the cached value. (Default) ; $IHCM_REFRESH (1) - Refresh the value. ; Return values .: Success: True if immersive color is using high contrast. ; Failure: False and sets the @error flag: ; -1: Operating system version is earlier than Windows 10 (version 17763) ; Other values: DllCall error, check @error @extended for more information. ; Author ........: NoNameCode ; Modified ......: ; Remarks .......: This function is applicable for Windows 10 (version 17763) and later. ; Related .......: ; Link ..........: http://www.opengate.at/blog/2021/08/dark-mode-win32/ ; Example .......: No ; =============================================================================================================================== Func _WinAPI_GetIsImmersiveColorUsingHighContrast($IMMERSIVE_HC_CACHE_MODE = $IHCM_USE_CACHED_VALUE) If @OSBuild < 17763 Then Return SetError(-1, 0, False) Local $fnGetIsImmersiveColorUsingHighContrast = 106 Local $aResult = DllCall($hUxthemeDll, 'bool', $fnGetIsImmersiveColorUsingHighContrast, 'int', $IMMERSIVE_HC_CACHE_MODE) If @error Then Return SetError(@error, @extended, False) Return $aResult[0] EndFunc ;==>_WinAPI_GetIsImmersiveColorUsingHighContrast ; #FUNCTION# ==================================================================================================================== ; Name ..........: _WinAPI_OpenNcThemeData ; Description ...: Opens the theme data for a window. ; Syntax ........: _WinAPI_OpenNcThemeData($hWnd, $pClassList) ; Parameters ....: $hWnd - Handle to the window. ; $sClassList - String that contains a semicolon-separated list of classes. ; Return values .: Success: A handle to the theme data. ; Failure: 0 and sets the @error flag: ; -1: Operating system version is earlier than Windows 10 (version 17763) ; Other values: DllCall error, check @error @extended for more information. ; Author ........: NoNameCode ; Modified ......: ; Remarks .......: ; Related .......: ; Link ..........: https://github.com/ysc3839/win32-darkmode/blob/master/win32-darkmode/DarkMode.h#L69 ; Example .......: No ; =============================================================================================================================== Func _WinAPI_OpenNcThemeData($hWnd, $sClassList) If @OSBuild < 17763 Then Return SetError(-1, 0, False) Local $fnOpenNcThemeData = 49 Local $aResult = DllCall($hUxthemeDll, 'hwnd', $fnOpenNcThemeData, 'hwnd', $hWnd, 'wstr', $sClassList) If @error Then Return SetError(@error, @extended, 0) Return $aResult[0] EndFunc ;==>_WinAPI_OpenNcThemeData ; #FUNCTION# ==================================================================================================================== ; Name ..........: _WinAPI_ShouldSystemUseDarkMode ; Description ...: Checks if system should use the dark mode. ; Syntax ........: _WinAPI_ShouldSystemUseDarkMode() ; Parameters ....: None ; Return values .: Success: Returns True if system should use dark mode. ; Failure: Returns False and sets @error: ; -1: Operating system version is earlier than Windows 10 (version 1903, build 18362). ; Other values: DllCall error, check @error @extended for more information. ; Author ........: NoNameCode ; Modified ......: ; Remarks .......: Requires Windows 10 (version 1903, build 18362) or later. ; Related .......: ; Link ..........: http://www.opengate.at/blog/2021/08/dark-mode-win32/ ; Example .......: No ; =============================================================================================================================== Func _WinAPI_ShouldSystemUseDarkMode() If @OSBuild < 18362 Then Return SetError(-1, 0, False) Local $fnShouldSystemUseDarkMode = 138 Local $aResult = DllCall($hUxthemeDll, 'bool', $fnShouldSystemUseDarkMode) If @error Then Return SetError(@error, @extended, False) Return $aResult[0] EndFunc ;==>_WinAPI_ShouldSystemUseDarkMode ; #FUNCTION# ==================================================================================================================== ; Name ..........: _WinAPI_SetPreferredAppMode ; Description ...: Sets the preferred application mode for Windows 10 (version 1903, build 18362) and later. ; Syntax ........: _WinAPI_SetPreferredAppMode($PREFERREDAPPMODE) ; Parameters ....: $PREFERREDAPPMODE - The preferred application mode. See enum PreferredAppMode for possible values. ; $APPMODE_DEFAULT (0) ; $APPMODE_ALLOWDARK (1) ; $APPMODE_FORCEDARK (2) ; $APPMODE_FORCELIGHT (3) ; $APPMODE_MAX (4) ; Return values .: Success: The PreferredAppMode retuned by the DllCall ; Failure: '' and sets the @error flag: ; -1: Operating system version is earlier than Windows 10 (version 18362) ; Other values: DllCall error, check @error @extended for more information. ; Author ........: NoNameCode ; Modified ......: ; Remarks .......: This function is applicable for Windows 10 (version 18362) and later. ; Related .......: _WinAPI_AllowDarkModeForApp ; Link ..........: http://www.opengate.at/blog/2021/08/dark-mode-win32/ ; Example .......: No ; =============================================================================================================================== Func _WinAPI_SetPreferredAppMode($PREFERREDAPPMODE) If @OSBuild < 18362 Then Return SetError(-1, 0, False) Local $fnSetPreferredAppMode = 135 Local $aResult = DllCall($hUxthemeDll, 'int', $fnSetPreferredAppMode, 'int', $PREFERREDAPPMODE) If @error Then Return SetError(@error, @extended, '') Return $aResult[0] EndFunc ;==>_WinAPI_SetPreferredAppMode Func _WinAPI_FindWindowEx($hParent, $hAfter, $sClass, $sTitle = "") Local $ret = DllCall($hUser32Dll, "hwnd", "FindWindowExW", "hwnd", $hParent, "hwnd", $hAfter, "wstr", $sClass, "wstr", $sTitle) If @error Or Not IsArray($ret) Then Return 0 Return $ret[0] EndFunc ;==>_WinAPI_FindWindowEx #EndRegion API Functions #Region Internal Functions ; #FUNCTION# ==================================================================================================================== ; Name ..........: _WinAPI_DwmSetWindowAttribute_unr ; Description ...: Dose the same as _WinAPI_DwmSetWindowAttribute; But has no Restrictions ; Syntax ........: _WinAPI_DwmSetWindowAttribute_unr($hWnd, $iAttribute, $iData) ; Parameters ....: $hWnd - a handle value. ; $iAttribute - an integer value. ; $iData - an integer value. ; Return values .: Success: 1 Failure: @error, @extended & False ; Author ........: argumentum ; Modified ......: ; Remarks .......: ; Related .......: ; Link ..........: https://www.autoitscript.com/forum/topic/211475-winapithemeex-darkmode-for-autoits-win32guis/?do=findComment&comment=1530103 ; Example .......: No ; =============================================================================================================================== Func _WinAPI_DwmSetWindowAttribute_unr($hWnd, $iAttribute, $iData) ; #include <WinAPIGdi.au3> ; unthoughtful unrestricting mod. Local $aCall = DllCall('dwmapi.dll', 'long', 'DwmSetWindowAttribute', 'hwnd', $hWnd, 'dword', $iAttribute, _ 'dword*', $iData, 'dword', 4) If @error Then Return SetError(@error, @extended, 0) If $aCall[0] Then Return SetError(10, $aCall[0], 0) Return 1 EndFunc ;==>_WinAPI_DwmSetWindowAttribute_unr #EndRegion Internal Functions #cs Func _ColorToCOLORREF($iColor) ;RGB to BGR Local $iR = BitAND(BitShift($iColor, 16), 0xFF) Local $iG = BitAND(BitShift($iColor, 8), 0xFF) Local $iB = BitAND($iColor, 0xFF) Return BitOR(BitShift($iB, -16), BitShift($iG, -8), $iR) EndFunc ;==>_ColorToCOLORREF #ce Func _WM_CTLCOLOR($hWnd, $iMsg, $wParam, $lParam) #forceref $hWnd, $iMsg Local $hDC = $wParam Local $hCtrl = $lParam Switch __WinAPI_GetClassName($hCtrl) Case 'Static' ; set transparent background __WinAPI_SetBkMode($hDC, $TRANSPARENT) ; set text color (if necessary) - e.g., white __WinAPI_SetTextColor($hDC, _ColorToCOLORREF($COLOR_TEXT_LIGHT)) ; return NULL_BRUSH (stock object), so Windows does NOT fill with your dark brush Local $hNull = __WinAPI_GetStockObject(5) ; 5 = NULL_BRUSH If $hNull Then Return $hNull ; Fallback if not available: Return $GUI_RUNDEFMSG EndSwitch ; --- Default behavior for all other statics / controls --- __WinAPI_SetTextColor($hDC, _ColorToCOLORREF($COLOR_TEXT_LIGHT)) Local $hBrush = $g_hBrushEdit _WinAPI_SetBkColor($hDC, _ColorToCOLORREF($COLOR_CONTROL_BG)) __WinAPI_SetBkMode($hDC, $TRANSPARENT) Return $hBrush EndFunc ;==>_WM_CTLCOLOR Func _WinProc($hWnd, $iMsg, $wParam, $lParam) ; Custom window procedure for tab control with Dark Mode Switch $iMsg Case $WM_ERASEBKGND Return 1 ; Prevent background erase to avoid flicker Case $WM_PAINT Local $tPaint = DllStructCreate($tagPAINTSTRUCT) Local $hDC = DllCall($hUser32Dll, "handle", "BeginPaint", "hwnd", $hWnd, "struct*", $tPaint) If @error Or Not $hDC[0] Then Return __WinAPI_CallWindowProc($g_hProc, $hWnd, $iMsg, $wParam, $lParam) $hDC = $hDC[0] ; Get client rectangle Local $tClient = __WinAPI_GetClientRect($hWnd) If Not IsDllStruct($tClient) Then __WinAPI_EndPaint($hWnd, $tPaint) Return 0 EndIf Local $iWidth = $tClient.Right Local $iHeight = $tClient.Bottom ; Create memory DC for double buffering Local $hMemDC = __WinAPI_CreateCompatibleDC($hDC) Local $hBitmap = __WinAPI_CreateCompatibleBitmap($hDC, $iWidth, $iHeight) Local $hOldBmp = __WinAPI_SelectObject($hMemDC, $hBitmap) ; Fill background but exclude overlapping GUI controls from painting Local $hParent = __WinAPI_GetParent($hWnd) Local $hChild = __WinAPI_GetWindow($hParent, $GW_CHILD) Local $tCR, $tPR = __WinAPI_GetWindowRect($hWnd) Local $left, $top, $right, $bottom While $hChild If $hChild <> $hWnd And __WinAPI_IsWindowVisible($hChild) Then $tCR = __WinAPI_GetWindowRect($hChild) ; Only exclude controls that lie fully within the tab control area If $tCR.left >= $tPR.left And $tCR.right <= $tPR.right And $tCR.top >= $tPR.top And $tCR.bottom <= $tPR.bottom Then $left = $tCR.left - $tPR.left $top = $tCR.top - $tPR.top $right = $tCR.right - $tPR.left $bottom = $tCR.bottom - $tPR.top ; Exclude from offscreen bitmap (prevents black fill) DllCall($hGdi32Dll, "int", "ExcludeClipRect", "handle", $hMemDC, "int", $left, "int", $top, "int", $right, "int", $bottom) ; Exclude from screen DC (prevents BitBlt overwrite) DllCall($hGdi32Dll, "int", "ExcludeClipRect", "handle", $hDC, "int", $left, "int", $top, "int", $right, "int", $bottom) EndIf EndIf $hChild = __WinAPI_GetWindow($hChild, $GW_HWNDNEXT) WEnd ; Fill background Local $hBrush = __WinAPI_CreateSolidBrush(_ColorToCOLORREF($COLOR_CONTROL_BG)) __WinAPI_FillRect($hMemDC, $tClient, $hBrush) __WinAPI_DeleteObject($hBrush) ; Get tab info Local $iTabCount = __SendMessage($hWnd, $TCM_GETITEMCOUNT, 0, 0) Local $iCurSel = __SendMessage($hWnd, $TCM_GETCURSEL, 0, 0) ; Setup font Local $hFont = __SendMessage($hWnd, $WM_GETFONT, 0, 0) If Not $hFont Then $hFont = __WinAPI_GetStockObject($DEFAULT_GUI_FONT) Local $hOldFont = __WinAPI_SelectObject($hMemDC, $hFont) __WinAPI_SetBkMode($hMemDC, $TRANSPARENT) __WinAPI_SetTextColor($hMemDC, _ColorToCOLORREF($COLOR_TEXT_LIGHT)) ; Draw each tab Local $tRect, $iLeft, $iTop, $iRight, $iBottom, $tItem, $tText, $bSelected, $iTabColor, $hTabBrush, $tTabRect, _ $sText, $hPen, $hOldPen, $hPenSep,$hOldPenSep, $tTextRect, $hBorderPen, $hOldBorderPen, $hNullBrush, $hOldBorderBrush For $i = 0 To $iTabCount - 1 ; Get tab rectangle using TCM_GETITEMRECT $tRect = DllStructCreate($tagRECT) Local $aResult = DllCall($hUser32Dll, "lresult", "SendMessageW", _ "hwnd", $hWnd, _ "uint", $TCM_GETITEMRECT, _ "wparam", $i, _ "struct*", $tRect) If @error Or Not $aResult[0] Then ContinueLoop $iLeft = $tRect.Left $iTop = $tRect.Top $iRight = $tRect.Right $iBottom = $tRect.Bottom ; Skip if rectangle is invalid If $iLeft >= $iRight Or $iTop >= $iBottom Then ContinueLoop ; Get tab text $tItem = DllStructCreate("uint Mask;dword dwState;dword dwStateMask;ptr pszText;int cchTextMax;int iImage;lparam lParam") $tText = DllStructCreate("wchar Text[256]") With $tItem .Mask = 0x0001 ; TCIF_TEXT .pszText = DllStructGetPtr($tText) .cchTextMax = 256 EndWith DllCall($hUser32Dll, "lresult", "SendMessageW", _ "hwnd", $hWnd, _ "uint", $TCM_GETITEMW, _ "wparam", $i, _ "struct*", $tItem) $sText = DllStructGetData($tText, "Text") ; Draw tab background $bSelected = ($i = $iCurSel) $iTabColor = $bSelected ? __WinAPI_ColorAdjustLuma($COLOR_CONTROL_BG, 20) : __WinAPI_ColorAdjustLuma($COLOR_CONTROL_BG, 10) $hTabBrush = __WinAPI_CreateSolidBrush($iTabColor) $tTabRect = DllStructCreate($tagRECT) With $tTabRect .Left = $iLeft .Top = $iTop .Right = $iRight .Bottom = $iBottom EndWith __WinAPI_FillRect($hMemDC, $tTabRect, $hTabBrush) __WinAPI_DeleteObject($hTabBrush) ; Draw selection indicator (top border for selected tab) If $bSelected Then $hPen = __WinAPI_CreatePen(0, 2, _ColorToCOLORREF(0x0078D4)) ; Blue accent $hOldPen = __WinAPI_SelectObject($hMemDC, $hPen) __WinAPI_MoveTo($hMemDC, $iLeft, $iTop) __WinAPI_LineTo($hMemDC, $iRight - 2, $iTop) __WinAPI_SelectObject($hMemDC, $hOldPen) __WinAPI_DeleteObject($hPen) EndIf ; Draw separator between tabs If $i < $iTabCount - 1 Then $hPenSep = __WinAPI_CreatePen(0, 1, _ColorToCOLORREF($COLOR_BORDER)) $hOldPenSep = __WinAPI_SelectObject($hMemDC, $hPenSep) __WinAPI_MoveTo($hMemDC, $iRight - 1, $iTop + 4) __WinAPI_LineTo($hMemDC, $iRight - 1, $iBottom - 4) __WinAPI_SelectObject($hMemDC, $hOldPenSep) __WinAPI_DeleteObject($hPenSep) EndIf ; Draw text centered in tab $tTextRect = DllStructCreate($tagRECT) With $tTextRect .Left = $iLeft + 6 .Top = $iTop + 3 .Right = $iRight - 6 .Bottom = $iBottom - 3 EndWith DllCall($hUser32Dll, "int", "DrawTextW", _ "handle", $hMemDC, _ "wstr", $sText, _ "int", -1, _ "struct*", $tTextRect, _ "uint", BitOR($DT_CENTER, $DT_VCENTER, $DT_SINGLELINE)) Next ; Draw border around entire control $hBorderPen = __WinAPI_CreatePen(0, 1, _ColorToCOLORREF($COLOR_BORDER)) $hOldBorderPen = __WinAPI_SelectObject($hMemDC, $hBorderPen) $hNullBrush = __WinAPI_GetStockObject(5) ; NULL_BRUSH $hOldBorderBrush = __WinAPI_SelectObject($hMemDC, $hNullBrush) DllCall($hGdi32Dll, "bool", "Rectangle", "handle", $hMemDC, "int", 0, "int", 0, "int", $iWidth, "int", $iHeight) __WinAPI_SelectObject($hMemDC, $hOldBorderPen) __WinAPI_SelectObject($hMemDC, $hOldBorderBrush) __WinAPI_DeleteObject($hBorderPen) ; Copy to screen __WinAPI_BitBlt($hDC, 0, 0, $iWidth, $iHeight, $hMemDC, 0, 0, $SRCCOPY) ; Cleanup __WinAPI_SelectObject($hMemDC, $hOldFont) __WinAPI_SelectObject($hMemDC, $hOldBmp) __WinAPI_DeleteObject($hBitmap) __WinAPI_DeleteDC($hMemDC) __WinAPI_EndPaint($hWnd, $tPaint) Return 0 EndSwitch Return __WinAPI_CallWindowProc($g_hProc, $hWnd, $iMsg, $wParam, $lParam) EndFunc ;==>_WinProc Func _LVWndProc($hWnd, $iMsg, $wParam, $lParam) #forceref $hWnd, $iMsg, $wParam If $iMsg = $WM_NOTIFY Then Local $tNMHDR, $hWndFrom, $iCode, $hDC $tNMHDR = DllStructCreate($tagNMHDR, $lParam) $hWndFrom = HWnd(DllStructGetData($tNMHDR, "hWndFrom")) $iCode = DllStructGetData($tNMHDR, "Code") Switch $hWndFrom Case $hWndListViewHeader Switch $iCode Case $NM_CUSTOMDRAW Local $tCustDraw = DllStructCreate($tagNMLVCUSTOMDRAW, $lParam) Switch DllStructGetData($tCustDraw, "dwDrawStage") Case $CDDS_PREPAINT Return $CDRF_NOTIFYITEMDRAW Case $CDDS_ITEMPREPAINT $hDC = DllStructGetData($tCustDraw, "hDC") DllCall($hGdi32Dll, "int", "SetTextColor", "handle", $hDC, "dword", __WinAPI_SwitchColor($COLOR_TEXT_LIGHT)) Return $CDRF_NEWFONT Return $CDRF_SKIPDEFAULT EndSwitch EndSwitch EndSwitch EndIf ;pass the unhandled messages to default WindowProc Local $aResult = DllCall($hUser32Dll, "lresult", "CallWindowProcW", "ptr", $g__ListView_wProcOld, _ "hwnd", $hWnd, "uint", $iMsg, "wparam", $wParam, "lparam", $lParam) If @error Then Return -1 Return $aResult[0] EndFunc ;==>_LVWndProc #Region WM_NOTIFY Func _DateProc($hWnd, $iMsg, $wParam, $lParam) Local $iRet Switch $iMsg Case $WM_PAINT Local $tPaint = DllStructCreate($tagPAINTSTRUCT) Local $hDC = __WinAPI_BeginPaint($hWnd, $tPaint) Local $tClient = __WinAPI_GetClientRect($hWnd) Local $iW = $tClient.Right Local $iH = $tClient.Bottom ; --- Memory DC for flicker-free rendering --- Local $hMemDC = __WinAPI_CreateCompatibleDC($hDC) Local $hBitmap = __WinAPI_CreateCompatibleBitmap($hDC, $iW, $iH) Local $hOldBmp = __WinAPI_SelectObject($hMemDC, $hBitmap) ; 1. Let Windows draw the light-mode control into memory DC __WinAPI_CallWindowProc($g_hDateOldProc, $hWnd, $WM_PRINTCLIENT, $hMemDC, $PRF_CLIENT) ; 2. Invert all pixels (background becomes black, text white, selection orange) Local $tRect = DllStructCreate($tagRECT) $tRect.right = $iW $tRect.bottom = $iH __WinAPI_InvertRect($hMemDC, $tRect) ; --- 3. PIXEL HACK: destroy orange highlight & set background color --- Local $iSize = $iW * $iH Local $tPixels = DllStructCreate("dword c[" & $iSize & "]") ; Load pixel array directly from bitmap memory Local $iBytes = DllCall($hGdi32Dll, "long", "GetBitmapBits", "handle", $hBitmap, "long", $iSize * 4, "ptr", DllStructGetPtr($tPixels))[0] If $iBytes = $iSize * 4 Then Local $iPixel, $r, $g, $b, $iGray For $i = 1 To $iSize $iPixel = $tPixels.c(($i)) ; Split into color channels $b = BitAND($iPixel, 0xFF) $g = BitAND(BitShift($iPixel, 8), 0xFF) $r = BitAND(BitShift($iPixel, 16), 0xFF) ; Convert to grayscale (orange becomes mid-gray) $iGray = Int(($r + $g + $b) / 3) ; Very dark pixel = inverted white background If $iGray < 15 Then $iPixel = $DTP_BG_DARK ; Replace with exact GUI background color Else ; Grayscale value for text (white) and selection (gray) ; (negative BitShift shifts left in AutoIt) $iPixel = BitOR(BitShift($iGray, -16), BitShift($iGray, -8), $iGray) EndIf $tPixels.c(($i)) = $iPixel Next ; Write cleaned pixels back into the bitmap DllCall($hGdi32Dll, "long", "SetBitmapBits", "handle", $hBitmap, "long", $iSize * 4, "ptr", DllStructGetPtr($tPixels)) EndIf ; --- END PIXEL HACK --- ; --- Border color (hover effect) --- Local $iBorderColor = $DTP_BORDER If __WinAPI_GetFocus() = $hWnd Then $iBorderColor = $DTP_BORDER Local $tCursorPos = DllStructCreate($tagPOINT) DllCall($hUser32Dll, "bool", "GetCursorPos", "struct*", $tCursorPos) DllCall($hUser32Dll, "bool", "ScreenToClient", "hwnd", $hWnd, "struct*", $tCursorPos) If $tCursorPos.X >= 0 And $tCursorPos.X <= $iW And $tCursorPos.Y >= 0 And $tCursorPos.Y <= $iH Then $iBorderColor = $DTP_BORDER_LIGHT EndIf ; --- Draw border --- Local $hPen = __WinAPI_CreatePen(0, 1, _ColorToCOLORREF($iBorderColor)) Local $hNullBr = __WinAPI_GetStockObject(5) Local $hOldPen = __WinAPI_SelectObject($hMemDC, $hPen) Local $hOldBr = __WinAPI_SelectObject($hMemDC, $hNullBr) DllCall($hGdi32Dll, "bool", "Rectangle", "handle", $hMemDC, "int", 0, "int", 0, "int", $iW, "int", $iH) __WinAPI_SelectObject($hMemDC, $hOldPen) __WinAPI_SelectObject($hMemDC, $hOldBr) __WinAPI_DeleteObject($hPen) ; --- Copy finished result to screen in one step (no flicker) --- __WinAPI_BitBlt($hDC, 0, 0, $iW, $iH, $hMemDC, 0, 0, $SRCCOPY) ; --- Cleanup --- __WinAPI_SelectObject($hMemDC, $hOldBmp) __WinAPI_DeleteObject($hBitmap) __WinAPI_DeleteDC($hMemDC) __WinAPI_EndPaint($hWnd, $tPaint) Return 0 Case $WM_ERASEBKGND Return 1 Case $WM_SETFOCUS, $WM_KILLFOCUS, $WM_LBUTTONDOWN, $WM_LBUTTONUP $iRet = __WinAPI_CallWindowProc($g_hDateOldProc, $hWnd, $iMsg, $wParam, $lParam) __WinAPI_InvalidateRect($hWnd, 0, False) Return $iRet Case $WM_MOUSEMOVE $iRet = __WinAPI_CallWindowProc($g_hDateOldProc, $hWnd, $iMsg, $wParam, $lParam) If Not $g_bHover Then $g_bHover = True __WinAPI_InvalidateRect($hWnd, 0, False) EndIf Return $iRet Case $WM_MOUSELEAVE $g_bHover = False __WinAPI_InvalidateRect($hWnd, 0, False) EndSwitch Return __WinAPI_CallWindowProc($g_hDateOldProc, $hWnd, $iMsg, $wParam, $lParam) EndFunc ;==>_DateProc Func _WM_NOTIFY($hWnd, $iMsg, $wParam, $lParam) #forceref $hWnd, $iMsg, $wParam Local Static $iTheme ; argumentum Local $hWndFrom, $iCode, $tNMHDR, $iCtrl $tNMHDR = DllStructCreate($tagNMHDR, $lParam) $hWndFrom = HWnd($tNMHDR.hWndFrom) $iCode = $tNMHDR.Code ; --- Slider (msctls_trackbar32) custom drawing --- If $iCode = $NM_CUSTOMDRAW And StringLower(__WinAPI_GetClassName($hWndFrom)) = "msctls_trackbar32" Then Local $tNMCD = DllStructCreate($tagNMCUSTOMDRAW, $lParam) Local $dwStage = $tNMCD.dwDrawStage Local $hDC = $tNMCD.hdc Local $dwItemSpec = $tNMCD.dwItemSpec Switch $dwStage Case $CDDS_PREPAINT ; Remove focus rectangle from slider DllStructSetData($tNMCD, 'ItemState', BitXOR(DllStructGetData($tNMCD, 'ItemState'), $CDIS_FOCUS)) Return $CDRF_NOTIFYITEMDRAW ; request per-item notifications Case $CDDS_ITEMPREPAINT Local Const $TBCD_TICS = 0x0001 ; tick marks Local Const $TBCD_THUMB = 0x0002 ; draggable thumb Local Const $TBCD_CHANNEL = 0x0003 ; slider channel/track Local $tRect = DllStructCreate($tagRECT) $tRect.left = $tNMCD.left $tRect.top = $tNMCD.top $tRect.right = $tNMCD.right $tRect.bottom = $tNMCD.bottom Switch $dwItemSpec Case $TBCD_TICS ; Let Windows draw tick marks normally Return $CDRF_DODEFAULT Case $TBCD_THUMB ; Draw thumb as a pentagon (rectangle + downward arrow) Local $iL = $tNMCD.left Local $iT = $tNMCD.top Local $iR = $tNMCD.right - 1 ; -1 to stay within bounds and avoid paint artifacts Local $iB = $tNMCD.bottom Local $iMid = ($iL + $iR) / 2 ; horizontal center (tip of arrow) Local $iSplit = $iB - ($iR - $iL) / 2 ; y-position where rectangle ends and arrow begins ; Pentagon points: top-left, top-right, right-middle, bottom-tip, left-middle Local $tPoints = DllStructCreate("int p[10]") $tPoints.p((1)) = $iL $tPoints.p((2)) = $iT $tPoints.p((3)) = $iR $tPoints.p((4)) = $iT $tPoints.p((5)) = $iR $tPoints.p((6)) = $iSplit $tPoints.p((7)) = $iMid $tPoints.p((8)) = $iB $tPoints.p((9)) = $iL $tPoints.p((10)) = $iSplit ; Fill and outline thumb with blue accent color Local $hBrush = __WinAPI_CreateSolidBrush(_ColorToCOLORREF(0x0078D4)) Local $hPen = __WinAPI_CreatePen(0, 1, _ColorToCOLORREF($COLOR_CONTROL_BG)) Local $hOldBrush = __WinAPI_SelectObject($hDC, $hBrush) Local $hOldPen = __WinAPI_SelectObject($hDC, $hPen) DllCall($hGdi32Dll, "bool", "Polygon", "handle", $hDC, "struct*", $tPoints, "int", 5) __WinAPI_SelectObject($hDC, $hOldBrush) __WinAPI_SelectObject($hDC, $hOldPen) __WinAPI_DeleteObject($hBrush) __WinAPI_DeleteObject($hPen) Return $CDRF_SKIPDEFAULT ; skip default drawing Case $TBCD_CHANNEL ; Fill channel with border color Local $hBrushChan = __WinAPI_CreateSolidBrush(_ColorToCOLORREF($COLOR_BORDER)) __WinAPI_FillRect($hDC, $tRect, $hBrushChan) __WinAPI_DeleteObject($hBrushChan) Return $CDRF_SKIPDEFAULT ; skip default drawing EndSwitch EndSwitch EndIf ; --- Per-control notification handling --- Switch $hWndFrom Case $g_hDate ;thanks to argumentum for the code :-) Switch $iCode Case $NM_SETFOCUS $iTheme = __WinAPI_GetThemeAppProperties() ; argumentum ; Disable the visual theme when the DateTime control receives focus __WinAPI_SetThemeAppProperties(0) Case $DTN_DROPDOWN;, $EVENT_OBJECT_CREATE ; Apply dark colors when the calendar dropdown appears $iCtrl = _GUICtrlDTP_GetMonthCal($hWndFrom) __WinAPI_SetWindowTheme($iCtrl, "", "") _GUICtrlMonthCal_SetColor($iCtrl, $MCSC_TEXT, $COLOR_TEXT_LIGHT) _GUICtrlMonthCal_SetColor($iCtrl, $MCSC_TITLEBK, $COLOR_CONTROL_BG) _GUICtrlMonthCal_SetColor($iCtrl, $MCSC_TITLETEXT, $COLOR_TEXT_LIGHT) _GUICtrlMonthCal_SetColor($iCtrl, $MCSC_BACKGROUND, $COLOR_CONTROL_BG) _GUICtrlMonthCal_SetColor($iCtrl, $MCSC_MONTHBK, $COLOR_CONTROL_BG) _GUICtrlMonthCal_SetColor($iCtrl, $MCSC_TRAILINGTEXT, $COLOR_TEXT_LIGHT) Case $DTN_CLOSEUP ; Reset visual theme __WinAPI_SetThemeAppProperties($iTheme) ; argumentum ; Calendar will closed EndSwitch EndSwitch Return $GUI_RUNDEFMSG EndFunc ;==>_WM_NOTIFY #EndRegion WM_NOTIFY Func hWnd2Styles($hWnd) Return _GetCtrlStyleString(__WinAPI_GetWindowLong($hWnd, $GWL_STYLE), __WinAPI_GetWindowLong($hWnd, $GWL_EXSTYLE), __WinAPI_GetClassName($hWnd)) EndFunc Func _GetStyleString($iStyle, $fExStyle) ConsoleWrite('+ Func _GetStyleString(' & $iStyle & ', ' & $fExStyle & ')' & @CRLF) Local $Text = '', $Data = $fExStyle ? $_g__Style_GuiExtended : $_g__Style_Gui For $i = 0 To UBound($Data) - 1 If BitAND($iStyle, $Data[$i][0]) = $Data[$i][0] Then $iStyle = BitAND($iStyle, BitNOT($Data[$i][0])) If StringLeft($Data[$i][1], 1) <> "!" Then $Text &= $Data[$i][1] & ', ' Else ; ex. '! WS_MINIMIZEBOX ! WS_GROUP' => 'WS_MINIMIZEBOX, ' $Text &= StringMid($Data[$i][1], 3, StringInStr($Data[$i][1], "!", 2, 2) - 4) & ', ' EndIf EndIf Next If $iStyle Then $Text = '0x' & Hex($iStyle, 8) & ', ' & $Text Return StringRegExpReplace($Text, ',\s\z', '') EndFunc ;==>_GetStyleString Func _GetCtrlStyleString($iStyle, $fExStyle, $sClass, $iLVExStyle = 0) If $sClass = "AutoIt v3 GUI" Or $sClass = "#32770" Or $sClass = "MDIClient" Then ; control = child GUI, dialog box (msgbox) etc... Return _GetStyleString($iStyle, 0) EndIf If StringLeft($sClass, 8) = "RichEdit" Then $sClass = "RichEdit" ; RichEdit, RichEdit20A, RichEdit20W, RichEdit50A, RichEdit50W Local $Text = '' _GetCtrlStyleString2($iStyle, $Text, $sClass, $iLVExStyle) ; 4th param. in case $sClass = "Ex_SysListView32" (special treatment) If $sClass = "ReBarWindow32" Or $sClass = "ToolbarWindow32" Or $sClass = "msctls_statusbar32" Then $sClass = "Common" ; "for rebar controls, toolbar controls, and status windows" (msdn) _GetCtrlStyleString2($iStyle, $Text, $sClass) ElseIf $sClass = "RichEdit" Then $sClass = "Edit" ; "Richedit controls also support many edit control styles (not all)" (msdn) _GetCtrlStyleString2($iStyle, $Text, $sClass) EndIf Local $Data = $fExStyle ? $_g__Style_GuiExtended : $_g__Style_Gui For $i = 0 To UBound($Data) - 1 If BitAND($iStyle, $Data[$i][0]) = $Data[$i][0] Then If (Not BitAND($Data[$i][0], 0xFFFF)) Or ($fExStyle) Then $iStyle = BitAND($iStyle, BitNOT($Data[$i][0])) If StringLeft($Data[$i][1], 1) <> "!" Then $Text &= $Data[$i][1] & ', ' Else ; ex. '! WS_MINIMIZEBOX ! WS_GROUP' => 'WS_GROUP, ' $Text &= StringMid($Data[$i][1], StringInStr($Data[$i][1], "!", 2, 2) + 2) & ', ' EndIf EndIf EndIf Next If $iStyle Then $Text = '0x' & Hex($iStyle, 8) & ', ' & $Text Return StringRegExpReplace($Text, ',\s\z', '') EndFunc ;==>_GetCtrlStyleString ;===================================================================== Func _GetCtrlStyleString2(ByRef $iStyle, ByRef $Text, $sClass, $iLVExStyle = 0) Local $Data Switch $sClass ; $Input[16] Case "Button" $Data = $_g__Style_Button Case "ComboBox", "ComboBoxEx32" $Data = $_g__Style_Combo Case "Common" $Data = $_g__Style_Common ; "for rebar controls, toolbar controls, and status windows (msdn)" Case "Edit" $Data = $_g__Style_Edit Case "ListBox" $Data = $_g__Style_ListBox Case "msctls_progress32" $Data = $_g__Style_Progress Case "msctls_statusbar32" $Data = $_g__Style_StatusBar Case "msctls_trackbar32" $Data = $_g__Style_Slider Case "msctls_updown32" $Data = $_g__Style_UpDown Case "ReBarWindow32" $Data = $_g__Style_Rebar Case "RichEdit" $Data = $_g__Style_RichEdit Case "Scrollbar" $Data = $_g__Style_Scrollbar Case "Static" $Data = $_g__Style_Static Case "SysAnimate32" $Data = $_g__Style_Avi Case "SysDateTimePick32" $Data = $_g__Style_DateTime Case "SysHeader32" $Data = $_g__Style_Header Case "SysListView32" $Data = $_g__Style_ListView Case "Ex_SysListView32" ; special treatment below $Data = $_g__Style_ListViewExtended Case "SysMonthCal32" $Data = $_g__Style_MonthCal Case "SysPager" $Data = $_g__Style_Pager Case "SysTabControl32", "SciTeTabCtrl" $Data = $_g__Style_Tab Case "SysTreeView32" $Data = $_g__Style_TreeView Case "ToolbarWindow32" $Data = $_g__Style_Toolbar Case Else Return EndSwitch If $sClass <> "Ex_SysListView32" Then For $i = 0 To UBound($Data) - 1 If BitAND($iStyle, $Data[$i][0]) = $Data[$i][0] Then $iStyle = BitAND($iStyle, BitNOT($Data[$i][0])) $Text = $Data[$i][1] & ', ' & $Text EndIf Next Else For $i = 0 To UBound($Data) - 1 If BitAND($iLVExStyle, $Data[$i][0]) = $Data[$i][0] Then $iLVExStyle = BitAND($iLVExStyle, BitNOT($Data[$i][0])) $Text = $Data[$i][1] & ', ' & $Text If BitAND($iStyle, $Data[$i][0]) = $Data[$i][0] Then $iStyle = BitAND($iStyle, BitNOT($Data[$i][0])) EndIf EndIf Next If $iLVExStyle Then $Text = 'LVex: 0x' & Hex($iLVExStyle, 8) & ', ' & $Text ; next test bc LVS_EX_FULLROWSELECT (default AutoIt LV ext style) and WS_EX_TRANSPARENT got both same value 0x20 (hard to solve in some cases) If BitAND($iStyle, $WS_EX_TRANSPARENT) = $WS_EX_TRANSPARENT Then ; note that $WS_EX_TRANSPARENT has nothing to do with listview $iStyle = BitAND($iStyle, BitNOT($WS_EX_TRANSPARENT)) EndIf EndIf EndFunc ;==>_GetCtrlStyleString2 #Region Public Functions ; #FUNCTION# ==================================================================================================================== ; Name ..........: _GUISetDarkTheme ; Description ...: Sets the theme for a specified window to either dark or light mode on Windows 10. ; Syntax ........: _GUISetDarkTheme($hwnd, $dark_theme = True) ; Parameters ....: $hwnd - The handle to the window. ; $dark_theme - If True, sets the dark theme; if False, sets the light theme. ; (Default is True for dark theme.) ; Return values .: None ; Author ........: DK12000, NoNameCode ; Modified ......: ; Remarks .......: ; Related .......: ; Link ..........: https://www.autoitscript.com/forum/topic/211196-gui-title-bar-dark-theme-an-elegant-solution-using-dwmapi/ ; Example .......: No ; =============================================================================================================================== Func _GUISetDarkTheme($hWnd, $bEnableDarkTheme = True) Local $iPreferredAppMode = ($bEnableDarkTheme == True) ? $APPMODE_FORCEDARK : $APPMODE_FORCELIGHT Local $iGUI_BkColor = ($bEnableDarkTheme == True) ? $COLOR_BG_DARK : _WinAPI_SwitchColor(_WinAPI_GetSysColor($COLOR_3DFACE)) _WinAPI_SetPreferredAppMode($iPreferredAppMode) _WinAPI_RefreshImmersiveColorPolicyState() _WinAPI_FlushMenuThemes() GUISetBkColor($iGUI_BkColor, $hWnd) _GUICtrlSetDarkTheme($hWnd, $bEnableDarkTheme) ;To Color the GUI's own Scrollbar _WinAPI_DwmSetWindowAttribute_unr($hWnd, $DWMWA_USE_IMMERSIVE_DARK_MODE, $bEnableDarkTheme) EndFunc ;==>_GUISetDarkTheme ; #FUNCTION# ==================================================================================================================== ; Name ..........: _GUICtrlAllSetDarkTheme ; Description ...: Sets the dark theme to all existing sub Controls from a GUI ; Syntax ........: _GUICtrlAllSetDarkTheme($hGUI[, $bEnableDarkTheme = True, $bPreferNewTheme = False]) ; Parameters ....: $hGUI - GUI handle ; $bEnableDarkTheme - [optional] a boolean value. Default is True. ; $bPreferNewTheme - Prefer the newer DarkMode_DarkTheme theme over DarkMode_Explorer when possible. ; (Default is False. DarkMode_DarkTheme is only available on Win11 26100.6899 and higher) ; Return values .: None ; Author ........: NoName ; Modified ......: WildByDesign ; Remarks .......: ; Related .......: ; Link ..........: ; Example .......: No ; =============================================================================================================================== Func _GUICtrlAllSetDarkTheme($hGUI, $bEnableDarkTheme = True, $bPreferNewTheme = False) Local $aCtrls = __WinAPI_EnumChildWindows($hGUI, False) For $i = 1 To $aCtrls[0][0] _GUICtrlSetDarkTheme($aCtrls[$i][0], $bEnableDarkTheme, $bPreferNewTheme) Next Local $aCtrlsEx = __WinAPI_EnumProcessWindows(0, False) ; allows getting handles for tooltips_class32, ComboLBox, etc. For $i = 1 To $aCtrlsEx[0][0] _GUICtrlSetDarkTheme($aCtrlsEx[$i][0], $bEnableDarkTheme, $bPreferNewTheme) Next Return $aCtrls EndFunc ; #FUNCTION# ==================================================================================================================== ; Name ..........: _GUICtrlSetDarkTheme ; Description ...: Sets the dark theme for a specified control. ; Syntax ........: _GUICtrlSetDarkTheme($vCtrl, $bEnableDarkTheme = True, $bPreferNewTheme = False) ; Parameters ....: $vCtrl - The control handle or identifier. ; $bEnableDarkTheme - If True, enables the dark theme; if False, disables it. ; (Default is True for enabling dark theme.) ; $bPreferNewTheme - Prefer the newer DarkMode_DarkTheme theme over DarkMode_Explorer when possible. ; (Default is False. DarkMode_DarkTheme is only available on Win11 26100.6899 and higher) ; Return values .: Success: True ; Failure: False and sets the @error flag: ; 1: Invalid control handle or identifier. ; 2: Error while allowing dark mode for the window. ; 3: Error while setting the window theme. ; 4: Error while sending the WM_THEMECHANGED message. ; Author ........: NoNameCode ; Modified ......: WildByDesign ; Remarks .......: This function requires the _WinAPI_SetWindowTheme and _WinAPI_AllowDarkModeForWindow functions. ; Related .......: ; Link ..........: http://www.opengate.at/blog/2021/08/dark-mode-win32/ ; Example .......: Yes ; =============================================================================================================================== Func _GUICtrlSetDarkTheme($vCtrl, $bEnableDarkTheme = True, $bPreferNewTheme = False) Local $sThemeName = Null, $sThemeList = Null Local $iGUI_Ctrl_Color = ($bEnableDarkTheme == True) ? $COLOR_TEXT_LIGHT : _WinAPI_SwitchColor(_WinAPI_GetSysColor($COLOR_WINDOWTEXT)) Local $iGUI_Ctrl_BkColor = ($bEnableDarkTheme == True) ? $COLOR_CONTROL_BG : _WinAPI_SwitchColor(_WinAPI_GetSysColor($COLOR_BTNFACE)) Local $bSpecialBtn = False, $bSpecialLV = False, $bSpecialTV = False Local $sStyles If Not IsHWnd($vCtrl) Then $vCtrl = GUICtrlGetHandle($vCtrl) If Not IsHWnd($vCtrl) Then Return SetError(1, 0, False) _WinAPI_AllowDarkModeForWindow($vCtrl, $bEnableDarkTheme) If @error <> 0 Then Return SetError(2, @error, False) ;========= ;ConsoleWrite(@CRLF & __WinAPI_GetClassName($vCtrl)) Switch __WinAPI_GetClassName($vCtrl) Case 'Button' $sStyles = hWnd2Styles($vCtrl) Switch $bEnableDarkTheme Case True If $bPreferNewTheme And $b24H2Plus Then $sThemeName = 'DarkMode_DarkTheme' Else If StringInStr($sStyles, "BS_GROUPBOX") Or StringInStr($sStyles, "BS_AUTORADIOBUTTON") Then $bSpecialBtn = True Else $sThemeName = 'DarkMode_Explorer' EndIf EndIf Case False $sThemeName = 'Explorer' EndSwitch Case 'msctls_trackbar32' GUICtrlSetColor(_WinAPI_GetDlgCtrlID($vCtrl), $iGUI_Ctrl_Color) GUICtrlSetBkColor(_WinAPI_GetDlgCtrlID($vCtrl), $iGUI_Ctrl_BkColor) If $bEnableDarkTheme Then GUIRegisterMsg($WM_NOTIFY, "_WM_NOTIFY") Case 'msctls_updown32' If $bEnableDarkTheme Then $sThemeName = 'DarkMode_Explorer' GUICtrlSetColor(_WinAPI_GetDlgCtrlID($vCtrl), $iGUI_Ctrl_Color) GUICtrlSetBkColor(_WinAPI_GetDlgCtrlID($vCtrl), $iGUI_Ctrl_BkColor) EndIf Case 'ListBox' Switch $bEnableDarkTheme Case True If $bPreferNewTheme And $b24H2Plus Then $sThemeName = 'DarkMode_DarkTheme' Else $sThemeName = 'DarkMode_Explorer' EndIf ; create brush and register GUI message If Not $g_hBrushEdit Then $g_hBrushEdit = __WinAPI_CreateSolidBrush(_ColorToCOLORREF($COLOR_CONTROL_BG)) GUIRegisterMsg($WM_CTLCOLORLISTBOX, "_WM_CTLCOLOR") Case False $sThemeName = 'Explorer' EndSwitch Case 'SysTreeView32' $sStyles = hWnd2Styles($vCtrl) Switch $bEnableDarkTheme Case True If $bPreferNewTheme And $b24H2Plus Then $sThemeName = 'DarkMode_DarkTheme' Else $sThemeName = 'DarkMode_Explorer' EndIf ; dark mode checkboxes If StringInStr($sStyles, "TVS_CHECKBOXES") Then $bSpecialTV = True EndIf Case False $sThemeName = 'Explorer' EndSwitch GUICtrlSetColor(_WinAPI_GetDlgCtrlID($vCtrl), $iGUI_Ctrl_Color) GUICtrlSetBkColor(_WinAPI_GetDlgCtrlID($vCtrl), $iGUI_Ctrl_BkColor) Case 'SysListView32' Switch $bEnableDarkTheme Case True If $bPreferNewTheme And $b24H2Plus Then $sThemeName = 'DarkMode_DarkTheme' Else $sThemeName = 'DarkMode_Explorer' EndIf ; register callback to subclass ListView header text color $hWndListViewHeader = _GUICtrlListView_GetHeader($vCtrl) $hWndListView = $vCtrl $g__ListView_wProcNew = DllCallbackRegister("_LVWndProc", "ptr", "hwnd;uint;wparam;lparam") $g__ListView_wProcOld = __WinAPI_SetWindowLong($vCtrl, $GWL_WNDPROC, DllCallbackGetPtr($g__ListView_wProcNew)) ; checkbox dark mode If (BitAND(_GUICtrlListView_GetExtendedListViewStyle($vCtrl), $LVS_EX_CHECKBOXES) = $LVS_EX_CHECKBOXES) Then $bSpecialLV = True EndIf Case False $sThemeName = 'Explorer' EndSwitch GUICtrlSetColor(_WinAPI_GetDlgCtrlID($vCtrl), $iGUI_Ctrl_Color) GUICtrlSetBkColor(_WinAPI_GetDlgCtrlID($vCtrl), $iGUI_Ctrl_BkColor) Case 'Edit' Switch $bEnableDarkTheme Case True If $bPreferNewTheme And $b24H2Plus Then $sThemeName = 'DarkMode_DarkTheme' Else $sThemeName = 'DarkMode_Explorer' EndIf ; create brush and register GUI message If Not $g_hBrushEdit Then $g_hBrushEdit = __WinAPI_CreateSolidBrush(_ColorToCOLORREF($COLOR_CONTROL_BG)) GUIRegisterMsg($WM_CTLCOLOREDIT, "_WM_CTLCOLOR") Case False $sThemeName = 'Explorer' EndSwitch Case 'SysHeader32' Switch $bEnableDarkTheme Case True If $bPreferNewTheme And $b24H2Plus Then $sThemeName = 'DarkMode_DarkTheme' Else $sThemeName = 'DarkMode_ItemsView' EndIf Case False $sThemeName = 'ItemsView' EndSwitch $sThemeList = 'Header' Case 'Static' If $bEnableDarkTheme Then GUICtrlSetColor(_WinAPI_GetDlgCtrlID($vCtrl), $iGUI_Ctrl_Color) EndIf Case 'SysDateTimePick32' ; if SysDateTimePick32 exists, obtain handle for SysDateTimePick32 and register WM_NOTIFY If $bEnableDarkTheme Then $g_hDate = $vCtrl $g_hDateProc_CB = DllCallbackRegister('_DateProc', 'ptr', 'hwnd;uint;wparam;lparam') $g_pDateProc_CB = DllCallbackGetPtr($g_hDateProc_CB) $g_hDateOldProc = __WinAPI_SetWindowLong($g_hDate, $GWL_WNDPROC, $g_pDateProc_CB) GUIRegisterMsg($WM_NOTIFY, "_WM_NOTIFY") EndIf Case 'msctls_progress32' If $bEnableDarkTheme Then If $bPreferNewTheme And $b24H2Plus Then $sThemeName = 'DarkMode_CopyEngine' Else $sThemeName = 'DarkMode' EndIf $sThemeList = 'Progress' EndIf Case 'Scrollbar' If $bEnableDarkTheme Then $sThemeName = 'DarkMode_Explorer' Case 'AutoIt v3 GUI' If $bEnableDarkTheme Then $sThemeName = 'DarkMode_Explorer' Case 'msctls_statusbar32' If $bEnableDarkTheme Then If $bPreferNewTheme And $b24H2Plus Then $sThemeName = 'DarkMode_DarkTheme' $sThemeList = 'Status' Else $sThemeName = 'DarkMode' $sThemeList = 'ExplorerStatusBar' EndIf Else ; EndIf Case 'tooltips_class32' If $bEnableDarkTheme Then If $bPreferNewTheme And $b24H2Plus Then ;$sThemeName = 'DarkMode_DarkTheme' ; works but is faded (MS still developing DarkMode_DarkTheme parts) $sThemeName = 'DarkMode_Explorer' ; use for now $sThemeList = 'ToolTip' Else $sThemeName = 'DarkMode_Explorer' $sThemeList = 'ToolTip' EndIf Else ; EndIf Case 'ComboLBox', 'ComboBox' If $bEnableDarkTheme Then If $bPreferNewTheme And $b24H2Plus Then $sThemeName = 'DarkMode_DarkTheme' $sThemeList = 'Combobox' Else $sThemeName = 'DarkMode_CFD' $sThemeList = 'Combobox' EndIf ; create brush and register GUI message If Not $g_hBrushEdit Then $g_hBrushEdit = __WinAPI_CreateSolidBrush(_ColorToCOLORREF($COLOR_CONTROL_BG)) GUIRegisterMsg($WM_CTLCOLORLISTBOX, "_WM_CTLCOLOR") Else ; EndIf GUICtrlSetColor(_WinAPI_GetDlgCtrlID($vCtrl), $iGUI_Ctrl_Color) GUICtrlSetBkColor(_WinAPI_GetDlgCtrlID($vCtrl), $iGUI_Ctrl_BkColor) #cs Local $hEdit = _WinAPI_FindWindowEx($vCtrl, 0, "Edit", "") If $hEdit Then __WinAPI_SetWindowTheme($hEdit, "DarkMode_CFD", 0) _WinAPI_AllowDarkModeForWindow($hEdit, True) EndIf ; ComboBox dropdown list Local $hComboLBox = _WinAPI_FindWindowEx($vCtrl, 0, "ComboLBox", "") If $hComboLBox Then __WinAPI_SetWindowTheme($hComboLBox, "DarkMode_Explorer", 0) _WinAPI_AllowDarkModeForWindow($hComboLBox, True) EndIf #ce Case 'SysTabControl32' If $bEnableDarkTheme Then If $bPreferNewTheme And $b24H2Plus Then $sThemeName = 'DarkMode_DarkTheme' $sThemeList = 'Tab' Else $sThemeName = 'DarkMode_Explorer' ; Register a custom window procedure for the tab control for owner-drawing EndIf ; Register a custom window procedure for the tab control for owner-drawing $g_hTab_CB = DllCallbackRegister('_WinProc', 'ptr', 'hwnd;uint;wparam;lparam') $g_pTab_CB = DllCallbackGetPtr($g_hTab_CB) $g_hProc = __WinAPI_SetWindowLong($vCtrl, $GWL_WNDPROC, $g_pTab_CB) $g_hTab = $vCtrl Else $sThemeName = 'Explorer' EndIf Case Else $sThemeName = 'Explorer' EndSwitch ;ConsoleWrite(@CRLF & 'Class:' & __WinAPI_GetClassName($vCtrl) & ' Theme:' & $sThemeName & '::' & $sThemeList) ;========= __WinAPI_SetWindowTheme($vCtrl, $sThemeName, $sThemeList) If @error <> 0 Then Return SetError(3, @error, False) __SendMessage($vCtrl, $WM_THEMECHANGED, 0, 0) If @error <> 0 Then Return SetError(4, @error, False) If $bSpecialBtn Then ; this is used to remove theme from group box and radio buttons which are not themed properly with older DarkMode_Explorer __WinAPI_SetWindowTheme($vCtrl, "", "") GUICtrlSetColor(_WinAPI_GetDlgCtrlID($vCtrl), $iGUI_Ctrl_Color) EndIf _GDIPlus_Startup() Local Static $hIcon_c, $hIcon_uc Local $hBmp If $hIcon_c = 0 Then $hBmp = _GDIPlus_BitmapCreateFromMemory(_checkedico()) $hIcon_c = _GDIPlus_HICONCreateFromBitmap($hBmp) _GDIPlus_ImageDispose($hBmp) EndIf If $hIcon_uc = 0 Then $hBmp = _GDIPlus_BitmapCreateFromMemory(_uncheckedico()) $hIcon_uc = _GDIPlus_HICONCreateFromBitmap($hBmp) _GDIPlus_ImageDispose($hBmp) EndIf If $bSpecialLV Then Local $hImageListLV = _GUICtrlListView_GetImageList($vCtrl, 2) _GUIImageList_Remove($hImageListLV) _GUIImageList_ReplaceIcon($hImageListLV, -1, $hIcon_uc) _GUIImageList_ReplaceIcon($hImageListLV, -1, $hIcon_c) EndIf If $bSpecialTV Then Local $hImageListTV = _GUICtrlTreeView_GetStateImageList($vCtrl) _GUIImageList_Remove($hImageListTV) _GUIImageList_ReplaceIcon($hImageListTV, -1, $hIcon_c) _GUIImageList_ReplaceIcon($hImageListTV, -1, $hIcon_c) _GUIImageList_ReplaceIcon($hImageListTV, -1, $hIcon_uc) EndIf _GDIPlus_Shutdown() Return True EndFunc ;==>_GUICtrlSetDarkTheme #EndRegion Public Functions #Region Enable GUI DARKMODE ; TODO: these functions probably need common #FUNCTION# to be more descriptive Func _ApplyDarkTheme($hGUI, $bPreferNewTheme = False) _GUISetDarkTheme($hGUI, True) _GUICtrlAllSetDarkTheme($hGUI, True, $bPreferNewTheme) ; GUIDarkMenu _GUITopMenuTheme($hGUI) ; redraw menus _GUICtrlMenu_DrawMenuBar($hGUI) EndFunc #EndRegion Enable GUI DARKMODE #Region Enable GUI LIGHTMODE Func _ApplyLightTheme($hGUI) _GUISetDarkTheme($hGUI, False) _GUICtrlAllSetDarkTheme($hGUI, False) EndFunc #EndRegion Enable GUI LIGHTMODE ;Code below was generated by: 'File to Base64 String' Code Generator v1.20 Build 2020-06-05 Func _uncheckedico($bSaveBinary = False, $sSavePath = @ScriptDir) Local $uncheckedico $uncheckedico &= 'JLgAAAABAAcADQ2iAAAACADhAFB2ABgEEBADeA0BAABXKQAMFBQDPBYALGQCUAAAGhoDPBkAPHqgAwAAICADHiIAHkCTBAAAKCgDHgyBAFa1BQAANDQDHgIlAB7BBwAAiVBATkcNChoKACgNMElIRFIBBwEDCAYhAAVy6+R8AAYJcIBIWXMAAA7DAQMgAcdvqGQAFBl0AEVYdFNvZnR3AGFyZQB3d3cuAGlua3NjYXBlgC5vcmeb7jwBmABuSURBVCiR7QDOsQ2DQBQDUAD7xBZJdXOQAQBQekZgJpIBMgBKtjjfSTCHPwADpOA6mlhy5wAnmaWUJ4AXyQAbzrOnlJaB5ABqe845f8+EpADR9geSIiLQWwBJkTou/eSPLgBBu6SxZ1xrfQAA2Nham2y/AQDcO9xGcjkAKYDDR/wtaZg+AXEASUVORK5CYIILEHABqRACcB/z/2EFOnCaAXA4je2TuwANwkAQBed8yADWBdRA7h4QOQBtIDpwN+BSkACQi9jotEWQ+ACTPBJMRGATewCkDd9sNMHdDwBACxyBkmVMQAAn6bIDWkmPYQAYznVdT0vWZgBWppSaEMI9uAD72Pf9ful4JgDnXMUYX7i7JADxz7m7ijVffwCxCTbBLJjMbABpRF9yzhUwFgBAl1Jq1kjMrACMMTZAFz453wCAE+tyfkq6vgAB5PhpkG9/YxbrHEPBkxQCQ42JHQuBfjdDowRD1bENwgAwEAXQfyeMbgAFkNO5o0ZMwwAqFGGLlGQZFgBwZ19FMkOa6ABoLCoqmwrlSwDXPv3qPsUY9wAicieiK4AD6gAym9m4LMttJwAiPRGdnHNn7wD9VKOllDwzDwAi0pOqTuu6XgBCCK/KdgCAnABzx8xPqKqZGQB+capq3NLqWwA2cAM38H/AOQCl5FuhnHMHYABmMxuZeWhBywAvHIjoQWUC+gAyAcdK8zMBbwBd7XfzBEcR9gtcRYEzGkJFqUpMzgV6RaZBRUiJ' $uncheckedico &= '7dYxAA7CMAyFYduiAMhXAKVbN2bEAGl6FYZwi4z0ADJcoFviieYMAFkqswQmxmTzAJM8f/L247quAEdmfiDiDAAnAGi7rKpLKeV+AGBmj4iXYRiuAM65raUSY3REABSY2aOIbPu+AN+maXq3RL5LACmNRPQCEVFVAIWeJyJKPb74QDeDDDLIIIAAqAAXlGOMrheQUgAaASCTqi5EFAB6YLWAAiI+sQAGpK8BeW5s/QAC8gMezIntdFgI9eUcI8GLIAIjc1h6evQfIxgjrwEjWACF7dexDQIxDAAFUNvikFcA5QC6dNSIaViF4gDY4kpuGRZIlwS44sBFk2kCFbUAafwl1/+5/JgAUtoz8x0RrwAAcACbVFVdWmsAtx0zT4h4GoYA4RxCWC3ac84AgYhmZp5QRNYAbdsuMcaXRfkAJ6WUkYieICIAqqrwjxMRJcsAr3/FAQ5wgANAHOAABzjAQgEIAABqzjlYF5dSAEYAqKSqCxHNAJaIvgtnRHxgAJ/nU5/nRyPDAHeevwHMfpvnsLW1yZQ8JAGuKCIkMIz+uG0/JDckAZkBJCTYsUocQRzHAPHv7t6yhdEgACkzXrVwEAPaAJ29RVLkCXIPAGB1wnEvYZMiAK11fANT6AuoAN0FEuG45Q72AG7bBKIyyDD8AFPcRIygCAO7ACnmW/2n+xS7AM0vEhEAiqLIAFqt1p6IfATeAAIr1NsN8B04ALLWHuZ5fgsQAIkIi8XitTHmACuwVTPqsUZpAJp+UEpV0WQyAMmSJLlgiZuLAMjAGHPa6XSuAOoUjcfj1SzLAHZF5ADoACNrAO1ONJvN9kXkADMwT9N0Wyn1ALNO2MPKsly3ANZ+AzaAfiwiAD0AERk0jQNoALfbv4Che/ZiAOANgDHmtDHVAIOstSfu3IyBABcAdX9zT5XnAPlvd67GjUqeAFEA+haAvgWgEG8B6FtWAQPXsADc5xq23DWdTgBfuvMqBi4BsgAs222O9G9RFAC9' $uncheckedico &= 'c+ePGPgCIAAiB2VZrjfHWgBWVdUr4JN7HgD9nYDPgW1gDgAMrbUn9yawWgAqimItSZL3DgCngJHWunt/RAA/dsj/obsRPQIGwB5a6y7QB84AcT9OzV0DZ0AAX2vdVUpVAH8AAOQTmFcI9KgW1HxBge00YkHFeBsvIbF/Qb8gsyCysSBogQDt2rFqFFEUgADhf2Z2mEKjBABLr1sNLETBdABrn0ILn8A8gADVCiEvkcbC1gDavIEWyQsYuwAVVFh22IXZnQDWQBK5yOVyLAB2DKkCbpA5gQDzVed25y9mqgCTiAgAVVUVvQBe77WIvAKeAAB30O0X8A04jAAxvi/L8jdAIgAiLJfLhyGETwDA005XXN84zwDzl865JplOpwBFlmVfWMUsRABkL4RwPBgMzgC73vI6k8lkowAoih0ROQAGwAA4xvgsmc/nbwBE5B2wyPN82wA597PjXf9JXQDXmzHGr8AjYACUisgugIjs3QC2GIB+v38K7AC3z90U2AIIIQAcd7bVDcUYjwDa8XEK3AXQ/gDNXKcsy7N23ABIO93kP7Ag7QAsSDsL0s6CtA6zrwCvAKEALgUuYAB1O9PxLmubzQBm99vxPAV+AAAURbHT3Uo3kwAkyfN2/J4CHwAAROSgruvN7gDWWk/TNA+AtwDt8/DvedkJsAANLID9GOPRlQBzE5WqqrqXZQDZC1YxDhh77wCHVw8AP7KKugCNLg8AUwDnXADjvR8CI+CE9gBHodwF8BkYeQDvh865BuAPs4CEmG/rOy7qSSI=' $uncheckedico = _WinAPI_Base64Decode($uncheckedico) If @error Then Return SetError(1, 0, 0) Local $tSource = DllStructCreate('byte[' & BinaryLen($uncheckedico) & ']') DllStructSetData($tSource, 1, $uncheckedico) Local $tDecompress _WinAPI_LZNTDecompress($tSource, $tDecompress, 2534) If @error Then Return SetError(3, 0, 0) $tSource = 0 Local Const $bString = Binary(DllStructGetData($tDecompress, 1)) If $bSaveBinary Then Local Const $hFile = FileOpen($sSavePath & "\unchecked.ico", 18) If @error Then Return SetError(2, 0, $bString) FileWrite($hFile, $bString) FileClose($hFile) EndIf Return $bString EndFunc ;==>_uncheckedico Func _checkedico($bSaveBinary = False, $sSavePath = @ScriptDir) Local $checkedico $checkedico &= 'FrwAAAABAAcADQ0CAAAACABoAQAAUnYASBAQA3icAHjeKQAMFBQDPLMALHoDUAAAGhoDPOoAPC0gBQAAICADHgUCAAAAFwcAACgoBQMeLAAeHAkAADQKNAMe7wAeSAsAAACJUE5HDQoaCsEAKA1JSERSAQcBA4QIBgAFcuvkfAAGAAFzUkdCAdnJBCx/AAwEZ0FNQYAAALGPC/xhAG9AACBjSFJNAIsmgAAAgIQAAPoAEgCA6AAAdTAAAEDqYAAAOpgAh3AQnLpRPAAYCXBIQFlzAAASdAEDARDeZh94ABQHdEkATUUH6QUDFScQC3AwyoBLAL5JAERBVCjPlZI9AArCUBCEv32IAJ2Q0lbIAQT1AAD2eoY8K8vgAAmMJzBHeAewABC8gIWluYGVABcwkC5F1sJGAGN+t5thPwZ2AFYAgkQjUQ0RAPGoG9UUwbmZANlJkBSxICFdAEc1EnsvXo0JABWJphcAIOKZAC57j4v70a3QAG1vQaQeel7PAH/AeLHEXwX1AFCepdyiTSMAADD4Fv7aAnBaAE+YbqNKAEBsAKJaNvMsZTiqAD+qQTUtm03AAKcniPv1hBMAAJsURxTb+nsQALu5ObwBAjdAINLNNQjVgbRJRcBORK5CYIKQs4HsQhCCsx/z/2HosyagLbsmfr6ABPLBWQA4y6WSoU4DQQAQhr/ZENSRNAC4Vi0JCfaa0AAHwNX0AVA9TADtlSegj3CVxQBwZ1AYwODaBwAoySoSEsQGQQAdIeEUooPClADL0Vs+OZP/mwCZZARguFyPRQBIQSxboY41WQDeM4UMl5qIcABFAKp6bkQ0JQAQgdSAxAQbxAAa/kkjwct9zgDX50eYwM0mPABdT9ndazUXuADZhNfFLf3LeQD9CeWb52ZwQAC58pXhzem/BABRxxKPLngYnQBQrvyfYYCdzQDC4SAB4O60SwDUtrVhAEkeVQCrGu/PjqhjawDDlRv8sH8UbwD7B+qDv0jVGQBV' $checkedico &= 'puECMlMcmwBMlTNUXYPJHgDVcd4zxTfIqsBYwb1oypbcZkHZ4hTCZo2JHQHE/2bkZqARlEkCOeANCWMzAGNkYGBQ0osvAFHTTqhqZeXiAFFjYmHlYSARAHx/+/LQ5UWdAO13V0+7xWhSANRjpRWRv4OJAJmFl4EC8P/fAN9PVxdN8GSMADn6bRsLB6cnAAMVwN/fP48yEFHLMAYAACYWVgAdJgYqAkZGJgB+qhrIwMDAMAA4DHx36wLDpgBIQ6xyLOQYtgCvKJDBqW895QAuRDZMSM2AeAADN0UaMry7dQCBZMNwGmjTOACfYV9xINxQYggNY2AAAEw4+/8AP07vFQcyGKQA1TNcmNlIlGEAeA0k1WVEGTgASBL2//8fqGsAICPDBeoZ938AA9N/JsZEqrgA8v//D/9/MRYAMi00ZHzwn5kA0ZCB4f8Gcg0AYvj//8D/34wAhgstGR8AAECAyXfEAJ1molw2hQGhGkI2qUpMzl82B182XzZCNiUtkAstCn3gDUBBNkjH7dYAvU7CUBwF8HMAbgwTJqwydfAABTo4kDjAxuIAAzhRF1b0CaAAT2AYZWpfwYkADQZHDT5CJ+cAm8BUI8cBjPUAq4G218TEM98A3F9Ocj/+xDYAvYU8rjWAEIAAbKBMpATEXCkQw7jFBGC3vXsFAISuSwNfQQvhADI6MTF7C3l8ANGiciSD6Zm+AOFaQ2cIAJANANY0MADacB0hADAAPecQ2TD4AKX8Q98mXVpMAPtt3I0uflxzAFAN0kG6sjgNACM3jbJIdzJDAP3Iqx7aB8mFAB5vRrg995EuAG1pJBc6PgveADfMYEWQXKjeAPTQncw+YEURAABg8CDlLVg9ACWY9juoHW7eAN0iyE6HIdusACiyU6NsMxCFAJC9Lmy96f2VALdOsu4/PiUGAETk/uPD3MhwAOy0lWSVMjSxAM9E4JUTbDtuAMUtJvw0QA43AMNKyTlCsiAiAKUcvw2Qr2rGwMEJ' $checkedico &= 'sCLwVzw9QdzCICI9c3p69D89Pz2DPz0jPQ9Fa2yZ4A0CWyE9WMPtl7FKAQGn/xnETghWVgCW1jHBTvBiZQBpa2XS2F7yBACeD3C4KZPmtABJq/gCuYBV5ABkq0AsfYAjTwBwkyLcEQOSuwBkvQXJXy67fAAfw8DOEJZy+wAhDrG4EDggqgDAZERmIISSUAD3+YzC9JgyeACUKAK5KCWingDq3MkEyoX/lACgRdkxhIVIggAGE4sLSyEWlwAhcGwJQOCw8QBuL1QCqjAsZwAn8H8FJgOFsQDfsSOgex7GfiAH8VSXL5AAdP8AAYcnVVz6L+UACizDr/pD7B8AVMoT2ASeS+AA7eZ0bTNtCs8AJXDcuMZkoPAA7rWMwwFgb90AherdfQYCgHMALzAGzyXwm4QACXhugVWJeKoAEX/preGFBFYAJUzAAYCakUgA0Uff4SuO6s4A1vCNBXa/oVkAAZGZvaFUZgwAQmhvKEXIklAA195QDMWLRVEAlIX6q6DGo2wAOW1GySNAbSsAy2ma1mdyIYIA9l+u50RQQY0AR+nxHEBxo7twn1z1Zk8gSiBxjSjhQiCM/rhtTyBPIE8gB08gTyBOICQvZx59CbB7AYJEINgxTgIAQRTG8f+bmsIAVqvlBmBiYScAnYUGboCVrUcAEG5AbWO2t8AAzg6tjWFv4FYA2lJQWexnAZgADUHDCosvcb8Ador55c28yeQAGUvpPuvEgtoAQAcsYidRAiQA+rB+fGxpfsUAvmBj7ZGpZ9gAFX8aDRSsHzcAbfIF7I61Z5kARmANXESJgrUA4qZNAgCZen4AcADWsEzXANYAHSuyjFccRhkArbCQeowFtQMA0PAKRHSCr7sAt1xCiwLOUwEAK2AF9AScvqUA3J3VuTuv+wMATt9SHi5bTN8AU38VzONqBxEApzcjP8BVuNoAfuQDuCmuVOAANnCFgIvuW+cAkm8LV7iC63QI4jZxAAGNfkJuABtXCJjfcBWy' $checkedico &= 'AAxc4SP+DlkWAA7ALl6kTTsUAFEK7tfPzHIlAMvCbfQO5kFlAOF+fcTVf7ACAP4zoFK3OikJAMDQ7+iDJCizAHu3BfywfoiPAOwRNHDIG8THAJYGAAXrzwfZAF5wycw07+K4AGkTBWv5qKQGAIv59OwaLmU2ABLWNaKB7Wh2ACilGEMzhreHAOEpv/QJnXUC4MfNU5eMvyK6IjGvwjSyIsV4G+u/Ir8iD78ivyK/Ir8iE0hxASCXAAACRbEiaN4A7dq/TttQFMcA8e+5SjOBFHUAqhiQh6pzKEUAiM3p1KUib2AAs6QrqA8A3asAMpcl8RukW6cA1h1bqBJWJqsAQ7shS2WC4NMAIYDSNKiQOP4AJ//Gq+vho3sA77m2dYRb4hwAqi1GNwEbxUIIpEaaQK8CwNeBAHjeuvQnTZN/ACA9tSTSNohNAKajXT2XHW9DAILRUfMX5khdALnUXvYxANKUAAfacw8jZ+IKADlH6orQJo+JANTtrBnvBuT0ANSSS+2lfk5mADhfeiEr3oYEAAZAIt3PLQZAAKQmVW0DiPNVAOtSoUcBohENACMVdShIxOimAAHsooBQbINiAFGcWCbXxWBCAHEwFCwlqASVAKASVIISzelJAJ9Pr5v88LtTAD1fyRrmY6vBAPnvkNOTY5btAGZ+V2gUA/D4AKWb3y03jqm/ANqj3trNJyhOAEzqoLgxqYLmAIFJDTQvzNSgAG9vt+msCv33AHuZwkwNur70APoHb+6FmjdmAGrQ83ddqou1AHuhksBMDXr4AKTOi4PPd0YlAIWZqSjcFZUkAGbmKvc/VNIYAABxv6vGXoZbALssN5qJY2IDIE1CVRdrgAC9WADHt18amNjfFADGUUljYt1yowA5+xlw9ivg0QCqnfhr1Vy+WAAXliwWlqzynwBCCSpBuQSphgCF0aiG5qrdpAAoCQzgF4Yj+ABGI/lQmB03EADPeGvig+Z/lQAi7Xrr0jcAagBkK9fFQTXU' $checkedico &= 'gQDs3JRtb0UCZQA4kE8Q29dtZgA395D3TDqq5ABrpVTD0U6sYQBdGMtVA+A+SAAz4xhfL2RrvAABUG6bP2xqUgAHxYaMtGhCgADgi9BtPzVfJgBN+wPXaGWGHAihNfHpLg==' $checkedico = _WinAPI_Base64Decode($checkedico) If @error Then Return SetError(1, 0, 0) Local $tSource = DllStructCreate('byte[' & BinaryLen($checkedico) & ']') DllStructSetData($tSource, 1, $checkedico) Local $tDecompress _WinAPI_LZNTDecompress($tSource, $tDecompress, 3639) If @error Then Return SetError(3, 0, 0) $tSource = 0 Local Const $bString = Binary(DllStructGetData($tDecompress, 1)) If $bSaveBinary Then Local Const $hFile = FileOpen($sSavePath & "\checked.ico", 18) If @error Then Return SetError(2, 0, $bString) FileWrite($hFile, $bString) FileClose($hFile) EndIf Return $bString EndFunc ;==>_checkedico Func _WinAPI_Base64Decode($sB64String) Local $aCrypt = DllCall("Crypt32.dll", "bool", "CryptStringToBinaryA", "str", $sB64String, "dword", 0, "dword", 1, "ptr", 0, "dword*", 0, "ptr", 0, "ptr", 0) If @error Or Not $aCrypt[0] Then Return SetError(1, 0, "") Local $bBuffer = DllStructCreate("byte[" & $aCrypt[5] & "]") $aCrypt = DllCall("Crypt32.dll", "bool", "CryptStringToBinaryA", "str", $sB64String, "dword", 0, "dword", 1, "struct*", $bBuffer, "dword*", $aCrypt[5], "ptr", 0, "ptr", 0) If @error Or Not $aCrypt[0] Then Return SetError(2, 0, "") Return DllStructGetData($bBuffer, 1) EndFunc ;==>_WinAPI_Base64Decode Func _WinAPI_LZNTDecompress(ByRef $tInput, ByRef $tOutput, $iBufferSize) $tOutput = DllStructCreate("byte[" & $iBufferSize & "]") If @error Then Return SetError(1, 0, 0) Local $aRet = DllCall("ntdll.dll", "uint", "RtlDecompressBuffer", "ushort", 0x0002, "struct*", $tOutput, "ulong", $iBufferSize, "struct*", $tInput, "ulong", DllStructGetSize($tInput), "ulong*", 0) If @error Then Return SetError(2, 0, 0) If $aRet[0] Then Return SetError(3, $aRet[0], 0) Return $aRet[6] EndFunc ;==>_WinAPI_LZNTDecompress For sure you can use GD+ to draw the check / uncheck icons (bitmaps) as @argumentum did above.
  6. I cannot reproduce the issue on my system. It displays as intended in the correct size and in dark mode.
  7. I'm on Win11 24H2. WM_NOTIFY should only change the thumb - not the whole slider control but if you change the style of the control, it would not fit with current setting. For the demo it is ok not if you use different styles.
  8. System Menu text colors (when you click on the Autoit icon in the left upper corner) and slider thumb are not working properly. Slider thumb is changing the color when dragged.
  9. ;Coded by UEZ build 2026-02-28 beta #include <WindowsConstants.au3> #include <GuiConstants.au3> #include <GuiDateTimePicker.au3> #include <GuiMonthCal.au3> #include <WinAPI.au3> #include <WinAPISysWin.au3> #include <WinAPITheme.au3> Opt("MustDeclareVars", True) Global $g_hDateProc_CB, $g_pDateProc_CB, $g_hDateOldProc, $g_hDate Global Const $PRF_CLIENT = 0x0004, $COLOR_BORDER = 0x404040, $COLOR_BG_DARK = 0x202020, $COLOR_TEXT_LIGHT = 0xFFFFFF, $COLOR_BORDER_LIGHT = 0xD8D8D8 Global $g_bHover = False Example() Func Example() Local $hGUI = GUICreate("Sample GUI", 400, 240) GUISetBkColor($COLOR_BG_DARK) Local $idDate = GUICtrlCreateDate("", 15, 15, 200, 20) $g_hDate = GUICtrlGetHandle($idDate) $g_hDateProc_CB = DllCallbackRegister('_DateProc', 'ptr', 'hwnd;uint;wparam;lparam') $g_pDateProc_CB = DllCallbackGetPtr($g_hDateProc_CB) $g_hDateOldProc = _WinAPI_SetWindowLong($g_hDate, $GWL_WNDPROC, $g_pDateProc_CB) GUIRegisterMsg($WM_NOTIFY, "_WM_NOTIFY") GUISetState() While True Switch GUIGetMsg() Case $GUI_EVENT_CLOSE _WinAPI_SetWindowLong($g_hDate, $GWL_WNDPROC, $g_hDateOldProc) DllCallbackFree($g_hDateProc_CB) GUIRegisterMsg($WM_NOTIFY, "") GUIDelete() ExitLoop EndSwitch WEnd EndFunc ;==>Example Func _DateProc($hWnd, $iMsg, $wParam, $lParam) Switch $iMsg Case $WM_PAINT Local $tPaint = DllStructCreate($tagPAINTSTRUCT) Local $hDC = _WinAPI_BeginPaint($hWnd, $tPaint) Local $tClient = _WinAPI_GetClientRect($hWnd) Local $iW = $tClient.Right Local $iH = $tClient.Bottom ; --- Memory DC for flicker-free rendering --- Local $hMemDC = _WinAPI_CreateCompatibleDC($hDC) Local $hBitmap = _WinAPI_CreateCompatibleBitmap($hDC, $iW, $iH) Local $hOldBmp = _WinAPI_SelectObject($hMemDC, $hBitmap) ; 1. Let Windows draw the light-mode control into memory DC _WinAPI_CallWindowProc($g_hDateOldProc, $hWnd, $WM_PRINTCLIENT, $hMemDC, $PRF_CLIENT) ; 2. Invert all pixels (background becomes black, text white, selection orange) Local $tRect = DllStructCreate($tagRECT) $tRect.right = $iW $tRect.bottom = $iH _WinAPI_InvertRect($hMemDC, $tRect) ; --- 3. PIXEL HACK: destroy orange highlight & set background color --- Local $iSize = $iW * $iH Local $tPixels = DllStructCreate("dword c[" & $iSize & "]") ; Load pixel array directly from bitmap memory Local $iBytes = DllCall("gdi32.dll", "long", "GetBitmapBits", "handle", $hBitmap, "long", $iSize * 4, "ptr", DllStructGetPtr($tPixels))[0] If $iBytes = $iSize * 4 Then Local $iPixel, $r, $g, $b, $iGray For $i = 1 To $iSize $iPixel = $tPixels.c(($i)) ; Split into color channels $b = BitAND($iPixel, 0xFF) $g = BitAND(BitShift($iPixel, 8), 0xFF) $r = BitAND(BitShift($iPixel, 16), 0xFF) ; Convert to grayscale (orange becomes mid-gray) $iGray = Int(($r + $g + $b) / 3) ; Very dark pixel = inverted white background If $iGray < 15 Then $iPixel = $COLOR_BG_DARK ; Replace with exact GUI background color Else ; Grayscale value for text (white) and selection (gray) ; (negative BitShift shifts left in AutoIt) $iPixel = BitOR(BitShift($iGray, -16), BitShift($iGray, -8), $iGray) EndIf $tPixels.c(($i)) = $iPixel Next ; Write cleaned pixels back into the bitmap DllCall("gdi32.dll", "long", "SetBitmapBits", "handle", $hBitmap, "long", $iSize * 4, "ptr", DllStructGetPtr($tPixels)) EndIf ; --- END PIXEL HACK --- ; --- Border color (hover effect) --- Local $iBorderColor = $COLOR_BORDER If _WinAPI_GetFocus() = $hWnd Then $iBorderColor = $COLOR_BORDER Local $tCursorPos = DllStructCreate($tagPOINT) DllCall("user32.dll", "bool", "GetCursorPos", "struct*", $tCursorPos) DllCall("user32.dll", "bool", "ScreenToClient", "hwnd", $hWnd, "struct*", $tCursorPos) If $tCursorPos.X >= 0 And $tCursorPos.X <= $iW And $tCursorPos.Y >= 0 And $tCursorPos.Y <= $iH Then $iBorderColor = $COLOR_BORDER_LIGHT EndIf ; --- Draw border --- Local $hPen = _WinAPI_CreatePen(0, 1, _ColorToCOLORREF($iBorderColor)) Local $hNullBr = _WinAPI_GetStockObject(5) Local $hOldPen = _WinAPI_SelectObject($hMemDC, $hPen) Local $hOldBr = _WinAPI_SelectObject($hMemDC, $hNullBr) DllCall("gdi32.dll", "bool", "Rectangle", "handle", $hMemDC, "int", 0, "int", 0, "int", $iW, "int", $iH) _WinAPI_SelectObject($hMemDC, $hOldPen) _WinAPI_SelectObject($hMemDC, $hOldBr) _WinAPI_DeleteObject($hPen) ; --- Copy finished result to screen in one step (no flicker) --- _WinAPI_BitBlt($hDC, 0, 0, $iW, $iH, $hMemDC, 0, 0, $SRCCOPY) ; --- Cleanup --- _WinAPI_SelectObject($hMemDC, $hOldBmp) _WinAPI_DeleteObject($hBitmap) _WinAPI_DeleteDC($hMemDC) _WinAPI_EndPaint($hWnd, $tPaint) Return 0 Case $WM_ERASEBKGND Return 1 Case $WM_SETFOCUS, $WM_KILLFOCUS, $WM_LBUTTONDOWN, $WM_LBUTTONUP Local $iRet = _WinAPI_CallWindowProc($g_hDateOldProc, $hWnd, $iMsg, $wParam, $lParam) _WinAPI_InvalidateRect($hWnd, 0, False) Return $iRet Case $WM_MOUSEMOVE Local $iRet = _WinAPI_CallWindowProc($g_hDateOldProc, $hWnd, $iMsg, $wParam, $lParam) If Not $g_bHover Then $g_bHover = True _WinAPI_InvalidateRect($hWnd, 0, False) EndIf Return $iRet Case $WM_MOUSELEAVE $g_bHover = False _WinAPI_InvalidateRect($hWnd, 0, False) EndSwitch Return _WinAPI_CallWindowProc($g_hDateOldProc, $hWnd, $iMsg, $wParam, $lParam) EndFunc ;==>_DateProc Func _ColorToCOLORREF($iColor) ;RGB to BGR Local $iR = BitAND(BitShift($iColor, 16), 0xFF) Local $iG = BitAND(BitShift($iColor, 8), 0xFF) Local $iB = BitAND($iColor, 0xFF) Return BitOR(BitShift($iB, -16), BitShift($iG, -8), $iR) EndFunc ;==>_ColorToCOLORREF Func _WM_NOTIFY($hWnd, $iMsg, $wParam, $lParam) #forceref $hWnd, $iMsg, $wParam Local $hWndFrom, $iIDFrom, $iCode, $tNMHDR, $tInfo, $tBuffer, $tBuffer2, $iCtrl $tNMHDR = DllStructCreate($tagNMHDR, $lParam) $hWndFrom = HWnd($tNMHDR.hWndFrom) $iIDFrom = $tNMHDR.IDFrom $iCode = $tNMHDR.Code Switch $hWndFrom Case $g_hDate ; thanks to argumentum for the code :-) Switch $iCode Case $NM_SETFOCUS ; Disable visual theme when DateTime control receives focus _WinAPI_SetThemeAppProperties(0) Case $DTN_DROPDOWN ; Apply dark colors when the calendar dropdown opens _WinAPI_SetWindowTheme($iCtrl, "", "") Local $iCtrl = _GUICtrlDTP_GetMonthCal($hWndFrom) _GUICtrlMonthCal_SetColor($iCtrl, $MCSC_TEXT, $COLOR_TEXT_LIGHT) _GUICtrlMonthCal_SetColor($iCtrl, $MCSC_TITLEBK, $COLOR_BG_DARK) _GUICtrlMonthCal_SetColor($iCtrl, $MCSC_TITLETEXT, $COLOR_TEXT_LIGHT) _GUICtrlMonthCal_SetColor($iCtrl, $MCSC_MONTHBK, $COLOR_BG_DARK) _GUICtrlMonthCal_SetColor($iCtrl, $MCSC_TRAILINGTEXT, $COLOR_TEXT_LIGHT) Case $DTN_CLOSEUP ; Calendar dropdown closed - no action needed EndSwitch EndSwitch Return $GUI_RUNDEFMSG EndFunc ;==>_WM_NOTIFY
  10. I created a fake DateTimePicker control. Does anyone know in which DLL or other file the original icon is hidden?
  11. The problem was that the entired tab client area was overwritten in _WinProc -> WM_PAINT section by _WinAPI_BitBlt. I exluded that client area. I added also a repaint when minimized GUI was restored again and added a checkbox on 2nd tab. Should work now - please test (see 1st post).
  12. Code updated. Added Cartoon mode for more arty results but very slow calculation.
  13. 1) This is not necessary, as it is only relevant for scaling purposes 2) This is a Windows GDI requirement. SelectObject always returns the previously selected object, and you must restore it before deleting the DC. If you don't, you're deleting a DC that still "owns" your bitmap, which can cause resource leaks or undefined behavior. 3) The shadow margins from DWM only apply to top-level windows with a drop shadow (the typical WS_OVERLAPPEDWINDOW style). In these cases: Cropping needed: Standard top-level windows (GUICreate, CreateWindowEx with default styles) — they have DWM shadow margins, so the captured bitmap is slightly larger than the visible content. Cropping not needed / potentially harmful: Borderless windows, child windows, embedded controls (WebView, IE, DebenuViewer), or windows with WS_POPUP and no shadow. Here DWMWA_EXTENDED_FRAME_BOUNDS equals the window rect, so all margins would be 0 anyway — but it's worth checking, since forcing a crop on such windows could cut off actual content. So your observation is correct: questions 1 and 3 are essentially the same issue — both assume scaling or size differences that may not actually exist.
  14. Here my suggestion: #include <GUIConstantsEx.au3> #include <GDIPlus.au3> #include <StaticConstants.au3> #include <WinAPIGdi.au3> #include <WindowsConstants.au3> Const $PW_RENDERFULLCONTENT = 2 _Example() Func _Example() ; Launch Calculator and wait for it to finish opening ShellExecuteWait(@SystemDir & "\calc.exe") Local $hWnd = WinWaitActive("[REGEXPCLASS:CalcFrame|ApplicationFrameWindow]", "", 3) If Not $hWnd Then Exit ; Abort if the window didn't appear in time Sleep(500) ; Wait for the window to fully render and skip the open animation ; Create a GUI slightly larger than the Calculator window Local $aSize = WinGetPos($hWnd) Local $hGUI = GUICreate("Test " & StringReplace(@ScriptName, ".au3", "()"), $aSize[2] + 80, $aSize[3] + 80) GUISetBkColor(0x404040, $hGUI) ; Dark gray background Local $idPic = GUICtrlCreatePic("", 48, 48, $aSize[2], $aSize[3]) ; Placeholder for the captured bitmap GUISetState(@SW_SHOW) ; Capture the Calculator window as a GDI bitmap (cropped, client area, GDI-compatible) Local $hGDIBitmap = _WinAPI_CreateBitmapFromPrintWindow($hWnd, True, $PW_RENDERFULLCONTENT, True) ; Assign the bitmap to the picture control, delete any previously set bitmap Local $hHBmp = GUICtrlSendMsg($idPic, $STM_SETIMAGE, $IMAGE_BITMAP, $hGDIBitmap) If $hHBmp Then _WinAPI_DeleteObject($hHBmp) Do Until GUIGetMsg() = $GUI_EVENT_CLOSE ; Cleanup _WinAPI_DeleteObject($hGDIBitmap) WinClose($hWnd, "") GUIDelete($hGUI) EndFunc ;==>_Example ; Captures a window's content using PrintWindow and returns a GDI+ or GDI bitmap. ; $bCrop - Crop the bitmap to the visible frame using DWM (removes window shadow/frame margins) ; $iClientMode - PrintWindow flags passed directly to PrintWindow (1 = PW_CLIENTONLY). PW_RENDERFULLCONTENT (required for UWP/DX windows) ; $bBmpGDI - Return a GDI HBITMAP instead of a GDI+ bitmap handle Func _WinAPI_CreateBitmapFromPrintWindow($hWnd, $bCrop = True, $iClientMode = 1, $bBmpGDI = False) Local $aWinSize = WinGetPos($hWnd) If @error Then Return SetError(1, 0, 0) ; Set up a memory DC with a compatible bitmap to draw into Local Const $hDC_Capture = _WinAPI_GetDC($hWnd) If @error Then Return SetError(2, 0, 0) Local Const $hMemDC = _WinAPI_CreateCompatibleDC($hDC_Capture) Local Const $hHBmp = _WinAPI_CreateCompatibleBitmap($hDC_Capture, $aWinSize[2], $aWinSize[3]) Local Const $hObjectOld = _WinAPI_SelectObject($hMemDC, $hHBmp) ; Use HALFTONE for better quality when stretching/scaling during capture _WinAPI_SetStretchBltMode($hDC_Capture, $HALFTONE) ; Capture the window content using the specified PrintWindow flags _WinAPI_PrintWindow($hWnd, $hMemDC, $iClientMode) ; Restore and release DC resources _WinAPI_SelectObject($hMemDC, $hObjectOld) _WinAPI_DeleteDC($hMemDC) _WinAPI_ReleaseDC($hWnd, $hDC_Capture) ; Skip GDI+ conversion if no cropping is needed and a raw HBITMAP (GDI) was requested If $bCrop = False And $bBmpGDI = True Then Return $hHBmp _GDIPlus_Startup() ; Convert the HBITMAP to a GDI+ bitmap Local $hBitmap = _GDIPlus_BitmapCreateFromHBITMAP($hHBmp) _WinAPI_DeleteObject($hHBmp) ; Optionally crop the bitmap to the visible window area, excluding shadow/frame margins If $bCrop Then Local $iLeft, $iTop, $iRight, $iBottom, $pX, $pY ; Query the actual visible frame bounds via DWM to get the exact shadow margins Local $tRECT = _WinAPI_DwmGetWindowAttribute($hWnd, $DWMWA_EXTENDED_FRAME_BOUNDS) ; Calculate the margin on each side $iLeft = $tRECT.left - $aWinSize[0] $iTop = $tRECT.top - $aWinSize[1] $iRight = $aWinSize[0] + $aWinSize[2] - $tRECT.right $iBottom = $aWinSize[1] + $aWinSize[3] - $tRECT.bottom Local $hBitmap_Cropped = _GDIPlus_BitmapCloneArea($hBitmap, $iLeft, $iTop, $aWinSize[2] - $iLeft - $iRight, $aWinSize[3] - $iTop - $iBottom) _GDIPlus_BitmapDispose($hBitmap) $hBitmap = $hBitmap_Cropped EndIf ; Optionally convert to a GDI HBITMAP (needed for use with STM_SETIMAGE etc.) If $bBmpGDI Then Local $hBitmap_GDI = _GDIPlus_BitmapCreateHBITMAPFromBitmap($hBitmap) _GDIPlus_BitmapDispose($hBitmap) _GDIPlus_Shutdown() Return $hBitmap_GDI EndIf _GDIPlus_Shutdown() Return $hBitmap EndFunc ;==>_WinAPI_CreateBitmapFromPrintWindow _WinAPI_CreateBitmapFromPrintWindow is from here:
  15. I enhanced the Delaunay function in my _GDIPlus_BitmapApplyFilter Dll and created a front-end GUI to generate Low-Polygon images: Code: ;Coded by UEZ v0.70build 2026-02-20 ;Requires 3.3.15.0+ version #AutoIt3Wrapper_Version=p #AutoIt3Wrapper_UseX64=y #AutoIt3Wrapper_Res_HiDpi=y #include <Array.au3> #include <ButtonConstants.au3> #include <ComboConstants.au3> #include <EditConstants.au3> #include <GDIPlus.au3> #include <GUIConstantsEx.au3> #include <GuiStatusBar.au3> #include <ScreenCapture.au3> #include <StaticConstants.au3> #include <WinAPIGdi.au3> #include <WinAPISysWin.au3> #include <WindowsConstants.au3> #include "_GDIPlus_BitmapApplyFilter.au3" Global Const $hDLL = _GDIPlus_BitmapApplyFilter_Open("c:\_BZ25LN\Coding\FreeBASIC\__UEZ\__Projects\_GDIPlus_BitmapApplyFilter\_GDIPlus_BitmapApplyFilter_x64.dll") Global Const $sVer = _GDIPlus_BitmapApplyFilter_Ver2() Global $tokenVer = StringRegExpReplace($sVer, "v(.+?)\h+.+", "$1") Global $tokenBuild = StringRegExpReplace($sVer, ".+build\h+(.+?)\hbeta", "$1") If Not CheckVer($tokenVer, "1.0.0") Or $tokenBuild < "2026-02-19" Then MsgBox(16, "Error", "Requires at least DLL v1.0.0 build 2026-02-19." & @CRLF & "Found: " & $sVer) Exit EndIf Global Const $hGUI = GUICreate("Low-Polygon Maker v0.71", 252, 906, @DesktopWidth - 260, 10, -1, BitOR($WS_EX_ACCEPTFILES, $WS_EX_TOPMOST)) GUISetFont(8, 400, 0, "Consolas") GUISetBkColor(0xABCDEF, $hGUI) Global $iInp_x = 96, $iInp_w = 100, $y = 60, $y2 = 92, $p Global Const $iLbl_Title = GUICtrlCreateLabel("Low-Polygon Maker", 0, 8, 238, 32, $SS_CENTER) GUICtrlSetFont(-1, 18, 400, 0, "Consolas") Global Const $iLbl_EdgeDetection = GUICtrlCreateLabel("Edge Detection", 4, $y, 88, 17) GUICtrlSetFont(-1, 8.5, 400, 0, "Consolas") Global Const $iCombo_EdgeDetection = GUICtrlCreateCombo("", 96, $y - 4, 145, 25, BitOR($CBS_DROPDOWNLIST, $CBS_AUTOHSCROLL)) GUICtrlSetFont(-1, 10, 400, 0, "Consolas") GUICtrlSetData($iCombo_EdgeDetection, "SOBEL|" & _ "SCHARR|" & _ "PREWITT|" & _ "SOVELVSPREWITT|" & _ "FREI_CHEN|" & _ "ROBINSON_COMPASS|" & _ "KAYYALI|" & _ "ROBERTS_CROSS|" & _ "RIDGE_DETECTION|" & _ "DIAGONAL_EDGES|" & _ "OUTLINE3X3|" & _ "LAPLACE3x3_1|" & _ "LAPLACE3x3_2|" & _ "LAPLACE5x5|" & _ "EDGE_DETECTION1|" & _ "EDGE_DETECTION2|" & _ "EDGE_DETECTION3|" & _ "EDGE_DETECTION4|" & _ "EDGE_DETECTION5|" & _ "EDGE_DETECTION6|" & _ "EMBOSS1|" & _ "EMBOSS2|" & _ "EMBOSS3|" & _ "EMBOSS4|" & _ "KIRSCH|" & _ "ISOTROPIC_SOBEL", _ "ROBERTS_CROSS") $y += 36 Global $aRet = _GDIPlus_BitmapCreateVerticalText("Coded by UEZ 2026", 21.75, "Consolas", 0x380000FF, 0x28000000, 2, 1) Global Const $iPic_Label = GUICtrlCreatePic("", 204, $y - 4, $aRet[1], $aRet[2]) _WinAPI_DeleteObject(GUICtrlSendMsg($iPic_Label, $STM_SETIMAGE, $IMAGE_BITMAP, $aRet[0])) Global Const $iLbl_Threshold = GUICtrlCreateLabel("ED Threshold", 4, $y, 76, 17) GUICtrlSetFont(-1, 8.5, 400, 0, "Consolas") Global Const $iInp_Threshold = GUICtrlCreateInput(1.2, $iInp_x, $y2, $iInp_w, 21) GUICtrlSetFont(-1, 10, 400, 0, "Consolas") GUICtrlSetTip(-1, "The lower the value, the larger the triangles.") Global Const $iLbl_Blur = GUICtrlCreateLabel("Blur Level", 4, $y + 1 * 32, 64, 17) GUICtrlSetFont(-1, 8.5, 400, 0, "Consolas") Global Const $iInp_Blur = GUICtrlCreateInput(1, $iInp_x, $y2 + 1 * 32, $iInp_w, 21, BitOR($GUI_SS_DEFAULT_INPUT, $ES_NUMBER)) GUICtrlSetFont(-1, 10, 400, 0, "Consolas") Global Const $iLbl_Colors = GUICtrlCreateLabel("Max. Colors", 4, $y + 2 * 32, 70, 17) GUICtrlSetFont(-1, 8.5, 400, 0, "Consolas") Global Const $iInp_Colors = GUICtrlCreateInput(256, $iInp_x, $y2 + 2 * 32, $iInp_w, 21, BitOR($GUI_SS_DEFAULT_INPUT, $ES_NUMBER)) GUICtrlSetFont(-1, 10, 400, 0, "Consolas") GUICtrlSetTip(-1, "Valid values are: 2, 16, 256") Global Const $iLbl_MinSpace = GUICtrlCreateLabel("Min Space", 4, $y + 3 * 32, 58, 17) GUICtrlSetFont(-1, 8.5, 400, 0, "Consolas") Global Const $iInp_MinSpace = GUICtrlCreateInput(8, $iInp_x, $y2 + 3 * 32, $iInp_w, 21, BitOR($GUI_SS_DEFAULT_INPUT, $ES_NUMBER)) GUICtrlSetFont(-1, 10, 400, 0, "Consolas") Global Const $iLbl_MaxSpace = GUICtrlCreateLabel("Max Space", 4, $y + 4 * 32, 58, 17) GUICtrlSetFont(-1, 8.5, 400, 0, "Consolas") Global Const $iInp_MaxSpace = GUICtrlCreateInput(45, $iInp_x, $y2 + 4 * 32, $iInp_w, 21, BitOR($GUI_SS_DEFAULT_INPUT, $ES_NUMBER)) GUICtrlSetFont(-1, 10, 400, 0, "Consolas") Global Const $iLbl_BorderSpaceX = GUICtrlCreateLabel("Border Space X", 4, $y + 5 * 32, 88, 17) GUICtrlSetFont(-1, 8.5, 400, 0, "Consolas") Global Const $iInp_BorderSpaceX = GUICtrlCreateInput(8, $iInp_x, $y2 + 5 * 32, $iInp_w, 21, BitOR($GUI_SS_DEFAULT_INPUT, $ES_NUMBER)) GUICtrlSetFont(-1, 10, 400, 0, "Consolas") Global Const $iLbl_BorderSpaceY = GUICtrlCreateLabel("Border Space Y", 4, $y + 6 * 32, 88, 17) GUICtrlSetFont(-1, 8.5, 400, 0, "Consolas") Global Const $iInp_BorderSpaceY = GUICtrlCreateInput(8, $iInp_x, $y2 + 6 * 32, $iInp_w, 21, BitOR($GUI_SS_DEFAULT_INPUT, $ES_NUMBER)) GUICtrlSetFont(-1, 10, 400, 0, "Consolas") Global Const $iLbl_Alpha = GUICtrlCreateLabel("Edges Alpha", 4, $y + 7 * 32, 70, 17) GUICtrlSetFont(-1, 8.5, 400, 0, "Consolas") Global Const $iInp_Alpha = GUICtrlCreateInput(24, $iInp_x, $y2 + 7 * 32, $iInp_w, 21, BitOR($GUI_SS_DEFAULT_INPUT, $ES_NUMBER)) GUICtrlSetFont(-1, 10, 400, 0, "Consolas") Global Const $iLbl_PosterizeLvl = GUICtrlCreateLabel("Posterize Lvl", 4, $y + 8 * 32, 85, 17) GUICtrlSetFont(-1, 8.5, 400, 0, "Consolas") Global Const $iInp_PosterizeLvl = GUICtrlCreateInput(10, $iInp_x, $y2 + 8 * 32, $iInp_w, 21, BitOR($GUI_SS_DEFAULT_INPUT, $ES_NUMBER)) GUICtrlSetFont(-1, 10, 400, 0, "Consolas") GUICtrlSetTip(-1, "When the posterization level is set, the value for 'Max. Colors' input is ignored.") Global Const $iLbl_Denoise = GUICtrlCreateLabel("Denoise Lvl", 4, $y + 9 * 32, 85, 17) GUICtrlSetFont(-1, 8.5, 400, 0, "Consolas") Global Const $iInp_DenoiseLvl = GUICtrlCreateInput(1, $iInp_x, $y2 + 9 * 32, $iInp_w, 21, BitOR($GUI_SS_DEFAULT_INPUT, $ES_NUMBER)) GUICtrlSetFont(-1, 10, 400, 0, "Consolas") GUICtrlSetTip(-1, "The higher the value, the slower the operation.") Global Const $iLbl_EdgePoints = GUICtrlCreateLabel("Edge Points", 4, $y + 10 * 32, 85, 17) GUICtrlSetFont(-1, 8.5, 400, 0, "Consolas") Global Const $iInp_EdgePoints = GUICtrlCreateInput(16, $iInp_x, $y2 + 10 * 32, $iInp_w, 21, BitOR($GUI_SS_DEFAULT_INPUT, $ES_NUMBER)) GUICtrlSetFont(-1, 10, 400, 0, "Consolas") GUICtrlSetTip(-1, "The lower the value, the more triangles.") Global Const $iLbl_CartoonRadius = GUICtrlCreateLabel("Cartoon Radius", 4, $y + 11 * 32, 85, 17) GUICtrlSetFont(-1, 8.5, 400, 0, "Consolas") Global Const $iInp_CartoonRadius = GUICtrlCreateInput(7, $iInp_x, $y2 + 11 * 32, $iInp_w, 21, BitOR($GUI_SS_DEFAULT_INPUT, $ES_NUMBER)) GUICtrlSetFont(-1, 10, 400, 0, "Consolas") GUICtrlSetTip(-1, "The higher the value, the slower the operation.") Global Const $iLbl_CartoonIntens = GUICtrlCreateLabel("Cartoon Intens", 4, $y + 12 * 32, 85, 17) GUICtrlSetFont(-1, 8.5, 400, 0, "Consolas") Global Const $iInp_CartoonIntens = GUICtrlCreateInput(150.00, $iInp_x, $y2 + 12 * 32, $iInp_w, 21) GUICtrlSetFont(-1, 10, 400, 0, "Consolas") $y2 += 102 $p = 10 Global Const $iChkB_ShowEdges = GUICtrlCreateCheckbox("Show Edges", 4, $y2 + $p * 32, 233, 17) GUICtrlSetFont(-1, 8.5, 400, 0, "Consolas") GUICtrlSetState(-1, $GUI_CHECKED) $p += 1 Global Const $iChkB_Wireframe = GUICtrlCreateCheckbox("Show Wireframes only", 4, $y2 + $p * 32, 233, 17) GUICtrlSetFont(-1, 8.5, 400, 0, "Consolas") $p += 1 Global Const $iChkB_GIFAnim = GUICtrlCreateCheckbox("Convert all GIF frames", 4, $y2 + $p * 32, 233, 17) GUICtrlSetFont(-1, 8.5, 400, 0, "Consolas") $p += 1 Global Const $iChkB_CartoonMode = GUICtrlCreateCheckbox("Enable Cartoon Mode", 4, $y2 + $p * 32, 233, 17) GUICtrlSetFont(-1, 8.5, 400, 0, "Consolas") GUICtrlSetState(-1, $GUI_CHECKED) GUICtrlSetTip(-1, "Very CPU intensive calculation.") $p += 1 Global Const $iChkB_AutoResize = GUICtrlCreateCheckbox("Resize large image to screen size", 4, $y2 + $p * 32, 233, 17) GUICtrlSetFont(-1, 8.5, 400, 0, "Consolas") GUICtrlSetState(-1, $GUI_CHECKED) GUICtrlSetTip(-1, "Large images are scaled to fit the screen size for faster processing, except GIF images.") $p += 1 $y2 += $p * 32 $p = 0 Global Const $iBtn_Apply = GUICtrlCreateButton("&Apply", 8, $y2 + $p * 72, 235, 57, $BS_DEFPUSHBUTTON) GUICtrlSetFont(-1, 12, 400, 0, "Consolas") GUICtrlSetBkColor(-1, 0xCCCCFF) GUICtrlSetState($iBtn_Apply, $GUI_DISABLE) $p += 1 Global Const $iBtn_Load = GUICtrlCreateButton("&Load Image", 8, $y2 + $p * 72, 235, 57) GUICtrlSetFont(-1, 12, 400, 0, "Consolas") GUICtrlSetBkColor(-1, 0xCCCCFF) $p += 1 Global Const $iBtn_Save = GUICtrlCreateButton("&Save Image", 8, $y2 + $p * 72, 235, 57) GUICtrlSetFont(-1, 12, 400, 0, "Consolas") GUICtrlSetBkColor(-1, 0xCCCCFF) GUICtrlSetState($iBtn_Save, $GUI_DISABLE) Global $aParts[1] = [-1] Global Const $hStatusBar = _GUICtrlStatusBar_Create($hGUI, $aParts, "Ready") Local $hFont = _WinAPI_CreateFont(12, 0, 0, 0, $FW_MEDIUM, False, False, False, $DEFAULT_CHARSET, $OUT_DEFAULT_PRECIS, $CLIP_DEFAULT_PRECIS, $DRAFT_QUALITY, 0, "Segoe UI") _WinAPI_SetFont($hStatusBar, $hFont, True) GUISetState(@SW_SHOW) Global $aAccelKeys[4][2] = [["^s", $iBtn_Save], ["^l", $iBtn_Load], ["^a", $iBtn_Apply], ["{ENTER}", $iBtn_Apply]] GUISetAccelerators($aAccelKeys) GUIRegisterMsg($WM_COMMAND, "_WM_COMMAND") GUIRegisterMsg($WM_DROPFILES, "_WM_DROPFILES") Global $aMsg, $hImage, $sImgFile, $hGUI_Display = 0, $hGDI_LowPoly, $sFileLowPoly, $g_iW, $g_iH, $hImgTmp = 0 ConsoleWrite("Screen: " & @DesktopWidth & "x" & @DesktopHeight & @CRLF) Dim $aFrameDelays[1], $aFramesGDI[1], $aFrames_LowPoly[1] Global $iCurrentFrame = 0, $iAnimFrameCount = 0, $bIsGIF, $iPic_LowPoly, $iSeed, $i, $r, $hImage_OrginalSize, $iDummy_Load = GUICtrlCreateDummy() While 1 $aMsg = GUIGetMsg(1) Switch $aMsg[1] Case $hGUI Switch $aMsg[0] Case $GUI_EVENT_CLOSE GUIRegisterMsg($WM_COMMAND, "") GUIRegisterMsg($WM_DROPFILES, "") AdlibUnRegister("PlayGIFAnimPreview") If $hGDI_LowPoly Then $r = MsgBox(BitOR($MB_ICONQUESTION, $MB_YESNO), "Question", "Save image before closing?", 5) If $r = $IDYES Then SaveImage() EndIf GUIDelete($hGUI) If UBound($aFrameDelays) > 1 Then For $i = 0 To UBound($aFramesGDI) - 1 _WinAPI_DeleteObject($aFramesGDI[$i]) Next For $i = 1 To $aFrames_LowPoly[0] _GDIPlus_ImageDispose($aFrames_LowPoly[$i]) Next EndIf If $hImage_OrginalSize Then _GDIPlus_ImageDispose($hImage_OrginalSize) If $hImgTmp Then _GDIPlus_ImageDispose($hImgTmp) _GDIPlus_BitmapApplyFilter_Close() Exit Case $iBtn_Load $sImgFile = FileOpenDialog("Select a GDI+ supported image", "", "Images (*.bmp;*.gif;*.png;*.jpg;*.tif)", $FD_FILEMUSTEXIST, "", $hGUI) If @error Then ContinueLoop If Not FileExists($sImgFile) Then MsgBox($MB_ICONERROR, "Error", $sImgFile & " doesn't exist", 30) ContinueLoop EndIf LoadImage($sImgFile) Case $iBtn_Save If $sImgFile = "" Or ($bIsGIF ? UBound($aFrames_LowPoly) < 2 : $hGDI_LowPoly = 0) Then ContinueLoop SaveImage() Case $iBtn_Apply If $sImgFile = "" Or $hImage = 0 Then ContinueLoop GUICtrlSetState($iBtn_Apply, $GUI_DISABLE) GUICtrlSetState($iBtn_Load, $GUI_DISABLE) GUICtrlSetState($iBtn_Save, $GUI_DISABLE) $iCurrentFrame = 0 EncodeAndDisplay($hImage) GUICtrlSetState($iBtn_Apply, $GUI_ENABLE) GUICtrlSetState($iBtn_Load, $GUI_ENABLE) GUICtrlSetState($iBtn_Save, $GUI_ENABLE) Case $iDummy_Load LoadImage($sImgFile) EndSwitch Case $hGUI_Display Switch $aMsg[0] Case $GUI_EVENT_CLOSE AdlibUnRegister("PlayGIFAnimPreview") GUIDelete($hGUI_Display) $hGUI_Display = 0 EndSwitch EndSwitch WEnd Func Min($a, $b) Return $a < $b ? $a : $b EndFunc ;==>Min Func Max($a, $b) Return $a > $b ? $a : $b EndFunc ;==>Max Func CalcResizeDim(ByRef $iW, ByRef $iH, $fFactor) Local $fScaleX, $fScaleY, $iMode = 0 If $iH > @DesktopHeight And $iW < @DesktopWidth + 1 Then $fScaleY = @DesktopHeight / $iH $iW *= $fScaleY $iH *= $fScaleY $iMode = 1 ElseIf $iH < @DesktopHeight + 1 And $iW > @DesktopWidth Then $fScaleX = @DesktopWidth / $iW $iW *= $fScaleX $iH *= $fScaleX $iMode = 2 ElseIf $iH > @DesktopHeight And $iW > @DesktopWidth Then If $iH > $iW Then $fScaleY = @DesktopHeight / $iH $iH *= $fScaleY $iW *= $fScaleY Else $fScaleX = @DesktopWidth / $iW $iH *= $fScaleX $iW *= $fScaleX EndIf $iMode = 3 EndIf If $iMode Or ($iW = @DesktopWidth Or $iH = @DesktopHeight) Then $iW *= $fFactor $iH *= $fFactor EndIf $iW = Int($iW) $iH = Int($iH) Return $iMode EndFunc Func EncodeAndDisplay($hImage, $ResizeInGUI = True) If $g_iW = 0 Or $g_iH = 0 Or $hImage = 0 Then Return SetError(1, 0, 0) Local $iW = $g_iW, $iH = $g_iH Local $fFactor = 0.925, $iMode = 0 If $ResizeInGUI Then $iMode = CalcResizeDim($iW, $iH, $fFactor) EndIf ConsoleWrite("Original: " & $g_iW & "x" & $g_iH & @CRLF) ConsoleWrite("Display: " & $iW & "x" & $iH & @CRLF) Static $iWp = 0, $iHp = 0 If ($iW <> $iWp Or $iH <> $iHp) Or $hGUI_Display = 0 Then If $hGUI_Display Then GUIDelete($hGUI_Display) $hGUI_Display = GUICreate("", $iW, $iH, -1, -1, $WS_POPUP, $WS_EX_OVERLAPPEDWINDOW) $iPic_LowPoly = GUICtrlCreatePic("", 0, 0, $iW - 1, $iH - 1, -1, $GUI_WS_EX_PARENTDRAG) GUISetState(@SW_SHOWNORMAL, $hGUI_Display) WinActivate($hGUI) EndIf $iWp = $iW $iHp = $iH If $hGDI_LowPoly Then _WinAPI_DeleteObject($hGDI_LowPoly) $hGDI_LowPoly = 0 ;~ ConsoleWrite("Blur level: " & Number(GUICtrlRead($iInp_Blur)) & @CRLF & _ ;~ "Kernel: " & Execute("$" & GUICtrlRead($iCombo_EdgeDetection)) & @CRLF & _ ;~ "Threshold: " & Number(GUICtrlRead($iInp_Threshold), $NUMBER_DOUBLE) & @CRLF & _ ;~ "Amount of Colors: " & Number(GUICtrlRead($iInp_Colors)) & @CRLF & _ ;~ "Min Space: " & Number(GUICtrlRead($iInp_MinSpace)) & @CRLF & _ ;~ "Max Space: " & Number(GUICtrlRead($iInp_MaxSpace)) & @CRLF & _ ;~ "Border Space X: " & Number(GUICtrlRead($iInp_BorderSpaceX)) & @CRLF & _ ;~ "Border Space Y: " & Number(GUICtrlRead($iInp_BorderSpaceY)) & @CRLF & _ ;~ "Show Edges Checked: " & Int(BitAND(GUICtrlRead($iChkB_ShowEdges), $GUI_CHECKED) = $GUI_CHECKED) & @CRLF & _ ;~ "Alpha Value: " & Number(GUICtrlRead($iInp_Alpha)) & @CRLF & _ ;~ "Wireframe Checked: " & Int(BitAND(GUICtrlRead($iChkB_Wireframe), $GUI_CHECKED) = $GUI_CHECKED) & @CRLF & _ ;~ "Posterize level: " & Number(GUICtrlRead($iInp_PosterizeLvl)) & @CRLF & _ ;~ "GIF Mode Checked: " & Int(BitAND(GUICtrlRead($iChkB_GIFAnim), $GUI_CHECKED) = $GUI_CHECKED) & @CRLF & _ ;~ "Posterize Lvl: " & Number(GUICtrlRead($iInp_PosterizeLvl)) & @CRLF & _ ;~ "Denoise Lvl: " & Number(GUICtrlRead($iInp_DenoiseLvl)) & @CRLF & _ ;~ "EdgePoints): " & Number(GUICtrlRead($iInp_EdgePoints)) & @CRLF & _ ;~ "CornerPoints: " & Number(GUICtrlRead($iInp_CornerPoints)) & @CRLF) ;~ ConsoleWrite("-----------------------------------------------------------------------" & @CRLF) AdlibUnRegister("PlayGIFAnimPreview") Local $i Local $iAnimDimCount = _GDIPlus_GIFAnimGetFrameDimensionsCount($hImage) Local $tGUID = _GDIPlus_GIFAnimGetFrameDimensionsList($hImage, $iAnimDimCount) $iAnimFrameCount = _GDIPlus_GIFAnimGetFrameCount($hImage, $tGUID) $aFrameDelays = _GDIPlus_GIFAnimGetFrameDelays($hImage, $iAnimFrameCount) If $iAnimFrameCount Then _GDIPlus_GIFAnimSelectActiveFrame($hImage, $tGUID, 0) _GUICtrlStatusBar_SetText($hStatusBar, "Calculation has started. Please wait...", 0, $SBT_POPOUT) ConsoleWrite("Image processing has started - please wait...") Local Const $fTimer = TimerInit() If Int(BitAND(GUICtrlRead($iChkB_GIFAnim), $GUI_CHECKED) = $GUI_CHECKED) And $bIsGIF And $iAnimFrameCount > 1 Then If UBound($aFramesGDI) > 1 Then For $i = 0 To UBound($aFramesGDI) - 1 _WinAPI_DeleteObject($aFramesGDI[$i]) _GDIPlus_ImageDispose($aFrames_LowPoly[$i + 1]) Next EndIf ReDim $aFramesGDI[$iAnimFrameCount] ReDim $aFrames_LowPoly[$iAnimFrameCount + 1] $aFrames_LowPoly[0] = $iAnimFrameCount For $i = 0 To $iAnimFrameCount - 1 _GDIPlus_GIFAnimSelectActiveFrame($hImage, $tGUID, $i) $aFrames_LowPoly[$i + 1] = _GDIPlus_BitmapApplyFilter_Delaunay3($hImage, _ Number(GUICtrlRead($iInp_Blur)), _ Execute("$" & GUICtrlRead($iCombo_EdgeDetection)), _ Number(GUICtrlRead($iInp_Threshold), $NUMBER_DOUBLE), _ Number(GUICtrlRead($iInp_Colors)), _ Number(GUICtrlRead($iInp_MinSpace)), _ Number(GUICtrlRead($iInp_MaxSpace)), _ Number(GUICtrlRead($iInp_BorderSpaceX)), _ Number(GUICtrlRead($iInp_BorderSpaceY)), _ Int(BitAND(GUICtrlRead($iChkB_ShowEdges), $GUI_CHECKED) = $GUI_CHECKED), _ Number(GUICtrlRead($iInp_Alpha)), _ Int(BitAND(GUICtrlRead($iChkB_Wireframe), $GUI_CHECKED) = $GUI_CHECKED), _ Number(GUICtrlRead($iInp_PosterizeLvl)), _ $iSeed, _ 0xFFFFFFFF, _ Number(GUICtrlRead($iInp_DenoiseLvl)), _ Number(GUICtrlRead($iInp_EdgePoints)), _ 50, _ Int(BitAND(GUICtrlRead($iChkB_CartoonMode), $GUI_CHECKED) = $GUI_CHECKED), _ Number(GUICtrlRead($iInp_CartoonRadius)), _ Number(GUICtrlRead($iInp_CartoonIntens), $NUMBER_DOUBLE), _ False) $aFramesGDI[$i] = _GDIPlus_BitmapCreateHBITMAPFromBitmap($aFrames_LowPoly[$i + 1]) _GDIPlus_BitmapConvertTo8Bit($aFrames_LowPoly[$i + 1], 256, $GDIP_DitherTypeNone, $GDIP_PaletteTypeFixedHalftone256) ToolTip($i + 1 & "/" & $iAnimFrameCount & " : " & Round(($i + 1) / UBound($aFrameDelays) * 100, 2) & "%", MouseGetPos(0), MouseGetPos(1) + 30, "", 0, $TIP_CENTER) Next ToolTip("") AdlibRegister("PlayGIFAnimPreview", 10) Else $hGDI_LowPoly = _GDIPlus_BitmapApplyFilter_Delaunay3($hImage, _ Number(GUICtrlRead($iInp_Blur)), _ Execute("$" & GUICtrlRead($iCombo_EdgeDetection)), _ Number(GUICtrlRead($iInp_Threshold), $NUMBER_DOUBLE), _ Number(GUICtrlRead($iInp_Colors)), _ Number(GUICtrlRead($iInp_MinSpace)), _ Number(GUICtrlRead($iInp_MaxSpace)), _ Number(GUICtrlRead($iInp_BorderSpaceX)), _ Number(GUICtrlRead($iInp_BorderSpaceY)), _ Int(BitAND(GUICtrlRead($iChkB_ShowEdges), $GUI_CHECKED) = $GUI_CHECKED), _ Number(GUICtrlRead($iInp_Alpha)), _ Int(BitAND(GUICtrlRead($iChkB_Wireframe), $GUI_CHECKED) = $GUI_CHECKED), _ Number(GUICtrlRead($iInp_PosterizeLvl)), _ $iSeed, _ 0, _ Number(GUICtrlRead($iInp_DenoiseLvl)), _ Number(GUICtrlRead($iInp_EdgePoints)), _ 50, _ Int(BitAND(GUICtrlRead($iChkB_CartoonMode), $GUI_CHECKED) = $GUI_CHECKED), _ Number(GUICtrlRead($iInp_CartoonRadius)), _ Number(GUICtrlRead($iInp_CartoonIntens), $NUMBER_DOUBLE), _ True) If $hGDI_LowPoly = 0 Then GUIDelete($hGUI_Display) $hGUI_Display = 0 Return SetError(1, 0, 0) EndIf If $iMode Then ResizeImage($hGDI_LowPoly, $iW, $iH) Local $hHBmp = GUICtrlSendMsg($iPic_LowPoly, $STM_SETIMAGE, $IMAGE_BITMAP, $hGDI_LowPoly) If $hHBmp Then _WinAPI_DeleteObject($hHBmp) EndIf Local $fEnd = Round(TimerDiff($fTimer), 2) ConsoleWrite($fEnd & " ms." & @CRLF & @CRLF) _GUICtrlStatusBar_SetText($hStatusBar, "Generated in: " & $fEnd & " ms. Dimension: " & _GDIPlus_ImageGetWidth($hImage) & "x" & _GDIPlus_ImageGetHeight($hImage), 0, $SBT_POPOUT) _WinAPI_InvalidateRect($hGUI_Display) _WinAPI_RedrawWindow($hGUI_Display) EndFunc ;==>EncodeAndDisplay Func PlayGIFAnimPreview() AdlibUnRegister("PlayGIFAnimPreview") Local $iDelay = $aFrameDelays[$iCurrentFrame] Local Static $iTimerCurrentFrame = TimerInit() _WinAPI_DeleteObject(GUICtrlSendMsg($iPic_LowPoly, 0x0172, 0, $aFramesGDI[$iCurrentFrame])) ;$STM_SETIMAGE = 0x0172, $IMAGE_BITMAP = 0 If TimerDiff($iTimerCurrentFrame) > $iDelay Then $iCurrentFrame += 1 $iTimerCurrentFrame = TimerInit() EndIf If $iCurrentFrame > UBound($aFrameDelays) - 1 Then $iCurrentFrame = 0 AdlibRegister("PlayGIFAnimPreview", 10) EndFunc ;==>PlayGIFAnimPreview Func ResizeImage(ByRef $hBitmapGDI, $newW, $newH) Local $hImageCopy = _GDIPlus_BitmapCreateFromHBITMAP($hBitmapGDI) If $hImage_OrginalSize Then _GDIPlus_ImageDispose($hImage_OrginalSize) $hImage_OrginalSize = _GDIPlus_BitmapCloneArea($hImageCopy, 0, 0, $g_iW, $g_iH, $GDIP_PXF32ARGB) ;save original size of low-polygon image to save original size Local $hImageResized = _GDIPlus_ImageResize($hImageCopy, $newW, $newH) _WinAPI_DeleteObject($hBitmapGDI) $hBitmapGDI = _GDIPlus_BitmapCreateHBITMAPFromBitmap($hImageResized, 0) _GDIPlus_ImageDispose($hImageResized) EndFunc ;==>ResizeImage Func LoadImage($sImgFile) If $hImage Then _GDIPlus_ImageDispose($hImage) $hImage = _GDIPlus_ImageLoadFromFile($sImgFile) If Not $hImage Then MsgBox($MB_ICONERROR, "Error", "Unable to load file to GDI+", 30) Return 0 EndIf $g_iW = _GDIPlus_ImageGetWidth($hImage) $g_iH = _GDIPlus_ImageGetHeight($hImage) $bIsGIF = False If StringRight($sImgFile, 4) = ".gif" Then $bIsGIF = True If $bIsGIF = False And Int(BitAND(GUICtrlRead($iChkB_AutoResize), $GUI_CHECKED) = $GUI_CHECKED) Then Local $iWt = $g_iW, $iHt = $g_iH, $iMode CalcResizeDim($iWt, $iHt, 1) If $iWt < $g_iW Or $iHt < $g_iH Then $hImgTmp = _GDIPlus_ImageResize($hImage, $iWt, $iHt) _GDIPlus_ImageDispose($hImage) $hImage = $hImgTmp ConsoleWrite("Original image " & $g_iW & "x" & $g_iH & " resized to " & $iWt & "x" & $iHt & @CRLF) $g_iW = _GDIPlus_ImageGetWidth($hImage) $g_iH = _GDIPlus_ImageGetHeight($hImage) EndIf EndIf $iSeed = Int(Random() * 0xFFFFFF) $iCurrentFrame = 0 $iAnimFrameCount = 0 Local $iMax = Int(Max($g_iW, $g_iH) / 192) If $iMax > 1 Then GUICtrlSetData($iInp_MinSpace, $iMax) GUICtrlSetData($iInp_MaxSpace, Ceiling($iMax * 4.5)) EndIf If $hImage Then GUICtrlSetState($iBtn_Apply, $GUI_ENABLE) GUICtrlSetState($iBtn_Save, $GUI_ENABLE) EndIf GUICtrlSetData($iInp_BorderSpaceX, Int($g_iW / 16)) GUICtrlSetData($iInp_BorderSpaceY, Int($g_iH / 16)) EncodeAndDisplay($hImage) EndFunc Func SaveImage() $sFileLowPoly = FileSaveDialog("Save Low-Polygone Image", "", "Images (*.bmp;*.gif;*.png;*.jpg;*.jpeg;*.tif;*.tiff)", 0, StringRegExpReplace($sImgFile, "^.*\\([^\\]+)(\.[^.]+)$", "\1_Low-Polygon\2"), $hGUI) If @error Or $sFileLowPoly = "" Then Return 0 If FileExists($sFileLowPoly) Then Local $r = MsgBox(BitOR($MB_ICONQUESTION, $MB_YESNO), "Question", "File already exists - overwwrite?", 5) If $r <> $IDYES Then Return MsgBox($MB_ICONINFORMATION, "Information", "Save aborted!", 15, $hGUI) EndIf EndIf If ((UBound($aFrames_LowPoly) > 1 And $bIsGIF) ? _ _GDIPlus_GIFAnimCreateFile2($aFrames_LowPoly, $sFileLowPoly, $aFrameDelays) _ : _ ($hImage_OrginalSize ? _GDIPlus_ImageSaveToFile($hImage_OrginalSize, $sFileLowPoly) _ : _ScreenCapture_SaveImage($sFileLowPoly, $hGDI_LowPoly, False))) Then MsgBox($MB_ICONINFORMATION, "Information", "Low-Poly image saved.", 15, $hGUI) Else MsgBox($MB_ICONERROR, "Error", "Low-Poly image could not be save!", 15, $hGUI) EndIf EndFunc ;==>SaveImage Func _WM_COMMAND($hWnd, $Msg, $wParam, $lParam) Local $iNotifyCode = BitShift($wParam, 16) Local $iCtrlID = BitAND($wParam, 0x0000FFFF) Local $var If $iNotifyCode = $EN_KILLFOCUS Then Switch $iCtrlID Case $iInp_Blur $val = GUICtrlRead($iInp_Blur) If $val = "" Then $val = 5 $val = Number($val) If $val < 0 Then $val = 0 If $val > 127 Then $val = 127 GUICtrlSetData($iInp_Blur, $val) Case $iInp_Threshold $val = GUICtrlRead($iInp_Threshold) If $val = "" Then $val = 0.35 $val = Number($val) If $val < 0 Then $val = 0 If $val > 10 Then $val = 10 GUICtrlSetData($iInp_Threshold, StringFormat("%.2f", $val)) Case $iInp_Colors $val = GUICtrlRead($iInp_Colors) If $val = "" Then $val = 32 $val = Number($val) If $val < 2 Then $val = 2 If $val > 255 Then $val = 255 GUICtrlSetData($iInp_Colors, $val) Case $iInp_MinSpace $val = GUICtrlRead($iInp_MinSpace) If $val = "" Then $val = 1 $val = Number($val) If $val < 1 Then $val = 1 GUICtrlSetData($iInp_MinSpace, $val) Case $iInp_MaxSpace $val = GUICtrlRead($iInp_MaxSpace) If $val = "" Then $val = 8 $val = Number($val) If $val < 1 Then $val = 2 GUICtrlSetData($iInp_MaxSpace, $val) Case $iInp_BorderSpaceX, $iInp_BorderSpaceY $val = GUICtrlRead($iCtrlID) If $val = "" Then $val = 2 $val = Number($val) If $val < 1 Then $val = 1 If $val > 4096 Then $val = 4096 GUICtrlSetData($iCtrlID, $val) Case $iInp_Alpha $val = GUICtrlRead($iInp_Alpha) If $val = "" Then $val = 32 $val = Number($val) If $val < 0 Then $val = 0 If $val > 255 Then $val = 255 GUICtrlSetData($iInp_Alpha, $val) Case $iInp_PosterizeLvl $val = GUICtrlRead($iInp_PosterizeLvl) If $val = "" Then $val = 8 $val = Number($val) If $val < 0 Then $val = 0 If $val > 255 Then $val = 255 GUICtrlSetData($iInp_PosterizeLvl, $val) Case $iInp_DenoiseLvl $val = GUICtrlRead($iInp_DenoiseLvl) If $val = "" Then $val = 0 $val = Number($val) If $val < 0 Then $val = 0 If $val > 255 Then $val = 255 GUICtrlSetData($iInp_DenoiseLvl, $val) Case $iInp_EdgePoints $val = GUICtrlRead($iInp_EdgePoints) If $val = "" Then $val = 30 $val = Number($val) If $val < 0 Then $val = 0 If $val > 255 Then $val = 255 GUICtrlSetData($iInp_EdgePoints, $val) Case $iInp_CartoonRadius $val = GUICtrlRead($iInp_CartoonRadius) If $val = "" Then $val = 8 $val = Number($val) If $val < 0 Then $val = 0 If $val > 255 Then $val = 255 GUICtrlSetData($iInp_CartoonRadius, $val) Case $iInp_CartoonIntens $val = GUICtrlRead($iInp_CartoonIntens) If $val = "" Then $val = 20 $val = Number($val) If $val < 0 Then $val = 0 If $val > 255 Then $val = 255 GUICtrlSetData($iInp_CartoonIntens, StringFormat("%.2f", $val)) EndSwitch EndIf Return $GUI_RUNDEFMSG EndFunc ;==>_WM_COMMAND Func _WM_DROPFILES($hWnd, $iMsg, $wParam, $lParam) Local $i = 1 Local $aFileList = _WinAPI_DragQueryFileEx($wParam) Do If StringInStr(FileGetAttrib($aFileList[$i]), "D") Then _ArrayDelete($aFileList, $i) Else $i += 1 EndIf Until $i = UBound($aFileList) $aFileList[0] = UBound($aFileList) - 1 $sImgFile = $aFileList[1] _WinAPI_DragFinish($wParam) GUICtrlSendToDummy($iDummy_Load) Return 0 EndFunc ;==>WM_DROPFILES# Func _GDIPlus_BitmapCreateVerticalText($sString, $fFontSize = 10, $sFont = "Arial", $iColor_Text = 0xFF000000, $iTxtBorderColor = 0x80808080, $iTxtBorderSize = 1, $iFlip = 3) $iFlip = ($iFlip <> 3 And $iFlip <> 1) ? 3 : $iFlip Local Const $hDC = _WinAPI_GetWindowDC(0) Local Const $hGraphic = _GDIPlus_GraphicsCreateFromHDC($hDC) Local Const $hBrush = _GDIPlus_BrushCreateSolid($iColor_Text), $hPen = _GDIPlus_PenCreate($iTxtBorderColor, $iTxtBorderSize) Local Const $hFormat = _GDIPlus_StringFormatCreate() Local Const $hFamily = _GDIPlus_FontFamilyCreate($sFont) Local Const $hFont = _GDIPlus_FontCreate($hFamily, $fFontSize) Local Const $hPath = _GDIPlus_PathCreate() Local $tLayout = _GDIPlus_RectFCreate() Local $iError = 1 Local Const $aInfo = _GDIPlus_GraphicsMeasureString($hGraphic, $sString, $hFont, $tLayout, $hFormat) If Not @error Then Local Const $iW = Ceiling($aInfo[0].Width), $iH = Ceiling($aInfo[0].Height) Local Const $hBitmap = _GDIPlus_BitmapCreateFromScan0($iW, $iH), $hCanvas = _GDIPlus_ImageGetGraphicsContext($hBitmap) _GDIPlus_GraphicsSetSmoothingMode($hCanvas, $GDIP_SMOOTHINGMODE_HIGHQUALITY) _GDIPlus_GraphicsSetTextRenderingHint($hCanvas, $GDIP_TEXTRENDERINGHINTANTIALIASGRIDFIT) $tLayout.X = 0 $tLayout.Y = 0 $tLayout.Width = $iW $tLayout.Height = $iH _GDIPlus_PathAddString($hPath, $sString, $tLayout, $hFamily, 0, $fFontSize, $hFormat) ;~ _GDIPlus_GraphicsDrawStringEx($hCanvas, $sString, $hFont, $tLayout, $hFormat, $hBrush) _GDIPlus_GraphicsFillPath($hCanvas, $hPath, $hBrush) _GDIPlus_GraphicsDrawPath($hCanvas, $hPath, $hPen) _GDIPlus_ImageRotateFlip($hBitmap, $iFlip) Local Const $hBitmap_GDI = _GDIPlus_BitmapCreateHBITMAPFromBitmap($hBitmap) _GDIPlus_GraphicsDispose($hCanvas) _GDIPlus_BitmapDispose($hBitmap) $iError = 0 EndIf _GDIPlus_PathDispose($hPath) _GDIPlus_FontDispose($hFont) _GDIPlus_FontFamilyDispose($hFamily) _GDIPlus_StringFormatDispose($hFormat) _GDIPlus_BrushDispose($hBrush) _GDIPlus_PenDispose($hPen) _GDIPlus_GraphicsDispose($hGraphic) _WinAPI_ReleaseDC(0, $hDC) If $iError Then Return SetError(1, 0, 0) Local $aResult[3] = [$hBitmap_GDI, $iH, $iW] Return $aResult EndFunc ;==>_GDIPlus_BitmapCreateVerticalText Func CheckVer($sVerInstalled, $sVerRequired) Local $aInst = StringSplit($sVerInstalled, ".") Local $aReq = StringSplit($sVerRequired, ".") Local $iInst, $iReq For $i = 1 To $aReq[0] $iInst = ($i <= $aInst[0]) ? Int($aInst[$i]) : 0 $iReq = Int($aReq[$i]) If $iInst > $iReq Then Return True If $iInst < $iReq Then Return False Next Return True EndFunc ;==>CheckVer #Region GIF ;_GDIPlus_GIFAnim* function taken from _GDIPlus_GIFAnim UDF Func _GDIPlus_GIFAnimGetFrameDimensionsCount($hImage) Local Const $aResult = DllCall($__g_hGDIPDll, "int", "GdipImageGetFrameDimensionsCount", "handle", $hImage, "ulong*", 0) If @error Then Return SetError(@error, @extended, 0) If $aResult[0] Then Return SetError(10, $aResult[0], 0) Return $aResult[2] EndFunc ;==>_GDIPlus_GIFAnimGetFrameDimensionsCount Func _GDIPlus_GIFAnimGetFrameDimensionsList($hImage, $iFramesCount) Local Const $tGUID = DllStructCreate($tagGUID) Local Const $aResult = DllCall($__g_hGDIPDll, "int", "GdipImageGetFrameDimensionsList", "handle", $hImage, "struct*", $tGUID, "uint", $iFramesCount) If @error Then Return SetError(@error, @extended, 0) If $aResult[0] Then Return SetError(10, $aResult[0], 0) Return $tGUID EndFunc ;==>_GDIPlus_GIFAnimGetFrameDimensionsList Func _GDIPlus_GIFAnimGetFrameCount($hImage, $tGUID) Local Const $aResult = DllCall($__g_hGDIPDll, "int", "GdipImageGetFrameCount", "handle", $hImage, "struct*", $tGUID, "ptr*", 0) If @error Then Return SetError(@error, @extended, 0) If $aResult[0] Then Return SetError(10, $aResult[0], 0) Return Int($aResult[3]) EndFunc ;==>_GDIPlus_GIFAnimGetFrameCount Func _GDIPlus_GIFAnimSelectActiveFrame($hImage, $tGUID, $iCurrentFrame) Local Const $aResult = DllCall($__g_hGDIPDll, "int", "GdipImageSelectActiveFrame", "handle", $hImage, "struct*", $tGUID, "uint", $iCurrentFrame) If @error Then Return SetError(@error, @extended, 0) If $aResult[0] Then Return SetError(10, $aResult[0], 0) Return True EndFunc ;==>_GDIPlus_GIFAnimSelectActiveFrame Func _GDIPlus_GIFAnimGetFrameDelays($hImage, $iAnimFrameCount) If $iAnimFrameCount < 2 Then Return SetError(1, 0, 0) Local Const $GDIP_PROPERTYTAGFRAMEDELAY = 0x5100 Local $tPropItem = __GDIPlus_ImageGetPropertyItem($hImage, $GDIP_PROPERTYTAGFRAMEDELAY) If IsDllStruct($tPropItem) And (Not @error) Then Local $iType = $tPropItem.type, $iLength, $tVal If $iType Then $iLength = $tPropItem.length Switch $iType Case 1 $tVal = DllStructCreate("byte delay[" & $iLength & "]", $tPropItem.value) Case 3 $tVal = DllStructCreate("short delay[" & Ceiling($iLength / 2) & "]", $tPropItem.value) Case 4 $tVal = DllStructCreate("long delay[" & Ceiling($iLength / 4) & "]", $tPropItem.value) Case Else Return SetError(3, 0, 0) EndSwitch Local $aFrameDelays[Int($iAnimFrameCount)], $i For $i = 0 To UBound($aFrameDelays) - 1 $aFrameDelays[$i] = $tVal.delay(($i + 1)) * 10 Next EndIf Return $aFrameDelays EndIf Return SetError(2, 0, 0) EndFunc ;==>_GDIPlus_GIFAnimGetFrameDelays Func __GDIPlus_ImageGetPropertyItem($hImage, $iPropID) Local $aResult = DllCall($__g_hGDIPDll, "int", "GdipGetPropertyItemSize", "handle", $hImage, "uint", $iPropID, "ulong*", 0) If @error Then Return SetError(@error, @extended, 0) If $aResult[0] Then Return SetError(10, $aResult[0], 0) Local Static $tBuffer $tBuffer = DllStructCreate("byte[" & $aResult[3] & "]") $aResult = DllCall($__g_hGDIPDll, "int", "GdipGetPropertyItem", "handle", $hImage, "uint", $iPropID, "ulong", $aResult[3], "struct*", $tBuffer) If @error Then Return SetError(@error, @extended, 0) If $aResult[0] Then Return SetError(11, $aResult[0], 0) Local Const $tagGDIPPROPERTYITEM = "uint id;ulong length;word type;ptr value" Local $tPropertyItem = DllStructCreate($tagGDIPPROPERTYITEM, DllStructGetPtr($tBuffer)) If @error Then Return SetError(20, $aResult[0], 0) Return $tPropertyItem EndFunc ;==>__GDIPlus_ImageGetPropertyItem Func _GDIPlus_GIFAnimCreateFile2($aImages, $sFilename, $aDelays = 100, $bReplay = True) Local Const $GDIP_EVTFrameDimensionTime = 21 Local $iMax = $aImages[0] If $iMax < 1 Then Return SetError(1, 0, False) Local Const $sCLSID = _GDIPlus_EncodersGetCLSID("GIF") Local $tMultiFrameParam = DllStructCreate("int type;") $tMultiFrameParam.type = 18 Local $tParams = _GDIPlus_ParamInit(1) _GDIPlus_ParamAdd($tParams, $GDIP_EPGSAVEFLAG, 1, 4, DllStructGetPtr($tMultiFrameParam)) Local Const $hStream = _WinAPI_CreateStreamOnHGlobal() Local $tGUID = _WinAPI_GUIDFromString($sCLSID) _GDIPlus_ImageSaveToStream($aImages[1], $hStream, DllStructGetPtr($tGUID), DllStructGetPtr($tParams)) If $iMax > 1 Then $tMultiFrameParam.type = $GDIP_EVTFrameDimensionTime $tParams = _GDIPlus_ParamInit(1) _GDIPlus_ParamAdd($tParams, $GDIP_EPGSAVEFLAG, 1, 4, DllStructGetPtr($tMultiFrameParam)) For $i = 2 To $iMax _GDIPlus_ImageSaveAddImage($aImages[1], $aImages[$i], $tParams) Next $tMultiFrameParam.type = 19 $tParams = _GDIPlus_ParamInit(1) _GDIPlus_ParamAdd($tParams, $GDIP_EPGSAVEFLAG, 1, 4, DllStructGetPtr($tMultiFrameParam)) _GDIPlus_ImageSaveAdd($aImages[1], $tParams) EndIf $tMultiFrameParam.type = 20 $tParams = _GDIPlus_ParamInit(1) _GDIPlus_ParamAdd($tParams, $GDIP_EPGSAVEFLAG, 1, 4, DllStructGetPtr($tMultiFrameParam)) _GDIPlus_ImageSaveAdd($aImages[1], $tParams) Local Const $hMemory = _WinAPI_GetHGlobalFromStream($hStream) Local Const $iMemSize = _MemGlobalSize($hMemory) Local Const $pMem = _MemGlobalLock($hMemory) Local Const $iNewSize = $bReplay ? ($iMemSize + 19) : $iMemSize Local Const $hNewMem = _MemGlobalAlloc($iNewSize, 0x0002) Local Const $pNewMem = _MemGlobalLock($hNewMem) Local $tNewData = DllStructCreate("byte mem[" & $iNewSize & "]", $pNewMem) Local Const $hDLL_msvcrt = DllOpen("msvcrt.dll") Local $iCopyOffset = 0 If $bReplay Then Local $tNetscape = DllStructCreate("byte mem[19]") $tNetscape.mem = Binary("0x21FF0B4E45545343415045322E300301000000") Local $aResult = DllCall($hDLL_msvcrt, "ptr:cdecl", "memchr", "ptr", $pMem, "int", 0x21, "ulong_ptr", $iMemSize) If @error Or Not IsArray($aResult) Then _MemGlobalUnlock($hMemory) _MemGlobalUnlock($hNewMem) _MemGlobalFree($hNewMem) _WinAPI_ReleaseStream($hStream) DllClose($hDLL_msvcrt) Return SetError(3, 0, False) EndIf Local $pFound = $aResult[0], $tCheck, $iInsertPos While $pFound <> 0 $tCheck = DllStructCreate("byte mem[3]", $pFound) If $tCheck.mem(1) = 0x21 And $tCheck.mem(2) = 0xF9 And $tCheck.mem(3) = 0x04 Then $iInsertPos = $pFound - $pMem DllCall($hDLL_msvcrt, "ptr:cdecl", "memcpy", "ptr", $pNewMem, "ptr", $pMem, "ulong_ptr", $iInsertPos) DllCall($hDLL_msvcrt, "ptr:cdecl", "memcpy", "ptr", $pNewMem + $iInsertPos, "struct*", $tNetscape, "ulong_ptr", 19) DllCall($hDLL_msvcrt, "ptr:cdecl", "memcpy", "ptr", $pNewMem + $iInsertPos + 19, "ptr", $pMem + $iInsertPos, "ulong_ptr", $iMemSize - $iInsertPos) $iCopyOffset = 19 ExitLoop EndIf $aResult = DllCall($hDLL_msvcrt, "ptr:cdecl", "memchr", "ptr", $pFound + 1, "int", 0x21, "ulong_ptr", $iMemSize - ($pFound - $pMem) - 1) $pFound = $aResult[0] WEnd Else DllCall($hDLL_msvcrt, "ptr:cdecl", "memcpy", "ptr", $pNewMem, "ptr", $pMem, "ulong_ptr", $iMemSize) EndIf _MemGlobalUnlock($hMemory) _WinAPI_ReleaseStream($hStream) _MemGlobalFree($hMemory) Local $pSearch = $pNewMem Local $iRemainingByte = $iNewSize Local $iFrameCount = 0, $iDelay, $aResult, $pFound, $tCheck, $isArray = IsArray($aDelays) While $iFrameCount < $iMax And $iRemainingByte > 6 $aResult = DllCall($hDLL_msvcrt, "ptr:cdecl", "memchr", "ptr", $pSearch, "int", 0x21, "ulong_ptr", $iRemainingByte) If $aResult[0] = 0 Then ExitLoop $pFound = $aResult[0] $tCheck = DllStructCreate("byte mem[6]", $pFound) If $tCheck.mem(2) = 0xF9 And $tCheck.mem(3) = 0x04 Then $iDelay = $isArray ? $aDelays[$iFrameCount] : $aDelays $iDelay = Int($iDelay / 10) $tCheck.mem(5) = BitAND($iDelay, 0xFF) $tCheck.mem(6) = BitShift($iDelay, 8) $iFrameCount += 1 $pSearch = $pFound + 8 Else $pSearch = $pFound + 1 EndIf $iRemainingByte = $iNewSize - ($pSearch - $pNewMem) WEnd DllClose($hDLL_msvcrt) Local $hFile = FileOpen($sFilename, BitOR(16, 2)) If $hFile = -1 Then _MemGlobalUnlock($hNewMem) _MemGlobalFree($hNewMem) Return SetError(2, 0, False) EndIf FileWrite($hFile, $tNewData.mem) FileClose($hFile) _MemGlobalUnlock($hNewMem) _MemGlobalFree($hNewMem) Return True EndFunc ;==>_GDIPlus_GIFAnimCreateFile2 Func _GDIPlus_BitmapConvertTo8Bit(ByRef $hBitmap, $iColorCount = 256, $iDitherType = 9, $iPaletteType = 8, $bUseTransparentColor = True) $iColorCount = ($iColorCount > 2 ^ 8) ? 2 ^ 8 : $iColorCount Local $tPalette = _GDIPlus_PaletteInitialize(256, $iPaletteType, $iColorCount, $bUseTransparentColor, $hBitmap) If @error Then Return SetError(1, @error, 0) Local $iRet = _GDIPlus_BitmapConvertFormat($hBitmap, 0x00030803, $iDitherType, $iPaletteType, $tPalette) If @error Then Return SetError(2, @error, 0) Return $iRet EndFunc ;==>_GDIPlus_BitmapConvertTo8Bit #EndRegion GIF Examples: The required DLLs (_GDIPlus_BitmapApplyFilter.dll / _GDIPlus_BitmapApplyFilter_x64.dll) and _GDIPlus_BitmapApplyFilter.au3 can be found on my OneDrive: _GDIPlus_BitmapApplyFilter
×
×
  • Create New...