-1

I'm completely new to WPF and I'm having problems with ItemsSource updates. I created a single main window Metro application with tabs (TabItem(s) as UserControl DataContext="{Binding}") in which different data is displayed / different methods used.

What I've found myself struggling with is INotifyPropertyChanged (I wasn't able to understand the solution of my problem from similar examples/questions) interface's concept. I'm trying to make that if new data is entered in a window (which is initialized from one of the UserControl), a ComboBoxin another UserControl (or TabItem) would be automatically updated. Here's what I have:

UserControl1.xaml

 public partial class UserControl1: UserControl
{
    private userlist addlist;
    public UserControl1()
    {
        InitializeComponent();
        fillcombo();
    }
      public void fillcombo()
     {
         Fillfromdb F = new Fillfromdb(); // class that simply connects 
         // to a database sets a datatable as ListCollectionView
         addlist = new addlist { List = F.returnlistview() }; // returns ListCollectionView
         UsersCombo.ItemsSource = addlist.List;
     }

userlist.cs

    public class userlist: INotifyPropertyChanged
   {
    private ListCollectionView _list;
    public ListCollectionView List
    {
        get { return this._list; }
        set
        {
            if (this._list!= value)
            {
                this._list= value;
                this.NotifyPropertyChanged("List");
            }
        }
    }
    public event PropertyChangedEventHandler PropertyChanged;

    public void NotifyPropertyChanged(string propertyName)
    {
        if (this.PropertyChanged != null)
            this.PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
    }
   }

Registration.xaml (called from another UserControl)

 public partial class Registration: MetroWindow
{
    public Registration()
    {
        InitializeComponent();
    } 
    private void confirm_button_click(object sender, RoutedEventArgs e)
    {
         // new user is saved to database
         // * here is where I don't know what to do, how to update the ItemSource

    }
   }

Here's the ComboBox's setting in UserControl.xaml:

<ComboBox x:Name="UsersCombo" 
 ItemsSource="{Binding List, Mode=OneWay, UpdateSourceTrigger=PropertyChanged}"/>

Since I don't have any programming education/experience a very generic advice/explanation would be very much appreciated.

EDIT: Registration.xaml with propertychanged (still doesn't work):

 public partial class Registration : MetroWindow
{
    public userlist instance = new userlist();
    public ListCollectionView _list1;
    public ListCollectionView List1
    {
        get { return this._list1; }
        set
        {
            if (this._list1 != value)
            {
                this._list1 = value;
                this.NotifyPropertyChanged("List1");
            }
        }
    }
    public event PropertyChangedEventHandler PropertyChanged;

    public void NotifyPropertyChanged(string propertyName)
    {
        if (this.PropertyChanged != null)
            this.PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
    }


    public Registration()
    {
        InitializeComponent();
        instance.List.PropertyChanged += ComboPropertyChangedHandler();
   }
    private void confirm_button_click(object sender, RoutedEventArgs e)
    {
         // new user is save to database
         // still don't now what to do with new ListCollectionView from database
    }
    public void ComboPropertyChangedHandler(object obj)
    {
        List1 = instance.List; // when new data from database should be loaded?
    }
L. Rendagan
  • 91
  • 1
  • 1
  • 4

1 Answers1

0

This is where PropertyChanged event comes handy. Bind the combobox in second xaml page to a List and create a similar property like in first xaml.

In second xaml.cs

public partial class Registration: MetroWindow, INotifyPropertyChanged
{
    private userlist instance = new userlist();
    private ListCollectionView _list1;
    public ListCollectionView List1
    {
        get { return this._list1; }
        set
    {
        if (this._list1 != value)
        {
            this._list1 = value;
            this.NotifyPropertyChanged("List1");
        }
    }
}
public Registration()
{
    InitializeComponent();
    instance.List.PropertyChanged += ComboPropertyChangedHandler();
} 

private void ComboPropertyChangedHandler(object obj)
{
    List1 = instance.List;
    //or iterate through the list and add as below
    foreach(var item in instance.List)
    {
        List1.Add(item);
    }
}
private void confirm_button_click(object sender, RoutedEventArgs e)
    {
         // new user is saved to database
         // * here is where I don't know what to do, how to update the ItemSource
    }
}
ViVi
  • 4,339
  • 8
  • 29
  • 52
  • For some reason it says that `CollectionView.PropertyChanged` is inaccessible duo to it's protection level and there is no argument for `+=ComboPropertyChangedHandler()` – L. Rendagan May 06 '16 at 08:01
  • Ensure class and member is **public** – ViVi May 06 '16 at 08:04
  • I did that. but it says the same :( – L. Rendagan May 06 '16 at 08:08
  • Just for me to be absolutely sure, this all code belongs to one window? Because without `public event PropertyChangedEventHandler` and `public void NotifyPropertyChanged(string propertyName)` (like in `userlist` class), `NotifyPropertyChanged("List1");` causes an error too. – L. Rendagan May 06 '16 at 08:13
  • Posted the code, just cannot understand how the Source should be updated. – L. Rendagan May 06 '16 at 08:50
  • I have edited the code. You need to implement the interface **INotifyPropertyChanged** the events NotifyPropertyChanged is to be implemented from this interface. – ViVi May 06 '16 at 17:17