问题描述
在 SwiftUI App
生命周期中使用 xcode 12.3
和 swift 5.3
来构建 macOS
应用程序,和更改 NSWindow
的外观和行为的最佳方法是什么?
Using xcode 12.3
and swift 5.3
with the SwiftUI App
Life cycle to build a macOS
application, what is the best way to access and change the appearance and behaviour of the NSWindow
?
我真正想要的是 NSWindow
实例.
What I'm really after is the NSWindow
instance.
我添加了 AppDelegate
,但是据我了解, NSWindow
可能为 nil
,因此无法进行修改,并且只需在此处创建一个类似于 AppKit App Delegate
生命周期方法的结果,就会在启动时出现两个窗口.
I've added an AppDelegate
, but as I understand it the NSWindow
is likely to be nil
, so unavailable for modification, and simply creating one here similar to the AppKit App Delegate
Life cycle method results in two windows appearing at launch.
一种解决方案是阻止默认窗口出现,并将其全部留给 applicationDidFinishLaunching
方法,但不确定是否可行或合理.
One solution would be preventing the default window from appearing, and leaving it all to the applicationDidFinishLaunching
method, but not sure this is possible or sensible.
WindowStyle
协议似乎是一个可能的解决方案,但不确定在此阶段如何最好地通过 CustomWindowStyle
来利用它,以及是否提供对 NSWindow
实例进行细粒度控制.
The WindowStyle
protocol looks to be a possible solution, but not sure how best to leverage that with a CustomWindowStyle
at this stage, and whether that provides access to the NSWindow
instance for fine-grained control.
class AppDelegate: NSObject, NSApplicationDelegate {
func applicationDidFinishLaunching(_ aNotification: Notification) {
// In AppKit simply create the NSWindow and modify style.
// In SwiftUI creating an NSWindow and styling results in 2 windows,
// one styled and the other default.
}
}
@main
struct testApp: App {
@NSApplicationDelegateAdaptor(AppDelegate.self) var appDelegate : AppDelegate
var body: some Scene {
WindowGroup {
ContentView()
}
}
}
推荐答案
尽管我并不完全确定这是正确的方法,但要基于以下问题的答案:https://stackoverflow.com/a/63439982/792406 我已经能够访问 NSWindow
实例并修改其外观.
Although I am not entirely sure this is exactly the right approach, based on the answer to this question: https://stackoverflow.com/a/63439982/792406 I have been able to access the NSWindow
instance and modify its appearance.
为了快速参考,这是一个基于 Asperi 使用 xcode 12.3提供的原始代码的工作示例./code>,
swift 5.3
和SwiftUI应用生命周期.
For quick reference, here's a working example based on the original code provided by Asperi using xcode 12.3
, swift 5.3
, and the SwiftUI App Life cycle.
@main
struct testApp: App {
var body: some Scene {
WindowGroup {
ContentView()
}
}
}
class Store {
var window: NSWindow
init(window: NSWindow) {
self.window = window
self.window.isOpaque = false
self.window.backgroundColor = NSColor.clear
}
}
struct ContentView: View {
@State private var window: NSWindow?
var body: some View {
VStack {
Text("Loading...")
if nil != window {
MainView(store: Store(window: window!))
}
}.background(WindowAccessor(window: $window))
}
}
struct MainView: View {
let store: Store
var body: some View {
VStack {
Text("MainView with Window: \(store.window)")
}.frame(width: 400, height: 400)
}
}
struct WindowAccessor: NSViewRepresentable {
@Binding var window: NSWindow?
func makeNSView(context: Context) -> NSView {
let view = NSView()
DispatchQueue.main.async {
self.window = view.window
}
return view
}
func updateNSView(_ nsView: NSView, context: Context) {}
}
这篇关于SwiftUI MacOS NSWindow实例的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!