CollectionView Masonry Style Xamarin Forms (Android)

En mas de una ocasión hemos visto este estilo para algunos Menu, en aplicaciones (tipo Pinterest) o el Menu de Opciones de Facebook, este caso vamos a crear este mismo estilo para una aplicación en Xamarin Form para nuestro Android Project.

Vamos a crear nuestro proyecto (Actualmente estoy utilizando la extensión de Prism para general el proyecto)

Lo primero que debemos hacer es crear un Custom Render para nuestro Collection View.

Vamos a crear una carpeta con el nombre Controls y dentro de, crearemos una clase que se llame CollectionViewMasonry.cs y hacemos que herede del CollectionView de Xamarin.Forms, de tal manera que quede así.

public class CollectionViewMasonry : CollectionView
{

}

Ahora vamos a crear una carpeta dentro de nuestro proyecto Android con el nombre CustomControls y dentro de, vamos a crear una clase llama CustomCollectionView.cs y la pondremos a heredar de CollectionViewRenderer proveniente de Xamarin.Forms.Platform.Android y dentro de la clase vamos a escribir el siguiente código.

[assembly: ExportRenderer(typeof(CollectionViewMasonry), typeof(CustomCollectionView))]
namespace MasonryStyle.Droid.CustomControls
{
    public class CustomCollectionView : CollectionViewRenderer
    {
        public CustomCollectionView(Context context):base(context)
        {

        }

        protected override void OnElementChanged(ElementChangedEventArgs<ItemsView> elementChangedEvent)
        {
            base.OnElementChanged(elementChangedEvent);

            if (elementChangedEvent.NewElement != null)
            {
                StaggeredGridLayoutManager manager = new StaggeredGridLayoutManager(2, StaggeredGridLayoutManager.Vertical);
                SetLayoutManager(manager);
            }
        }

    }
}

Luego de esto, vamos a volver a nuestro proyecto compartido crearemos una carpeta llamada Models y agregaremos la siguiente clase MenuItems.cs y agregaremos la siguientes propiedades.

public class MenuItems
{
   public int Id { get; set; }
   public string BackgroundColor { get; set; }
   public int Height { get; set; }
}

Vamos ahora dentro de nuestra carpeta de ViewModels y abrimos el archivo MainPageViewModel.cs y vamos a agregar el código que llenara nuestra lista, quedando de la siguiente manera.

public class MainPageViewModel : ViewModelBase
    {

        public ObservableCollection<MenuItems> MenuItemsList { get; set; } = new ObservableCollection<MenuItems>();
        public ICommand LoadData { get; set; }

        public MainPageViewModel(INavigationService navigationService)
            : base(navigationService)
        {
            Title = "Main Page";

            LoadData = new DelegateCommand(() => LoadDataMenuItems());
            LoadData.Execute(null);
        }

        public void LoadDataMenuItems()
        {
            var rnd = new Random();
            string[]  ColorsArray = { "#FF7D7D", "#FFF3B8", "#A1CAFF", "#FDBAFF", "#ACB7FF", "#B2FFC7", "#BEBEBE", "#FEC1C1", "#DBB6D5", "#FFC1AA" };
            for (var i = 1; i <= 30; i++) {
                MenuItemsList.Add(new MenuItems { 
                    Id = i,
                    BackgroundColor = ColorsArray[rnd.Next(0,9)],
                    Height = rnd.Next(86,196)
                });
            }
        }
    }

Ahora vamos a ir a nuestra carpeta Views y abriremos el archivo MainPage.xaml y dentro de las propiedades del ContentPage vamos a agregar el siguiente namespace.

xmlns:Controls="clr-namespace:MasonryStyle.Controls"

y ahora eliminaremos el StackLayout que esta creado por defecto y vamos a agregar el diseño de nuestra vista, quedando el código de la siguiente manera.

<?xml version="1.0" encoding="utf-8" ?>
<ContentPage xmlns="http://xamarin.com/schemas/2014/forms"
             xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
             x:Class="MasonryStyle.Views.MainPage"
             Title="{Binding Title}"
             xmlns:Controls="clr-namespace:MasonryStyle.Controls">

    <ContentPage.Content>
        <StackLayout>
            <Controls:CollectionViewMasonry ItemsSource="{Binding MenuItemsList}" Margin="5">
                <CollectionView.ItemTemplate>
                    <DataTemplate>
                        <StackLayout>
                            <Frame Margin="5" BackgroundColor="{Binding BackgroundColor}" HeightRequest="{Binding Height}">
                                <Label Text="{Binding Id}" HorizontalOptions="Center" VerticalOptions="Center"/>
                            </Frame>
                        </StackLayout>
                    </DataTemplate>
                </CollectionView.ItemTemplate>
            </Controls:CollectionViewMasonry>
        </StackLayout>
    </ContentPage.Content>
</ContentPage>

Ahora ejecutaremos nuestra aplicación y tendremos nuestro efecto creado.

Si te gusto este post no te olvides de comentar para que la motivación de seguir creando contenido de ayuda siga en pie, gracias por tu apoyo.

Leave a Reply

Your email address will not be published.