Binding collaction of items into ListView's custom ViewCell dynamically in Xamarin Forms

I am facing some issue while binding collection to ListView's custom ViewCell. Collection has deep hierarchy.

Models

public class ViewModel : INotifyPropertyChanged
{
    public event PropertyChangedEventHandler PropertyChanged;

    private ObservableCollection<ParentViewModel> parentList;

    public ObservableCollection<ParentViewModel> ParentList
    {
        get
        {
            return parentList;
        }
        set
        {
            if (parentList != value)
            {
                parentList = value;

                if (PropertyChanged != null)
                {
                    PropertyChanged(this,
                        new PropertyChangedEventArgs("ParentList"));
                }
            }
        }
    }
}

public class ParentViewModel : INotifyPropertyChanged
{
    private ObservableCollection<ChildViewModel> myProperty;

    public ObservableCollection<ChildViewModel> MyProperty
    {
        get
        {
            return myProperty;
        }
        set
        {
            if (myProperty != value)
            {
                myProperty = value;

                if (PropertyChanged != null)
                {
                    PropertyChanged(this,
                        new PropertyChangedEventArgs("MyProperty"));
                }
            }
        }
    }

    public event PropertyChangedEventHandler PropertyChanged;
}

public class ChildViewModel : INotifyPropertyChanged
{
    private string prop1;
    private string prop2;

    public string Prop1
    {
        get
        {
            return prop1;
        }
        set
        {
            if (prop1 != value)
            {
                prop1 = value;

                if (PropertyChanged != null)
                {
                    PropertyChanged(this,
                        new PropertyChangedEventArgs("Prop1"));
                }
            }
        }
    }
    public string Prop2
    {
        get
        {
            return prop2;
        }
        set
        {
            if (prop2 != value)
            {
                prop2 = value;

                if (PropertyChanged != null)
                {
                    PropertyChanged(this,
                        new PropertyChangedEventArgs("Prop2"));
                }
            }
        }
    }

    public event PropertyChangedEventHandler PropertyChanged;
}

Here is ViewModel creation logic and bindingcontext

ChildViewModel objChildViewModel1 = new ChildViewModel { Prop1 = "Prop1", Prop2 = "Prop2" };
        ChildViewModel objChildViewModel2 = new ChildViewModel { Prop1 = "Prop1", Prop2 = "Prop2" };

        ParentViewModel objParentViewModel1 = new ParentViewModel();
        objParentViewModel1.MyProperty = new ObservableCollection<ChildViewModel> { objChildViewModel1, objChildViewModel2 };

        ParentViewModel objParentViewModel2 = new ParentViewModel();
        objParentViewModel2.MyProperty = new ObservableCollection<ChildViewModel> { objChildViewModel1, objChildViewModel2 };

        ViewModel obj = new ViewModel
        {
            ParentList = new ObservableCollection<ParentViewModel> { objParentViewModel1, objParentViewModel2 }
        };

        //set binding context
        this.BindingContext = obj;

List View in Xaml

        <ListView x:Name="lstView" ItemsSource="{Binding ParentList}">
        </ListView>

List View in C#

 lstView.ItemTemplate = new DataTemplate(() =>
        {
            var cell = new ViewCell();
            var grid1 = new Grid();
            grid1.RowDefinitions.Add(new RowDefinition { Height = new GridLength(1, GridUnitType.Star) });
            grid1.RowDefinitions.Add(new RowDefinition { Height = new GridLength(1, GridUnitType.Star) });
            grid1.ColumnDefinitions.Add(new ColumnDefinition { Width = new GridLength(1, GridUnitType.Star) });
            grid1.ColumnDefinitions.Add(new ColumnDefinition { Width = new GridLength(1, GridUnitType.Star) });

            //I am using static count variable  as below to access collection item
            //Is there any way I can access a collection item for which this DataTemplate called  ????
            //It will be called equals to number of items in collection bound to listView**
            for (int i = 0; i < obj.ParentList[count].MyProperty.Count; i++)
            {

                var Label11 = new Label { };

               //how to databind obj.MyProperty[0].Prop1 to Label1 ? Did my implementation is correct ?????
                Label1.SetBinding(Label.TextProperty, "ParentList[" + count.ToString() + "].MyProperty[" + i.ToString() +"].Prop1");

                var Entry11 = new Entry { };

                //how to databind obj.MyProperty[0].Prop2 to Entry1 ? Did my implementation is correct ?????
                Entry1.SetBinding(Entry.TextProperty, "ParentList[" + count.ToString() + "].MyProperty[" + i.ToString() + "].Prop2");

                grid.Children.Add(Label11, 0, 0 + i);
                grid.Children.Add(Entry11, 1, 0 + i);

            }

            count++;

            cell.View = grid1;
            return cell;
        });

The requirement is to have to show childrenlist data per parentListItem. So, one ListView Row would have multiple child row which I have tried to implement using grids in ViewCell of List View as I have shown in the code.

Questions,

  1. Did I correctly data bind viewmodel with label and entry view/control as I am not getting data binded on screen.
  2. ItemTemplate for List would be created for each viewmodel (in this case parentmodel) in collection. So, is there any way I can get that viewModel for which ItemTemplate has been created?
Sign In or Register to comment.