ios - 将完整的编程自定义视图添加到 ViewController。自动布局问题
问题描述
创建自定义视图时,我真的不明白如何使用布局。
主要问题在这里:
rect.heightAnchor.constraint(equalTo: heightAnchor, multiplier: 0.5),
rect.widthAnchor.constraint(equalTo: widthAnchor, multiplier: 1),
如果我使用乘数,它可以正常工作。但是如果我使用常量:
rect.widthAnchor.constraint(equalToConstant: self.frame.width)
它不起作用。
如何为我的自定义视图 autoLayout 约束使用任何 superView 帧大小?
class MainView: UIView {
lazy var rect: UIView = {
let view = UIView()
view.backgroundColor = .green
view.translatesAutoresizingMaskIntoConstraints = false
return view
}()
override init(frame: CGRect) {
super.init(frame: frame)
backgroundColor = .red
layout()
}
func layout() {
addSubview(rect)
self.translatesAutoresizingMaskIntoConstraints = false
NSLayoutConstraint.activate([
rect.heightAnchor.constraint(equalTo: heightAnchor, multiplier: 0.5),
rect.widthAnchor.constraint(equalTo: widthAnchor, multiplier: 1),
rect.centerYAnchor.constraint(equalTo: centerYAnchor),
rect.centerXAnchor.constraint(equalTo: centerXAnchor)
])
}
required init?(coder: NSCoder) {
fatalError("init(coder:) has not been implemented")
}
}
class ViewController: UIViewController {
let mainView = MainView(frame: .zero)
override func loadView() {
self.view = mainView
}
解决方案
如果我使用乘数,它可以正常工作。但是如果我使用常量:
rect.widthAnchor.constraint(equalToConstant: self.frame.width)
这一定会发生,在您的 viewController 中,您实例化您的asmainView
这
let mainView = MainView(frame: .zero)
将触发frame 为零init
MainView
你在里面调用布局init
override init(frame: CGRect) {
super.init(frame: frame)
backgroundColor = .red
layout()
}
所以你基本上在MainView
框架为时调用布局Zero
此时如果你设置rect.widthAnchor.constraint(equalToConstant: self.frame.width)
那么你本质上说的是rect.widthAnchor.constraint(equalToConstant: 0)
因此宽度设置为零
请仔细阅读声明,在这种情况下,您将矩形宽度锚设置为常数,即 0,因此即使在 UI 周期的未来阶段您MainView
获得适当的宽度,矩形的宽度将始终为零,因为您将其设置为常数0 值。
但是我在 self.view= mainView 之前设置了 mainView.frame = view.frame
不幸的是,对于您的 rect,此语句来晚了一点 :) 在 mainView 的 init 中调用了布局,因此 rects 宽度锚已设置为常量 0。现在尽管您更新 mainView.frame,但您的 rect 永远不会费心更新其宽度,为什么会吗?它的约束已经解析为一个常数值,在这种情况下显然是“ 0 ”:)
rect.widthAnchor.constraint(equalTo: widthAnchor, multiplier: 1)
,为什么这样有效?
在这里你说你的矩形的宽度锚等于你的宽度锚MainView
,你没有将矩形的宽度锚设置为一个常数,而是将它设置为与 MainView 的宽度锚匹配,所以当 MainView 的框架最终设置为适当的值时,您的矩形也将更新其宽度以匹配 MainViews 宽度。
坦率地说multiplier: 1
,在这种情况下没有任何意义,因为您试图匹配矩形的宽度以匹配 MainView 的宽度,如果您希望矩形的宽度与 MainView 的宽度成比例变化(例如 MainView 宽度的 50% 等) ) 只有这样乘数才有意义
自动布局约束只不过是数学方程式,正确理解/可视化它们是获得完美 UI 约束的关键
希望这可以帮助
推荐阅读
- php - 表单中的数据不会传递到 MySQL 数据库
- c# - 将模型中的属性值从控制器传递到视图 - 显示不正确的数据
- python - python调试器在命令行失败时执行完全相同的代码片段
- r - 如何在R中按条件划分数据集
- intellij-idea - 如何在我的 Mac WebStorm 中将 Blisk 配置为默认浏览器?
- azure-cosmosdb - CosmosDB API for Mongo 对待多键唯一索引的方式与 MongoDB 不同
- javascript - 管理没有时区的 moment.js 范围
- mysql - AWS Glue 没有将 id(int) 列复制到 Redshift - 它是空白的
- imgur - 如何使用 API 将 mp4(或其他视频)上传到 Imgur?
- javascript - 在画布上用鼠标绘图。笔划与当前鼠标位置不匹配