动态集合视图单元格的顶部对齐方式应该相同
Posted
技术标签:
【中文标题】动态集合视图单元格的顶部对齐方式应该相同【英文标题】:Top alignment of dynamic collection view cells should be same 【发布时间】:2020-01-16 12:57:01 【问题描述】:我们正在显示一个包含两个单元格的集合视图,并在每个集合视图单元格中显示标签(带有文本的动态)。
我们能够做到这一点
override func preferredLayoutAttributesFitting(_ layoutAttributes: UICollectionViewLayoutAttributes) -> UICollectionViewLayoutAttributes
一行数据中的两个单元格居中对齐。我们可以让它顶部对齐吗?
示例: 假设有两个单元格,一个单元格中有 2 行文本,第二个单元格中有 4 行文本。 在这种情况下,这两个标签彼此居中对齐。我们可以让它们顶部对齐吗?
提前致谢, 拉姆
【问题讨论】:
你能提供截图吗? 更新了@jtouzy。你能看一下吗 【参考方案1】:我使用AlignedCollectionViewFlowLayout
来快速解决问题。
https://github.com/mischa-hildebrand/AlignedCollectionViewFlowLayout
【讨论】:
【参考方案2】:我有 aprx 相同的功能,所以我分享我在工作条件下所做的事情。如果您的要求稍有不同,则需要进行更多自定义。
对于代码解释,我建议您浏览答案最后一部分中提到的参考链接。
创建自定义 FlowLayout 类
class CustomLayout: UICollectionViewFlowLayout
private var computedContentSize: CGSize = .zero
private var cellAttributes = [IndexPath: UICollectionViewLayoutAttributes]()
var array = [String]()
override var collectionViewContentSize: CGSize
return computedContentSize
override func prepare()
computedContentSize = .zero
cellAttributes = [IndexPath: UICollectionViewLayoutAttributes]()
var preY = 10
var highY = 10
for section in 0 ..< collectionView!.numberOfSections
var i = 0
for item in 0 ..< collectionView!.numberOfItems(inSection: section)
let awidth = Int((self.collectionView?.bounds.width)!) / 3 - 15
let aheight = self.array[item].height(withConstrainedWidth: CGFloat(awidth), font: UIFont.systemFont(ofSize: 16)) + 20
var aX = 10
if item % 3 == 1
aX = aX + 10 + awidth
else if item % 3 == 2
aX = aX + 20 + 2 * awidth
else
aX = 10
preY = highY
if highY < preY + Int(aheight)
highY = preY + Int(aheight) + 5
let itemFrame = CGRect(x: aX, y: preY, width: awidth, height: Int(aheight))
let indexPath = IndexPath(item: item, section: section)
let attributes = UICollectionViewLayoutAttributes(forCellWith: indexPath)
attributes.frame = itemFrame
cellAttributes[indexPath] = attributes
i += 1
computedContentSize = CGSize(width: (self.collectionView?.bounds.width)!,
height: CGFloat(collectionView!.numberOfItems(inSection: 0) * 70))
override func layoutAttributesForElements(in rect: CGRect) -> [UICollectionViewLayoutAttributes]?
var attributeList = [UICollectionViewLayoutAttributes]()
for (_, attributes) in cellAttributes
if attributes.frame.intersects(rect)
attributeList.append(attributes)
return attributeList
override func layoutAttributesForItem(at indexPath: IndexPath) -> UICollectionViewLayoutAttributes?
return cellAttributes[indexPath]
MainViewController
class ViewController: UIViewController, UICollectionViewDelegate, UICollectionViewDataSource, UICollectionViewDelegateFlowLayout
@IBOutlet weak var myColView: UICollectionView!
var array = ["Hello", "Look Behind", "Gotta get there", "Hey buddy", "Earth is rotating around the sun", "Sky is blue", "Kill yourself", "Humble docters", "Lets make party tonight Lets make party tonight", "Lets play PUB-G", "Where are you?", "Love you Iron Man."]
override func viewDidLoad()
super.viewDidLoad()
let myLayout = CustomLayout()
myLayout.array = self.array
myColView.collectionViewLayout = myLayout
func collectionView(_ collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int
return array.count
func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell
let cell = collectionView.dequeueReusableCell(withReuseIdentifier: "MyCell", for: indexPath) as! MyCell
cell.myLabel.text = array[indexPath.row]
cell.myLabel.layer.borderColor = UIColor.lightGray.cgColor
cell.myLabel.layer.borderWidth = 1
return cell
使用的扩展程序
extension String
func height(withConstrainedWidth width: CGFloat, font: UIFont) -> CGFloat
let constraintRect = CGSize(width: width, height: .greatestFiniteMagnitude)
let boundingBox = self.boundingRect(with: constraintRect, options: .usesLineFragmentOrigin, attributes: [NSAttributedString.Key.font: font], context: nil)
return ceil(boundingBox.height)
func width(withConstrainedHeight height: CGFloat, font: UIFont) -> CGFloat
let constraintRect = CGSize(width: .greatestFiniteMagnitude, height: height)
let boundingBox = self.boundingRect(with: constraintRect, options: .usesLineFragmentOrigin, attributes: [NSAttributedString.Key.font: font], context: nil)
return ceil(boundingBox.width)
输出:
参考:
https://www.raywenderlich.com/4829472-uicollectionview-custom-layout-tutorial-pinterest https://www.netguru.com/codestories/practical-introduction-to-custom-uicollectionview-layouts https://developer.apple.com/documentation/uikit/uicollectionview/customizing_collection_view_layouts【讨论】:
以上是关于动态集合视图单元格的顶部对齐方式应该相同的主要内容,如果未能解决你的问题,请参考以下文章