Browse Source

Allow changing virtualization mode in test app.

Not yet working correctly.
pull/545/head
Steven Kirk 10 years ago
parent
commit
ae2ea31c6e
  1. 5
      samples/VirtualizationTest/MainWindow.xaml
  2. 12
      samples/VirtualizationTest/ViewModels/MainWindowViewModel.cs
  3. 12
      src/Avalonia.Controls/Presenters/ItemVirtualizer.cs
  4. 18
      src/Avalonia.Controls/Presenters/ItemsPresenter.cs
  5. 35
      tests/Avalonia.Controls.UnitTests/Presenters/ItemsPresenterTests_Virtualization.cs

5
samples/VirtualizationTest/MainWindow.xaml

@ -5,6 +5,8 @@
Margin="16 0 0 0"
MinWidth="150"
Gap="4">
<DropDown Items="{Binding VirtualizationModes}"
SelectedItem="{Binding VirtualizationMode}"/>
<TextBox Watermark="Item Count"
UseFloatingWatermark="True"
Text="{Binding ItemCount}"/>
@ -28,7 +30,8 @@
<ListBox Name="listBox"
Items="{Binding Items}"
SelectedItems="{Binding SelectedItems}"
SelectionMode="Multiple">
SelectionMode="Multiple"
VirtualizationMode="{Binding VirtualizationMode}">
<ListBox.ItemTemplate>
<DataTemplate>
<TextBlock Text="{Binding Header}"/>

12
samples/VirtualizationTest/ViewModels/MainWindowViewModel.cs

@ -2,8 +2,10 @@
// Licensed under the MIT license. See licence.md file in the project root for full license information.
using System;
using System.Collections.Generic;
using System.Linq;
using Avalonia.Collections;
using Avalonia.Controls;
using ReactiveUI;
namespace VirtualizationTest.ViewModels
@ -15,6 +17,7 @@ namespace VirtualizationTest.ViewModels
private int _newItemIndex;
private IReactiveList<ItemViewModel> _items;
private string _prefix = "Item";
private ItemVirtualizationMode _virtualizationMode = ItemVirtualizationMode.Simple;
public MainWindowViewModel()
{
@ -50,6 +53,15 @@ namespace VirtualizationTest.ViewModels
private set { this.RaiseAndSetIfChanged(ref _items, value); }
}
public ItemVirtualizationMode VirtualizationMode
{
get { return _virtualizationMode; }
set { this.RaiseAndSetIfChanged(ref _virtualizationMode, value); }
}
public IEnumerable<ItemVirtualizationMode> VirtualizationModes =>
Enum.GetValues(typeof(ItemVirtualizationMode)).Cast<ItemVirtualizationMode>();
public ReactiveCommand<object> AddItemCommand { get; private set; }
public ReactiveCommand<object> RecreateCommand { get; private set; }

12
src/Avalonia.Controls/Presenters/ItemVirtualizer.cs

@ -14,8 +14,10 @@ namespace Avalonia.Controls.Presenters
/// <summary>
/// Base class for classes which handle virtualization for an <see cref="ItemsPresenter"/>.
/// </summary>
internal abstract class ItemVirtualizer : IVirtualizingController
internal abstract class ItemVirtualizer : IVirtualizingController, IDisposable
{
private bool disposedValue;
/// <summary>
/// Initializes a new instance of the <see cref="ItemVirtualizer"/> class.
/// </summary>
@ -181,6 +183,14 @@ namespace Avalonia.Controls.Presenters
return false;
}
/// <inheritdoc/>
public virtual void Dispose()
{
VirtualizingPanel.Controller = null;
VirtualizingPanel.Children.Clear();
Owner.ItemContainerGenerator.Clear();
}
/// <summary>
/// Invalidates the current scroll.
/// </summary>

18
src/Avalonia.Controls/Presenters/ItemsPresenter.cs

@ -32,6 +32,9 @@ namespace Avalonia.Controls.Presenters
KeyboardNavigation.TabNavigationProperty.OverrideDefaultValue(
typeof(ItemsPresenter),
KeyboardNavigationMode.Once);
VirtualizationModeProperty.Changed
.AddClassHandler<ItemsPresenter>(x => x.VirtualizationModeChanged);
}
/// <summary>
@ -113,5 +116,20 @@ namespace Avalonia.Controls.Presenters
var maxY = Math.Max(scrollable.Extent.Height - scrollable.Viewport.Height, 0);
return new Vector(Clamp(value.X, 0, maxX), Clamp(value.Y, 0, maxY));
}
private void VirtualizationModeChanged(AvaloniaPropertyChangedEventArgs e)
{
_virtualizer?.Dispose();
_virtualizer = ItemVirtualizer.Create(this);
if (Items != null && Panel != null)
{
_virtualizer.ItemsChanged(
Items,
new NotifyCollectionChangedEventArgs(NotifyCollectionChangedAction.Reset));
}
((ILogicalScrollable)this).InvalidateScroll?.Invoke();
}
}
}

35
tests/Avalonia.Controls.UnitTests/Presenters/ItemsPresenterTests_Virtualization.cs

@ -59,6 +59,20 @@ namespace Avalonia.Controls.UnitTests.Presenters
Assert.True(((ILogicalScrollable)target).IsLogicalScrollEnabled);
}
[Fact]
public void Parent_ScrollContentPresenter_Properties_Should_Be_Set()
{
var target = CreateTarget();
target.ApplyTemplate();
target.Measure(new Size(100, 100));
target.Arrange(new Rect(0, 0, 100, 100));
var scroll = (ScrollContentPresenter)target.Parent;
Assert.Equal(new Size(0, 20), scroll.Extent);
Assert.Equal(new Size(0, 10), scroll.Viewport);
}
[Fact]
public void Should_Fill_Panel_With_Containers()
{
@ -138,6 +152,27 @@ namespace Avalonia.Controls.UnitTests.Presenters
}
}
[Fact]
public void Changing_VirtualizationMode_Simple_To_None_Should_Update_Scroll_Properties()
{
var target = CreateTarget();
target.ApplyTemplate();
target.Measure(new Size(100, 100));
target.Arrange(new Rect(0, 0, 100, 100));
var scroll = (ScrollContentPresenter)target.Parent;
Assert.Equal(10, target.Panel.Children.Count);
Assert.Equal(new Size(0, 20), scroll.Extent);
Assert.Equal(new Size(0, 10), scroll.Viewport);
target.VirtualizationMode = ItemVirtualizationMode.None;
Assert.Equal(20, target.Panel.Children.Count);
Assert.Equal(new Size(0, 200), scroll.Extent);
Assert.Equal(new Size(0, 100), scroll.Viewport);
}
private static ItemsPresenter CreateTarget(
ItemVirtualizationMode mode = ItemVirtualizationMode.Simple,
Orientation orientation = Orientation.Vertical,

Loading…
Cancel
Save