How to create a list with Compositional Layout
The easiest way for creating standard list layouts with the new APIs available from iOS 14.
Published: July 5, 2022 Sponsored See booksLists are one of the most common layouts in iOS apps, and while in the past, we created these with the UITableView
, we can quickly achieve lists with UICollectionView
, which gives you more flexibility.
Simple collection view list
In this post, we will look at creating the simplest list possible. It takes just a few lines of code.
Like this:
let configuration = UICollectionLayoutListConfiguration(appearance: .plain)
let layout = UICollectionViewCompositionalLayout.list(using: configuration)
collectionView.setCollectionViewLayout(layout, animated: false)
And we could compress this code even further…
The code above will get you the most basic list that automatically handles the sizes of each item. I recommend using this new list as a default unless you have needs that cannot be met with this API.
You can also easily get the “inset grouped” style popular in iOS. Just by creating different configuration:
var configuration = UICollectionLayoutListConfiguration(appearance: .insetGrouped)
This list will also handle separators for you.
Basic configuration
Above I used extra constant to store the UICollectionLayoutListConfiguration
because it offers a lot of useful customizations. Let’s look at a few:
configuration.backgroundColor = .systemTeal
configuration.showsSeparators = false
We have now changed the background color of the collection view and turned off the separators.
Another useful property is headerTopPadding
, which allows us to control the space above each section header. Note that this has been added in iOS 15.
configuration.headerTopPadding = 32
How to add headers and footer to list layout
Configuring the list layout to show headers or footers is also fairly straigthforward thanks to the configuration:
configuration.headerMode = .supplementary
configuration.footerMode = .supplementary
The above will configure the layout to use the supplementaryViewProvider
on your Diffable data source to provide the header view.
Per section configuration
While the code above is nicely concise, there are limitations. For example, let’s say you have multiple sections and want to show headers for only some sections.
The only way (that I know of) is to use the list configuration but to configure it section by section.
We will use the UICollectionViewCompositionalLayout
initializer with the section provider, which lets us return different sections based on the index.
Basic example looks like this:
let layout = UICollectionViewCompositionalLayout { [unowned self] index, environment in
switch index {
case 0:
var configuration = UICollectionLayoutListConfiguration(appearance: .insetGrouped)
configuration.headerMode = .supplementary
return .list(using: configuration, layoutEnvironment: environment)
default:
let configuration = UICollectionLayoutListConfiguration(appearance: .plain)
return .list(using: configuration, layoutEnvironment: environment)
}
}
We would first get the section from our Diffable data source in real code and switch
on that.
As you can see, the first section will be .insetGrouped
with a header, and all the remaining sections will be plain lists without supplementary views.
This approach also has the benefit that we can mix the list layout with any other kinds of layouts Compositional Layout supports. You could have horizontal sections mixed with the lists, for example.
Example code on GitHub
You can also check out my GitHub repository, which has many examples that use various parts of Compositional Layout and Diffable.