AppCommands.swift (1634B)
1 import Foundation 2 3 // Bridges SwiftUI view state to AppKit without using SwiftUI's Commands API. 4 // One instance per window; AppDelegate resolves the key window's coordinator at dispatch time. 5 @MainActor 6 final class WindowCoordinator { 7 8 // Actions — set by ItemListView on each relevant state change. 9 var newItem: (() -> Void)? 10 var newWindow: (() -> Void)? 11 var copySelectedItem: (() -> Void)? 12 var cutSelectedItem: (() -> Void)? 13 var pasteAfterSelectedItem: (() -> Void)? 14 var deleteSelectedItem: (() -> Void)? 15 var moveSelectedItemUp: (() -> Void)? 16 var moveSelectedItemDown: (() -> Void)? 17 var markSelectedItemCompleted: (() -> Void)? 18 var selectAllItems: (() -> Void)? 19 var clearCompletedItems: (() -> Void)? 20 21 // Enabled state — read by AppDelegate in menuWillOpen and validateMenuItem. 22 var canSelectAllItems = false 23 var canCopySelectedItem = false 24 var canCutSelectedItem = false 25 var canPasteAfterSelectedItem = false 26 var canDeleteSelectedItem = false 27 var canMoveSelectedItemUp = false 28 var canMoveSelectedItemDown = false 29 var canMarkSelectedItemCompleted = false 30 var canClearCompletedItems = false 31 32 // Dynamic titles — read by AppDelegate in validateMenuItem. 33 var markCompletedTitle: String = "Mark as Complete" 34 35 // Focus gating — checked by ClickableNSTextField.acceptsFirstResponder 36 // to prevent AppKit's key-view loop from focusing the wrong text field 37 // during SwiftUI reconciliation. When non-nil, only the text field 38 // matching this target may accept first responder. 39 var allowedFocusTarget: FocusField? 40 }