@@ -80,10 +80,12 @@ extension AppDelegate {
8080 } catch {
8181 windowLogger. error ( " Dock connection failed for ' \( connection. name) ': \( error. localizedDescription) " )
8282
83- for window in NSApp . windows where self . isMainWindow ( window ) {
83+ for window in WindowLifecycleMonitor . shared . windows ( for : connection . id ) {
8484 window. close ( )
8585 }
86- self . openWelcomeWindow ( )
86+ if !NSApp. windows. contains ( where: { self . isMainWindow ( $0) && $0. isVisible } ) {
87+ self . openWelcomeWindow ( )
88+ }
8789 }
8890 }
8991 }
@@ -251,18 +253,27 @@ extension AppDelegate {
251253 // If no code opened this window (pendingId is nil), this is a
252254 // SwiftUI WindowGroup state restoration — not a window we created.
253255 // Hide it (orderOut, not close) to break the close→restore loop.
256+ // Exception: if the window is already part of a tab group, it was
257+ // attached by our addTabbedWindow call — not a restoration orphan.
258+ // Ordering it out would crash NSWindowStackController.
254259 if pendingId == nil && !isAutoReconnecting {
255260 configuredWindows. insert ( windowId)
261+ if let tabbedWindows = window. tabbedWindows, tabbedWindows. count > 1 {
262+ // Already in a tab group — leave it alone
263+ return
264+ }
256265 window. orderOut ( nil )
257266 return
258267 }
259268
260269 let existingIdentifier = NSApp . windows
261270 . first { $0 !== window && isMainWindow ( $0) && $0. isVisible } ?
262271 . tabbingIdentifier
272+ let groupAll = MainActor . assumeIsolated { AppSettingsManager . shared. tabs. groupAllConnectionTabs }
263273 let resolvedIdentifier = TabbingIdentifierResolver . resolve (
264274 pendingConnectionId: pendingId,
265- existingIdentifier: existingIdentifier
275+ existingIdentifier: existingIdentifier,
276+ groupAllConnections: groupAll
266277 )
267278 window. tabbingIdentifier = resolvedIdentifier
268279 configuredWindows. insert ( windowId)
@@ -273,10 +284,25 @@ extension AppDelegate {
273284
274285 // Explicitly attach to existing tab group — automatic tabbing
275286 // doesn't work when tabbingIdentifier is set after window creation.
276- if let existingWindow = NSApp . windows. first ( where: {
277- $0 !== window && isMainWindow ( $0) && $0. isVisible
278- && $0. tabbingIdentifier == resolvedIdentifier
279- } ) {
287+ let matchingWindow : NSWindow ?
288+ if groupAll {
289+ // When grouping all connections, attach to any visible main window
290+ // and normalize all existing windows' tabbingIdentifiers so future
291+ // windows also match (not just the first one found).
292+ let existingMainWindows = NSApp . windows. filter {
293+ $0 !== window && isMainWindow ( $0) && $0. isVisible
294+ }
295+ for existing in existingMainWindows {
296+ existing. tabbingIdentifier = resolvedIdentifier
297+ }
298+ matchingWindow = existingMainWindows. first
299+ } else {
300+ matchingWindow = NSApp . windows. first {
301+ $0 !== window && isMainWindow ( $0) && $0. isVisible
302+ && $0. tabbingIdentifier == resolvedIdentifier
303+ }
304+ }
305+ if let existingWindow = matchingWindow {
280306 let targetWindow = existingWindow. tabbedWindows? . last ?? existingWindow
281307 targetWindow. addTabbedWindow ( window, ordered: . above)
282308 window. makeKeyAndOrderFront ( nil )
@@ -339,18 +365,21 @@ extension AppDelegate {
339365 window. close ( )
340366 }
341367 } catch is CancellationError {
342- for window in NSApp . windows where self . isMainWindow ( window ) {
368+ for window in WindowLifecycleMonitor . shared . windows ( for : connection . id ) {
343369 window. close ( )
344370 }
345- self . openWelcomeWindow ( )
371+ if !NSApp. windows. contains ( where: { self . isMainWindow ( $0) && $0. isVisible } ) {
372+ self . openWelcomeWindow ( )
373+ }
346374 } catch {
347375 windowLogger. error ( " Auto-reconnect failed for ' \( connection. name) ': \( error. localizedDescription) " )
348376
349- for window in NSApp . windows where self . isMainWindow ( window ) {
377+ for window in WindowLifecycleMonitor . shared . windows ( for : connection . id ) {
350378 window. close ( )
351379 }
352-
353- self . openWelcomeWindow ( )
380+ if !NSApp. windows. contains ( where: { self . isMainWindow ( $0) && $0. isVisible } ) {
381+ self . openWelcomeWindow ( )
382+ }
354383 }
355384 }
356385 }
0 commit comments