Kobi Hari
Kobi Hari

Reputation: 1248

ItemsWrapGrid hides items passed an offset

I am writing a Windows 8.1 Application where I am using a very long GridView. I am using UI virtualization, and the view model contains an observable collection with 100K items.

<GridView ItemsSource="{Binding Items}">
    <GridView.ItemsPanel>
        <ItemsPanelTemplate>
            <ItemsWrapGrid Orientation="Vertical"/>
        </ItemsPanelTemplate>
    </GridView.ItemsPanel>
    <GridView.ItemTemplate>
        <DataTemplate>
            <Border 
                Background="LightBlue"
                Height="200" Width="200"
                >
                <TextBlock 
                    Text="{Binding Index}" 
                    VerticalAlignment="Center" HorizontalAlignment="Center" 
                    FontSize="30"
                    />
            </Border>
        </DataTemplate>
    </GridView.ItemTemplate>
</GridView>

On screen it looks like this: enter image description here

When using the default items panel (ItemsWrapGrid) and scrolling towards the end of the list, at some point items start disappearing.

enter image description here

I have tested it with various sizes of items, and the clipping always starts at the same scroll offset (around 2,000,000 pixels). When I replace the panel with a WrapGrid the bug does not happen. I understand that the ItemsWrapGrid has a better virtualization, and would like to use it, but the bug is of course unacceptable.

Is there a way to resolve this bug while still using ItemsWrapGrid?

Upvotes: 0

Views: 367

Answers (1)

ezaspi
ezaspi

Reputation: 714

just after posting my OutOfMemoryException quandary, I did a little bit more research and I think I have a solution for you, I found this:

The concept of a viewport is critical to UI virtualization because the framework must create the elements that are likely to be shown. In general, the viewport of an ItemsControl is the extent of the logical control. For example, the viewport of a ListView is the width and height of the ListView element. Some panels allow child elements unlimited space, examples being ScrollViewer and a Grid, with auto-sized rows or columns. When a virtualized ItemsControl is placed in a panel like that, it takes enough room to display all of its items, which defeats virtualization. Restore virtualization by setting a width and height on the ItemsControl. ListView and GridView UI optimization

So I added this to your GridView ItemsSource:

<GridView ItemsSource="{Binding Items}" VirtualizingStackPanel.VirtualizationMode="Recycling" Width="800" Height="800">

It looks like it needed a Width and Height. enter image description here

Upvotes: 1

Related Questions