SwiftUI窗口组:如何限制窗口数量?

hgqdbh6s  于 2023-04-19  发布在  Swift
关注(0)|答案(4)|浏览(159)

我正在构建一个 * 单 * 窗口应用程序,并希望使用新的 *Swift应用程序生命周期 *。

import SwiftUI

@main
struct SingleWindowApp: App {
    var body: some Scene {
        WindowGroup {
            ContentView()
        }
    }
}

WindowGroup的默认实现允许窗口的多个示例(即,如果你点击⌘N)。我无法找到一个修改器来改变这种行为。

如何将窗口组中的窗口数量限制为1个?

vq8itlhq

vq8itlhq1#

这应该可以做到:

import SwiftUI

@main
struct SingleWindowApp: App {
    var body: some Scene {
        WindowGroup {
            ContentView()
        }.commands {
            CommandGroup(replacing: .newItem, addition: { })
        }
    }
}
insrf1ej

insrf1ej2#

当我面临同样的问题时,但在iPad上,命令修饰符没有效果,我发现了这个:在你的Info.plist中有一个“应用程序场景清单”UIApplicationSceneManifest属性,它是一个字典,作为一个子项“启用多个窗口”UIApplicationSupportsMultipleScenes,默认设置为YES。将此选项设置为NO可以获得所需的效果:)

qxgroojn

qxgroojn3#

每次打开WindowGroup对象时,都可以使用NSViewControllerRepresentable获取视图的NSWindow示例。
然后考虑定义一个外部对象来存储NSWindows的集合。下次打开WindowGroup对象时,如果NSWindow集合已满,请查找一个相应的NSWindow来显示。例如

if windowList.isfull {
let window = windowList.getWindow()
window.makeKey()
window.orderFront(nil)
} else {
  NSWorkspace.shared.open(url)
}

关于如何从WindowGroup获取NSWindow的示例,您可以考虑开源实现:https://github.com/happycodelucky/SwiftUIWindowBinder

dvtswwa3

dvtswwa34#

以下是如何使用普通SwiftUI代码在主窗口打开时禁用“文件-〉新窗口”,并在主窗口关闭时启用“文件-〉新窗口”。
这段代码可能有一些边缘情况需要改进,但它确实有效。

import SwiftUI

@main
struct MyApp: App {
    @State var isMainWindowOpen = false
    
    var body: some Scene {
        WindowGroup {
            ContentView()
                .onAppear {
                    print("Main window appeared")
                    self.isMainWindowOpen = true
                }
                .onDisappear {
                    print("Main window disappeared")
                    self.isMainWindowOpen = false
                }

        }.commands {
            if isMainWindowOpen {
                CommandGroup(replacing: .newItem) {
                    Button("New Window", action: {})
                        .disabled(true)
                        // This is the same keyboard shortcut as the default New Window option.
                        // We're just doing this so that our disabled dummy option shows
                        // the same shortcut visually.
                        .keyboardShortcut(KeyboardShortcut("n", modifiers: [.command]))
                }
            } else {
                // By doing nothing here, we let the default 
                // "File -> New Window" item display and handle input.
                EmptyCommands()
            }
        }
    }
}

相关问题