I have a ListBox with the property VirtualizingStackPanel.VirtualizationMode set to "Recycling".
I am binding a custom collection (implements IList
and IList<T>
) to it.
Now, if I understand right, when data is bound, GetEnumerator is called.
And then property public T this[int index] { }
is called for every item in the current view.
My question is how to get the items that are currently visible (after the data is loaded)?
After trying to figure out something similar, I thought I would share my result here (as it seems easier than the other responses):
Simple visibility test I got from here.
private static bool IsUserVisible(FrameworkElement element, FrameworkElement container)
{
if (!element.IsVisible)
return false;
Rect bounds =
element.TransformToAncestor(container).TransformBounds(new Rect(0.0, 0.0, element.ActualWidth, element.ActualHeight));
var rect = new Rect(0.0, 0.0, container.ActualWidth, container.ActualHeight);
return rect.Contains(bounds.TopLeft) || rect.Contains(bounds.BottomRight);
}
Afterwards you can loop through the ListBoxItems and use that test to determine which are visible.
private List<object> GetVisibleItemsFromListbox(ListBox listBox, FrameworkElement parentToTestVisibility)
{
var items = new List<object>();
foreach (var item in PhotosListBox.Items)
{
if (IsUserVisible((ListBoxItem)listBox.ItemContainerGenerator.ContainerFromItem(item), parentToTestVisibility))
{
items.Add(item);
}
else if (items.Any())
{
break;
}
}
return items;
}
Sometime back i also faced the same issue. I found a workaround of my problem by using "SelectedItem" of Listbox as selected item would be visible always. In my case it was Scrolling which was causing issue. You can have a look if it helps -
Virtualization issue in listbox
Also - Virtualization scrollview - Good One
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With