Follow

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use
Contact

Xamarin Forms CollectionView Grouping Not Working With Intellisense

The Issue

I am getting extremely confused with how grouping works in the CollectionView.

I am able to get an output as expected using the recommended example from the Xamarin Documentation with the code below:

MEDevel.com: Open-source for Healthcare and Education

Collecting and validating open-source software for healthcare, education, enterprise, development, medical imaging, medical records, and digital pathology.

Visit Medevel

CollectionView XAML

<CollectionView IsGrouped="True" ItemsSource="{Binding CategoriesList}" RelativeLayout.WidthConstraint="{ConstraintExpression Type=RelativeToParent, Property=Width, Factor=0.5}">
            <CollectionView.ItemsLayout>
                <LinearItemsLayout Orientation="Vertical" ItemSpacing="10" />
            </CollectionView.ItemsLayout>
            <CollectionView.GroupHeaderTemplate>
                <DataTemplate>
                    <Label Text="{Binding Name}" />
                </DataTemplate>
            </CollectionView.GroupHeaderTemplate>
            <CollectionView.ItemTemplate>
                <DataTemplate>
                    <SwipeView>

                        <SwipeView.LeftItems>
                            <SwipeItems>
                                <SwipeItem Text="Delete" IconImageSource="CategoryPhoto" />
                            </SwipeItems>
                        </SwipeView.LeftItems>
                        <SwipeView.RightItems>
                            <SwipeItems>
                                <SwipeItem Text="Edit" IconImageSource="CategoryPhoto" />
                            </SwipeItems>
                        </SwipeView.RightItems>

                        <SwipeView.Content>
                            <StackLayout BackgroundColor="Red">
                                <StackLayout.GestureRecognizers>
                                    <TapGestureRecognizer Command="{Binding Path=BindingContext.EditProduct, Source={x:Reference Name=MainView}}" CommandParameter="{Binding ID}" />
                                </StackLayout.GestureRecognizers>
                                <StackLayout Orientation="Horizontal" Padding="15">
                                    <Image Source="CategoryPhoto" />
                                    <StackLayout Orientation="Vertical">
                                        <Label Text="{Binding Name}" TextColor="Black" />
                                        <Label Text="doy" TextColor="Black" />
                                    </StackLayout>
                                    <StackLayout Orientation="Horizontal" HorizontalOptions="EndAndExpand">

                                        <Label Text="&#8854;" TextColor="Black" VerticalTextAlignment="Center" RelativeLayout.HeightConstraint="{ConstraintExpression Property=Height, Factor=1, Type=RelativeToParent}">
                                            <Label.GestureRecognizers>
                                                <!--<TapGestureRecognizer Command="{Binding Path=BindingContext.RemoveItem, Source={x:Reference Name=MainView}}" CommandParameter="{Binding ID}" />-->
                                            </Label.GestureRecognizers>
                                        </Label>

                                        <Label x:Name="QuantityLabel" Text="{Binding Quantity}" TextColor="Black" VerticalTextAlignment="Center" />

                                        <Label Text="&#8853;" TextColor="Black" VerticalTextAlignment="Center">
                                            <Label.GestureRecognizers>
                                                <!--<TapGestureRecognizer Command="{Binding Path=BindingContext.PurchaseItem, Source={x:Reference Name=MainView}}" CommandParameter="{Binding ID}" />-->
                                            </Label.GestureRecognizers>
                                        </Label>

                                    </StackLayout>
                                </StackLayout>
                                <Rectangle Fill="LightGray" HeightRequest="2" />
                            </StackLayout>
                        </SwipeView.Content>

                    </SwipeView>
                
                </DataTemplate>
            </CollectionView.ItemTemplate>
        </CollectionView>

Product Class

using System;
using System.ComponentModel;
using SQLite;
using SQLiteNetExtensions.Attributes;

namespace TakeItAwayPOS.Structures
{
    public class Product
    {
        [PrimaryKey, AutoIncrement]
        public int ID { get; set; }

        public string Name { get; set; }
        public double Price { get; set; }
        public int Stock { get; set; }

        [ForeignKey(typeof(Category))]
        public int Category { get; set; }

        //for adding to orders
        [Ignore]
        private int quantity { get; set; }
        public int Quantity
        {
            get => quantity;
            set { quantity = value; QuantityChanged(); }
        }

        public delegate void PropertyChangedEvent(object sender, PropertyChangedEventArgs args);
        public event PropertyChangedEvent PropertyChanged;

        private void QuantityChanged()
        {
            PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(null));
        }


    }
}

CategoryGroup Class

using System;
using System.Collections.Generic;

namespace TakeItAwayPOS.Structures
{
    public class CategoryGroup : List<Product>
    {
        public string Name { get; private set; }
        public CategoryGroup(string name, List<Product> products) : base(products)
        {
            Name = name;
        }
    }
}

EditProduct Command

public ICommand EditProduct
        {
            get
            {
                return new Command<string>((param) =>
                {
                    Console.WriteLine("Triggered!");
                    LoadProduct(Convert.ToInt32(param));

                });
            }
        }

My issue is with the GestureRecogniser for the StackLayout inside of the DataTemplate:

<StackLayout.GestureRecognizers>
   <TapGestureRecognizer Command="{Binding Path=BindingContext.EditProduct, Source={x:Reference Name=MainView}}" CommandParameter="{Binding ID}" />
</StackLayout.GestureRecognizers>

the CommandParameter binding wont work and the Command is only fired if I replace "{Binding ID}" with "0":

When I hover over all of the binding items in the CollectionView, intellisense references them to the CategoryGroup type instead of the Product type that would be expected, the odd thing is that the other binding values except the Command all work even though intellisense references them to the wrong type.

My two questions are:

  1. How would I go about trying to fix that command
  2. Can I fix the intellisense so that it recognises when grouping is true (or is this a known issue?)

Thanks in advance!

Solved
Thanks @Jason!

For some reason earlier in my code, the CommandParameter didn’t want to work as an int and so I had used this long winded method that converted to a string and then back to an int within the Command‘s lambda method. Turns out I didn’t need this and the fix was just to change the parameter type of the Command to int as so:

public ICommand EditProduct
        {
            get
            {
                return new Command<int>((param) =>
                {
                    Console.WriteLine("Triggered!");
                    LoadProduct(param);

                });
            }
        }

>Solution :

ID is an int, so you need to use Command<int>, not Command<string>

Add a comment

Leave a Reply

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use

Discover more from Dev solutions

Subscribe now to keep reading and get access to the full archive.

Continue reading