fix(window): a maximised window comes back maximised after Show desktop
Win+D / Show desktop minimises the window without any tray transition, so the restore took the non-tray branch. FMainForm.Show runs first there and re-applies FMX's own WindowState (normal), discarding the WPF_RESTORETOMAXIMIZED flag Windows had recorded — the app returned in normal size. Read the placement flag BEFORE showing, and re-apply SW_SHOWMAXIMIZED when it was set. The tray path is untouched: it already replays its own captured placement. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
@@ -693,7 +693,8 @@ end;
|
|||||||
procedure TPMBridge.RestoreFromTray;
|
procedure TPMBridge.RestoreFromTray;
|
||||||
var
|
var
|
||||||
LFormHwnd, LAppHwnd: HWND;
|
LFormHwnd, LAppHwnd: HWND;
|
||||||
LWasTrayHidden: Boolean;
|
LWasTrayHidden, LRestoreMax: Boolean;
|
||||||
|
LPlace: TWindowPlacement;
|
||||||
begin
|
begin
|
||||||
// Tray icon stays in the tray — we only show the window again.
|
// Tray icon stays in the tray — we only show the window again.
|
||||||
LFormHwnd := MainFormHWND(FMainForm);
|
LFormHwnd := MainFormHWND(FMainForm);
|
||||||
@@ -713,6 +714,19 @@ begin
|
|||||||
// MinimizeToTray) vs merely taskbar-minimised (Visible but iconic).
|
// MinimizeToTray) vs merely taskbar-minimised (Visible but iconic).
|
||||||
LWasTrayHidden := not FMainForm.Visible;
|
LWasTrayHidden := not FMainForm.Visible;
|
||||||
|
|
||||||
|
// Windows remembers "this minimised window was maximised" in the placement
|
||||||
|
// flags, but FMainForm.Show below re-applies FMX's own WindowState (normal)
|
||||||
|
// and loses it — hence a maximised window coming back normal after Win+D /
|
||||||
|
// Show desktop. Read the flag BEFORE showing so we can re-apply it.
|
||||||
|
LRestoreMax := False;
|
||||||
|
if not LWasTrayHidden then
|
||||||
|
begin
|
||||||
|
FillChar(LPlace, SizeOf(LPlace), 0);
|
||||||
|
LPlace.length := SizeOf(LPlace);
|
||||||
|
LRestoreMax := GetWindowPlacement(LFormHwnd, @LPlace) and
|
||||||
|
((LPlace.flags and WPF_RESTORETOMAXIMIZED) <> 0);
|
||||||
|
end;
|
||||||
|
|
||||||
// Reverse order: show the app proxy first so the taskbar entry comes back,
|
// Reverse order: show the app proxy first so the taskbar entry comes back,
|
||||||
// then show and foreground the form.
|
// then show and foreground the form.
|
||||||
if LAppHwnd <> 0 then
|
if LAppHwnd <> 0 then
|
||||||
@@ -747,6 +761,11 @@ begin
|
|||||||
end;
|
end;
|
||||||
SetWindowPlacement(LFormHwnd, @FSavedPlacement);
|
SetWindowPlacement(LFormHwnd, @FSavedPlacement);
|
||||||
end
|
end
|
||||||
|
else if LRestoreMax then
|
||||||
|
// Was maximised before Windows minimised it (Win+D, taskbar, Show
|
||||||
|
// desktop): come back maximised. SW_RESTORE alone would land on the
|
||||||
|
// pre-maximise "normal" geometry.
|
||||||
|
ShowWindow(LFormHwnd, SW_SHOWMAXIMIZED)
|
||||||
else
|
else
|
||||||
begin
|
begin
|
||||||
ShowWindow(LFormHwnd, SW_SHOW);
|
ShowWindow(LFormHwnd, SW_SHOW);
|
||||||
|
|||||||
Reference in New Issue
Block a user