#macos #swiftui #window
#macos #свифтуи #окно
Вопрос:
Я могу открыть новое окно, но если я закрою его с помощью кнопки закрытия окна, тогда мое приложение выйдет из строя.
import SwiftUI
struct ContentView: View
{
var body: some View
{
Button(action: {openMyWindow()},
label: {Image(systemName: "paperplane")})
.padding()
}
}
func openMyWindow()
{
var windowRef:NSWindow
windowRef = NSWindow(
contentRect: NSRect(x: 100, y: 100, width: 100, height: 600),
styleMask: [.titled, .closable, .miniaturizable, .resizable, .fullSizeContentView],
backing: .buffered, defer: false)
windowRef.contentView = NSHostingView(rootView: WindowView())
windowRef.makeKeyAndOrderFront(nil)
}
struct WindowView: View
{
var body: some View
{
Text("Hello World")
.padding()
}
}
@main
struct Open_WindowApp: App
{
var body: some Scene
{
WindowGroup
{
ContentView()
}
}
}
Я думаю, мне нужно сохранить свой windowRef активным, но как мне это сделать?
Комментарии:
1. пожалуйста, укажите стек потока сбоев
Ответ №1:
- объявить windowRef вне области
openMyWindow()
- если окно уже существует, выведите его на передний план, не создавайте другое.
- не допускайте освобождения окна при закрытии
windowRef.isReleasedWhenClosed = false
(показано ниже) (документация), ИЛИsomeGlobalWindowController = NSWindowController(window: w)
var windowRef: NSWindow?
func openMyWindow()
{
if let curWindow = windowRef {
curWindow.makeKeyAndOrderFront(nil)
return
}
let w = NSWindow(
contentRect: NSRect(x: 100, y: 100, width: 100, height: 600),
styleMask: [.titled, .closable, .miniaturizable, .resizable, .fullSizeContentView],
backing: .buffered, defer: false)
w.contentView = NSHostingView(rootView: WindowView())
w.makeKeyAndOrderFront(nil)
w.isReleasedWhenClosed = false // <--- important
windowRef = w
}
Ответ №2:
Нам нужно сохранить ссылку на window, попробуйте следующее
struct ContentView: View
{
@State private var windowRef: NSWindow?
var body: some View
{
Button(action: {openMyWindow()},
label: {Image(systemName: "paperplane")})
.padding()
}
func openMyWindow()
{
// handle previously opened window here somehow if needed
guard windowRef == nil else { return }
windowRef = NSWindow(
contentRect: NSRect(x: 100, y: 100, width: 100, height: 600),
styleMask: [.titled, .closable, .miniaturizable, .resizable, .fullSizeContentView],
backing: .buffered, defer: false)
windowRef?.contentView = NSHostingView(rootView: WindowView())
windowRef?.makeKeyAndOrderFront(nil)
}
}
Комментарии:
1. это не компилируется, потому что последние две строки
openMyWindow()
должны развернуть необязательные. как только мы это исправим, он запустится, но только до тех пор, пока вы не нажмете кнопку 2-го раза, затем произойдет сбой (EXC_BAD_ACCESS) в операторе guard