Skip to content

Instantly share code, notes, and snippets.

What would you like to do?
UICollectionViewControllerFlowLayout boiler plate. Just fill out the `prepare` function with you layout logic and the rest just works.
class SampleFlowLayout: UICollectionViewLayout {
override func prepare() {
guard let collectionView = self.collectionView else { return }
// go through every section..
for section in 0..<collectionView.numberOfSections {
let numberOfItems = collectionView.numberOfItems(inSection: section)
// ..and every item
for item in 0..<numberOfItems {
// create the frame attribute for the index path
let attributes = UICollectionViewLayoutAttributes(forCellWith: IndexPath(item: item, section: section))
attributes.frame = self.frameForItemNumber(itemNumber, isBelowRibbon: isBelowRibbon)
attributes.zIndex = 1
// save the last frame
let lastAtt = self.itemAttributes.lastObject as? UICollectionViewLayoutAttributes
// calculate the total content size
if (lastAtt != nil) {
let maxCellY = lastAtt!.frame.maxY
self.contentSize = CGSize(width: self.collectionView!.frame.width, height: maxCellY + bottomPadding)
else {
self.contentSize =
// MARK: Flow Layout Overrides
override var collectionViewContentSize: CGSize {
return self.contentSize
override func layoutAttributesForElements(in rect: CGRect) -> [UICollectionViewLayoutAttributes]? {
// hand back the attributes that are in the rect
let filteredArray = self.itemAttributes.filtered(using: NSPredicate(block: { (object, binding) -> Bool in
let attObject = object as! UICollectionViewLayoutAttributes
return rect.intersects(attObject.frame)
})) as! [UICollectionViewLayoutAttributes]
return filteredArray
override func shouldInvalidateLayout(forBoundsChange newBounds: CGRect) -> Bool {
return newBounds.width != self.collectionView?.frame.width || newBounds.height != self.collectionView?.frame.height
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.