我正在尝试将我的 View Controller 内容分解为从 xib 加载的更小的单个 View block 。我这样做是通过将占位符 UIView
对象放入我的 Storyboard View Controller 中,并使用它们添加我在 xib 文件中作为 subview 布置的实际 UIView
子类在构建时。
但是,问题在于 xib 文件中定义的 AutoLayout 约束在我添加 View 时不起作用。
为了说明这个问题,我创建了一个示例项目:ViewController
有一个类型为 CustomColorView
的 colorView
( 的子类>UIView
) 将添加到普通 UIView
占位符。 CustomColorView
类有一个 coloredView
的属性,它应该填充整个空间(由 xib 文件中每一边的 AutoLayout 约束定义)。
NibLoadable
协议(protocol):
public protocol NibLoadable {
static var nibName: String { get }
}
public extension NibLoadable where Self: UIView {
public static var nibName: String {
return String(describing: Self.self)
}
public static var nib: UINib {
let bundle = Bundle(for: Self.self)
return UINib(nibName: Self.nibName, bundle: bundle)
}
func setupFromNib() {
guard let loadedView = Self.nib.instantiate(withOwner: self, options: nil).first as? UIView else { fatalError("Error loading \(self) from nib") }
loadedView.frame = bounds
addSubview(loadedView)
loadedView.translatesAutoresizingMaskIntoConstraints = false
loadedView.leadingAnchor.constraint(equalTo: self.safeAreaLayoutGuide.leadingAnchor, constant: 0).isActive = true
loadedView.topAnchor.constraint(equalTo: self.safeAreaLayoutGuide.topAnchor, constant: 0).isActive = true
loadedView.trailingAnchor.constraint(equalTo: self.safeAreaLayoutGuide.trailingAnchor, constant: 0).isActive = true
loadedView.bottomAnchor.constraint(equalTo: self.safeAreaLayoutGuide.bottomAnchor, constant: 0).isActive = true
}
}
当我将自定义 View 添加到普通 UIView
时,我会假设它应用了 nib 文件中所有已定义的约束,但事实并非如此。两个 View 的 print
结果应该相同,但它们不同(coloredView
仍然具有来自 xib 文件的大小)。
有什么可能出错的想法吗?感谢您的帮助!
整个项目都在 GitHub 上:XibAutoLayoutExample
最佳答案
您的 View 高度正确,请添加 layer.borderColor
和 layer.borderWidth
并检查
func setup() {
print("CustomColorView bounds: \(bounds)")
print("coloredView subview bounds: \(coloredView.bounds)")
self.coloredView.layer.borderColor = UIColor.red.cgColor
self.coloredView.layer.borderWidth = 1
}
此外,如果您在 viewDidAppear
中调用 setup()
将显示正确的值,这是因为 viewDidAppear
在 viewDidLayoutSubviews< 之后执行
因此,当您的 viewController 正确结束其布局时,您的日志会显示正确的值
override func viewDidAppear(_ animated: Bool) {
super.viewDidAppear(animated)
colorView.setup()
}
日志
CustomColorView bounds: (0.0, 0.0, 320.0, 227.0)
coloredView subview bounds: (0.0, 0.0, 320.0, 227.0)
关于ios - 从 Xib 加载的 UIView 不能正确应用 AutoLayout,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48822981/