首页 > 解决方案 > 组合布局和损坏的自身大小的单元格

问题描述

我使用的是相对简单的组合布局,它可以工作,但在某些情况下,我的 UICollectionView 中的最后一个或两个单元格似乎宽度损坏。

我的 collectionView 由具有动态宽度和静态高度的单元格组成。我可以预先计算高度,因为我的单元格基本上是 UILabel 加上背景 UIView 加上顶部/左侧/右侧/底部约束(每个都有 UIPriority(1000))。

topicBackView = UIView()
topicBackView.translatesAutoresizingMaskIntoConstraints = false
contentView.addSubview(topicBackView)
        
topicLabel = MyLabel()
topicLabel.translatesAutoresizingMaskIntoConstraints = false
topicLabel.numberOfLines = 0
topicLabel.font = cs.usualFont
topicLabel.textColor = UIColor.black
topicLabel.textAlignment = .center
contentView.addSubview(topicLabel)

let tpp = topicBackView.topAnchor.constraint(equalTo: contentView.topAnchor, constant: 0)
tpp.priority = UILayoutPriority(1000)
tpp.isActive = true

等等。

我知道 UILabel 的字体,我知道所有约束的常量,所以很容易预测单元格的高度。

因此,我的布局如下所示:

func giveMeFreeTagsLayout() -> UICollectionViewLayout {
    let estimatedHeight: CGFloat = topicsCellCollectionHeight
    let estimatedWidth: CGFloat = 200

    let itemSize = NSCollectionLayoutSize(
        widthDimension: .estimated(estimatedWidth),
        heightDimension: .absolute(estimatedHeight)
    )
    // height is absolute because I know it, and in some cases not in this one,
    // though I have to calculate the height of UICollectionView 
    let item = NSCollectionLayoutItem(layoutSize: itemSize)

    item.edgeSpacing = NSCollectionLayoutEdgeSpacing(
        leading: .fixed(0), 
        top: .fixed(8), 
        trailing: .fixed(8), 
        bottom: .fixed(8)
    )

    let groupSize = NSCollectionLayoutSize(
        widthDimension: .fractionalWidth(1.0),
        heightDimension: .estimated(estimatedHeight)
    )
    let group = NSCollectionLayoutGroup.horizontal(
        layoutSize: groupSize,
        subitems: [item]
    )
    group.contentInsets = NSDirectionalEdgeInsets(
        top: 0, 
        leading: 16, 
        bottom: 0, 
        trailing: 16
    )

    let section = NSCollectionLayoutSection(group: group)
    section.contentInsets = NSDirectionalEdgeInsets(
        top: 0, 
        leading: 0, 
        bottom: 20, 
        trailing: 0
    )

    let layout = UICollectionViewCompositionalLayout(section: section)
    return layout
}

问题是,它可以在 iPhone 11 上的模拟器中运行,但是当我试图在较小的屏幕上模拟它时,这个 collectionView 似乎被破坏了(在我的例子中,iPad Air 第 3 代与 iPhone 兼容)。

在这种情况下,最后一两个单元格的宽度已损坏,我不知道为什么:

坏的

应该如何: 好一个(像魅力一样工作)

这里发生了什么?

标签: swiftuicollectionviewuicollectionviewlayoutuicollectionviewcompositionallayout

解决方案


让估计宽度:CGFloat = 200 将其更改为 50,它将起作用


推荐阅读