浏览代码

Merge branch 'darker'

Martijn Laan 2 月之前
父节点
当前提交
5f28313043

+ 7 - 2
Components/BrowseFunc.pas

@@ -2,7 +2,7 @@ unit BrowseFunc;
 
 
 {
 {
   Inno Setup
   Inno Setup
-  Copyright (C) 1997-2024 Jordan Russell
+  Copyright (C) 1997-2025 Jordan Russell
   Portions by Martijn Laan
   Portions by Martijn Laan
   For conditions of distribution and use, see LICENSE.TXT.
   For conditions of distribution and use, see LICENSE.TXT.
 
 
@@ -29,7 +29,7 @@ function NewGetSaveFileName(const Prompt: String; var FileName: String;
 implementation
 implementation
 
 
 uses
 uses
-  CommDlg, ShlObj, ActiveX,
+  CommDlg, ShlObj, ActiveX, Themes,
   PathFunc;
   PathFunc;
 
 
 function BrowseCallback(Wnd: HWND; uMsg: UINT; lParam, lpData: LPARAM): Integer; stdcall;
 function BrowseCallback(Wnd: HWND; uMsg: UINT; lParam, lpData: LPARAM): Integer; stdcall;
@@ -167,6 +167,10 @@ begin
 
 
   ActiveWindow := GetActiveWindow;
   ActiveWindow := GetActiveWindow;
   WindowList := DisableTaskWindows(ParentWnd);
   WindowList := DisableTaskWindows(ParentWnd);
+  { Temporarily clear SystemHooks to make it support dark mode if Windows is in dark mode.
+    Taken from Vcl.Dialogs' TCustomFileDialog.Execute. }
+  const SaveHooks = TStyleManager.SystemHooks;
+  TStyleManager.SystemHooks := [];
   try
   try
     asm
     asm
       // Avoid FPU control word change in NETRAP.dll, NETAPI32.dll, etc
       // Avoid FPU control word change in NETRAP.dll, NETAPI32.dll, etc
@@ -194,6 +198,7 @@ begin
       end;
       end;
     end;
     end;
   finally
   finally
+    TStyleManager.SystemHooks := SaveHooks;
     EnableTaskWindows(WindowList);
     EnableTaskWindows(WindowList);
     SetActiveWindow(ActiveWindow);
     SetActiveWindow(ActiveWindow);
   end;
   end;

+ 5 - 2
Components/ModernColors.pas

@@ -2,7 +2,7 @@ unit ModernColors;
 
 
 {
 {
   Inno Setup
   Inno Setup
-  Copyright (C) 1997-2024 Jordan Russell
+  Copyright (C) 1997-2025 Jordan Russell
   Portions by Martijn Laan
   Portions by Martijn Laan
   For conditions of distribution and use, see LICENSE.TXT.
   For conditions of distribution and use, see LICENSE.TXT.
 
 
@@ -43,7 +43,10 @@ const
 
 
   DFore = $D6D6D6;           { VSCode Modern Dark, 2 tints lightened using color-hex.com }
   DFore = $D6D6D6;           { VSCode Modern Dark, 2 tints lightened using color-hex.com }
   DBack = $1F1F1F;           { VSCode Modern Dark }
   DBack = $1F1F1F;           { VSCode Modern Dark }
-  DToolBack = $413E40;       { Monokai Pro }
+  { If you combine this unit with a dark VCL Style then the following color should match the style's
+    window background color. Value can be found using BitmapStyleDesigner.exe from BDS\Bin. Open the
+    style .vsf file, go to the Colors section and then to the Window color. }
+  DToolBack = $2B2B2B;       { VCL Style 'Windows11 Dark 1.0' }
   DSelBack = $764F1D;        { VSCode Modern Dark }
   DSelBack = $764F1D;        { VSCode Modern Dark }
   //DSelInactiveBack = $51504F;{ VSCode Modern Dark }
   //DSelInactiveBack = $51504F;{ VSCode Modern Dark }
   DIntelliBack = $202020;    { VSCode Modern Dark }
   DIntelliBack = $202020;    { VSCode Modern Dark }

+ 61 - 7
Components/NewCheckListBox.pas

@@ -205,7 +205,7 @@ procedure Register;
 implementation
 implementation
 
 
 uses
 uses
-  NewUxTheme.TmSchema, PathFunc, ActiveX, BidiUtils, Types;
+  Themes, NewUxTheme.TmSchema, PathFunc, ActiveX, BidiUtils, UITypes, Types;
 
 
 const
 const
   sRadioCantHaveDisabledChildren = 'Radio item cannot have disabled child items';
   sRadioCantHaveDisabledChildren = 'Radio item cannot have disabled child items';
@@ -720,6 +720,13 @@ const
     (CBS_CHECKEDNORMAL, CBS_CHECKEDHOT, CBS_CHECKEDPRESSED, CBS_CHECKEDDISABLED),
     (CBS_CHECKEDNORMAL, CBS_CHECKEDHOT, CBS_CHECKEDPRESSED, CBS_CHECKEDDISABLED),
     (CBS_MIXEDNORMAL, CBS_MIXEDHOT, CBS_MIXEDPRESSED, CBS_MIXEDDISABLED)
     (CBS_MIXEDNORMAL, CBS_MIXEDHOT, CBS_MIXEDPRESSED, CBS_MIXEDDISABLED)
   );
   );
+  FontColorStates: array[Boolean] of TStyleFont = (sfListItemTextDisabled, sfListItemTextNormal);
+  CheckListItemStates: array[Boolean] of TThemedCheckListBox = (tclListItemDisabled, tclListItemNormal);
+  CheckBoxCheckedStates: array[Boolean] of TThemedButton = (tbCheckBoxCheckedDisabled, tbCheckBoxCheckedNormal);
+  CheckBoxUncheckedStates: array[Boolean] of TThemedButton = (tbCheckBoxUncheckedDisabled, tbCheckBoxUncheckedNormal);
+  CheckBoxMixedStates: array[Boolean] of TThemedButton = (tbCheckBoxMixedDisabled, tbCheckBoxMixedNormal);
+  RadioButtonCheckedStates: array[Boolean] of TThemedButton = (tbRadioButtonCheckedDisabled, tbRadioButtonCheckedNormal);
+  RadioButtonUncheckedStates: array[Boolean] of TThemedButton = (tbRadioButtonUncheckedDisabled, tbRadioButtonUncheckedNormal);
 var
 var
   SavedClientRect: TRect;
   SavedClientRect: TRect;
 
 
@@ -773,17 +780,39 @@ begin
   ItemState := ItemStates[Index];
   ItemState := ItemStates[Index];
   UIState := SendMessage(Handle, WM_QUERYUISTATE, 0, 0);
   UIState := SendMessage(Handle, WM_QUERYUISTATE, 0, 0);
   Disabled := not Enabled or not ItemState.Enabled;
   Disabled := not Enabled or not ItemState.Enabled;
+
+  { Style code below is based on Vcl.StdCtrls' TCustomListBox.CNDrawItem and Vcl.CheckLst's
+    TCustomCheckListBox.DrawItem and .DrawCheck }
+  var LStyle := StyleServices(Self);
+  if not LStyle.Enabled or LStyle.IsSystemStyle then
+    LStyle := nil;
+
   with Canvas do begin
   with Canvas do begin
+    { Initialize colors }
     if not FWantTabs and (odSelected in State) and Focused then begin
     if not FWantTabs and (odSelected in State) and Focused then begin
-      Brush.Color := clHighlight;
       NewTextColor := clHighlightText;
       NewTextColor := clHighlightText;
-    end
-    else begin
-      Brush.Color := Self.Color;
+      if (LStyle <> nil) and (seClient in StyleElements) then begin
+        Brush.Color := LStyle.GetSystemColor(clHighlight);
+        if seFont in StyleElements then
+          NewTextColor := LStyle.GetStyleFontColor(sfListItemTextSelected);
+      end else
+        Brush.Color := clHighlight;
+    end else begin
       if Disabled then
       if Disabled then
         NewTextColor := clGrayText
         NewTextColor := clGrayText
       else
       else
         NewTextColor := Self.Font.Color;
         NewTextColor := Self.Font.Color;
+      if (LStyle <> nil) and (seClient in StyleElements) then begin
+        Brush.Color := LStyle.GetStyleColor(scListBox);
+        if seFont in StyleElements then begin
+          NewTextColor := LStyle.GetStyleFontColor(FontColorStates[not Disabled]);
+          const Details = LStyle.GetElementDetails(CheckListItemStates[Enabled]);
+          var LColor: TColor;
+          if LStyle.GetElementColor(Details, ecTextColor, LColor) and (LColor <> clNone) then
+            NewTextColor := LColor;
+        end;
+      end else
+        Brush.Color := Self.Color;
     end;
     end;
     { Draw threads }
     { Draw threads }
     if FShowLines then begin
     if FShowLines then begin
@@ -810,7 +839,32 @@ begin
         Rect.Top + ((Rect.Bottom - Rect.Top - FCheckHeight) div 2),
         Rect.Top + ((Rect.Bottom - Rect.Top - FCheckHeight) div 2),
         FCheckWidth, FCheckHeight);
         FCheckWidth, FCheckHeight);
       FlipRect(CheckRect, SavedClientRect, FUseRightToLeft);
       FlipRect(CheckRect, SavedClientRect, FUseRightToLeft);
-      if FThemeData = 0 then begin
+      if LStyle <> nil then begin
+        var Detail: TThemedButton;
+        if ItemState.State <> cbGrayed then begin
+          if ItemState.ItemType = itCheck then begin
+            if ItemState.State = cbChecked then
+              Detail := CheckBoxCheckedStates[not Disabled]
+            else
+              Detail := CheckBoxUncheckedStates[not Disabled];
+          end else begin
+            if ItemState.State = cbChecked then
+              Detail := RadioButtonCheckedStates[not Disabled]
+            else
+              Detail := RadioButtonUncheckedStates[not Disabled];
+          end;
+        end else
+          Detail := CheckBoxMixedStates[not Disabled];
+        const ElementDetails = LStyle.GetElementDetails(Detail);
+        const SaveColor = Brush.Color;
+        const SaveIndex = SaveDC(Handle);
+        try
+          LStyle.DrawElement(Handle, ElementDetails, CheckRect, nil, CurrentPPI);
+        finally
+          RestoreDC(Handle, SaveIndex);
+        end;
+        Brush.Color := SaveColor;
+      end else if FThemeData = 0 then begin
         case ItemState.State of
         case ItemState.State of
           cbChecked: uState := ButtonStates[ItemState.ItemType] or DFCS_CHECKED;
           cbChecked: uState := ButtonStates[ItemState.ItemType] or DFCS_CHECKED;
           cbUnchecked: uState := ButtonStates[ItemState.ItemType];
           cbUnchecked: uState := ButtonStates[ItemState.ItemType];
@@ -897,7 +951,7 @@ begin
       lines are drawn -- and we mustn't draw too many. }
       lines are drawn -- and we mustn't draw too many. }
     InternalDrawText(Items[Index], Rect, DrawTextFormat or DT_CALCRECT, False);
     InternalDrawText(Items[Index], Rect, DrawTextFormat or DT_CALCRECT, False);
     FlipRect(Rect, SavedClientRect, FUseRightToLeft);
     FlipRect(Rect, SavedClientRect, FUseRightToLeft);
-    InternalDrawText(Items[Index], Rect, DrawTextFormat, FWantTabs and Disabled);
+    InternalDrawText(Items[Index], Rect, DrawTextFormat, FWantTabs and Disabled and (LStyle = nil));
     { Draw focus rectangle }
     { Draw focus rectangle }
     if FWantTabs and not Disabled and (odSelected in State) and Focused and
     if FWantTabs and not Disabled and (odSelected in State) and Focused and
       (UIState and UISF_HIDEFOCUS = 0) then
       (UIState and UISF_HIDEFOCUS = 0) then

+ 53 - 2
Components/NewStaticText.pas

@@ -35,6 +35,8 @@ type
     procedure Loaded; override;
     procedure Loaded; override;
     procedure Notification(AComponent: TComponent; Operation: TOperation); override;
     procedure Notification(AComponent: TComponent; Operation: TOperation); override;
     procedure SetAutoSize(Value: Boolean); override;
     procedure SetAutoSize(Value: Boolean); override;
+    procedure WMEraseBkgnd(var Message: TWMEraseBkgnd); message WM_ERASEBKGND;
+    procedure WMPaint(var Message: TWMPaint); message WM_PAINT;
   public
   public
     constructor Create(AOwner: TComponent); override;
     constructor Create(AOwner: TComponent); override;
     function AdjustHeight: Integer;
     function AdjustHeight: Integer;
@@ -58,6 +60,8 @@ type
     property ShowAccelChar: Boolean read FShowAccelChar write SetShowAccelChar
     property ShowAccelChar: Boolean read FShowAccelChar write SetShowAccelChar
       default True;
       default True;
     property ShowHint;
     property ShowHint;
+    property StyleElements;
+    property StyleName;
     property TabOrder;
     property TabOrder;
     property TabStop;
     property TabStop;
     property Visible;
     property Visible;
@@ -78,6 +82,7 @@ procedure Register;
 implementation
 implementation
 
 
 uses
 uses
+  Graphics, Themes, Types,
   BidiUtils;
   BidiUtils;
 
 
 procedure Register;
 procedure Register;
@@ -87,11 +92,55 @@ end;
 
 
 { TNewStaticText }
 { TNewStaticText }
 
 
+procedure TNewStaticText.WMEraseBkgnd(var Message: TWMEraseBkgnd);
+begin;
+  if IsCustomStyleActive and (seClient in StyleElements) then
+    Message.Result := 1
+  else
+    inherited;
+end;
+
+procedure TNewStaticText.WMPaint(var Message: TWMPaint);
+const
+  CStates: array[Boolean] of TThemedTextLabel = (ttlTextLabelDisabled, ttlTextLabelNormal);
+begin
+  { Based on Vcl.StdCtrl's TCustomLabel.DoDrawThemeTextEx and its callers. Only the
+    DrawParentBackground call is new compared to it.  }
+  if IsCustomStyleActive and (seClient in StyleElements) then begin
+    const LStyle = StyleServices(Self);
+    var DC := Message.DC;
+    var PS: TPaintStruct;
+    if DC = 0 then
+      DC := BeginPaint(Handle, PS);
+    try
+      var R := ClientRect;
+      const Details = LStyle.GetElementDetails(CStates[Enabled]);
+      LStyle.DrawParentBackground(Handle, DC, Details, False, @R);
+      var Text: String := Caption;
+      if (Text = '') or (FShowAccelChar and (Text[1] = '&') and (Length(Text) = 1)) then
+        Text := Text + ' ';
+      const TextFlags = GetDrawTextFlags;
+      const OldFont = SelectObject(DC, Font.Handle);
+      try
+        LStyle.DrawText(DC, Details, Text, R, TTextFormat(TextFlags), Font.Color);
+      finally
+        SelectObject(DC, OldFont);
+      end;
+    finally
+      if Message.DC = 0 then
+        EndPaint(Handle, PS);
+    end;
+  end else
+    inherited;
+end;
+
 constructor TNewStaticText.Create(AOwner: TComponent);
 constructor TNewStaticText.Create(AOwner: TComponent);
 begin
 begin
   inherited Create(AOwner);
   inherited Create(AOwner);
   ControlStyle := [csCaptureMouse, csClickEvents, csSetCaption,
   ControlStyle := [csCaptureMouse, csClickEvents, csSetCaption,
-    csOpaque, csReplicatable, csDoubleClicks];
+    csReplicatable, csDoubleClicks];
+  if not (StyleServices.Enabled and not StyleServices.IsSystemStyle) then
+    ControlStyle := ControlStyle + [csOpaque];
   Width := 65;
   Width := 65;
   Height := 17;
   Height := 17;
   FAutoSize := True;
   FAutoSize := True;
@@ -132,12 +181,14 @@ end;
 procedure TNewStaticText.CMFontChanged(var Message: TMessage);
 procedure TNewStaticText.CMFontChanged(var Message: TMessage);
 begin
 begin
   inherited;
   inherited;
+  Invalidate;
   AdjustBounds;
   AdjustBounds;
 end;
 end;
 
 
 procedure TNewStaticText.CMParentFontChanged(var Message: TMessage);
 procedure TNewStaticText.CMParentFontChanged(var Message: TMessage);
 begin
 begin
   inherited;
   inherited;
+  Invalidate;
   { What we're really trapping here is changes to Parent. Recalculate size
   { What we're really trapping here is changes to Parent. Recalculate size
     if the new Parent's RTL setting is different. }
     if the new Parent's RTL setting is different. }
   if IsParentRightToLeft(Self) <> FLastAdjustBoundsRTL then
   if IsParentRightToLeft(Self) <> FLastAdjustBoundsRTL then
@@ -186,7 +237,7 @@ begin
   if R.Right > 0 then Dec(R.Right);
   if R.Right > 0 then Dec(R.Right);
 
 
   S := Caption;
   S := Caption;
-  if (S = '') or (FShowAccelChar and (S[1] = '&') and (S[2] = #0)) then
+  if (S = '') or (FShowAccelChar and (S[1] = '&') and (Length(S) = 1)) then
     S := S + ' ';
     S := S + ' ';
 
 
   DC := GetDC(0);
   DC := GetDC(0);

+ 9 - 1
Projects/Compil32.dpr

@@ -72,7 +72,9 @@ uses
   IDE.ImagesModule in 'Src\IDE.ImagesModule.pas' {ImagesModule: TDataModule},
   IDE.ImagesModule in 'Src\IDE.ImagesModule.pas' {ImagesModule: TDataModule},
   ECDSA in '..\Components\ECDSA.pas',
   ECDSA in '..\Components\ECDSA.pas',
   ISSigFunc in '..\Components\ISSigFunc.pas',
   ISSigFunc in '..\Components\ISSigFunc.pas',
-  StringScanner in '..\Components\StringScanner.pas';
+  StringScanner in '..\Components\StringScanner.pas',
+  VCL.Styles,
+  VCL.Themes;
 
 
 {$SETPEOSVERSION 6.1}
 {$SETPEOSVERSION 6.1}
 {$SETPESUBSYSVERSION 6.1}
 {$SETPESUBSYSVERSION 6.1}
@@ -81,6 +83,7 @@ uses
 {$R Res\Compil32.docicon.res}
 {$R Res\Compil32.docicon.res}
 {$R Res\Compil32.manifest.res}
 {$R Res\Compil32.manifest.res}
 {$R Res\Compil32.versionandicon.res}
 {$R Res\Compil32.versionandicon.res}
+{$R Res\Compil32.darkstyle.res}
 
 
 procedure SetAppUserModelID;
 procedure SetAppUserModelID;
 var
 var
@@ -252,6 +255,11 @@ begin
       Title := SCompilerFormCaption;
       Title := SCompilerFormCaption;
   end;
   end;
 
 
+  if Assigned(FlushMenuThemes) then begin
+    { We don't need VCL Styles for dark menus. This keeps shDialogs and shTooltips. }
+    TStyleManager.SystemHooks := TStyleManager.SystemHooks - [shMenus];
+  end;
+
   Application.CreateForm(TImagesModule, ImagesModule);
   Application.CreateForm(TImagesModule, ImagesModule);
   Application.CreateForm(TMainForm, MainForm);
   Application.CreateForm(TMainForm, MainForm);
   Application.Run;
   Application.Run;

+ 2 - 0
Projects/Res/Compil32.darkstyle.rc

@@ -0,0 +1,2 @@
+// The name below doesn't matter except that it must be a name and not just an index
+MYSTYLE1 VCLSTYLE Compil32.darkstyle.vsf

二进制
Projects/Res/Compil32.darkstyle.res


+ 10 - 0
Projects/Res/Compil32.darkstyle.vsf.txt

@@ -0,0 +1,10 @@
+Compil32.darkstyle.vsf should any VCL Style File with its name changed to Dark using
+Bitmap Style Designer (BDS\Bin\BitmapStyleDesigner.exe)
+
+Currently equals VCL Style 'Windows11 Dark 1.0' by Embarcadero from GetIt
+
+For easier testing, you could instead use VCL Style 'Stellar 2.0' by Embarcadero
+from GetIt, in either variant. This style features a colored (blue) background with
+a white foreground. This combination is very rare, if not unique, among all available
+styles. Other styles with a colored background use a black foreground, but since things
+are black by default, those are not useful for testing.

+ 1 - 0
Projects/Src/IDE.FilesDesignerForm.pas

@@ -50,6 +50,7 @@ uses
 procedure TFilesDesignerForm.FormCreate(Sender: TObject);
 procedure TFilesDesignerForm.FormCreate(Sender: TObject);
 begin
 begin
   InitFormFont(Self);
   InitFormFont(Self);
+  InitFormTheme(Self);
 
 
   FFilesHelper := TWizardFormFilesHelper.Create(Self,
   FFilesHelper := TWizardFormFilesHelper.Create(Self,
     NotCreateAppDirCheck, AppFilesListBox, AppFilesAddButton, AppFilesAddDirButton,
     NotCreateAppDirCheck, AppFilesListBox, AppFilesAddButton, AppFilesAddDirButton,

+ 32 - 39
Projects/Src/IDE.HelperFunc.pas

@@ -13,7 +13,7 @@ interface
 
 
 uses
 uses
   Windows,
   Windows,
-  Classes, Forms, Dialogs, Menus, Controls, StdCtrls,
+  Classes, Forms, Dialogs, Menus, Controls, StdCtrls, Graphics,
   ScintEdit, IDE.IDEScintEdit, ModernColors;
   ScintEdit, IDE.IDEScintEdit, ModernColors;
 
 
 const
 const
@@ -26,8 +26,10 @@ type
 
 
 procedure InitFormFont(Form: TForm);
 procedure InitFormFont(Form: TForm);
 procedure SetControlWindowTheme(const WinControl: TWinControl; const Dark: Boolean);
 procedure SetControlWindowTheme(const WinControl: TWinControl; const Dark: Boolean);
-procedure InitFormThemeInit(const ATheme: TTheme);
-procedure InitFormTheme(Form: TForm);
+procedure InitFormThemeInit(const Theme: TTheme);
+function InitFormTheme(const Form: TForm): Boolean;
+function InitFormThemeGetBkColor(const WindowColor: Boolean): TColor;
+function InitFormThemeIsDark: Boolean;
 function GetDisplayFilename(const Filename: String): String;
 function GetDisplayFilename(const Filename: String): String;
 function GetFileTitle(const Filename: String): String;
 function GetFileTitle(const Filename: String): String;
 function GetCleanFileNameOfFile(const Filename: String): String;
 function GetCleanFileNameOfFile(const Filename: String): String;
@@ -85,7 +87,7 @@ implementation
 uses
 uses
   ActiveX, ShlObj, ShellApi, CommDlg, SysUtils, IOUtils, StrUtils, ExtCtrls,
   ActiveX, ShlObj, ShellApi, CommDlg, SysUtils, IOUtils, StrUtils, ExtCtrls,
   Messages, DwmApi, Consts,
   Messages, DwmApi, Consts,
-  Shared.CommonFunc, Shared.CommonFunc.Vcl, PathFunc, Shared.FileClass, NewUxTheme,
+  Shared.CommonFunc, Shared.CommonFunc.Vcl, PathFunc, Shared.FileClass, NewUxTheme, NewNotebook,
   IDE.MainForm, IDE.Messages, Shared.ConfigIniFile;
   IDE.MainForm, IDE.Messages, Shared.ConfigIniFile;
 
 
 procedure InitFormFont(Form: TForm);
 procedure InitFormFont(Form: TForm);
@@ -108,8 +110,10 @@ begin
 end;
 end;
 
 
 procedure SetControlWindowTheme(const WinControl: TWinControl; const Dark: Boolean);
 procedure SetControlWindowTheme(const WinControl: TWinControl; const Dark: Boolean);
+{ Can be used for memos and listboxes to switch them to (or from) a native dark scrollbar }
 begin
 begin
   if UseThemes then begin
   if UseThemes then begin
+    WinControl.StyleName := 'Windows';
     if Dark then
     if Dark then
       SetWindowTheme(WinControl.Handle, 'DarkMode_Explorer', nil)
       SetWindowTheme(WinControl.Handle, 'DarkMode_Explorer', nil)
     else
     else
@@ -120,56 +124,45 @@ end;
 var
 var
   FormTheme: TTheme;
   FormTheme: TTheme;
 
 
-procedure InitFormThemeInit(const ATheme: TTheme);
+procedure InitFormThemeInit(const Theme: TTheme);
 begin
 begin
-  FormTheme := ATheme;
+  FormTheme := Theme;
 end;
 end;
 
 
-procedure InitFormTheme(Form: TForm);
-
-  procedure InitListBoxDarkTheme(const ListBox: TListBox);
-  begin
-    ListBox.Font.Color := FormTheme.Colors[tcFore];
-    ListBox.Color := FormTheme.Colors[tcBack];
-    ListBox.Invalidate;
-    SetControlWindowTheme(ListBox, FormTheme.Dark);
-  end;
-
-  procedure InitWinControlTheme(const ParentControl: TWinControl);
-  begin
-    for var I := 0 to ParentControl.ControlCount-1 do begin
-      var Control := ParentControl.Controls[I];
-      if Control is TListBox then
-        InitListBoxDarkTheme(Control as TListBox)
-      else if (Control is TButton) or (Control is TRadioButton) or (Control is TCheckBox) then begin
-        { Not actually used at the moment since only TMainForm calls InitFormTheme and it doesn't
-          have any of these controls. If it would be used: it works fully for buttons but for
-          radiobuttons and checkboxes it only updates the glyph and not the text color. }
-        SetControlWindowTheme(Control as TWinControl, FormTheme.Dark);
-      end;
-
-      if Control is TWinControl then
-        InitWinControlTheme(Control as TWinControl);
-    end;
-  end;
-
+function InitFormTheme(const Form: TForm): Boolean;
+{ Assumes forms other then MainForm call this function only once during creation, and assumes they
+  don't need any styling if the theme is non dark. Always styles MainForm. Returns True if it did
+  style, False otherwise. }
 begin
 begin
-  if (Form = MainForm) or FormTheme.Dark then begin
-    Form.Color := FormTheme.Colors[tcBack];
-  
+  Result := (Form = MainForm) or FormTheme.Dark;
+  if Result then begin
+    Form.Color := InitFormThemeGetBkColor(Form = MainForm);
+
     { Based on https://learn.microsoft.com/en-us/windows/apps/desktop/modernize/apply-windows-themes
     { Based on https://learn.microsoft.com/en-us/windows/apps/desktop/modernize/apply-windows-themes
       Unlike this article we check for Windows 10 Version 2004 because that's the first version
       Unlike this article we check for Windows 10 Version 2004 because that's the first version
       that introduced DWMWA_USE_IMMERSIVE_DARK_MODE as 20 (the now documented value) instead of 19 }
       that introduced DWMWA_USE_IMMERSIVE_DARK_MODE as 20 (the now documented value) instead of 19 }
     if WindowsVersionAtLeast(10, 0, 19041) then begin
     if WindowsVersionAtLeast(10, 0, 19041) then begin
+      Form.StyleElements := Form.StyleElements - [seBorder];
       const DWMWA_USE_IMMERSIVE_DARK_MODE = 20;
       const DWMWA_USE_IMMERSIVE_DARK_MODE = 20;
       var value: BOOL := FormTheme.Dark;
       var value: BOOL := FormTheme.Dark;
       DwmSetWindowAttribute(Form.Handle, DWMWA_USE_IMMERSIVE_DARK_MODE, @value, SizeOf(value));
       DwmSetWindowAttribute(Form.Handle, DWMWA_USE_IMMERSIVE_DARK_MODE, @value, SizeOf(value));
     end;
     end;
-  
-    InitWinControlTheme(Form);
   end;
   end;
 end;
 end;
 
 
+function InitFormThemeGetBkColor(const WindowColor: Boolean): TColor;
+begin
+  if WindowColor then
+    Result := FormTheme.Colors[tcBack] { This is white/window if not dark mode }
+  else
+    Result := FormTheme.Colors[tcToolBack]; { This is gray/btnface if not dark mode }
+end;
+
+function InitFormThemeIsDark: Boolean;
+begin
+  Result := FormTheme.Dark;
+end;
+
 function GetDisplayFilename(const Filename: String): String;
 function GetDisplayFilename(const Filename: String): String;
 var
 var
   Buf: array[0..MAX_PATH-1] of Char;
   Buf: array[0..MAX_PATH-1] of Char;

+ 1 - 0
Projects/Src/IDE.InputQueryComboForm.pas

@@ -63,6 +63,7 @@ end;
 procedure TInputQueryComboForm.FormCreate(Sender: TObject);
 procedure TInputQueryComboForm.FormCreate(Sender: TObject);
 begin
 begin
   InitFormFont(Self);
   InitFormFont(Self);
+  InitFormTheme(Self);
 end;
 end;
 
 
 function TInputQueryComboForm.GetValue: String;
 function TInputQueryComboForm.GetValue: String;

+ 1 - 0
Projects/Src/IDE.InputQueryMemoForm.pas

@@ -77,6 +77,7 @@ end;
 procedure TInputQueryMemoForm.FormCreate(Sender: TObject);
 procedure TInputQueryMemoForm.FormCreate(Sender: TObject);
 begin
 begin
   InitFormFont(Self);
   InitFormFont(Self);
+  InitFormTheme(Self);
   UpdateImages;
   UpdateImages;
 end;
 end;
 
 

+ 4 - 0
Projects/Src/IDE.MainForm.dfm

@@ -14,6 +14,7 @@ object MainForm: TMainForm
   KeyPreview = True
   KeyPreview = True
   Menu = MainMenu1
   Menu = MainMenu1
   Position = poDefault
   Position = poDefault
+  StyleElements = []
   OnAfterMonitorDpiChanged = FormAfterMonitorDpiChanged
   OnAfterMonitorDpiChanged = FormAfterMonitorDpiChanged
   OnCloseQuery = FormCloseQuery
   OnCloseQuery = FormCloseQuery
   OnKeyDown = FormKeyDown
   OnKeyDown = FormKeyDown
@@ -47,6 +48,7 @@ object MainForm: TMainForm
       FullRepaint = False
       FullRepaint = False
       TabOrder = 1
       TabOrder = 1
       Visible = False
       Visible = False
+      StyleName = 'Windows'
       OnMouseMove = SplitPanelMouseMove
       OnMouseMove = SplitPanelMouseMove
     end
     end
     object StatusPanel: TPanel
     object StatusPanel: TPanel
@@ -195,6 +197,7 @@ object MainForm: TMainForm
     Align = alTop
     Align = alTop
     BevelOuter = bvNone
     BevelOuter = bvNone
     TabOrder = 0
     TabOrder = 0
+    StyleName = 'Windows'
     object ToolBar: TToolBar
     object ToolBar: TToolBar
       AlignWithMargins = True
       AlignWithMargins = True
       Left = 7
       Left = 7
@@ -369,6 +372,7 @@ object MainForm: TMainForm
     BevelOuter = bvNone
     BevelOuter = bvNone
     TabOrder = 1
     TabOrder = 1
     Visible = False
     Visible = False
+    StyleName = 'Windows'
     object UpdatePanelClosePaintBox: TPaintBox
     object UpdatePanelClosePaintBox: TPaintBox
       AlignWithMargins = True
       AlignWithMargins = True
       Left = 330
       Left = 330

+ 59 - 96
Projects/Src/IDE.MainForm.pas

@@ -680,7 +680,7 @@ var
 implementation
 implementation
 
 
 uses
 uses
-  ActiveX, Clipbrd, ShellApi, ShlObj, IniFiles, Registry, Consts, Types, UITypes,
+  ActiveX, Clipbrd, ShellApi, ShlObj, IniFiles, Registry, Consts, Types, UITypes, Themes,
   Math, StrUtils, WideStrUtils, TypInfo,
   Math, StrUtils, WideStrUtils, TypInfo,
   PathFunc, Shared.CommonFunc.Vcl, Shared.CommonFunc, Shared.FileClass, IDE.Messages, NewUxTheme.TmSchema, BrowseFunc,
   PathFunc, Shared.CommonFunc.Vcl, Shared.CommonFunc, Shared.FileClass, IDE.Messages, NewUxTheme.TmSchema, BrowseFunc,
   IDE.HtmlHelpFunc, TaskbarProgressFunc, IDE.ImagesModule,
   IDE.HtmlHelpFunc, TaskbarProgressFunc, IDE.ImagesModule,
@@ -783,6 +783,7 @@ begin
   Memo.SetAutoCompleteSeparators(InnoSetupStylerWordListSeparator, InnoSetupStylerWordListTypeSeparator);
   Memo.SetAutoCompleteSeparators(InnoSetupStylerWordListSeparator, InnoSetupStylerWordListTypeSeparator);
   Memo.SetWordChars(Memo.GetDefaultWordChars+'#{}[]');
   Memo.SetWordChars(Memo.GetDefaultWordChars+'#{}[]');
   Memo.Theme := FTheme;
   Memo.Theme := FTheme;
+  Memo.StyleName := 'Windows';
   Memo.Visible := False;
   Memo.Visible := False;
   Result := Memo;
   Result := Memo;
 end;
 end;
@@ -814,92 +815,6 @@ begin
   Result := Memo;
   Result := Memo;
 end;
 end;
 
 
-function DarkStatusBarSubclassProc(hWnd: HWND; uMsg: UINT; wParam: WPARAM; lParam: LPARAM; uIdSubclass: UINT_PTR; dwRefData: DWORD_PTR): LRESULT; stdcall;
-const
-  { See TStatusBarStyleHook.Paint }
-  AlignStyles: array [TAlignment] of Integer = (DT_LEFT, DT_RIGHT, DT_CENTER);
-  cGripSize = 17;
-begin
-  case uMsg of
-    WM_ERASEBKGND:
-      begin
-        const MainForm = TMainForm(dwRefData);
-        if MainForm.FTheme.Dark then begin
-          { See StatusBarStyleHook.WMEraseBkgnd }
-          Exit(1);
-        end;
-      end;
-    WM_PAINT, WM_PRINTCLIENT:
-      begin
-        const MainForm = TMainForm(dwRefData);
-        if MainForm.FTheme.Dark then begin
-          var PaintStruct: TPaintStruct;
-          const Canvas = TCanvas.Create;
-          try
-            if uMsg = WM_PAINT then
-              Canvas.Handle := BeginPaint(hWnd, PaintStruct)
-            else
-              Canvas.Handle := wParam;
-
-            const Control = MainForm.StatusBar;
-            Canvas.Font := Control.Font;
-            Canvas.Font.Color := MainForm.FTheme.Colors[tcFore];
-
-            { See TStatusBarStyleHook.Paint }
-
-            Canvas.Brush.Color := $171717; { Same as themed scrollbar drawn by Windows 11 }
-            Canvas.FillRect(Rect(0, 0, Control.Width, Control.Height));
-
-            const Count = Control.Panels.Count;
-            for var I := 0 to Count-1 do begin
-              var R := Default(TRect);
-              SendMessage(hWnd, SB_GETRECT, I, IntPtr(@R));
-              if IsRectEmpty(R) then
-                Continue;
-              var R1 := R;
-              if I = Count - 1 then
-                R1.Right := Control.ClientWidth + 10;
-              Canvas.FillRect(R1);
-              InflateRect(R, -1, -1);
-              var Flags := Control.DrawTextBiDiModeFlags(AlignStyles[Control.Panels[I].Alignment]);
-              Flags := Flags + DT_VCENTER;
-              var LText: String;
-              SetLength(LText, Word(SendMessage(hWnd, SB_GETTEXTLENGTH, I, 0)));
-              if Length(LText) > 0 then begin { Always False at the moment }
-                var Res := SendMessage(hWnd, SB_GETTEXT, I, IntPtr(@LText[1]));
-                if (Res and SBT_OWNERDRAW = 0) then
-                  DrawText(Canvas.Handle, LText, Length(LText), R, Flags)
-                else
-                  MainForm.StatusBarCanvasDrawPanel(Canvas, Control.Panels[I], R);
-              end else begin
-                if Control.Panels[I].Style <> psOwnerDraw then
-                  DrawText(Canvas.handle, Control.Panels[I].Text, Length(Control.Panels[I].Text), R, Flags)
-                else
-                  MainForm.StatusBarCanvasDrawPanel(Canvas, Control.Panels[I], R);
-              end;
-            end;
-
-            if not IsZoomed(MainForm.Handle) and (MainForm.FStatusBarThemeData <> 0) then begin
-              var R1 := Control.ClientRect;
-              R1.Left := R1.Right - MainForm.ToCurrentPPI(cGripSize);
-              R1.Top := R1.Bottom - MainForm.ToCurrentPPI(cGripSize);
-              DrawThemeBackground(MainForm.FStatusBarThemeData, Canvas.Handle, SP_GRIPPER, 0, R1, nil);
-            end;
-          finally
-            Canvas.Free;
-          end;
-          if uMsg = WM_PAINT then
-            EndPaint(hWnd, PaintStruct);
-          Exit(0);
-        end;
-      end;
-    WM_NCDESTROY:
-      RemoveWindowSubclass(hWnd, @DarkStatusBarSubclassProc, 0);
-  end;
-
-  Result := DefSubclassProc(hWnd, uMsg, wParam, lParam);
-end;
-
 constructor TMainForm.Create(AOwner: TComponent);
 constructor TMainForm.Create(AOwner: TComponent);
 
 
   procedure CheckUpdatePanelMessage(const Ini: TConfigIniFile; const ConfigIdent: String;
   procedure CheckUpdatePanelMessage(const Ini: TConfigIniFile; const ConfigIdent: String;
@@ -1155,8 +1070,6 @@ begin
 
 
   UpdateThemeData(True);
   UpdateThemeData(True);
   
   
-  SetWindowSubclass(StatusBar.Handle, @DarkStatusBarSubclassProc, 0, DWORD_PTR(Self));
-
   FMenuBitmaps := TMenuBitmaps.Create;
   FMenuBitmaps := TMenuBitmaps.Create;
   FMenuBitmapsSize.cx := 0;
   FMenuBitmapsSize.cx := 0;
   FMenuBitmapsSize.cy := 0;
   FMenuBitmapsSize.cy := 0;
@@ -1319,7 +1232,6 @@ begin
   UpdateMarginsAndSquigglyAndCaretWidths;
   UpdateMarginsAndSquigglyAndCaretWidths;
   UpdateOutputTabSetListsItemHeightAndDebugTimeWidth;
   UpdateOutputTabSetListsItemHeightAndDebugTimeWidth;
   UpdateStatusPanelHeight(StatusPanel.Height);
   UpdateStatusPanelHeight(StatusPanel.Height);
-  SetWindowSubclass(StatusBar.Handle, @DarkStatusBarSubclassProc, 0, DWORD_PTR(Self));
 end;
 end;
 
 
 procedure TMainForm.FormCloseQuery(Sender: TObject;
 procedure TMainForm.FormCloseQuery(Sender: TObject;
@@ -6556,19 +6468,45 @@ begin
 end;
 end;
 
 
 procedure TMainForm.UpdateTheme;
 procedure TMainForm.UpdateTheme;
+
+  procedure SetListBoxWindowTheme(const ListBox: TListBox);
+  begin
+    ListBox.Font.Color := FTheme.Colors[tcFore];
+    ListBox.Color := FTheme.Colors[tcBack];
+    ListBox.Invalidate;
+    SetControlWindowTheme(ListBox, FTheme.Dark);
+  end;
+
 begin
 begin
   FTheme.Typ := FOptions.ThemeType;
   FTheme.Typ := FOptions.ThemeType;
 
 
   SetHelpFileDark(FTheme.Dark);
   SetHelpFileDark(FTheme.Dark);
 
 
+  { For MainForm the active style only impacts message boxes and tooltips: FMemos, ToolbarPanel,
+    UpdatePanel, SplitPanel and the 4 ListBoxes all ignore it because their StyleName property is set
+    to 'Windows' always, either by the .dfm or by code. Additionally, for scrollbars and StatusBar,
+    MainForm's StyleElements is empty. Menus ignore it because shMenus is removed from
+    TStyleManager.SystemHooks at startup. }
+  if FTheme.Dark then
+    TStyleManager.TrySetStyle('Dark')
+  else
+    TStyleManager.TrySetStyle('Windows');
+  { For some reason only MainForm needs this: with StyleName set to an empty string, dialog boxes
+    it opens, such as MsgBox, look broken }
+  StyleName := TStyleManager.ActiveStyle.Name;
+
+  InitFormTheme(Self);
+
+  ToolbarPanel.Color := FTheme.Colors[tcToolBack];
+
   for var Memo in FMemos do begin
   for var Memo in FMemos do begin
     Memo.UpdateThemeColorsAndStyleAttributes;
     Memo.UpdateThemeColorsAndStyleAttributes;
     SetControlWindowTheme(Memo, FTheme.Dark);
     SetControlWindowTheme(Memo, FTheme.Dark);
   end;
   end;
-
-  InitFormTheme(Self);
-  ToolbarPanel.Color := FTheme.Colors[tcToolBack];
-  BodyPanel.Color := FTheme.Colors[tcBack];
+  SetListBoxWindowTheme(CompilerOutputList);
+  SetListBoxWindowTheme(DebugOutputList);
+  SetListBoxWindowTheme(DebugCallStackList);
+  SetListBoxWindowTheme(FindResultsList);
 
 
   if FTheme.Dark then begin
   if FTheme.Dark then begin
     ThemedToolbarVirtualImageList.ImageCollection := ImagesModule.DarkToolBarImageCollection;
     ThemedToolbarVirtualImageList.ImageCollection := ImagesModule.DarkToolBarImageCollection;
@@ -7278,6 +7216,13 @@ begin
           RGlyph.Left := RText.Right; { RGlyph is now a square }
           RGlyph.Left := RText.Right; { RGlyph is now a square }
           DrawThemeBackground(FToolbarThemeData, Canvas.Handle, TP_DROPDOWNBUTTONGLYPH, TS_NORMAL, RGlyph, nil);
           DrawThemeBackground(FToolbarThemeData, Canvas.Handle, TP_DROPDOWNBUTTONGLYPH, TS_NORMAL, RGlyph, nil);
         end;
         end;
+        var Color: TColor := FTheme.Colors[tcFore];
+        const LStyle = TStyleManager.ActiveStyle;
+        if LStyle <> nil then begin
+          const Details = LStyle.GetElementDetails(tsPane);
+          LStyle.GetElementColor(Details, ecTextColor, Color);
+        end;
+        Canvas.Font.Color := Color;
         var S := Format('Tabs closed: %d', [FHiddenFiles.Count]);
         var S := Format('Tabs closed: %d', [FHiddenFiles.Count]);
         Canvas.TextRect(RText, S, [tfCenter]);
         Canvas.TextRect(RText, S, [tfCenter]);
       end;
       end;
@@ -7292,7 +7237,25 @@ begin
       if FCompiling and (FProgressMax > 0) then begin
       if FCompiling and (FProgressMax > 0) then begin
         var R := Rect;
         var R := Rect;
         InflateRect(R, -2, -2);
         InflateRect(R, -2, -2);
-        if FProgressThemeData = 0 then begin
+        var LStyle := StyleServices(Self);
+        if not LStyle.Enabled or LStyle.IsSystemStyle then
+          LStyle := nil;
+        if LStyle <> nil then begin
+          { See Vcl.ComCtrl's TProgressBarStyleHook.Paint, .PaintFrame, and .PaintBar }
+          var Details: TThemedElementDetails;
+          Details.Element := teProgress;
+          if LStyle.HasTransparentParts(Details) then
+            LStyle.DrawParentBackground(Handle, Canvas.Handle, Details, False, @R);
+          Details := LStyle.GetElementDetails(tpBar);
+          LStyle.DrawElement(Canvas.Handle, Details, R);
+          InflateRect(R, -1, -1);
+          const W = R.Width;
+          const Pos = Round(W * (FProgress / FProgressMax));
+          var FillR := R;
+          FillR.Right := FillR.Left + Pos;
+          Details := LStyle.GetElementDetails(tpChunk);
+          LStyle.DrawElement(Canvas.Handle, Details, FillR);
+        end else if FProgressThemeData = 0 then begin
           { Border }
           { Border }
           Canvas.Pen.Color := clBtnShadow;
           Canvas.Pen.Color := clBtnShadow;
           Canvas.Brush.Style := bsClear;
           Canvas.Brush.Style := bsClear;
@@ -7488,7 +7451,7 @@ end;
 { Should be removed if the main menu ever gets removed }
 { Should be removed if the main menu ever gets removed }
 procedure TMainForm.UAHDrawMenuBottomLine;
 procedure TMainForm.UAHDrawMenuBottomLine;
 begin
 begin
-  if FTheme.Dark then begin
+  if not (csDestroying in ComponentState) and (FTheme <> nil) and FTheme.Dark then begin
     var ClientRect: TRect;
     var ClientRect: TRect;
     Windows.GetClientRect(Handle, ClientRect);
     Windows.GetClientRect(Handle, ClientRect);
 		MapWindowPoints(Handle, 0, ClientRect, 2);
 		MapWindowPoints(Handle, 0, ClientRect, 2);

+ 1 - 0
Projects/Src/IDE.MsgBoxDesignerForm.pas

@@ -117,6 +117,7 @@ uses
 procedure TMsgBoxDesignerForm.FormCreate(Sender: TObject);
 procedure TMsgBoxDesignerForm.FormCreate(Sender: TObject);
 begin
 begin
   InitFormFont(Self);
   InitFormFont(Self);
+  InitFormTheme(Self);
 
 
   cb_Suppressible.Checked := True;
   cb_Suppressible.Checked := True;
   MSGText.Lines[MSGText.CaretPos.Y] := '<Enter your text here...>';
   MSGText.Lines[MSGText.CaretPos.Y] := '<Enter your text here...>';

+ 1 - 0
Projects/Src/IDE.OptionsForm.pas

@@ -82,6 +82,7 @@ uses
 procedure TOptionsForm.FormCreate(Sender: TObject);
 procedure TOptionsForm.FormCreate(Sender: TObject);
 begin
 begin
   InitFormFont(Self);
   InitFormFont(Self);
+  InitFormTheme(Self);
 
 
   { Order must match CompFunc.TKeyMappingType }
   { Order must match CompFunc.TKeyMappingType }
   KeyMappingComboBox.Items.Add('Classic');
   KeyMappingComboBox.Items.Add('Classic');

+ 1 - 0
Projects/Src/IDE.RegistryDesignerForm.pas

@@ -69,6 +69,7 @@ end;
 procedure TRegistryDesignerForm.FormCreate(Sender: TObject);
 procedure TRegistryDesignerForm.FormCreate(Sender: TObject);
 begin
 begin
   InitFormFont(Self);
   InitFormFont(Self);
+  InitFormTheme(Self);
 
 
   FRegistryHelper := TWizardFormRegistryHelper.Create(Self, AppRegistryFileEdit,
   FRegistryHelper := TWizardFormRegistryHelper.Create(Self, AppRegistryFileEdit,
     AppRegistryFileButton, AppRegistryUninsDeleteKeyCheck,
     AppRegistryFileButton, AppRegistryUninsDeleteKeyCheck,

+ 1 - 0
Projects/Src/IDE.SignToolsForm.pas

@@ -80,6 +80,7 @@ procedure TSignToolsForm.FormCreate(Sender: TObject);
 begin
 begin
   FSignTools := TStringList.Create();
   FSignTools := TStringList.Create();
   InitFormFont(Self);
   InitFormFont(Self);
+  InitFormTheme(Self);
 end;
 end;
 
 
 { This and CreateParams make bsSizeable (which has an unwanted icon) look like bsDialog, see:
 { This and CreateParams make bsSizeable (which has an unwanted icon) look like bsDialog, see:

+ 1 - 0
Projects/Src/IDE.StartupForm.pas

@@ -99,6 +99,7 @@ begin
   FResult := srNone;
   FResult := srNone;
 
 
   InitFormFont(Self);
   InitFormFont(Self);
+  InitFormTheme(Self);
 
 
   DonateImage.Hint := MainForm.UpdatePanelDonateImage.Hint;
   DonateImage.Hint := MainForm.UpdatePanelDonateImage.Hint;
 
 

+ 1 - 0
Projects/Src/IDE.Wizard.WizardFileForm.pas

@@ -119,6 +119,7 @@ var
   I: Integer;
   I: Integer;
 begin
 begin
   InitFormFont(Self);
   InitFormFont(Self);
+  InitFormTheme(Self);
 
 
   MakeBold(SourceLabel);
   MakeBold(SourceLabel);
   MakeBold(DestRootDirLabel);
   MakeBold(DestRootDirLabel);

+ 311 - 43
Projects/Src/IDE.Wizard.WizardForm.dfm

@@ -56,12 +56,8 @@ object WizardForm: TWizardForm
     Height = 314
     Height = 314
     ActivePage = MainPage
     ActivePage = MainPage
     Anchors = [akLeft, akTop, akRight, akBottom]
     Anchors = [akLeft, akTop, akRight, akBottom]
-    Color = clBtnFace
-    ParentColor = False
     TabOrder = 3
     TabOrder = 3
     object WelcomePage: TNewNotebookPage
     object WelcomePage: TNewNotebookPage
-      Color = clWindow
-      ParentColor = False
       DesignSize = (
       DesignSize = (
         496
         496
         314)
         314)
@@ -233,6 +229,166 @@ object WizardForm: TWizardForm
           7188BC220000000049454E44AE426082}
           7188BC220000000049454E44AE426082}
         Stretch = True
         Stretch = True
       end
       end
+      object WelcomeImageDark: TImage
+        Left = 33
+        Top = 12
+        Width = 164
+        Height = 314
+        Anchors = [akLeft, akTop, akBottom]
+        Picture.Data = {
+          0954506E67496D61676589504E470D0A1A0A0000000D49484452000000A40000
+          013A080200000017CC6E91000000017352474200AECE1CE90000000467414D41
+          0000B18F0BFC6105000000097048597300000EC300000EC301C76FA864000000
+          1874455874536F667477617265005061696E742E4E455420352E312E381B69EA
+          A8000000B66558496649492A000800000005001A010500010000004A0000001B
+          010500010000005200000028010300010000000200000031010200100000005A
+          00000069870400010000006A0000000000000060000000010000006000000001
+          0000005061696E742E4E455420352E312E380003000090070004000000303233
+          3001A00300010000000100000005A00400010000009400000000000000020001
+          000200040000005239380002000700040000003031303000000000AB80211353
+          9E3828000011524944415478DAED9D0B701BE59DC0F7A1956C4B962C5996E457
+          1CC7719ED8319036A101CAA3B4CC9502074D0F98BE063AB407B992D03425254C
+          43798483030243E963FA005A62DA14EEDA4287B9D2E38692262910923889E3D8
+          4EFC922C5BB665C9926D3D76B7DFAE1C59B2654BB6A595E2FFFF379ECCB7D26A
+          B5DADFFEBFF77EA12FBEFE560A81018DB2E180B20181B20181B20181B20181B2
+          0181B20181B20181B20181B20181B20181B20181B20181B20181B20181B20181
+          B20181B20181B20181B20181B20181B20181B20181B20181B20181B20181B201
+          81B20181B20181B20181B20181B20181B20181B20181B20181B20181B20181B2
+          0181B20181B20181B20181B20181B20181B20181B20181B20181B20181B20181
+          B20181B20181B20181B20181B20181B20181B20181B20181B20181B20181B201
+          81B20181B20181B20181B20181B20181B20181B20181B20181B20181B20181B2
+          0181B20181B20181B20181B20181B20181B20181B20181B20181B20181B20181
+          B20181B20181B20181B20181B20181B20181B20181B20181B20181B20181B201
+          81B2019143B24DEAF0E36B1D2191DE75B2D4135265FB74162139247BBDD1FFF8
+          45BD24B1ED58F9496F7EB64F67119243B2AFB57877AE7691C48E63B623C3DA6C
+          9FCE22248764DF5836FCEDDA4192D8D5643D34A4CBF6E92C427248F61D4B86EE
+          AC7693C4C3272D7F1B28CCF6E92C427248F6DDCB06BE54E921893DCD96BFF6A3
+          ECF49343B2EF5FEEFC97723F49FCD7E992B7FBF4D93E9D45480EC97E6855EFA7
+          ADA324F1DC99E23FF51665FB7416213924FBC93AFB25A67192F8719BE975BB31
+          DBA7B308C921D92F5EDCBD421F24899FB71B5FEB3165FB7416211991AD57F11B
+          4DFE43435A6F984DFD53AF7CA2A3AC8097121D45AF7416A7FE412317DE58EC3F
+          30A09BD3D7012423B23F6BF1EE58ED6AF6A8F79CB63AC6D5297EEAF5CBCE1AD4
+          22493476197E71CE9CE2A76AB481EFADEA5BA60B3DD95CF2BFFD58AD9B8D4C45
+          F66375F6D5FAD05080F9E129DB8994FA3EC5B7AF6857313449BDDEA3FF717B49
+          F253A7C42B8A7DDB57F517A8A866AFFAC1A6B22991EDDF707BB07AFDBC7F8528
+          4A771EC5870A3EFE435EFBA1B45F25E5C954995D9617DCDB603769044F907EA1
+          CDFCAE2B49CC15B0FC1F2FEF88A4FF682F7CBECD92EC1BC4AF550D6DAE18CE53
+          51EE00BDF568853D3E0B111976E4BAADBCB16CDE3F81C8A669E9E613C341DDE1
+          4675F7F14C5C2825C96005ADDE30BA7B8D53AF1679417CB9C3B4BFA728243233
+          ED6CD184F66DEC8AA4FFECC87FA6753649455CF83F96BB3E6D91DA69DE20BDFB
+          94EDB8A760CA3EBCB9CA7BCDBD14939E525C0C05B41FBEAEE9FC2843D74A1932
+          5B1BBFCEE2F9EE4A17C3D06141FC8B53F75C9B352CD209F75CA60DFC6C7D4F24
+          FD5767C19E96D2998E49F28C87D6386BB441725841109F6CB1BC33BDA8A6E991
+          6BB784CD4BD3F85B24DF871B353D4D99BB5C9926E34DAFAF560DDEB1C41D298C
+          8F0C699E3A637505B8E9BBD519469F6DE88DA4DF7315FCF05462D99B8A7D5B6B
+          FB8D1AA9342537506397F1E544F5F6228E2AA4430B3CF3E3B73C3FE51539BE7F
+          AFE93C92D12B9639322E9BA385ED2BFAAEB58D46363B7CAA874F95768F4DADA2
+          5F66F23D52D717491F1ACCDF75626A36CE50E24DE5C3772D1DCA3B3FADE19DDE
+          82A75BADD38B069D8A2AA24374E21C640E4C974DC9BE75871AD5F60B32BE95E8
+          5421BE9FAC77D41505229BA43EF5F419CB9441CCCF5ABD3B56B922E92343793B
+          9ACA63DF25D5B7FB6AFBAF2EF133CC84C313C39A1D4D654161AAE97C462866F9
+          859BA6E265D37C486427322431342EC7F7C799BE6E6947A11E345B5E704F9DA3
+          52EE33218C86A917DBCCF268C784969BCBDC5B6A8722E9A661CDB66315939FD5
+          8476AC70D69B82D157BA47D99D4D65CE692D78352D98553C9B0ED354BCECF28F
+          F6391A36C7FAD61DDAA7B69F54E0D2A511E5BA4BABB581A7EBED7AB9DB84924B
+          DCFFEED1FFB2A3242457D9BE5235F8B5A5C391B75ABCEA7B3FAE9493E23AC3E8
+          83ABFB49132E7A1C52FDDE7EBCFCAC5F33E5F82C255AB970BA4C53F1B2EBDFF8
+          B6BBE2D29E4BEF888BEF0FF66BBA8E2A73F5D282A27DE3579A4776ACEC8F16BA
+          A42EFDAE4BF75C6BC928CFFE7B8DEBD60A6FE4F5B33EEEEE8F9690C48DA5C377
+          560FE938317A84F13045AADFEF4D9BDA405362898AD730622AA7912253649366
+          F7E0D24FF5367C312EBE0FEE533B2E98F8567A20E4A6B2E17B6A06586632004F
+          7BB8479A4BBF5A35F4B9525FE4959E51D53D472AEEAA1EBCA97C24F6B3A4BD4E
+          32FF3F241EFD94F207528033B428FF2B55E8261334897B8AA545566A94A57AAA
+          53645372378BBB72BD7D6A7CFF4ED3754CC96B386F94964D42F0BEE5FD3794FB
+          625FECF2AB4836BD541B8E6C7A8234C9A5EB0D63B1F704E12D876E6FAB45A4E6
+          97534BEED5B46860793593D207A6CB968E4251527CAFBB75D2779094DFAFAA1D
+          A794BC8CF3230B439C1A46F8FECADE4D96F1397DEA407FDEE32DA501213551B3
+          417C0B858C9034C413CAA664DFEECA4FD82FB92DD6B714DFDDB91EDFD919CFD6
+          ABC2CF34D8A3A19C944E9FEAFE63E59E70BA9E1C108D2CAF639314F033C9A622
+          F15DBDA9B7FE96B8F83EF86B75EF6985AEE0BCC8DAE485CAFCE013750E6B3E9F
+          74CFBE3176E789D2AE514D0A474D1552905BB830376B70CF229B9A29BEFFF15B
+          4D4FEE8E976450761E231472BC4E25903F838AD7AA8442155FC849FFEAE4F472
+          5D20D2F1393BC341BA75443312667D616684FC855892F687198FFC8A4F7E657C
+          EED97B21C317A9845976985D363511DF97CBF13D91E548F1FDF75FAB9D391ADF
+          F3946DE2C235BA804176A9E7F842C96844A194D0CB46B934B6799311E2457207
+          7843C43DB91518F9269012DE90744378426CBB4F3314FFFC18478B366EB67224
+          A96C4AF63DB4E4938E8B6F8BF13D26C7772EF6A7CE53F68F1A3A571A522D7173
+          81168FEADEA35571BF9C122BD40B954DC9BE07965DE1ACFBD758DF727CB764FB
+          474F659EB25FBCB87385FE42927DC6A3BA2733B2A9487C576D7034FC5B5C7C1F
+          7E4D633F91EDDF1D0766E33392BA6C6A22BEAF74D6DD1C1FDFAFA89D6714BB08
+          49C970058DDC01DC8C15B41A5D30B6D37B2686024CBB4F7DBE82C68E8498B80A
+          9ABC99950ADA14E4F8DE686FF81215EBFB5063EEF4A766ADE965CB0B91A65745
+          41F2B2A06754F58034C6C5A570D4545978D32B21C4B78BC477FDCD1413E3FBC0
+          CBEABED60C5CC239931DD95A967F6A5DCF8AC2544BFD562FB7FD78B99F4FD7B4
+          F08576AACC7668A93FF53247C3E638DFB911DF5990CDD1C27757F65F63F5CFE9
+          53FFD7A77DAAC532CB94C59459687769F22F20E577CD55BD7537C6FA2E3CF032
+          97EDF8565EB6F8AD6503B7947B9898410EFB28AB614473DE64093A30CE0404BA
+          BC60B27F4D10C437EC869F9C3553591D0849F5CBE4F11247C317A3BEA9C0A8F6
+          D03E756F73A6AFEF2C282DFB7A9B676BAD4B1563BACDCB3DDC6CBBAFD6B5DE34
+          3934F2C160DEF36D253F58ED5CAE9F9C371816C4BDAD256F3B0D890E2C0F68CA
+          439C74CC10276910D0E91BE29C1352F9BDFC2AE74537C6FAD61D7889EB6F57F2
+          82C7A2A8EC0D26DF83ABFB0A62262FBC37A023FE4833E9C1D5CEAB2D9319FBBB
+          FDDAC79A6DA41547EE8C2BCDBE6836301AA61E6BB61E9EB60807516BCEF0E485
+          791C418EEF4D727C9FAF6D6435BE95935D9E1778B6C1116D6B9130FD93C3F0B3
+          B3C5916278AB34C83D3955E14D47E1DE56E9A11052C0DFBD6CF00B659E686640
+          5A62DB8E96D9C7959E9634BF83C8F17DB51CDF93BEB315DF0AC936AB437BEA7A
+          AB751379F25898FA49BBE9CFCEA2E84C84BB960EDC5EE589EEDFD869F845C7C4
+          B37D241FFEBC6DF89B3543F9E7B384733E6E6753E940706A632C73130EE72D9B
+          3A3F5EE258776B7C7CBFAAFC78A812B24961F9F845F64B4D1353893D41FA9933
+          9603837159F16D1543DFA8714737A73FA27D79F1C8B6152EC3F9F98A1F0D6ABE
+          7FB29C9FF67C490123983230957821B2A9487CD75EE35CFB85B8F87EFF579CEB
+          6C1AAF7352322E5B458B5B48165D36310FA9DBAFDA7DCAD6396D709AC4EEB695
+          83D1CD675B8ADF724E9D6B565510D8BDC659797ECAC39B0EDD0B6D96E9CF13E9
+          195ECF266F5925258DB2A9F3E325BDF5B7C4F8F66B0FBEAAE47849C6656FAE70
+          DF593DC8C9256ED3B0E63F4F5B9D891EFFB9AA6464D79AFEE8E6A3A72CFFEF4A
+          B060924D13FADEAABEC8F3062141FCE5B9E2FD3DD317E41049706B93F5992425
+          BDB229D9777FEDB57D6B6F88F5ADFBDBAFB881730B3F782A645636C97B1F5AD3
+          C7CA0FF6BDDBA77BA675C65E91F546FF13F5CEE8E603C76D1FBA132F7248AA6C
+          F7D7F65F6DF5912A1B2F888F9CB2BE3F38FDB610ADAA708AEDE99948F8F84FDA
+          91C6C73ED8AFCCFCB50CCA5E5938F6E8DA5EA346244DACDF74191BBB8CB3F47F
+          AD2A1C7FE1127B7473CB91F2D3237933ED4C7CDFBEC4FDE5256ED2247307A485
+          6D5B46A63EEFAFA18512D5820A6F656453B26FD31BBB14F8A24CC92ED1849E6B
+          E8B1E4092321FAC536F35F922D8051911F7CE993DDD1CDAFFFA3B2672CC9FA1C
+          D759BCF72C1F28E4C4FE71E6BEA315D31E0E5D68702B275B144DBFDDAEC01765
+          44B68EE577AF75341883C341FA9193D663DEE4ABCE1AB9F0FE4F75463737FFBD
+          CA9DC22AD4EBF4FE87D6F615A9C5A36EF5EE9365BEF89112131B5E48C9AD5036
+          2E2FE67101CB8E2CA073C6CBED396DEB4E16A01148CEFCD6E567233D6524DBFF
+          FCFBCBE2F37C694348D42B5E991FDCB9CAB9429F60011D032B55CB15B888F323
+          F66632BEF61D05BE31834B631D7617CC698DF83737B5471E031B0F53371CA889
+          3B4BF951AEC130CB27F26DE0C21B8CA3D357E232B2E1A4E398596491C89E1F8D
+          1BCE95C8035FAE71E6F6C3D5B16FB19458A60EF32235106683A98E7292329B57
+          A7B5B73CBD8096FDF3F59D9167443AFCAA6F7C183739303A5F8CF876F3EC580A
+          9390D4726D9C516E1ADC9C012D7BEFBA9E8BE4DE9213C39AAD310FE353723BCA
+          C24D8C6D930A8D87674624DFB398142DE91E044B3BA0653FBAD6B1D13C46255A
+          53259F16CCDCE44406E2DB2FD06EA9EE9DD0B758C40A85395C358B005AF6032B
+          9C9F299586B4DF71163C11BF349696114CAAA94F8505056A98670352DF7854B9
+          A8A625D3391ED31140CBDE52D37F738534A4FD3F3DBA17DAADB16FE918DE9868
+          DA2F09F1904805459AB4CA18C9B434EE92CBE5742CA0657FBD6AF0CBF2B22ABF
+          E930BCD419B750AD9EE50D399F2DCF15D0B23757B8BF59232D98F4D336D3FEF8
+          C5E58B583EF7CBE0B9025AF6F536CFF6950394F47F8498DFEE8B9B55B8C08ECF
+          DC04B4ECCB4CBEDD6B9DA4B2B5FB84ED60FC9442B32A9C7F21D4B9E60468D933
+          9386C1E91C04652720EDD3467304949D8099DA5D173AE0640BF90666CC33CB0E
+          8B35AC2980B2BDD77F477BF055D6E34CF82E478BA41EBEF84AEB08E064BB6F7B
+          9A0EF8F2CEBCAFEE3EC68CB82879DA064D892A5A9A01AE65844519D31120CA8E
+          A6D3325DF7020265030265030265030265030265030265030265030265030265
+          0302650302650302650302650302650302650302650302650302650302650302
+          6503026503026503026503026503026503026503026503026503026503026503
+          0265030265030265030265030265030265030265030265030265030265030265
+          0302650302650302650302650302650302650302650302650302650302650302
+          650302650302650302650302650302650302B46CC8A06C40A06C40A06C408090
+          8D2809CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA06
+          04CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA
+          0604CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA0604
+          CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA06
+          04CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA
+          0604CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA0604
+          CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA06
+          04CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA0604CA
+          0604CA0604CA0604CA0604CA0604CA0604CA0604CA06C43F0177A1F3EBFA099C
+          F20000000049454E44AE426082}
+        Stretch = True
+        Visible = False
+      end
       object WelcomeLabel1: TNewStaticText
       object WelcomeLabel1: TNewStaticText
         Left = 176
         Left = 176
         Top = 16
         Top = 16
@@ -1184,7 +1340,7 @@ object WizardForm: TWizardForm
         Height = 58
         Height = 58
         Anchors = [akLeft, akTop, akRight]
         Anchors = [akLeft, akTop, akRight]
         BevelOuter = bvNone
         BevelOuter = bvNone
-        Color = clWindow
+        ParentColor = True
         TabOrder = 1
         TabOrder = 1
         DesignSize = (
         DesignSize = (
           497
           497
@@ -1197,43 +1353,157 @@ object WizardForm: TWizardForm
           Anchors = [akTop, akRight]
           Anchors = [akTop, akRight]
           Picture.Data = {
           Picture.Data = {
             0954506E67496D61676589504E470D0A1A0A0000000D49484452000000370000
             0954506E67496D61676589504E470D0A1A0A0000000D49484452000000370000
-            003708030000009F052274000000017352474200AECE1CE90000000467414D41
-            0000B18F0BFC6105000001D7504C5445FFFFFFFAE7D6F1AE76F8DAC1EFA464F7
-            D3B4EEA05EFEFDFBF6CBA7EE9D58FEFCFAEFA364F4C39AED9952FEFBF9F2B684
-            F7D0AFE4F0F890C4E391C4E4A4CEE8FEFEFEFAE6D5EC9043F8DAC0F3BB8DED94
-            4CFDF3ECEFA160F1B0799CCAE62289C8228AC886BEE1F8D8BEEA8733F5C8A2F2
-            B47FEC9145FAE5D4EC9246EEA05FFEFBF8FAFCFCFDFDFDFCFCFC8FC3E3228AC9
-            86BFE1F5C79FEB852FF0AC72EB8F40F7D2B3EA8937EC944AFEFEFD82BBDF238A
-            C987BFE1EA842FEFA669EE9E5AEB8A38EA8630EB8B3BFBEADB8FC2E2FBFCFC81
-            BBDF88C0E1EB8732F9DCC32289C9F7D2B2F5C9A4F4C196F3B988F0A86BEB8B39
-            F2B480F3BD8FF5C59DF6CDABF8D6B9F9DEC8FDF7F180BADF89C0E2EB8D3BEA89
-            35ED9951EFA15F7FBADE8AC0E2FDF6F0FBEDE1FAE5D3F2B683EB8E3FFBE9DAFC
-            F1E8FEFAF78AC1E2FAE4D2EB8B3AF1AD757DB9DE8BC1E2FCF0E7EC9144EB8C3B
-            F9DDC6F8DBC2F1AD73F4C0947DB8DE8DC2E2FDF9F5EE9B56EC954BFBEADCF4BE
-            91EA85317CB8DEFEFDFCF0AA6FFDF4ECF2B37EFCF1E7FAE2CE8EC2E23493CDF1
-            AF78F3BB8CFDF8F4F9E0CAED974FFCEFE490C3E3238AC8F6D0AFF4C399EA8632
-            FBEDE0F9DFC9F6CAA6EB8D3EFCF0E5F7D1B1FCFDFE64ADD9D8EAF5F8FBFC90C3
-            E259A7D658A7D6976A4558000000097048597300000EC300000EC301C76FA864
-            0000023B4944415478DAED955F48145118C5BFB3195B52B622B377B6720343B6
-            C8AC5516F62522AD207A0BEAD5D7A82C7A11A4D422B08528A296A27A3302699F
-            9308AD087A8B5628F641D6226A4B19849642CBFE8CDF9D3F8BE9CCB8CE4B44FB
-            71B9C3CCE577CFB9E75EEE80FC15FE2A07FCF6C5ADC04F5FDC4ACC2E930B7E97
-            FD2ACC186FD5D36572C1AA699D1F6BF085FB1AE0732DA083F85B009A975E1898
-            208AE023D106E09B16B506A007DE7AAEAF01C85323C6280620B74DCAE9922A86
-            50D03C388A63FCC756BC48001F0AC9AF54E2D603CFBD38252458698CE51E9342
-            C21A0AE7D943EC91D73E54CF3673900A1EDA1309436FAD8AAA5F59CD81836861
-            A5D1F89346E6EA1FECA88751F7156170A4D6BD8F0E3A70ADB9E6864F7F1C94E8
-            C85E0C4F28AAF459432422CF760F38FB4CCA1847592F5ED808DC36BE35993EB9
-            5723E3DB6FB9ADEFE8CBA9FDAF62D96446AE4521231A8B2335966D493B739D2C
-            78279EC0D33D97CD48AC7D3038889D9923979CB82EC62EB6AEDEF2BA0DD9214E
-            C43E47727DB244F2EE7CD01EEFC19BCDE7E9DCF0BE3E0A75D4F5CA282DBD75A4
-            68B21D4666577A111739712F47D43F74B09B28057429AAC9756084DAED967BB7
-            900BF6A7641A57709A13D1AEE294DC838515CE2FE2ACBA864E4E7F92A768B27C
-            CE6F81A21B97684F4962924A7996C7A9C51927834BFA4CE3B84CD29CBE7CBD1B
-            C7F8A0F8D0BB099C15B47CBD036D033AF9E0369DB94E1EE5EAD3AF5EC567C567
-            C5E77FE4F3D0205FF1E6EF47D1EC67A99DBCE0E6939628B7FBBAFCFA57B83987
-            B69D473A0117C30000000049454E44AE426082}
+            00370806000000A8DBD246000000017352474200AECE1CE90000000467414D41
+            0000B18F0BFC6105000000097048597300000EC300000EC301C76FA864000000
+            1874455874536F667477617265005061696E742E4E455420352E312E381B69EA
+            A8000000B66558496649492A000800000005001A010500010000004A0000001B
+            010500010000005200000028010300010000000200000031010200100000005A
+            00000069870400010000006A0000000000000060000000010000006000000001
+            0000005061696E742E4E455420352E312E380003000090070004000000303233
+            3001A00300010000000100000005A00400010000009400000000000000020001
+            000200040000005239380002000700040000003031303000000000AB80211353
+            9E3828000007654944415478DAED99094C944714C7DF7C7BB00B0BCB7DA3EB81
+            8A58AC82E27D1595D6466C4B15AD68C0461BC4AB8A45AD152B5AEF8A89A66A6B
+            D17AB4464DEB5153E315B546D378342516D36A520E0FF00695E5F8A6FF597775
+            31C821A0EE8649DECE9BF9E69BF77EF3DECECC6619D97161AFDA8126B8970517
+            DFC59D560E0BECC4189BC9391F69989F450F4AE557CDD1307033FA7B53EA40BF
+            21503F05DC5B3609D7CA436DAA4BCB39E5DE2B7BD23F3FDA8F927A7B7D84C825
+            01AEA7359C5AC128D05565D28B8D32151497BF7E7002ECF4B476425542CAD37E
+            BB466B4F14124763C9D0001AD7CD7322D404C04558E0BC744AFA3EAE197535E8
+            C4ACAAF3C5EE6523FFEA58BD756EAEE472BA77EC07921FDD7F69704A44E720EC
+            4FE7C4CF6F3F7B8B527EB94A1B4735A7E810FDE7181607B80EBD32B249AD9468
+            5B7C73F275513B3062AB38B1337BA4DE990B95630D183316F3106A12B5098673
+            6B7337D05A579A97CDAF6F486E50C02AE182F42A3A9B120267A8331CDA076726
+            A07BEF89CB4526906E06DD72B818031F83D79C2CA0C4484FD2AA241F8CDF8129
+            73C94117FF67C7397CC195C085FFDD2D99550B3F56C0C6CCD2FC4B009C08C0A2
+            C6831325B9B727CD8BF617036240B90329948A087E6D7A89B16F510D86434124
+            A220B108446C37FA7248A18E721C30B5A42C3476A08B562D164685F10C3567E6
+            D059F48C535729E3F77C6E7E2E166CA65100AE6F9808B2EA1E64BC1F4823C3DD
+            45234522B644A40F9C980C5FB6E3711F78E98DBE78B4BF41FB3A9EF550B78DBA
+            E11CB32884291D4EA2CFDD02521D5C42B80FCB3C5720BA57E0718A31EF6FBABE
+            6152BD01AB3D0AC4EEB72BB18548430486ADC7E071F0EC2074105308641D641A
+            A4088EF502689666E852D2850EEA80BEF6103701080980C442BCADE75F2DE020
+            FFCE88A0F4A3B99479F686E85E06FCCF8C7997A8BE295A094E1CD0BECE4AD239
+            28C845A3206FEC809E90CE818E26562CF601C800EBD54755068941D781729953
+            897F2479B5082549EB4A4CE342CCD195146ECD48E1DEDC932954229A6D9F8DDC
+            95942E4C467A03906F3A5720E65C0A0BA9F54DD14A70850BC3C4CD23C0BCDA6E
+            56626937C7F30ECFC089A5FD03720772DB5C5BEBB749A939E7F44EDA1D4D6874
+            02DA1BAB82137302902F3892CB369F37A5280029B53E295A09EEE6A2B09DE832
+            5801B9D08BDD3F8DD6909CCB4BB53DC7EF75EC33311AED5F2D832C6979196969
+            29E290F8F2700E0150341703723676D1174AD1CA915B14F6C482E96C222EA1E5
+            4A9CB9A32980C7A17FC23391BB89463C1A7978E30E1791E2F4C8B47748B8ADA8
+            34A4F46A458E513349E5D77E0D5E4D7A5EE42CFD224501C8375F28149D8B21B3
+            4B0078A38EE760253827B5443EE6EF9C5E23E1D6A1A2FEAD9D282EDC438CEC8A
+            5DE5088689FB5509C419720BBE78C2A71D90B8F20ACE1F45265350C7BEC4B47A
+            622A2D83A84852BA61B5C663EC3CBCA3A809CE92A2698773D8D60B85A2FB2B3C
+            9C63CCCFAE538A569B7206DC54F68F6F898D451D049BA7D1E5082323E0682AF4
+            7E303A04FD8990582ECBE988F45CA741B348131E371C7D6922EA18A383EE64F6
+            BBCAA3A02A38A18B044A3B94435B2E14886C5D28E62FADC32EFA5C3837AD447B
+            C6B7A6763E1A710E9C109182B9A1A82FC2FE2ED4EFA1FD26EA2C4C924EE22710
+            F144A56FE866E7D85592A4F3FA911E6FFFCF2D557DE79E2D82CA0C482640CEE7
+            9A22B82E89B8F141DDE1D40AA2ADF106EA1BECAC909824403C30E907A80BC4F7
+            412149DFD1E38BB3A142E63918848958023E56C299A1EA90E813BAE8394E92C6
+            F938C674AAE9109FD233E0E9A5D3FA026A95A2484F76FB619988A62945AFAE1E
+            4BA580AC335C4B71719EDA9698C47025223FC83859E625B3F65FA5416D5C28AA
+            9D8BB8494C834DBDE6EDB42205C964BCB08BCAAF5DEC0F77D6CAC486E806A55E
+            D1868F10D1DD551DDCEA53F9A6EDCB1CA71AF5C7D94A527EC6987AC12901178F
+            BCC87C881F7509DB73E9C83F45B465B4810687E8E7C2D417B0A3D6276CE34ADF
+            F6B17251E1EE078797C9A5D98782F11B2650D365F451A7A819BD30DD716AA062
+            4963D8955E3872E266B2758CC194F0A515324DFF399FB20B8C8F0DE0BE392AC2
+            631254B1F379BA7EB20F3790C02C18CCE2C6E24463D6FE871577F3481316434A
+            EFE00CF44F7A5EE4EAAA5BD2B85E91ABAE885FE2137B7B8FC69B69D8E25BBB25
+            1F24C9C93D0FF6FD61FF1C86A4432F843E1C7AB265976C4838A852DEAAF88687
+            9B3BD097A6F4F779176A1AA9B411EE938FA870508BAD4C5FD7B9EA5A2C69D9F0
+            916312A9FDDBD0C850252DEFABC01D93FA491E2D36B97EBCD385498A5B585C45
+            75ABFE5A478EA91DC9907E8C7CA422C568CDD98A61018FC82B2C8A542DBA7F88
+            C73F3576D41A3572163807A57460F81B9E6B9322FD8A7D9CD5E210171B8BBEA6
+            55B789C8093F27F7F0A7C9DDFD9E18AF8D63360187224FE929E0FC6BFB6A8395
+            464F4BBB8E9C5DC351535ADA68E4EC1A8E9AD2D2462367D770D49496361A39BB
+            86A3A6B4B4D1C8D9351C35A5A58D46CEAEE1A8292D6D3472C2CFC820678A0CD4
+            3DFD47C6EC4155FFD03CD16B7A5E0BFD4C6E119DCEB9DFB86959DB771AB134CE
+            7F05B6549AE06CB5D835DCFF41CF90A123E252D40000000049454E44AE426082}
+          Stretch = True
+        end
+        object InnerImageDark: TImage
+          Left = 414
+          Top = 3
+          Width = 55
+          Height = 55
+          Anchors = [akTop, akRight]
+          Picture.Data = {
+            0954506E67496D61676589504E470D0A1A0A0000000D49484452000000370000
+            00370806000000A8DBD246000000017352474200AECE1CE90000000467414D41
+            0000B18F0BFC6105000000097048597300000EC300000EC301C76FA864000000
+            1874455874536F667477617265005061696E742E4E455420352E312E381B69EA
+            A8000000B66558496649492A000800000005001A010500010000004A0000001B
+            010500010000005200000028010300010000000200000031010200100000005A
+            00000069870400010000006A0000000000000060000000010000006000000001
+            0000005061696E742E4E455420352E312E380003000090070004000000303233
+            3001A00300010000000100000005A00400010000009400000000000000020001
+            000200040000005239380002000700040000003031303000000000AB80211353
+            9E3828000007714944415478DAED5909709345147EFBA7092D49539AA6698142
+            6329D2324C2B82CA288728481505E59016880E650667003944A08895E2002A2D
+            2ACE88E089CA218C1CA252611C7404471D0566B0220EA0E58A4DDA94A3E99134
+            F9D76FD3A4A6D813522499EEE465DFDBDD7FF77DFBBD7FF765C228840BFBBF1D
+            E80077A3C099EED0D1AB8F26F4678C2DE29C6719971751A553FEBF710406DCB3
+            C30D9433B2EB68A8CF00DCFD4109AE578CCA533B5D9CCE5DAEAD6F5F9ED19566
+            0E899D02E66602DC3DFEE0540A46095D941EDDEE90C96A77DD7CE004B01FE7A7
+            08350CE2CADBF737AD3B584A1CC62B63BAD3F441FA5950A701DC401FB8584D18
+            7D90D993EE346AC4ACCAA3D5B1B599A70635BD32E7FFAA6E375D29DC4072E5A5
+            1B062E0CECEC870B0B38F1A35B0FDB68E167667A7F722265A4463D8F619900D7
+            6FF0DA13A40A93688B2991E2B5AA4E8CD8EB9CD84FBB23466C5C193DDB88E79F
+            C43CC08256C6BCB8B8FF7216D81B9C678AB8B5E08980026C145C8F28251D5E98
+            0A67E87638F405167F0ACD9F1F3C5DE10132C8A829808B63E163EF370F5929FB
+            2E3D4528A5388CDF8E29CF55BA98A9E0D260BE2FE9C9950EB57E492BFC588335
+            1639CFFCC6ADF95349AEBADC7EE044993D444FCB32BA89016381723B6232070C
+            BEE67988B177518D82433D3CE125B181606C27DACED6CA3462DB99E89AAF6DB1
+            232597436C8C12E3196ACEBCD4F9744BEA83549292C1BDFD05F5000B4C016190
+            35D7B1765C02650DD00963A144EC15C0D80007E6C097ADE81E0A2F0D6833C15E
+            0FBB047D77FF62EB6C79E7B43ED5C5A54368D3F98034074E7FEA5B664BBE576C
+            D31A742F7414FF4A8108D166AF0271FAEDC8BE45842188616F63F07478B61F3A
+            10532A6403643EA402FE0E8673456B7F8FA1639735FDD0D617122D0042BA4326
+            400CFEF35BFA3E4496940C4ADB3597CC69E3A8ACD730D19C8FB9168341B2E64F
+            41885E090C387141C7478691A69382B4E10A32E004D4436E4FE8ECC18ACD2E84
+            DCE7BFFBA86A2163D154E89239FD6051919D7726BB4BA24A4805C45AA3244BB5
+            52EF2626D8EC733573E9BBE63271C40020078362CED5909CEB0DD106E04A57A6
+            89CCA3BB77B7A3FDC46727A2BFDF55E02A60FE0CB90829F7D6FE7A79B58B8E6C
+            FC33E6E2CFE59A69B0DF6F0C9C674E7CCC69E399ADD75011A2ABF18EE7388B8B
+            AE39441B802B5B95F6299A8C7E80B4746DF9A7C31F24E7F2EA3DE7A33EDF7D3E
+            3A03F65EDFA0FAB0DC39C7CF2389CCE908D1A4A1C27A19FBF01CAE09AA3B45DB
+            16A20D995B9556A770CF89888A4BB0BA10673A9802F074B43F75157365304C30
+            CEE3898B5C30C6A95A4CED86E190195DA852D296621D9DADEAF4261E9DD92473
+            BE39A19BD3C773CF3BC8B91720DEC136866803706A954471DE772E2A5C42D6A1
+            A4E1C96ACA1C102346DE8953E5008689FCAA061209B1C1173D16DF0EC974B939
+            5F7F22924A65ADE77D73B81973C89212AF62341C9E814996E119454BE07C217A
+            217D222B4F1A2C42F425742DF530D886106D36E48CC854BE9C91848345D5036B
+            FE88A6CEF0601268CD818EB39B8F467B36640297E515603A7713183A50A27D1C
+            6D7982758CD140577BFD6EF42A68149C27A591D885F409644B120731ADC457AE
+            535C13F9A6565DF44D828B8E9068CF8C644A890B17F7C041C114D61B83FA38D6
+            DF81FA31D8B7A12EC2242B48FC04229E5D6C577DF4C61F06E99253F109D51DFF
+            4D9646DFB9FF7888B04E9F2800920720E7B922442DABB38857DBDB0E4EA520DA
+            6C32D2B0DE910A894902480C261D8FDA2A63431592F41ED525CE46B7CCCF6210
+            2662D3F0F52AFAC7FC54A63EF8F15F3A758DACF80E63FAB77489C79FF8AA3E14
+            99D7A7863AE300C75C2A8D687E095F4B4BF21E2111A66D06972412E7797D4454
+            2087A4AE90E9B2CC6B967C69A6076ED5D28814ADC824E6C3C7A8B74FEA2AC465
+            3FCC60A75B348EE1F0795DAD9B8FDE5AACFBF3DB52AD60774773E0C05CC38CBA
+            059DD765DDD2DFD7092E0CE04CD8B68D55F851376DEB393A70B282364D35D2A8
+            D4A85C2CF502D651BDF86B577EA64A35A18BD2BD735262B93C20BAAAB742A284
+            7DE6C86FB69DD58958FA8E02547C618C75A592E563AE0D9CC84C363F61F4C486
+            D32DD382DD17E884D5E1E97B03F9E6E481314F435D863DD42F3EDA8DCA9CCA22
+            AC58141126670F8AA9AC8A0DAFA543A59164AE56AD85234F37C55C5B755F185F
+            1773CD15F14B7CD610C3543C99E7922979C19104A4588AF358BF1BD63F82212B
+            A097427F1CFA6CDF291948705025F3B287030F2E77643CCD1D1EF730D4BC1A37
+            1B38EF708212F7991576545BE76A6BF18565E099435AA44AEC4B59290A2A188A
+            1C13F79CB92AECC3DC63DDB478DB6DD85C4573BB7E5333C7C2D5D4F3AD22D2BB
+            6C8A472E7DE1EE63F99E8E59887EBB1C3E11EFDEB6F666AD5D99F381936457A1
+            AEF88775863FF6DB953557C4252E52AAA896763D2898137EC6FD5E4886E37BEB
+            176F8D6341010E458E17E02037BAB47B58863473210D8E3AC23248990B6970D4
+            119641CA5C4883A38EB00C52E6421A1C758465903217D2E0A8232C8394B99006
+            471D6119A4CC093FD5A527495D76AAFE5F188F034DFE4353A7B7D4DF1ADDAE4F
+            2648FB86656B9F69C7D23EFF150453E90017AC25A4C1FD0312C399A1223ED74E
+            0000000049454E44AE426082}
           Stretch = True
           Stretch = True
+          Visible = False
         end
         end
         object PageNameLabel: TNewStaticText
         object PageNameLabel: TNewStaticText
           Left = 24
           Left = 24
@@ -1260,8 +1530,6 @@ object WizardForm: TWizardForm
       end
       end
     end
     end
     object FinishedPage: TNewNotebookPage
     object FinishedPage: TNewNotebookPage
-      Color = clWindow
-      ParentColor = False
       DesignSize = (
       DesignSize = (
         496
         496
         314)
         314)

+ 9 - 2
Projects/Src/IDE.Wizard.WizardForm.pas

@@ -140,6 +140,8 @@ type
     AppRegistryMinVerCheck: TCheckBox;
     AppRegistryMinVerCheck: TCheckBox;
     AppRegistryMinVerEdit: TEdit;
     AppRegistryMinVerEdit: TEdit;
     AppRegistryMinVerDocImage: TImage;
     AppRegistryMinVerDocImage: TImage;
+    WelcomeImageDark: TImage;
+    InnerImageDark: TImage;
     procedure FormCreate(Sender: TObject);
     procedure FormCreate(Sender: TObject);
     procedure FormShow(Sender: TObject);
     procedure FormShow(Sender: TObject);
     procedure FormCloseQuery(Sender: TObject; var CanClose: Boolean);
     procedure FormCloseQuery(Sender: TObject; var CanClose: Boolean);
@@ -298,6 +300,9 @@ begin
   FLanguages.Insert(0, LanguagesDefaultIsl);
   FLanguages.Insert(0, LanguagesDefaultIsl);
 
 
   InitFormFont(Self);
   InitFormFont(Self);
+  if not InitFormTheme(Self) then
+    OuterNotebook.Color := InitFormThemeGetBkColor(True);
+
   if Font.Name = 'Segoe UI' then begin
   if Font.Name = 'Segoe UI' then begin
     { See Setup.WizardForm.pas }
     { See Setup.WizardForm.pas }
     for I := 0 to OuterNotebook.PageCount-1 do
     for I := 0 to OuterNotebook.PageCount-1 do
@@ -309,8 +314,6 @@ begin
   if FontExists('Verdana') then
   if FontExists('Verdana') then
     WelcomeLabel1.Font.Name := 'Verdana';
     WelcomeLabel1.Font.Name := 'Verdana';
 
 
-  OuterNotebook.Color := clWindow;
-
   MakeBold(PageNameLabel);
   MakeBold(PageNameLabel);
   MakeBold(RequiredLabel1);
   MakeBold(RequiredLabel1);
   MakeBold(AppNameLabel);
   MakeBold(AppNameLabel);
@@ -324,6 +327,10 @@ begin
   MakeBold(PrivilegesRequiredLabel);
   MakeBold(PrivilegesRequiredLabel);
   MakeBold(LanguagesLabel);
   MakeBold(LanguagesLabel);
 
 
+  if InitFormThemeIsDark then begin
+    WelcomeImage.Picture := WelcomeImageDark.Picture;
+    InnerImage.Picture := InnerImageDark.Picture;
+  end;
   FinishedImage.Picture := WelcomeImage.Picture;
   FinishedImage.Picture := WelcomeImage.Picture;
 
 
   RequiredLabel2.Left := RequiredLabel1.Left + RequiredLabel1.Width;
   RequiredLabel2.Left := RequiredLabel1.Left + RequiredLabel1.Width;

+ 7 - 2
Projects/Src/Shared.TaskDialogFunc.pas

@@ -2,7 +2,7 @@ unit Shared.TaskDialogFunc;
 
 
 {
 {
   Inno Setup
   Inno Setup
-  Copyright (C) 1997-2020 Jordan Russell
+  Copyright (C) 1997-2025 Jordan Russell
   Portions by Martijn Laan
   Portions by Martijn Laan
   For conditions of distribution and use, see LICENSE.TXT.
   For conditions of distribution and use, see LICENSE.TXT.
 
 
@@ -19,7 +19,7 @@ function TaskDialogMsgBox(const Icon, Instruction, Text, Caption: String; const
 implementation
 implementation
 
 
 uses
 uses
-  Classes, StrUtils, Math, Forms, Dialogs, SysUtils,
+  Classes, StrUtils, Math, Forms, Dialogs, SysUtils, Themes,
   Commctrl, Shared.CommonFunc, {$IFDEF SETUPPROJ} Setup.InstFunc, {$ENDIF} PathFunc;
   Commctrl, Shared.CommonFunc, {$IFDEF SETUPPROJ} Setup.InstFunc, {$ENDIF} PathFunc;
 
 
 var
 var
@@ -81,9 +81,14 @@ begin
       TriggerMessageBoxCallbackFunc(TriggerMessageBoxCallbackFuncFlags, False);
       TriggerMessageBoxCallbackFunc(TriggerMessageBoxCallbackFuncFlags, False);
       ActiveWindow := GetActiveWindow;
       ActiveWindow := GetActiveWindow;
       WindowList := DisableTaskWindows(Config.hwndParent);
       WindowList := DisableTaskWindows(Config.hwndParent);
+      { Temporarily clear SystemHooks to stop it from breaking the title bar. Does not make it dark.
+        Also see BrowseFunc's NewGetOpenOrSaveFileName. }
+      const SaveHooks = TStyleManager.SystemHooks;
+      TStyleManager.SystemHooks := [];
       try
       try
         Result := TaskDialogIndirectFunc(Config, @ModalResult, nil, pfVerificationFlagChecked) = S_OK;
         Result := TaskDialogIndirectFunc(Config, @ModalResult, nil, pfVerificationFlagChecked) = S_OK;
       finally
       finally
+        TStyleManager.SystemHooks := SaveHooks;
         EnableTaskWindows(WindowList);
         EnableTaskWindows(WindowList);
         SetActiveWindow(ActiveWindow);
         SetActiveWindow(ActiveWindow);
         TriggerMessageBoxCallbackFunc(TriggerMessageBoxCallbackFuncFlags, True);
         TriggerMessageBoxCallbackFunc(TriggerMessageBoxCallbackFuncFlags, True);

+ 1 - 1
whatsnew.htm

@@ -199,7 +199,7 @@ Source: "https://jrsoftware.org/download.php/iscrypt.dll?dontcount=1"; DestName:
     <ul>
     <ul>
       <li>The <i>Find in Files</i> result list will now update its line numbers when you add or delete lines.</li>
       <li>The <i>Find in Files</i> result list will now update its line numbers when you add or delete lines.</li>
       <li>The <i>Highlight occurrences of current word</i> option (which is disabled by default) no longer highlights a section's directive names, parameter names, or Pascal keywords. The <i>Highlight occurrences of current selection</i> option (which is enabled by default) still does.</li>
       <li>The <i>Highlight occurrences of current word</i> option (which is disabled by default) no longer highlights a section's directive names, parameter names, or Pascal keywords. The <i>Highlight occurrences of current selection</i> option (which is enabled by default) still does.</li>
-      <li>Added dark mode support to the status bar on all versions of Windows.</li>
+      <li>Improved dark mode support.</li>
     </ul>
     </ul>
   </li>
   </li>
   <li><tt>[Files]</tt> section parameter <tt>Excludes</tt> can now be combined with the <tt>external</tt> flag.</li>
   <li><tt>[Files]</tt> section parameter <tt>Excludes</tt> can now be combined with the <tt>external</tt> flag.</li>