需求分析:
- 标签根据文字长度,自适应
- 标签居中显示
- 扩展 超过内容显示范围,需要换行显示,且保持居中显示
AI实现过程
提问:
回答:
import UIKit
import SnapKit
class DynamicLabelsContainerView: UIView {
private let horizontalSpacing: CGFloat = 8.0
private let verticalSpacing: CGFloat = 4.0
// 初始化方法
override init(frame: CGRect) {
super.init(frame: frame)
}
required init?(coder: NSCoder) {
fatalError("init(coder:) has not been implemented")
}
// 配置容器视图
func configure(with strings: [String]) {
// 先清除所有子视图
self.subviews.forEach { $0.removeFromSuperview() }
var lastLabel: UILabel? = nil
var isFirstLabelInLine = true
for string in strings {
let label = UILabel()
label.text = string
label.backgroundColor = .lightGray // 仅为了可视化,实际使用时可移除
label.numberOfLines = 1
self.addSubview(label)
label.snp.makeConstraints { make in
if let lastLabel = lastLabel {
make.top.equalTo(isFirstLabelInLine ? lastLabel.snp.bottom : lastLabel.snp.top).offset(isFirstLabelInLine ? verticalSpacing : 0)
make.left.equalTo(isFirstLabelInLine ? self.snp.left : lastLabel.snp.right).offset(horizontalSpacing)
} else {
make.top.equalTo(self.snp.top).offset(verticalSpacing)
make.left.equalTo(self.snp.left).offset(horizontalSpacing)
}
// 确保标签不会超出容器视图的宽度
make.right.lessThanOrEqualTo(self.snp.right).offset(-horizontalSpacing)
}
// 使用布局完成回调来决定是否需要换行
label.snp.makeConstraints { make in
make.width.equalTo(label.intrinsicContentSize.width).priority(.high)
}
// 强制立即布局以获取label的frame
self.layoutIfNeeded()
// 检查是否需要换行
if label.frame.maxX > self.bounds.width {
isFirstLabelInLine = true
label.snp.remakeConstraints { make in
make.top.equalTo(lastLabel?.snp.bottom ?? self.snp.top).offset(verticalSpacing)
make.left.equalTo(self.snp.left).offset(horizontalSpacing)
make.width.equalTo(label.intrinsicContentSize.width).priority(.high)
}
} else {
isFirstLabelInLine = false
}
lastLabel = label
}
// 更新容器视图的高度约束以适应所有标签
self.snp.makeConstraints { make in
make.bottom.equalTo(lastLabel?.snp.bottom ?? self.snp.top).offset(verticalSpacing)
}
}
}
验证
问题:
- 超出范围没有换行展示
解决:
将下面这句代码注释
验证:
问题:
- 第二排第二个label的布局有问题
解决问题后的最终代码:
import UIKit
import SnapKit
class DynamicLabelsView: UIView {
private let horizontalSpacing: CGFloat = 8.0
private let verticalSpacing: CGFloat = 4.0
// 初始化方法
override init(frame: CGRect) {
super.init(frame: frame)
}
required init?(coder: NSCoder) {
fatalError("init(coder:) has not been implemented")
}
// 配置容器视图
func configure(with strings: [String]) {
// 先清除所有子视图
self.subviews.forEach { $0.removeFromSuperview() }
var lastLabel: UILabel? = nil
for string in strings {
let label = UILabel()
label.text = string
label.backgroundColor = .lightGray // 仅为了可视化,实际使用时可移除
label.numberOfLines = 1
self.addSubview(label)
label.snp.makeConstraints { make in
if let lastLabel = lastLabel {
make.top.equalTo(lastLabel.snp.top).offset(0)
make.left.equalTo(lastLabel.snp.right).offset(horizontalSpacing)
} else {
make.top.equalTo(self.snp.top).offset(verticalSpacing)
make.left.equalTo(self.snp.left).offset(horizontalSpacing)
}
}
// 使用布局完成回调来决定是否需要换行
label.snp.makeConstraints { make in
make.width.equalTo(label.intrinsicContentSize.width).priority(.high)
}
// 强制立即布局以获取label的frame
self.layoutIfNeeded()
// 检查是否需要换行
if label.frame.maxX > self.bounds.width {
label.snp.remakeConstraints { make in
make.top.equalTo(lastLabel?.snp.bottom ?? self.snp.top).offset(verticalSpacing)
make.left.equalTo(self.snp.left).offset(horizontalSpacing)
make.width.equalTo(label.intrinsicContentSize.width).priority(.high)
}
}
lastLabel = label
}
// 更新容器视图的高度约束以适应所有标签
self.snp.makeConstraints { make in
make.bottom.equalTo(lastLabel?.snp.bottom ?? self.snp.top).offset(verticalSpacing)
}
}
}
效果:
总结
到这里我们通过AI快速实现了动态标签控件的核心部分,只需再稍微调整一下label的样式就能完美实现我们的需求。AI帮我们写了大部分的可用的代码,虽然不能完全采用,但是确实提升了我们的开发效率,代码质量也是很不错的,我们要做的就是根据自己的需求进行修改一下。后面继续在实战中探索如何高效使用AI来帮助我们开发和学习。
感谢您的阅读和参与,HH思无邪愿与您一起在技术的道路上不断探索。如果您喜欢这篇文章,不妨留下您宝贵的赞!如果您对文章有任何疑问或建议,欢迎在评论区留言,我会第一时间处理,您的支持是我前行的动力,愿我们都能成为更好的自己!