locked
Bug in ListView with VirtualizingStackPanel.VirtualizationMode="Recycling" RRS feed

  • Question

  • Hi,

    I have recently discovered the attached property "VirtualizingStackPanel.VirtualizingMode" from SP1. Setting it to "Recycle" drastically increases the speed when scrolling many items in a ListView, so I would not like to miss this in our application.

    But there seems to be a bug. When I put own WPF controls in the ListView, which use the Loaded event, under certain circumstances there is one item in the recycle-container, where the Loaded event is not called.

    In the following example you get a ListView with three columns, where the third one is out of view at the beginning. It contains my own Controls, which show in the view whether they have been "Loaded" or not ('true' or 'false'). When you just scroll to the right with the horizontal scroll bar and then a few items down, everything works fine, but instead try to decrease the width of the first column so that cou can see the third column completely and then scroll down. Then periodically items appear which say "false".

    Is it a known problem and is it reproducable for you?

    Thanks for any response,
    Alex


    using System;
    using System.Collections.ObjectModel;
    using System.Windows;
    using System.Windows.Controls;
    
    namespace WpfApplication10
    {
        /// <summary>
        /// Interaction logic for Window1.xaml
        /// </summary>
        public partial class Window1 : Window
        {
            public Window1 ()
            {
                InitializeComponent ();
    
                ObservableCollection<MyControl> collection = new ObservableCollection<MyControl> ();
                for (int i = 0; i < 10000; i++)
                {
                    collection.Add (new MyControl (i.ToString ("d4")));
                }
                listView.ItemsSource = collection;
            }
        }
    
    
        class MyControl : Control
        {
            public static readonly DependencyProperty AnyTextProperty =
                DependencyProperty.Register ("AnyText", typeof (string), typeof (MyControl));
    
            public string AnyText
            {
                get { return (string) GetValue (AnyTextProperty); }
                set { SetValue (AnyTextProperty, value); }
            }
    
            public MyControl (string id)
            {
                m_id = id;
                UpdateText ();
    
                Loaded += ViewModel_Loaded;
                Unloaded += ViewModel_Unloaded;
            }
    
            private void ViewModel_Loaded (object sender, RoutedEventArgs args)
            {
                m_isLoaded = true;
                UpdateText ();
            }
    
            private void ViewModel_Unloaded (object sender, RoutedEventArgs args)
            {
                m_isLoaded = false;
                UpdateText ();
            }
    
            private void UpdateText ()
            {
                AnyText = m_id + ", is loaded: " + m_isLoaded.ToString ();
            }
    
            private bool m_isLoaded = false;
            private string m_id;
        }
    }
    
    <Window x:Class="WpfApplication10.Window1"
            xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
            xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
            xmlns:local="clr-namespace:WpfApplication10"
            Title="Window1" Height="600" Width="500">
    
        <Window.Resources>
            <Style TargetType="{x:Type local:MyControl}">
                <Setter Property="Template">
                    <Setter.Value>
                        <ControlTemplate TargetType="{x:Type local:MyControl}">
                            <TextBlock Text="{Binding Path=AnyText}" />
                        </ControlTemplate>
                    </Setter.Value>
                </Setter>
            </Style>
        </Window.Resources>
        
        <DockPanel>
            <TextBlock Margin="4" TextWrapping="Wrap" DockPanel.Dock="Top"
                       Text="The third column contains the bool value which shows whether the Loaded event of the item has been called." />
            <TextBlock Margin="4" TextWrapping="Wrap" DockPanel.Dock="Top"
                       Text="Everything works as expected (everywhere is a 'true') when you scroll horizontally to the right and then down." />
            <TextBlock Margin="4" TextWrapping="Wrap" DockPanel.Dock="Top"
                       Text="But try to decrease the width of the first column until you see the third column completely (and the horizontal scrollbar disappears) and then scroll down..." />
            <ListView Name="listView"
                      SelectionMode="Single"
                      Margin="8"
                      VerticalAlignment="Stretch" 
                      HorizontalAlignment="Stretch"
                      VirtualizingStackPanel.VirtualizationMode="Recycling">
                <ListView.View>
                    <GridView>
                        <GridViewColumn Width="Auto" Header="Header 1" >
                            <GridViewColumn.CellTemplate>
                                <DataTemplate>
                                    <TextBlock Text="Don´t scroll horizontally, but reduce width of this column and then scroll down a bit" />
                                </DataTemplate>
                            </GridViewColumn.CellTemplate>
                        </GridViewColumn>
                        <GridViewColumn Width="Auto" Header="Header 2" >
                            <GridViewColumn.CellTemplate>
                                <DataTemplate>
                                    <TextBlock Text="Only to occupy space." />
                                </DataTemplate>
                            </GridViewColumn.CellTemplate>
                        </GridViewColumn>
                        <GridViewColumn Width="150" Header="Items should be up to date" />
                    </GridView>
                </ListView.View>
            </ListView>
        </DockPanel>
    </Window>
    

    • Edited by RealityHopper Monday, April 6, 2009 3:01 PM wrong formatted
    Monday, April 6, 2009 3:00 PM

All replies