diff --git a/Kanban/App/WindowAccessor.swift b/Kanban/App/WindowAccessor.swift index d759fd7..10c0a36 100644 --- a/Kanban/App/WindowAccessor.swift +++ b/Kanban/App/WindowAccessor.swift @@ -113,15 +113,20 @@ final class HostedWindowController: NSObject, NSWindowDelegate { applyToolbarIfPossible() } - /// Puts the previous delegate back, and takes the titlebar accessory and toolbar back out. - /// Called when the hosting view goes away; the delegate half is a no-op if something else has - /// since taken the delegate, because stomping a third party's would be the bug this whole file - /// exists to avoid. + /// Puts the previous delegate back and takes the titlebar accessory and toolbar off the window — + /// **without discarding them**. The delegate half is a no-op if something else has since taken + /// the delegate, because stomping a third party's would be the bug this whole file exists to + /// avoid. + /// + /// The held chrome survives a detach deliberately: its lifetime is this controller's, not the + /// sensing view's. SwiftUI dismantles and re-makes the background representable while it moves a + /// scene's content into its final window (observed on macOS 26: install arrives before any + /// window, a dismantle follows, and only *then* does the real window attach) — so chrome + /// discarded here would never reach the window it was made for. `attach` reinstalls whatever is + /// held; a controller that is genuinely done takes its slots down with it. func detach() { removeTitlebarAccessory() - titlebarAccessory = nil removeToolbar() - toolbarController = nil guard let window, window.delegate === self else { return } window.delegate = previousDelegate self.window = nil