locked
ListView ItemsSource and DataContext TwoWay binding

    Question

  • Hi All!

    i have a trouble to bind DataContext to ListView with TwoWay.

    Problem:
    When i click on Item in SelectListView (to Select/Unselect) - databind change item in SelectListView.ItemsSource but Page.DataContext not changed.

    Friday, October 24, 2014 7:59 AM

Answers

  • Solve.. set ItemsSource to TwoWay binding... :D
    • Marked as answer by Alexey.U Tuesday, October 28, 2014 8:51 AM
    Tuesday, October 28, 2014 8:50 AM

All replies

  • Not exactly know what you mean.
    Could you give more information ?

    在現實生活中,你和誰在一起的確很重要,甚至能改變你的成長軌跡,決定你的人生成敗。 和什麼樣的人在一起,就會有什麼樣的人生。 和勤奮的人在一起,你不會懶惰; 和積極的人在一起,你不會消沈; 與智者同行,你會不同凡響; 與高人為伍,你能登上巔峰。

    Friday, October 24, 2014 3:57 PM
  • Hi Alexey,

    Are you using ObservableCollection as your data source? If not, assign an ObservableCollection as your DataContext. This way new and deleted items in the collection will be automatically reflected in your ListView.

    Also, in order to reflect changes in your UI through data binding you need to implement INotifyPropertyChanged on the properties you expose on UI.


    My Apps


    • Edited by ata6502 Friday, October 24, 2014 5:05 PM
    Friday, October 24, 2014 5:04 PM
  • I have my own class, this class contains ObservableCollection. I'm binding that class to Page.DataContext and that DataContext.MyCollection to ListView ItemsSource. I want to update that collection in Page.DataSource when element selected in ListView, but Page.DataContext is not update. I see changes only in List.View.ItemsSource
    Saturday, October 25, 2014 7:51 AM
  • Are you saying that when the selection changes, you want the page.DataContext to be the selected item of the list?

    In that case, add a property to your class.  Bind the listbox's SelectedItem to that propery.  Then, bind the page's DataContext to that property.


    Darin R.

    Saturday, October 25, 2014 6:00 PM
  • TwoWay no working.. 

    Now i have custom ListView:

        public class SelectListView : ListView
        {
            protected override void PrepareContainerForItemOverride(Windows.UI.Xaml.DependencyObject element, object item)
            {
                base.PrepareContainerForItemOverride(element, item);
    
                ListViewItem listItem = element as ListViewItem;
                listItem.SetBinding(ListViewItem.IsSelectedProperty, new Windows.UI.Xaml.Data.Binding()
                {
                    Mode = Windows.UI.Xaml.Data.BindingMode.TwoWay,
                    Source = item,
                    Path = new Windows.UI.Xaml.PropertyPath("IsSelected")
                });
            }
        }

    And this working, but working only in ListView.ItemsSource and DataContext not updating.

    Another way:

    For testing i'm add property Selected to my custom List:

            public IEnumerable<T> Selected
            {
                get
                {
                    return this.Where(s => s != null && (Boolean)s.GetType().GetRuntimeProperty("IsSelected").GetValue(s));
                }
                set
                {
                    foreach (var kana in value)
                    {
    
                    }
                }
            }

    Set is not invoked when i select item in ListView. But i set ListView.Selected is TwoWay




    • Edited by Alexey.U Sunday, October 26, 2014 6:42 PM
    Sunday, October 26, 2014 6:11 PM
  • Hi Alexey,

    You’ve not posted enough information to make your question clear. So I assume you want to bind some data to ListView, edit something in TextBox and then the modification will show in ListView.

    Per my understanding, the problem of this case is that you’ve not implement INotifyPropertyChanged interface in Model class. So the modification will not update into UI automatically. The property of Model class should expose to UI using DependencyProperty.

    I create a code snippets, please see the following code.

    In XAML.

    <Page.Resources>
            <local:PageViewModel x:Key="array1"></local:PageViewModel>
        </Page.Resources>
        <Grid Background="{ThemeResource ApplicationPageBackgroundThemeBrush}">
            <StackPanel>
                <ListView x:Name="lvEmployees" ItemsSource="{Binding Source={StaticResource array1}, Path=Collections}" VerticalAlignment="Top" Height="500" Margin="60,10,0,0" HorizontalAlignment="Left" Width="400">
                    <ListView.ItemTemplate>
                        <DataTemplate>
                            <StackPanel Orientation="Horizontal">
                                <TextBlock Text="Name:"></TextBlock>
                                <TextBlock  Text="{Binding Path=Name}"></TextBlock>
                                <TextBlock Text=";Age:"></TextBlock>
                                <TextBlock Text="{Binding Path=Age}"></TextBlock>
                            </StackPanel>
                        </DataTemplate>
                    </ListView.ItemTemplate>
                </ListView>
                <Grid>
                    <Grid.RowDefinitions>
                        <RowDefinition Height="30"></RowDefinition>
                        <RowDefinition Height="30"></RowDefinition>
                        <RowDefinition Height="50"></RowDefinition>
                    </Grid.RowDefinitions>
                    <StackPanel Orientation="Horizontal" Grid.Row="0">
                        <TextBlock Text="Name:"></TextBlock>
                        <TextBox x:Name="txtName" Text="{Binding ElementName=lvEmployees,Path=SelectedItem.Name}"></TextBox>
                    </StackPanel>
                    <StackPanel Orientation="Horizontal" Grid.Row="1">
                        <TextBlock Text="Age:"></TextBlock>
                        <TextBox x:Name="txtAge" Text="{Binding ElementName=lvEmployees,Path=SelectedItem.Age}"></TextBox>
                    </StackPanel>
                    <Button Click="Button_Click" Content="Save Content" Grid.Row="2"></Button>
                </Grid>
            </StackPanel>
    </Grid>
    

    In XAML.cs

       

    public sealed partial class MainPage : Page
        {
            public MainPage()
            {
                this.InitializeComponent();
                Random rnd = new Random();
                for (int i = 0; i < 20; i++)
                {
                    PageViewModel.Collections.Add(new Employee() { Name = "hello" + rnd.Next(0, 101), Age = rnd.Next(20, 31) });
                }
            }
            private void Button_Click(object sender, RoutedEventArgs e)
            {
                if (lvEmployees.SelectedIndex!=-1)
                {
                    var emp = lvEmployees.SelectedItem as Employee;
                    if (emp!=null)
                    {
                        emp.Name = txtName.Text;
                        emp.Age = Int32.Parse(txtAge.Text);
                    }
                }
            }
        }
        public class PageViewModel
        {
            private static System.Collections.ObjectModel.ObservableCollection<Employee> list = new System.Collections.ObjectModel.ObservableCollection<Employee>();
            public static System.Collections.ObjectModel.ObservableCollection<Employee> Collections { get { return list; }}
        }
        public class Employee : INotifyPropertyChanged
        {
            private string _name;
            public string Name
            {
                get { return this._name; }
                set { if (value != this._name) { this._name = value; NotifyPropertyChanged(); } }
            }
            private int _age;
            public int Age
            {
                get { return this._age; }
                set { if (value != this._age) { this._age = value; NotifyPropertyChanged(); } }
            }
            public event PropertyChangedEventHandler PropertyChanged;
            private void NotifyPropertyChanged(String propertyName = "")
            { if (PropertyChanged != null) { PropertyChanged(this, new PropertyChangedEventArgs(propertyName)); } }
        }
    

    If I misunderstand you, please feel free to let me know.

    Regards,


    We are trying to better understand customer views on social support experience, so your participation in this interview project would be greatly appreciated if you have time. Thanks for helping make community forums a great place. Click HERE to participate the survey.

    Tuesday, October 28, 2014 5:51 AM
    Moderator
  • No, I want to bind 'IsSelected' property of ListViewItem.

    I have ListView.ItemsSource binded to Page.DataContext.

    I have custom ListView with bindable 'IsSelected' property for items. Its working on load and i can see selected items. But i want bind it to TwoWay, - when i click on item in ListTView i want to change it in Page.DataContext item 'IsSelected' property too.

    Now changes apply only ListView.ItemsSource but not Page.DataContext.

    Tuesday, October 28, 2014 8:26 AM
  • Hello,

    Can you send me a repro project? I will look into it. Use  your OneDrive and share a link here.

    Regards,


    We are trying to better understand customer views on social support experience, so your participation in this interview project would be greatly appreciated if you have time. Thanks for helping make community forums a great place. Click HERE to participate the survey.

    Tuesday, October 28, 2014 8:48 AM
    Moderator
  • Solve.. set ItemsSource to TwoWay binding... :D
    • Marked as answer by Alexey.U Tuesday, October 28, 2014 8:51 AM
    Tuesday, October 28, 2014 8:50 AM