IOS 横向屏幕的 SafeAreaLayoutGuide 锚点
IOS SafeAreaLayoutGuide anchor for landscape screen
我一直在关注 Paul Hudsons 的 Hacking Swift 教程,我正在学习项目 6,他以编程方式使用布局约束。我一直只使用 Interface Builder 来完成这类任务,但我很想了解如何以编程方式完成它。
从他的教程中,我们有以下代码将 5 个 UILabel 添加到主控制器的视图。
let label1 = UILabel()
label1.translatesAutoresizingMaskIntoConstraints = false
label1.text = "THESE"
label1.backgroundColor = #colorLiteral(red: 0.5725490451, green: 0, blue: 0.2313725501, alpha: 1)
label1.sizeToFit()
// do the same with label2, label3, label4, label5
view.addSubview(label1)
view.addSubview(label2)
view.addSubview(label3)
view.addSubview(label4)
view.addSubview(label5)
然后我可以手动添加约束:
let dictionary = [
"label1": label1,
"label2": label2,
"label3": label3,
"label4": label4,
"label5": label5
]
let metrics=[ "labelHeight":80]
view.addConstraints(NSLayoutConstraint.constraints(withVisualFormat: "V:|[label1(labelHeight@999)]-[label2(label1)]-[label3(label1)]-[label4(label1)]-[label5(label1)]-(>=10)-|", options: [], metrics: metrics, views: dictionary))
for label in dictionary.keys {
view.addConstraints(NSLayoutConstraint.constraints(withVisualFormat: "H:|[\(label)]|", options: [], metrics:nil, views: dictionary))
}
如您所见,我将第一个标签的高度设置为 80。然后将标签 1 的优先级设置为 999,并使其余标签遵循标签 1 的高度限制。
这在纵向和横向模式下都运行良好。
现在我正在转换代码以使用锚点。
let heightConstraint = label1.heightAnchor.constraint(equalToConstant: 88)
heightConstraint.priority = UILayoutPriority(rawValue: 999)
heightConstraint.isActive = true
for label in [label2, label3, label4, label5] {
label.heightAnchor.constraint(equalTo: label1.heightAnchor, multiplier: 1).isActive = true
}
var previousLabel : UILabel?
for label in [label1, label2, label3, label4, label5] {
label.leadingAnchor.constraint(equalTo: view.safeAreaLayoutGuide.leadingAnchor, constant: 0).isActive = true
label.trailingAnchor.constraint(equalTo: view.safeAreaLayoutGuide.trailingAnchor, constant: 0).isActive = true
if let previousLabel = previousLabel {
label.topAnchor.constraint(equalTo: previousLabel.bottomAnchor, constant: 10).isActive = true
} else {
label.topAnchor.constraint(equalTo: view.safeAreaLayoutGuide.topAnchor, constant: 0).isActive = true
}
previousLabel = label
}
label5.bottomAnchor.constraint(greaterThanOrEqualTo: view.safeAreaLayoutGuide.bottomAnchor, constant: 10.0).isActive = true
我想我在这里遗漏了一些东西,因为
- 当应用处于纵向模式时,它会尝试填满整个屏幕
- 当应用程序处于横向模式时,label5 被切断。
我想我在使用锚点时遗漏了什么?我猜是这样的:
-(>=10)-
但我不确定如何使用锚点模式来做到这一点。如有任何帮助,我们将不胜感激!
对于 label5,您应该将底部约束更改为:
label5.bottomAnchor.constraint(lessThanOrEqualTo: view.safeAreaLayoutGuide.bottomAnchor, constant: -10.0).isActive = true
它应该是一个负数,因为您将其固定到下方的锚点(与之前的锚点相反,您将其固定到当前标签上方的标签)。对于负数,您需要使用 lessThanOrEqualTo
.
对于垂直布局,它也可以正常工作,因为约束是 lessThanOrEqualTo
:
我一直在关注 Paul Hudsons 的 Hacking Swift 教程,我正在学习项目 6,他以编程方式使用布局约束。我一直只使用 Interface Builder 来完成这类任务,但我很想了解如何以编程方式完成它。
从他的教程中,我们有以下代码将 5 个 UILabel 添加到主控制器的视图。
let label1 = UILabel()
label1.translatesAutoresizingMaskIntoConstraints = false
label1.text = "THESE"
label1.backgroundColor = #colorLiteral(red: 0.5725490451, green: 0, blue: 0.2313725501, alpha: 1)
label1.sizeToFit()
// do the same with label2, label3, label4, label5
view.addSubview(label1)
view.addSubview(label2)
view.addSubview(label3)
view.addSubview(label4)
view.addSubview(label5)
然后我可以手动添加约束:
let dictionary = [
"label1": label1,
"label2": label2,
"label3": label3,
"label4": label4,
"label5": label5
]
let metrics=[ "labelHeight":80]
view.addConstraints(NSLayoutConstraint.constraints(withVisualFormat: "V:|[label1(labelHeight@999)]-[label2(label1)]-[label3(label1)]-[label4(label1)]-[label5(label1)]-(>=10)-|", options: [], metrics: metrics, views: dictionary))
for label in dictionary.keys {
view.addConstraints(NSLayoutConstraint.constraints(withVisualFormat: "H:|[\(label)]|", options: [], metrics:nil, views: dictionary))
}
如您所见,我将第一个标签的高度设置为 80。然后将标签 1 的优先级设置为 999,并使其余标签遵循标签 1 的高度限制。
这在纵向和横向模式下都运行良好。
现在我正在转换代码以使用锚点。
let heightConstraint = label1.heightAnchor.constraint(equalToConstant: 88)
heightConstraint.priority = UILayoutPriority(rawValue: 999)
heightConstraint.isActive = true
for label in [label2, label3, label4, label5] {
label.heightAnchor.constraint(equalTo: label1.heightAnchor, multiplier: 1).isActive = true
}
var previousLabel : UILabel?
for label in [label1, label2, label3, label4, label5] {
label.leadingAnchor.constraint(equalTo: view.safeAreaLayoutGuide.leadingAnchor, constant: 0).isActive = true
label.trailingAnchor.constraint(equalTo: view.safeAreaLayoutGuide.trailingAnchor, constant: 0).isActive = true
if let previousLabel = previousLabel {
label.topAnchor.constraint(equalTo: previousLabel.bottomAnchor, constant: 10).isActive = true
} else {
label.topAnchor.constraint(equalTo: view.safeAreaLayoutGuide.topAnchor, constant: 0).isActive = true
}
previousLabel = label
}
label5.bottomAnchor.constraint(greaterThanOrEqualTo: view.safeAreaLayoutGuide.bottomAnchor, constant: 10.0).isActive = true
我想我在这里遗漏了一些东西,因为
- 当应用处于纵向模式时,它会尝试填满整个屏幕
- 当应用程序处于横向模式时,label5 被切断。
我想我在使用锚点时遗漏了什么?我猜是这样的:
-(>=10)-
但我不确定如何使用锚点模式来做到这一点。如有任何帮助,我们将不胜感激!
对于 label5,您应该将底部约束更改为:
label5.bottomAnchor.constraint(lessThanOrEqualTo: view.safeAreaLayoutGuide.bottomAnchor, constant: -10.0).isActive = true
它应该是一个负数,因为您将其固定到下方的锚点(与之前的锚点相反,您将其固定到当前标签上方的标签)。对于负数,您需要使用 lessThanOrEqualTo
.
对于垂直布局,它也可以正常工作,因为约束是 lessThanOrEqualTo
: