Gre*_*reg 2 xib uiview nib ios swift3
问题:为什么UILabel在从XIB以编程方式创建UIView后,在init(代码附加)中没有?(参考下面的代码)这就是该行label1.text = "TBC - It was updated"
引发错误
背景:我想以编程方式创建多个自定义视图,在这种情况下是多个GCDateView.我想使用一个XIB
文件来布局自定义视图与关联类,以编程方式完成自定义,因此我在这里有一个GCDateView.swift和一个GCDateView.xib文件.
除了:作为第2搁置的问题,我注意到我从厦门国际银行文件GCDateView内创建视图不能直接分配是主视图(例如,在初始化结束时,我不能说self = gcDateViewView
).也许我需要一个单独的问题.
从父控制器/视图中:
let dv = GCDateView()
Run Code Online (Sandbox Code Playgroud)
GCDateView:
import UIKit
class GCDateView : UIView {
@IBOutlet weak var label1: UILabel!
func commonInit() {
// Programmtically use XIB file
if self.subviews.count == 0 {
let bundle = Bundle(for: type(of: self))
let nib = UINib(nibName: "GCDateView", bundle: bundle)
let gcDateViewView : UIView = nib.instantiate(withOwner: self, options: nil)[0] as! UIView
gcDateViewView.frame = self.bounds
gcDateViewView.autoresizingMask = [.flexibleWidth, .flexibleHeight]
addSubview(gcDateViewView)
}
**label1.text = "TBC - It was updated" // ** ERROR: label1 was Nil ****
}
override init(frame: CGRect) {
NSLog("GCDateView: Init frame")
super.init(frame: frame)
commonInit()
}
required init?(coder aDecoder: NSCoder) {
NSLog("GCDateView: Init decoder")
super.init(coder: aDecoder)
commonInit()
}
}
Run Code Online (Sandbox Code Playgroud)
IBOutlet
实例未初始化init?(coder aDecoder: NSCoder)
.
该过程在单独的步骤中完成.
有一种方法awakeFromNib
可以保证所有IBOutlet
实例都被初始化:
override func awakeFromNib() {
super.awakeFromNib()
label1.text = "TBC - It was updated" // Won't crash.
}
Run Code Online (Sandbox Code Playgroud)
要解决你的第二个问题(即避免添加另一个自我类型的实例作为自我子视图)我建议创建类方法,GCDateView
通过从xib加载它来创建新实例.
这是更新的代码:
import UIKit
class GCDateView : UIView {
@IBOutlet weak var label1: UILabel!
class func loadFromXIB() -> GCDateView {
let bundle = Bundle(for: type(of: self))
let nib = UINib(nibName: "GCDateView", bundle: bundle)
let gcDateView = nib.instantiate(withOwner: self, options: nil)[0] as! GCDateView
gcDateView.frame = self.bounds
gcDateView.autoresizingMask = [.flexibleWidth, .flexibleHeight]
gcDateView.label1.text = "TBC - It was updated"
return gcDateView
}
}
Run Code Online (Sandbox Code Playgroud)
用法:
let dateView = GCDateView.loadFromXIB()
Run Code Online (Sandbox Code Playgroud)