Skip to content

Commit

Permalink
Ensure all TSetupForms have a taskbar button when main form hasn't be…
Browse files Browse the repository at this point in the history
…en created or is invisible.
  • Loading branch information
jordanrussell authored Jan 11, 2025
1 parent 3d883ce commit 0b99e78
Show file tree
Hide file tree
Showing 3 changed files with 34 additions and 19 deletions.
13 changes: 1 addition & 12 deletions Projects/Src/Setup.NewDiskForm.pas
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@

{
Inno Setup
Copyright (C) 1997-2024 Jordan Russell
Copyright (C) 1997-2025 Jordan Russell
Portions by Martijn Laan
For conditions of distribution and use, see LICENSE.TXT.
Expand Down Expand Up @@ -31,8 +31,6 @@ TNewDiskForm = class(TSetupForm)
Filename: string;
function GetSanitizedPath: String;
procedure CMShowingChanged(var Message: TMessage); message CM_SHOWINGCHANGED;
protected
procedure CreateParams(var Params: TCreateParams); override;
public
{ Public declarations }
constructor Create(AOwner: TComponent); override;
Expand Down Expand Up @@ -91,15 +89,6 @@ constructor TNewDiskForm.Create(AOwner: TComponent);
FlipSizeAndCenterIfNeeded(Assigned(WizardForm), WizardForm, False);
end;

procedure TNewDiskForm.CreateParams(var Params: TCreateParams);
begin
inherited;
{ Make sure the form gets a taskbar button if WizardForm doesn't exist yet
or if it isn't visible because it's a very silent install }
if (WizardForm = nil) or not WizardForm.Visible then
Params.WndParent := 0;
end;

procedure TNewDiskForm.CMShowingChanged(var Message: TMessage);
begin
inherited;
Expand Down
21 changes: 18 additions & 3 deletions Projects/Src/Setup.SetupForm.pas
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@

{
Inno Setup
Copyright (C) 1997-2024 Jordan Russell
Copyright (C) 1997-2025 Jordan Russell
Portions by Martijn Laan
For conditions of distribution and use, see LICENSE.TXT.
Expand All @@ -13,7 +13,7 @@ interface

uses
Windows, SysUtils, Messages, Classes, Graphics, Controls, Forms, Dialogs,
UIStateForm, Shared.SetupMessageIDs;
UIStateForm;

type
TSetupForm = class(TUIStateForm)
Expand Down Expand Up @@ -74,7 +74,7 @@ implementation

uses
Generics.Collections, UITypes,
Shared.CommonFunc, Setup.MainFunc, SetupLdrAndSetup.Messages, BidiUtils;
Shared.CommonFunc, Shared.CommonFunc.Vcl, Setup.MainFunc, BidiUtils;

var
WM_QueryCancelAutoPlay: UINT;
Expand Down Expand Up @@ -379,6 +379,21 @@ procedure TSetupForm.Center;
procedure TSetupForm.CreateParams(var Params: TCreateParams);
begin
inherited;
{ With Application.MainFormOnTaskBar=True, by default, a form won't get a
taskbar button if the main form hasn't been created yet (due to the owner
being an invisible Application.Handle), or if the main form exists but
isn't visible (e.g., because it's a silent install). Force it to have a
taskbar button in those cases by specifying no owner for the window.
(Another method is to set WS_EX_APPWINDOW and leave WndParent set to
Application.Handle, but it doesn't quite work correctly: if the form
displays a message box, and you activate another app's window, clicking on
the form's taskbar button activates the message box again, but the taskbar
button doesn't change to a "selected" state.) }
if (Params.WndParent <> 0) and
(Application.MainFormOnTaskBar or (Params.WndParent <> Application.Handle)) and
not IsWindowOnTaskbar(Params.WndParent) then
Params.WndParent := 0;

if FRightToLeft then
Params.ExStyle := Params.ExStyle or (WS_EX_RTLREADING or WS_EX_LEFTSCROLLBAR or WS_EX_RIGHT);
end;
Expand Down
19 changes: 15 additions & 4 deletions Projects/Src/Shared.CommonFunc.Vcl.pas
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,7 @@ function GetMessageBoxRightToLeft: Boolean;
procedure SetMessageBoxCallbackFunc(const AFunc: TMsgBoxCallbackFunc; const AParam: LongInt);
procedure TriggerMessageBoxCallbackFunc(const Flags: LongInt; const After: Boolean);
function GetOwnerWndForMessageBox: HWND;
function IsWindowOnTaskbar(const Wnd: HWND): Boolean;

implementation

Expand Down Expand Up @@ -241,21 +242,31 @@ function GetOwnerWndForMessageBox: HWND;
if (Result = Application.Handle) and IsIconic(Result) then
Exit(0);

if not IsWindowOnTaskbar(Result) then
Result := 0;
end;

function IsWindowOnTaskbar(const Wnd: HWND): Boolean;
begin
{ Find the "root owner" window, which is what appears in the taskbar.
We avoid GetAncestor(..., GA_ROOTOWNER) because it's broken in the same
way as GetParent(): it stops if it reaches a top-level window that doesn't
have the WS_POPUP style (i.e., a WS_OVERLAPPED window). }
var RootWnd := Result;
var RootWnd := Wnd;
while True do begin
{ Visible WS_EX_APPWINDOW windows have their own taskbar button regardless
of their root owner's visibility }
if (GetWindowLong(RootWnd, GWL_EXSTYLE) and WS_EX_APPWINDOW <> 0) and
(GetWindowLong(RootWnd, GWL_STYLE) and WS_VISIBLE <> 0) then
Exit(True);
var ParentWnd := HWND(GetWindowLongPtr(RootWnd, GWLP_HWNDPARENT));
if ParentWnd = 0 then
Break;
RootWnd := ParentWnd;
end;

if (GetWindowLong(RootWnd, GWL_STYLE) and WS_VISIBLE = 0) or
(GetWindowLong(RootWnd, GWL_EXSTYLE) and WS_EX_TOOLWINDOW <> 0) then
Result := 0;
Result := (GetWindowLong(RootWnd, GWL_STYLE) and WS_VISIBLE <> 0) and
(GetWindowLong(RootWnd, GWL_EXSTYLE) and WS_EX_TOOLWINDOW = 0);
end;

function AppMessageBox(const Text, Caption: PChar; Flags: Longint): Integer;
Expand Down

0 comments on commit 0b99e78

Please sign in to comment.