在“cellForRowAt”中激活 NSLayoutConstraint 直到滚动后才会呈现
Activating NSLayoutConstraint in `cellForRowAt` is not rendering until after scrolling
我需要支持 UITableViewAutomaticDimension
(对于动态高度),但约束有所不同:有些需要处于活动状态,有些则不需要。
我设置故事板 aConstraint
未安装 ,并且安装了 bConstraint
。我 activate/deactivate 他们在 tableView(_:cellForRowAt:)
需要他们。
class ViewController: UIViewController {
@IBOutlet weak var tableView: UITableView! {
didSet {
tableView.estimatedRowHeight = 10
tableView.rowHeight = UITableViewAutomaticDimension
}
}
}
class MyTableViewCell: UITableViewCell {
@IBOutlet var aConstraint: NSLayoutConstraint!
@IBOutlet var bConstraint: NSLayoutConstraint!
}
extension ViewController: UITableViewDataSource {
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return 20
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "MyTableViewCell", for: indexPath) as! MyTableViewCell
cell.contentView.translatesAutoresizingMaskIntoConstraints = false
if indexPath.row % 2 == 0 {
NSLayoutConstraint.deactivate([cell.aConstraint])
NSLayoutConstraint.activate([cell.bConstraint])
} else {
NSLayoutConstraint.deactivate([cell.bConstraint])
NSLayoutConstraint.activate([cell.aConstraint])
}
return cell
}
}
问题
初始可见布局忽略了所有这些activations/deactivations,并且所有单元格都与原始故事板状态相同。
您会注意到只有在滚动后才会应用正确的约束。
尝试次数
我确实尝试了一些但没有成功cell.setNeedsUpdateConstraints(); cell.updateConstraintsIfNeeded(); cell.layoutIfNeeded(); ...
在代码中设置约束的几个问题。
1.
UILabel intrinsicContentSize 将参与自动布局。
自动布局系统将根据 intrinsicContentSize 创建宽度和高度约束。
您在 xib 文件中明确设置了标签的高度约束,导致歧义,然后添加了垂直中心 Y 约束来解决问题。
2
如果您想尝试激活或停用约束,您可能希望使用简单的 UIView 来实现。
3
如果要做各种高度的行,利用intrinsicContentSize,设置UILabel的preferredWidth。
同时安装 'aConstraint' 和 'bConstraint' 的设置故事板,但将较低的优先级放在 'aConstraint' 上以删除警告并且有效:)
我需要支持 UITableViewAutomaticDimension
(对于动态高度),但约束有所不同:有些需要处于活动状态,有些则不需要。
我设置故事板 aConstraint
未安装 ,并且安装了 bConstraint
。我 activate/deactivate 他们在 tableView(_:cellForRowAt:)
需要他们。
class ViewController: UIViewController {
@IBOutlet weak var tableView: UITableView! {
didSet {
tableView.estimatedRowHeight = 10
tableView.rowHeight = UITableViewAutomaticDimension
}
}
}
class MyTableViewCell: UITableViewCell {
@IBOutlet var aConstraint: NSLayoutConstraint!
@IBOutlet var bConstraint: NSLayoutConstraint!
}
extension ViewController: UITableViewDataSource {
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return 20
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "MyTableViewCell", for: indexPath) as! MyTableViewCell
cell.contentView.translatesAutoresizingMaskIntoConstraints = false
if indexPath.row % 2 == 0 {
NSLayoutConstraint.deactivate([cell.aConstraint])
NSLayoutConstraint.activate([cell.bConstraint])
} else {
NSLayoutConstraint.deactivate([cell.bConstraint])
NSLayoutConstraint.activate([cell.aConstraint])
}
return cell
}
}
问题
初始可见布局忽略了所有这些activations/deactivations,并且所有单元格都与原始故事板状态相同。
您会注意到只有在滚动后才会应用正确的约束。
尝试次数
我确实尝试了一些但没有成功cell.setNeedsUpdateConstraints(); cell.updateConstraintsIfNeeded(); cell.layoutIfNeeded(); ...
在代码中设置约束的几个问题。
1.
UILabel intrinsicContentSize 将参与自动布局。 自动布局系统将根据 intrinsicContentSize 创建宽度和高度约束。
您在 xib 文件中明确设置了标签的高度约束,导致歧义,然后添加了垂直中心 Y 约束来解决问题。
2
如果您想尝试激活或停用约束,您可能希望使用简单的 UIView 来实现。
3
如果要做各种高度的行,利用intrinsicContentSize,设置UILabel的preferredWidth。
同时安装 'aConstraint' 和 'bConstraint' 的设置故事板,但将较低的优先级放在 'aConstraint' 上以删除警告并且有效:)