У меня есть ObservableCollection, который прекрасно работает, но я не могу удалить связывающую ошибку, которая появляется во время выполнения, когда я очищаю этот ObservableCollection:Binding Ошибка выполнения клирингового ObservableCollection
System.Windows.Data Information: 21 : BindingExpression cannot retrieve value from null data item. This could happen when binding is detached or when binding to a Nullable type that has no value. BindingExpression:Path=Icon; DataItem='NamedObject' (HashCode=40835417); target element is 'Image' (Name=''); target property is 'Source' (type 'ImageSource')
Я сделал небольшой код, чтобы воспроизвести моя проблема, что я показываю ниже: (Вид):
<Button Height="40" Width="40" Click="Button_Click"></Button>
<ListBox ItemsSource="{Binding ProductList}">
<ListBox.ItemsPanel>
<ItemsPanelTemplate>
<UniformGrid IsItemsHost="True"/>
</ItemsPanelTemplate>
</ListBox.ItemsPanel>
<ListBox.ItemTemplate>
<DataTemplate>
<Grid>
<Grid.RowDefinitions>
<RowDefinition/>
<RowDefinition Height="Auto" />
</Grid.RowDefinitions>
<Image Height="32" Source="{Binding Icon}" Stretch="Fill" Width="32"/>
<Label Grid.Row="1" Content="{Binding Description}"/>
</Grid>
</DataTemplate>
</ListBox.ItemTemplate>
</ListBox>
public ObservableCollection<Product> ProductList { get; set; }
public void TestList()
{
ProductList = new ObservableCollection<Product>();
ProductList.Add(new Product("Product1", "pack://application:,,,/Product1.png"));
ProductList.Add(new Product("Product2", "pack://application:,,,/Product2.png"));
ProductList.Add(new Product("Product3", "pack://application:,,,/Product3.png"));
}
private void Button_Click(object sender, RoutedEventArgs e)
{
ProductList.Clear();
ProductList.Add(new Product("Product4", "pack://application:,,,/Product4.png"));
}
И мой произво кт класс:
public class Product : INotifyPropertyChanged
{
#region "## INotifyPropertyChanged Members ##"
public event PropertyChangedEventHandler _propertyChanged;
public event PropertyChangedEventHandler PropertyChanged
{
add { this._propertyChanged += value; }
remove { this._propertyChanged -= value; }
}
protected virtual void OnPropertyChanged(string propertyName)
{
App.Current.Dispatcher.BeginInvoke((Action)delegate
{
if (this._propertyChanged != null)
this._propertyChanged(this, new PropertyChangedEventArgs(propertyName));
});
}
#endregion
public string Description
{
get { return this.description; }
set
{
this.description = value;
this.OnPropertyChanged("Description");
}
}
private string description;
public BitmapImage Icon
{
get { return this.icon; }
set
{
this.icon = value;
this.OnPropertyChanged("Icon");
}
}
private BitmapImage icon;
public Product(string desc, string iconPath)
{
Description = desc;
BitmapImage bi = new BitmapImage(new Uri(iconPath));
bi.Freeze();
Icon = bi;
}
}
Ошибка появляется при нажатии на кнопку, и следующая строка выполняется: ProductList.Clear();
я сделал много испытаний:
Индивидуально удалять элементы из списка
Используйте Fallback и TargetNullValue:
<Image Height="32" Source="{Binding Icon, FallbackValue='pack://application:,,,/transparent.png', TargetNullValue='pack://application:,,,/transparent.png'}" Stretch="Fill" Width="32"/>
Любые идеи?
Вы попробовали ProductList.ClearItems()? https://msdn.microsoft.com/en-us/library/ms654925(v=vs.110).aspx – AVK
Я могу удалить список продуктов без проблем. Ошибка не воспроизводится. – jsanalytics
Ваша реализация 'INotifyPropertyChanged' выглядит немного грязной, и она может даже не понадобиться, если вы не будете динамически изменять описание и/или значок для отдельных продуктов в своем списке. – jsanalytics