Search code examples
listviewxamarinbindingdatatemplateitemtemplate

Xamarin.ListView. How binding working in itemtemplate/datatemplate?


I have this XAML code.

 <?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="Android_1.MainPage" Title="">
    <StackLayout>
        <Label Text="{Binding Type}"/>
        <Label Text="{Binding Question}"/>
        <ListView ItemsSource="{Binding Answers}"/>
        <Button Text="Next Question" Clicked="Button_Clicked"/>
    </StackLayout>
</ContentPage>

In MainPage class C# code:

        public MyView answerView;
        public MainPage()
        {
            InitializeComponent();
            answerView = new MyView();
            this.BindingContext = answerView;
        }
        private void Button_Clicked(object sender, EventArgs e)
        {
             answerView.QuestCase = Program.GetRandomCase();
        }

Now so it works. The code above works. All bindings work.

When I change the XAML, binding in ListView stops working, Binding in Labels still working:

<?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="Android_1.MainPage" Title="">
    <StackLayout>
        <Label Text="{Binding Type}"/>
        <Label Text="{Binding Question}"/>
        <ListView ItemsSource="{Binding Answers}">
            <ListView.ItemTemplate>
                <DataTemplate>
                    <ViewCell>
                        <StackLayout>
                            <Label LineBreakMode="WordWrap"/>
                        </StackLayout>
                    </ViewCell>
                </DataTemplate>
            </ListView.ItemTemplate>
        </ListView>
        <Button Text="Next Question" Clicked="Button_Clicked"/>
    </StackLayout>
</ContentPage>

How to solve it? Thanks.


And MyView class:

  public class MyView : INotifyPropertyChanged
        {
            public event PropertyChangedEventHandler PropertyChanged;
            private QuestCase questCase;

            public QuestCase QuestCase
            {
                get { return questCase; }
                set {
                    if(value != questCase)
                    {
                        questCase = value;
                        OnPropertyChanged("Question");
                        OnPropertyChanged("Type");
                        OnPropertyChanged("Answers");                  
                    }
                }
            }
            public MyView()
            {
                questCase = Program.GetRandomCase();
            }
            public string Question
            {
                get { return questCase.Question; }
            }
            public string Type
            {
                get { return questCase.Type; }
            }
            public string[] Answers
            {
                get { return questCase.Answers.Keys.ToArray(); }
            }

            protected void OnPropertyChanged(string propName)
            {
                if (PropertyChanged != null)
                    PropertyChanged(this, new PropertyChangedEventArgs(propName));
            }
        }

Solution

  • <?xml version="1.0" encoding="utf-8" ?>
    <ContentPage xmlns="http://xamarin.com/schemas/2014/forms"
                 xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
                 xmlns:local ="clr-namespace:Android_1"
                 x:Class="Android_1.MainPage" Title="">
        <ContentPage.Resources>
            <ResourceDictionary>
                <DataTemplate x:Key="MyDataTemplate">
                    <ViewCell>
                        <Label LineBreakMode="WordWrap" Text="{Binding}"></Label>
                    </ViewCell>
                </DataTemplate>
            </ResourceDictionary>
        </ContentPage.Resources>
        <StackLayout>
            <Label Text="{Binding Type}"/>
            <Label Text="{Binding Question}"/>
            <ListView x:Name="ListAnswers" ItemsSource="{Binding Answers}" ItemTemplate="{x:StaticResource MyDataTemplate}">
            </ListView>
            <Button Text="Next Question" Clicked="Button_Clicked"/>
        </StackLayout>
    </ContentPage>
    

    This works!