必须适配VirtualizingCollection的实现,请查看以下文章http://www.codeproject.com/Articles/34405/WPF-Data-Virtualization。
我使用适用于 Windows Phone 8.1 运行时应用程序的 VirtualizingCollection 编写了一个示例应用程序。
public class ThumbnailItem
{
public Uri ImageUri { get; set; }
}
稍后编写 ThumbnailItem 提供程序。
public class ThumbnailProvider : IItemsProvider<ThumbnailItem>
{
private readonly int _itemsCount;
public ThumbnailProvider(int itemsCount)
{
_itemsCount = itemsCount;
}
public int FetchCount()
{
return _itemsCount;
}
public IList<ThumbnailItem> FetchRange(int startIndex, int count)
{
var items = new List<ThumbnailItem>();
while (count-- > 0)
{
items.Add(new ThumbnailItem()
{
ImageUri = new Uri("ms-appx:///Assets/Square71x71Logo.scale-240.png")
});
}
return items;
}
}
然后,在您的 ViewModel 中,您必须创建一个 IList 属性并使用 VirtualizingCollection 的实现来设置该值。我建议你使用 AsyncVirtualizingCollection。
Items = new AsyncVirtualizingCollection<ThumbnailItem>(new ThumbnailProvider(1000000), 100);
最后,在视图上,您必须使用 ViewModel 的实例设置 DataContext 对象,您的 ListView 应该类似于:
<ListView
ItemsSource="{Binding Items,Mode=OneWay}"
VirtualizingStackPanel.VirtualizationMode="Recycling">
<ListView.ItemsPanel>
<ItemsPanelTemplate>
<WrapGrid Orientation="Horizontal"/>
</ItemsPanelTemplate>
</ListView.ItemsPanel>
<ListView.ItemTemplate>
<DataTemplate>
<Grid Margin="0 0 20 20">
<Image Source="{Binding ImageUri,Mode=OneTime}"
Width="72" Height="72"/>
</Grid>
</DataTemplate>
</ListView.ItemTemplate>
当然,提供者的逻辑必须根据你的要求改变,我写的代码只是一个示例。
如果对你有帮助,请标记为答案。
最好的问候,
拒绝
编辑
朋友@Quincy,我贴了一个简单的例子,你可以适应它。也许对于您的应用程序,ThumbnailItem 类将包含指示 IsolateStorageFile 文件名的 Filename 属性。在这种情况下,您必须使用转换器创建一个 Binding,因此您需要实现一个 IValueConverter 对象以使用 IsolateStorageFile 创建一个 BitmapImage 实例。
BitmapImage image = new BitmapImage();
image.SetSource(sourceFile);
返回图片;
关于图片关闭,VirtualizingCollection定义了一个pagesize,默认为100。您的 IsolateStorageFiles 将用于在您的 IValueConverter 对象中创建 BitmapImage 一次。之后VirtualizingCollection会删除不使用的旧页面(不显示,检查VirtualizingCollection实现),最后GC将关闭并处理BitmapImage。
移植 VirtualizingCollection 很简单,我记得我刚刚对 AsyncVirtualizingCollection 类进行了更改。我的解决方案很简单:
将 ThreadPool.QueueUserWorkItem 替换为 ThreadPool.RunAsync。
将 Trace 替换为 Debug(只是调试消息,不是很重要)。
使用以下方法替换 SynchronizationContext 方法调用:
(对于 Windows 手机应用)CoreApplication.MainView.CoreWindow.Dispatcher。
(对于 Windows 应用)CoreApplication.MainView.Dispatcher。
希望对你有帮助。