我有一个“Hello World”类型的应用程序 listbox.ItemsSource =玩家。玩家是实施INotifyPropertyChanged的玩家的ObservableCollection。
当我在Players构造函数中添加项目时,项目显示正常。 当我更新现有项目时,会反映更改。 但是,当我为ObserveableCollection添加或删除项目时,列表框不会反映添加/删除的项目。
主页中的xaml:
<Grid x:Name="ContentPanel" Grid.Row="1" Margin="12,0,12,0">
<ListBox Name="lstPlayers" ItemsSource="{Binding}" Margin="12,66,13,24" Grid.Row="1">
<ListBox.ItemTemplate>
<DataTemplate>
<!--<StackPanel Background="#FFD1D1D1">-->
<Grid Margin="0,0,0,0" Grid.RowSpan="2">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="60"/>
<ColumnDefinition Width="*"/>
</Grid.ColumnDefinitions>
<TextBlock Grid.Column="0" Text="{Binding Number}" FontSize="48" />
<TextBlock Grid.Column="1" Text="{Binding Name}" FontSize="48" />
</Grid>
<!--</StackPanel>-->
</DataTemplate>
</ListBox.ItemTemplate>
</ListBox>
<Button Content="Button" Height="95" HorizontalAlignment="Left" Margin="183,350,0,0" Name="button1" VerticalAlignment="Top" Width="260" Click="button1_Click" />
<Button Content="Button" Height="72" HorizontalAlignment="Left" Margin="198,472,0,0" Name="button3" VerticalAlignment="Top" Width="232" Click="button3_Click" />
</Grid>
列表框绑定在后面的代码中:
lstPlayers.ItemsSource = plys;
玩家等级:
using System.ComponentModel;
namespace DatabindList
{
public class TcrPlayer : INotifyPropertyChanged
{
public event PropertyChangedEventHandler PropertyChanged;
private void NotifyPropertyChanged(string propertyName)
{
if (PropertyChanged != null)
{
PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
}
}
private string _name;
public string Name
{
get { return _name; }
set
{
if (_name != value)
_name = value;
NotifyPropertyChanged("Name");
}
}
}
}
球员班:
using System.Collections.Generic;
using System.Collections.ObjectModel;
namespace DatabindList
{
public class TcrPlayers : List<TcrPlayer>
{
public ObservableCollection<TcrPlayers> Items { get; private set; }
public TcrPlayers()
{
//these are displayed
Add(new TcrPlayer { Name = "Christine"});
Add(new TcrPlayer { Name = "Janet"});
Add(new TcrPlayer { Name = "Ian"});
}
public void AddPlayer()
{
//THIS HAS NO EFFECT ON THE LISTBOX
Add(new TcrPlayer { Name = "Newbie", Number = "99" });
}
}
}
我可以使用
中的主页后面的代码更新列表中的现有项目 var itm = lstPlayers.SelectedItem as TcrPlayer;
itm.Name = "Fred";
但我无法反映对Players集合中的项目数量所做的任何更改。
答案 0 :(得分:4)
TcrPlayers
派生自List<TcrPlayer>
并将项目添加到自身。但是,ObservableCollection<TcrPlayer>
属性未以任何方式连接到该列表。假设plys
是TcrPlayers
,你根本不绑定ObservableCollection
- 你绑定到一个不可观察的List
。
继承ObservableCollection<TcrPlayer>
而不是List<TcrPlayer>
并删除未使用的属性可能会让您更接近您想要的位置。
顺便说一句,您并不经常使用此模式,因为除非您添加新功能,否则从集合类继承通常不被认为非常有用。通常,您只有父视图模型的ObservableCollection<TcrPlayer>
属性,并将列表框的ItemsSource
绑定到该视图。
说到这一点,您还要将ItemsSource
设置为两次 - 在您的XAML中设置为{Binding}
,即当前DataContext
,以及代码隐藏。
答案 1 :(得分:2)
您不使用ObservableCollection
。相反,您的TcrPlayers
类本身就是一个列表(派生自List<T>
)。
来自ObservableCollection
并删除您的Items
媒体资源或使用Items.Add(..)
代替Add()
。
E.g。
public class TcrPlayers : ObservableCollection<TcrPlayer>
{
..
或
public class TcrPlayers
{
public ObservableCollection<TcrPlayers> Items { get; private set; }
public TcrPlayers()
{
//these are displayed
Items.Add(new TcrPlayer { Name = "Christine"});
Items.Add(new TcrPlayer { Name = "Janet"});
Items.Add(new TcrPlayer { Name = "Ian"});
}