CollectionView on Xamarin Forms. How to solve this annoying bug on iOS

CollectionViews are one of the most used components available on Xamarin. Every app has lists of items to show and CollectionViews offer an incredible flexibility to show your data and define a template for whatever collection you need how show to your users.

A CollectionView offers the option to define an header for your list:

<CollectionView.Header>
//Your Header here...
</CollectionView.Header>

It gives you the opportunity to group your items in the list and create a Header for your group:

<CollectionView.GroupHeaderTemplate>
    <DataTemplate>
    //Your Group Header here...
    </DataTemplate>
</CollectionView.GroupHeaderTemplate>

and of course a CollectionView allows you to define a template for your items:

<CollectionView.ItemTemplate>
    <DataTemplate>
    //Your item template here...
    </DataTemplate>
</CollectionView.ItemTemplate>

Of course there are cases where your list doesn’t have any items yet. In this case you don’t want to show an empty list so the CollectionView allows you to define a View that appears only when your list is empty. You can define your Empty View here:

<CollectionView.EmptyView>
//Your Empty View here...
</CollectionView.EmptyView>

When you list has at least an element you will see them according to the content of your ItemTemplate, when your list is empty, you’ll see the view defined in EmptyView. So far so good!

The problem

On Android, everything works just fine. You define your EmptyView and you see that when your list is empty. Unfortunately on iOS, this doesn’t work correctly. There is a bug in Xamarin.Forms that hasn’t been fixed yet, so it can happen that you see the EmptyView even if your list is not empty. I discovered this problem while working on my new app Safe Money Budget (Android, iOS (available soon)). Even if my list was not empty, on iOS the CollectionView was showing both the contents from ItemTemplate and EmptyView.

The solution

Of, the bug it’s annoying but the solution is incredibly easy so luckily we can solve this bug in just a moment. The solution consists of adding the IsVisible property and bind it to your list using a converter to check if your list is actually null empty. Here is an example:

<CollectionView.EmptyView>
    <StackLayout IsVisible="{Binding Movements, Converter={views1:ListIsNullOrEmptyConverter}}">
    //Your view here
    </StackLayout>
</CollectionView.EmptyView>

Of course you can replace the StackLayout with whatever you like. Then you bind the IsVisible property to the list associated to your CollectionView (in my case Movements).

The ListIsNullOrEmptyConverter comes from the Xamarin Community toolkit package. If you already have it in your app, then you don’t have to do anything else, if you don’t have it, then you should really download it, it contains a lot of useful code to make your life easier.

Of course if you don’t want to download the entire package for a single converter you can create your own converter or you can copy it from the Xamarin Community toolkit source code.

For any doubts or questions, just leave a message and I’ll reply.

If you are not sure what Databinding is or your want to know more about MVVM, you should really have a look at this other article: https://www.xamarinexpert.it/how-to-correctly-use-databinding-with-listview-and-collectionview/