2016-10-12 16 views
8

Tôi đang cố tạo ứng dụng macOS mà không có bảng phân cảnh trong Xcode 8 (ổn định) trên macOS Sierra. Tuy nhiên, AppDelegate của tôi thậm chí không được bắt đầu. Dưới đây là đoạn code tôi có:NSApplicationDelegate không hoạt động mà không có Storyboard

import Cocoa 

@NSApplicationMain 
class AppDelegate: NSObject, NSApplicationDelegate { 
    var window: NSWindow! 

    override init() { 
     super.init() 
     print("Init") 
    } 

    func applicationDidFinishLaunching(_ aNotification: Notification) { 
     print("Finished launching") 

     // Create a window 
     window = NSWindow() 

     // Add the view controller 
     let viewController = ViewController() 
     window.contentView?.addSubview(viewController.view) 

     // Show the window 
     window.makeKeyAndOrderFront(nil) 
    } 
} 

Cả init hoặc applicationDidFinishLaunching(_ aNotification: Notification) đang được gọi. Bất kì sự trợ giúp nào đều được đánh giá cao.

+0

Mã có vẻ hoàn toàn phù hợp với tôi ... không có lý do gì không nên bắt đầu hoặc applicationDidFinishLaunching ... –

+0

Tại sao bạn không bỏ chọn Sử dụng bảng phân cảnh khi tạo dự án mới? –

+0

@LeoDabus Vì nó vẫn mang lại cho tôi một tệp XIB. Điều kỳ lạ là nếu tôi loại bỏ tập tin XIB/Storyboard là "Giao diện chính" nhưng giữ nó trong dự án, AppDelegate vẫn được gọi. Tuy nhiên, một khi tôi xóa nó, nó sẽ không được gọi. – Zoyt

Trả lời

10

Bạn cần phải làm một vài điều ở đây

  1. Xóa NSMainStoryboardFile chìa khóa/giá trị từ plist
  2. Tạo một lớp con NSApplication và gán nó vào phím Principal Class (NSPrincipalClass).

assign custom class to principal class

Tên phải có đủ điều kiện với tên module của bạn.

  1. Tạo thủ công đại biểu của bạn trong lớp con NSApplication của bạn và gán nó cho thuộc tính delegate.

Đảm bảo bạn giữ tham chiếu mạnh mẽ với đối tượng đại biểu của mình. Tôi vừa mới sử dụng một số let tại đây.

class GrookApplication: NSApplication { 

    let strongDelegate = AppDelegate() 

    override init() { 
     super.init() 
     self.delegate = strongDelegate 
    } 

    required init?(coder: NSCoder) { 
     fatalError("init(coder:) has not been implemented") 
    } 

} 

ví dụ: một đại biểu đơn giản.

@NSApplicationMain 
class AppDelegate: NSObject, NSApplicationDelegate { 

    override init() { 
     super.init() 
     print("wassup") 
    } 

    func applicationDidFinishLaunching(_ aNotification: Notification) { 
     print("yo! I'm alive") 
    } 

} 
+0

làm thế nào để bạn giữ một tài liệu tham khảo mạnh mẽ? Tôi đã thử điều này và tất cả làm việc ok - cửa sổ đã được hiển thị, nhưng khi tôi đã cố gắng để thiết lập 'styleMask' của cửa sổ để' .title' nó đã cho tôi một ngoại lệ nói 'Xác nhận thất bại trong - [X.XApplication init],/Thư viện/Caches/com.apple.xbs/Nguồn/AppKit/AppKit-1504.82.104/AppKit.subproj/NSApplication.m: 1778 2017-04-08 13: 25: 35.761585 + 0100 X [9073: 1059806] [Chung ] Một ngoại lệ không bị bắt được nâng lên 2017-04-08 13: 25: 35.761601 + 0100 X [9073: 1059806] [Chung] Tạo nhiều ứng dụng'. –

+0

@TylerDurden tham chiếu mạnh mẽ được thực hiện bằng cách sử dụng 'var' hoặc' let'. Nếu bạn không làm điều đó, tham chiếu ủy nhiệm yếu sẽ giải phóng cá thể. tức là 'self.delegate = AppDelegate()' không hoạt động. Đối với câu hỏi khác của bạn mà không nhìn thấy mã của bạn tôi không biết. Tôi nghi ngờ bạn đã cố gắng để làm điều này '[NSApplication sharedApplication] .window' và nó không hoạt động vì lý do. –

0

Trong trường hợp ai đó đang tìm phiên bản Swift (dựa trên câu trả lời @WarrenBurtons).

appdelegate

@NSApplicationMain 
class AppDelegate: NSObject, NSApplicationDelegate { 
    var window: NSWindow? 

    func applicationDidFinishLaunching(_ aNotification: Notification) { 
     // Insert code here to initialize your application 
     window = NSWindow(contentViewController: RootViewController()) 
     window?.makeKeyAndOrderFront(self) 
    } 
} 

class RootViewController: NSViewController { 
    override func loadView() { 
     self.view = NSView() 
     self.view.frame = NSRect(x: 0, y: 0, width: 600, height: 400) 
    } 
} 

NSApplication lớp con

import Cocoa 

class Application: NSApplication { 
    let strongDelegate = AppDelegate() 

    override init() { 
     super.init() 
     self.delegate = strongDelegate 
    } 

    required init?(coder: NSCoder) { 
     fatalError("init(coder:) has not been implemented") 
    } 
} 

nhập Info.plist

<?xml version="1.0" encoding="UTF-8"?> 
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd"> 
<plist version="1.0"> 
<dict> 
    ... 
    <key>NSPrincipalClass</key> 
    <string>$(PRODUCT_MODULE_NAME).Application</string> 
    ... 
</dict> 
</plist> 

Tôi cũng đã tạo ra một ý chính cho điều này, rằng tôi sẽ giữ lên đến dat e cho các phiên bản Xcode/Swift mới. https://gist.github.com/florieger/7ac5e7155f6faf18666f92f7d82f6cbc

Edit: Hãy chắc chắn để xóa các Main.storyboard/MainMenu.xib, nếu không bạn có thể kết thúc với hai Windows trong giao diện người dùng Debugger.

Các vấn đề liên quan