0

how can I get the actual interItemSpacing for a horizontal flow layout in the UICollectionView ? the only info I can get (and set) is minimumInteritemSpacing.

I need it for the sake of the following small calculation to always display 3 equally width items in the collection view regardless to screen size (i want to replace minimumInteritemSpacing with the current value of interItemSpacing in the formula): flowLayout.itemSize = CGSizeMake((_collectionView.frame.size.width/3.0)-(flowLayout.minimumInteritemSpacing/3.0), _collectionView.frame.size.height); I put this calculation in viewDidLayoutSubviews and it's not working precisely for some screens because their current interItemSpacing is different than the minimumInteritemSpacing

thanks in advance.

JAHelia
  • 6,934
  • 17
  • 74
  • 134
  • If there a reason you’re not using the [UICollectionViewFlowlayoutDelegate method](https://developer.apple.com/documentation/uikit/uicollectionviewdelegateflowlayout/1617708-collectionview) which allows dynamically sized cells - put your calculation in there and return your desired size? – Rich Aug 26 '18 at 07:36
  • Ignore the above - someone dragged up a 2 year old question into the top questions... – Rich Aug 26 '18 at 07:38

2 Answers2

3

You could get the actual spacing by comparing two sequential cells

Something like

let firstIndex =  IndexPath(item: 0, section: 0)
let secondIndex = IndexPath(item: 1, section: 0)
if let att1 = collectionView.layoutAttributesForItem(at: firstIndex),
let att2 = collectionView.layoutAttributesForItem(at: secondIndex) {
  let actualSpace = att2.frame.minX - att1.frame.maxX
  print (actualSpace)
}
Ryan Heitner
  • 13,119
  • 6
  • 77
  • 119
1

For creating cells with fixing spacing try this:

private let minItemSpacing: CGFloat = 8
private let itemWidth: CGFloat      = 100
private let headerHeight: CGFloat   = 32

override func viewDidLayoutSubviews() {
    super.viewDidLayoutSubviews()

    // Create our custom flow layout that evenly space out the items, and have them in the center
    let layout = UICollectionViewFlowLayout()
    layout.itemSize = CGSize(width: itemWidth, height: itemWidth)
    layout.minimumInteritemSpacing = minItemSpacing
    layout.minimumLineSpacing = minItemSpacing
    layout.headerReferenceSize = CGSize(width: 0, height: headerHeight)

    // Find n, where n is the number of item that can fit into the collection view
    var n: CGFloat = 1
    let containerWidth = collectionView.bounds.width
    while true {
        let nextN = n + 1
        let totalWidth = (nextN*itemWidth) + (nextN-1)*minItemSpacing
        if totalWidth > containerWidth {
            break
        } else {
            n = nextN
        }
    }

    // Calculate the section inset for left and right. 
    // Setting this section inset will manipulate the items such that they will all be aligned horizontally center.
    let inset = max(minItemSpacing, floor( (containerWidth - (n*itemWidth) - (n-1)*minItemSpacing) / 2 ) )
    layout.sectionInset = UIEdgeInsets(top: minItemSpacing, left: inset, bottom:    minItemSpacing, right: inset)

    collectionView.collectionViewLayout = layout
}

For more information, this excellent article:

http://samwize.com/2015/11/30/understanding-uicollection-flow-layout/

Jasper Alblas
  • 348
  • 2
  • 8