Reputation: 1508
I have a problem displaying data in a GridView. I cannot seem to get it right and I could not find any other topics regarding this. Probably I'm overseeing something really simple.
I have got this gridview:
<GridView ItemsSource="{Binding Source={StaticResource itemsViewSource}}" Width="383" Height="216"/>
<Button Content="Button" Click="Button_Click" />
I have got this CollectionViewSource:
<Page.Resources>
<CollectionViewSource x:Name="itemsViewSource" Source="{Binding NamesList, Mode=TwoWay}"/>
</Page.Resources>
And this Code behind:
Person Class:
public class Person : INotifyPropertyChanged {
private string m_name;
private string m_gender;
public event PropertyChangedEventHandler PropertyChanged;
public string Name {
get {
return m_name;
}
set {
m_name = value;
RaisePropertyChanged("Name");
}
}
public string Gender {
get {
return m_gender;
}
set {
m_gender = value;
RaisePropertyChanged("Gender");
}
}
protected void RaisePropertyChanged(string PropertyName) {
var eventhandler = this.PropertyChanged;
if (eventhandler != null) {
eventhandler(this, new PropertyChangedEventArgs(PropertyName));
}
}
}
Mainpage:
public sealed partial class MainPage : Page{
public ObservableCollection<Person> NamesList {get; set;}
public MainPage(){
this.InitializeComponent();
Person p = new Person();
Person p2 = new Person();
Person p3 = new Person();
p.Name = "Piet";
p.Gender = "Male";
p2.Name = "Pietin";
p2.Gender = "Female";
p3.Name = "Piet de tweede";
p3.Gender = "Male";
NamesList = new ObservableCollection<Person>();
NamesList.Add(p);
NamesList.Add(p2);
NamesList.Add(p3);
}
: private void Button_Click(object sender, RoutedEventArgs e) {
itemsViewSource.Source = NamesList;
}
}
Why is my GridView not showing any data or adding data on button clicks?
@edit 16:16 - 15-09-2014 If after the click I add the following, it shows the items. But that is not how it is supposed to be.
itemsViewSource.Source = NamesList;
@edit 09:04 - 16-09-2014
I added this debugging image to show that the binding is good, he can find the NamesList. But if I look at the itemsViewSource it says the Source is null.
Upvotes: 1
Views: 819
Reputation: 1508
I have found two answers.
Answer 1:
Simply add this to the < page >
DataContext="{Binding RelativeSource={RelativeSource Self}}
Answer 2:
I have to set the DataContext in the Mainpage and refer it to a Class (In my case a Person class) (In my opinion it is not logical and setting the following line of code is way easier:
itemsViewSource.Source = NamesList;
I have made the following adaptions;
MainPage:
public sealed partial class MainPage : Page{
public MainPage(){
this.InitializeComponent();
DataContext = new Person();
}
}
Person Class (Added the following) (I have to see this more as a Data Class):
public ObservableCollection<Person> NamesList { get; set; }
public Person() {
Person p = new Person("Piet", "Male");
Person p2 = new Person("Pietin", "Female");
NamesList = new ObservableCollection<Person>();
NamesList.Add(p);
NamesList.Add(p2);
}
public Person(string Name, string Gender){
m_name = Name;
m_gender = Gender;
}
If I set it up like this I am able to use the source binding of the CollectionViewSource correctly. (Where the source binding was null before.)
<CollectionViewSource x:Name="itemsViewSource" Source="{Binding NamesList, Mode=TwoWay}"/>
Upvotes: 0
Reputation: 21261
Since you are using a plain List<T>
, WPF has no way of knowing when items are added or removed.
Try using an ObservableCollection<T>
instead.
EDIT:
NamesList
needs to be a property. WPF can only bind to properties:
public sealed partial class MainPage : Page
{
public ObservableCollection<Person> NamesList { get; private set; }
public MainPage(){
this.InitializeComponent();
Person p = new Person();
Person p2 = new Person();
p.Name = "Piet";
p.Gender = "Male";
p2.Name = "Pietin";
p2.Gender = "Female";
NamesList = new ObservableCollection<Person>();
NamesList.Add(p);
NamesList.Add(p2);
}
Upvotes: 2