Reputation: 267
I am attempting to create a UICollectionView
which is horizontal scrolling and a single row. Cells can be added dynamically to the end of the collection. I want the behaviour to be that when a certain number of cells are in the UICollectionView
and a new one is added, the first x
number of cells will squish their spacing whilst remaining the same size. Ideally I want the first x
cells to actually overlap each other somewhat (would look like a stack) to conserve maximum space. The remaining cells in the collection after x
will display with the normal spacing between them.
A visual:
( ) ( ) ( ) ( ) ( )
normal layout where ( )
is an item
would become as such when two more items are added:
((((( ) ( ) ( )
or ( ))))) ( ) ( )
if the first item was at the top of the stack (I don't mind which right now, just the stack is important)
Can anyone offer any help and advice on how this can be achieved?
Upvotes: 0
Views: 58
Reputation: 267
For anyone interested, I achieved this by subclassing UICollectionViewFlowLayout
and overriding as below. Bare in mind I used an additional cell at the end of the collection as an addCell
button, so this implementation accounts for that and will do the rearrangement after 5 real items have been added and you go to add a 6th. My cells had a width of 50
with a minimum spacing of 10
when normally laid out.
override func layoutAttributesForElements(in rect: CGRect) -> [UICollectionViewLayoutAttributes]? {
guard collectionView!.numberOfItems(inSection: 0) > 6 else {
return super.layoutAttributesForElements(in: rect)
}
let layouts = super.layoutAttributesForElements(in: rect)?.map { $0.copy() as! UICollectionViewLayoutAttributes }
for (index, layout) in layouts!.enumerated() {
var frame = layout.frame
frame.origin.x = frame.origin.x - (35.0 * CGFloat(index < 5 ? index : (index - (index - 4))))
layout.frame = frame
}
return layouts
}
Upvotes: 1
Reputation: 535556
You can achieve any positioning you like, because you get to write the UICollectionViewLayout that tells the collection view how to position its items.
A flow layout, by default, will not do what you are describing. It simply lays out all the items in each row with the same spacing, based on the collection view content width and the minimum item spacing you supply. But if you subclass UICollectionViewFlowLayout, you can probably modify the behavior of the flow layout to do what you are describing. Thus, you would not need to write the layout object entirely from scratch.
However, for maximum flexibility, writing the layout object entirely from scratch is exactly what you would do. It really isn't all that hard. Apple has many examples and of course there are many tutorial examples out there as well.
Upvotes: 0