Swift 3 загрузить xib. NSBundle.mainBundle().loadNibNamed вернуть Боол
Я пытался выяснить, как создать пользовательское представление с помощью xib-файлов. В этом вопрос использовать следующий метод.
NSBundle.mainBundle().loadNibNamed("CardView", owner: nil, options: nil)[0] as! UIView
Cocoa имеет тот же метод,однако этот метод изменился в swift 3 на loadNibNamed (_: owner:topLevelObjects:), который возвращает Bool, и предыдущий код создает "тип Bool не имеет членов индекса" error, что очевидно, так как возвращаемый тип Тип bool.
Итак, мой вопрос в том, как загрузить представление из xib-файла в Swift 3
3 ответов
прежде всего метод не был изменен в Swift 3.
loadNibNamed(_:owner:topLevelObjects:)
был представлен в macOS 10.8 и присутствовал во всех версиях Swift. Однако loadNibNamed(nibName:owner:options:)
был сброшен в Swift 3.
подпись метода
func loadNibNamed(_ nibName: String,
owner: Any?,
topLevelObjects: AutoreleasingUnsafeMutablePointer<NSArray>?) -> Bool
Итак, вам нужно создать указатель, чтобы получить массив с видом на возвращение.
var topLevelObjects = NSArray()
if Bundle.main.loadNibNamed("CardView", owner: self, topLevelObjects: &topLevelObjects) {
let views = (topLevelObjects as Array).filter { is NSView }
return views[0] as! NSView
}
Edit: я обновил ответ, чтобы отфильтровать NSView
экземпляр надежно.
на Swift 4 синтаксис слегка изменен и используется first(where
более эффективен:
var topLevelObjects : NSArray?
if Bundle.main.loadNibNamed(assistantNib, owner: self, topLevelObjects: &topLevelObjects) {
return topLevelObjects!.first(where: { is NSView }) as? NSView
}
Swift 4 версия ответы @вадиан это
var topLevelObjects: NSArray?
if Bundle.main.loadNibNamed(NSNib.Name(rawValue: nibName), owner: self, topLevelObjects: &topLevelObjects) {
return topLevelObjects?.first(where: { is NSView } ) as? NSView
}
я написал расширение, которое безопасно и позволяет легко загружать с наконечника:
extension NSView {
class func fromNib<T: NSView>() -> T? {
var viewArray = NSArray()
guard Bundle.main.loadNibNamed(String(describing: T.self), owner: nil, topLevelObjects: &viewArray) else {
return nil
}
return viewArray.first(where: { is T }) as? T
}
}
тогда просто используйте так:
let view: CustomView = .fromNib()
ли CustomView
это NSView
подкласс, а также CustomView.xib
.