2017-12-27 1026 views
0

我想從xib文件加載視圖。我期望做的事情對我來說似乎很簡單,但由於某種原因,這比我想象的要困難得多。我只是有一個自定義視圖(帶有標籤,按鈕和表格),我想在同一個窗口中多次重複使用(在堆棧視圖中)。這裏是我的代碼爲自定義視圖加載視圖從XIB和獲取零的MacOS應用程序

class PlatformView: NSView { 
    @IBOutlet var testLabel: NSTextField! 

    required init?(coder decoder: NSCoder) { 
     super.init(coder: decoder) 
    } 

    override func awakeFromNib() { 
     super.awakeFromNib() 
     self.testLabel.stringValue = "Init" 
    } 

    override func draw(_ dirtyRect: NSRect) { 
     super.draw(dirtyRect) 

     // Drawing code here. 
    } 
} 

這是我的視圖在視圖主視圖控制器負載。我做了兩次,因爲我需要在堆棧視圖中使用兩個相同的視圖。問題是我得到一個錯誤。這條線路沒有let topLevelObjects = objectArray2?.firstObject as? PlatformView,並導致很多問題。這隻有在我運行應用程序時纔會發生。這是非常隨機的,我不知道它爲什麼會發生。有一個更好的方法嗎?或者我在我的代碼中做錯了什麼?

var objectArray:NSArray? 
guard let nib = NSNib(nibNamed: NSNib.Name(rawValue: "PlatformView"), bundle: nil) else {return} 
if nib.instantiate(withOwner: self, topLevelObjects: &objectArray), let topLevelObjects = objectArray?.firstObject as? PlatformView { 
    self.platformStackView.addArrangedSubview(topLevelObjects) 
    self.firstPlatformView = topLevelObjects 
} 

if nib.instantiate(withOwner: self, topLevelObjects: &objectArray), let topLevelObjects = objectArray?.firstObject as? PlatformView { 
    self.platformStackView.addArrangedSubview(topLevelObjects) 
    self.secondPlatformView = topLevelObjects 
} 
+0

您不能保證firstObject是您正在尋找的PlatformView。可以有多個頂級對象,因此您應該檢查所有您想要的PlatformView。在我的測試中,我在XIB文件中只有一個視圖(具有子視圖),但界面生成器還添加了其他我需要忽略的內容。在我的測試中,頂級對象是我的TestView和NSApplication的一個實例。我不得不檢查數組以獲得第二個項目的TestView。 –

回答

0

的實例化返回頂層對象的XIB文件,其中一些界面生成器本身可能已添加的陣列(見XIB的佈局,如果你真的很好奇吧)。

簡單的方式是搜索返回的topLevelObjects您PlatformView這樣的:

if nib.instantiate(withOwner: self, topLevelObjects: &objectArray) { 
    for object in topLevelObjects { 
     if let platformView = object as? PlatformView { 
      self.platformStackView.addArrangedSubview(platformView) 
      self.firstPlatformView = platformView 
     } 
    } 
} 

但是假設你肯定你的PlatformView是在廈門國際銀行一個更好的解決方案是這樣的:

if nib.instantiate(withOwner: self, topLevelObjects: &objectArray) { 
    if let topLevelObjects = objectArray { 
     let platformView = topLevelObjects.flatMap({ object in return object as? PlatformView }).first! 
     self.platformStackView.addArrangedSubview(platformView) 
     self.firstPlatformView = platformView 
    } 
} 

正如我所說,你必須小心,因爲強制解包的可選項。

+0

在平面圖之前引用了什麼'topLevelObjects?如果你打算把'objectArray'也不起作用。第一種方法似乎最初工作時,我試圖它,但如果有一個更優雅的解決方案,我寧願使用它。 –

+0

對不起。我已經更新了我的示例,因爲我已將可選的objectArray解包爲一個使用的權威數組。 –

相關問題