I'm trying to modify a property of a grid depending on whether or not there are any items in the ObservableCollection<>
the ItemsSource
is bound to. I currently have an event for OnItemsSourceChanged
on the grid, but the problem is that ItemsSource
is an object, and without casting it, I don't have access to the CollectionChanged
event of the ObservableCollection<>
. The generic type of ObservableCollection<>
is undetermined until runtime and can be many things.
I've tried casting it with ItemsSource as ObservableCollection<object>
, but that returns null. No luck with ItemsSource as ObservableCollection<dynamic>
, either. Doing ItemsSource as IEnumerable<object>
works surprisingly enough, but that still does not allow me to access the CollectionChanged
event.
How can I cast my object to the underlying ObservableCollection<>
? I'd prefer to avoid using reflection, but I'm not going to be picky here.
What about casting it to INotifyCollectionChanged?
EDIT:
What you probably should be doing is something like this:
<TextBlock Visibility="{Binding MyObservableCollection.Count, Converter={StaticResource NonZeroToVisibleConverter}}">
Where NonZeroToVisibleConverter
is something like:
public class ColorConverter : IValueConverter
{
public object Convert(object value, Type targetType,
object parameter, CultureInfo culture)
{
return (int)value > 0 ? Visibility.Visible : Visibility.Collapsed
}
public object ConvertBack(object value, Type targetType,
object parameter, CultureInfo culture)
{
throw new NotImplmentedException();
}
}
OR probably even better
<Grid Name="MyGrid" ItemsSource="{Binding MyObservableCollection" />
<TextBlock Visibility="{Binding HasItems, ElementName=MyGrid, Converter={StaticResource BoolToVisibilityConverter}}" />
Last Resort For Future Reference
Your last resort would of been better to expose a property ShouldBe/IsVisible in you ViewModel and and bind to that in your View.
Consider the following code:
// where
ObservableCollection<Foo> foo = new();
element.ItemsSource = foo;
// then negotiate to non-generic types
var bar = element.ItemsSource as INotifyCollectionChanged;
bar.CollectionChanged += (NotifyCollectionChangedEventHandler)(delegate(object sender, NotifyCollectionChangedEventArgs e)
{
var collection = bar as ICollection;
// TODO: handle based on collection.Count
});
This way you are able to handle the event regardless of the generic types applied to ObservableCollection<T>
.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.