我有一个包含大量嵌套数据的 WPF TreeView ,我已启用虚拟化,该虚拟化在加载数据方面发挥作用。但是滚动变得不稳定,直到整个 View 滚动一次然后它才稳定下来(仍然不是很好)。我已经覆盖了 ScrollViewer,我可以看到 VirtualizingStackPanel 中的范围高度在滚动时不规则地变化。
有谁知道解决这个问题的方法吗?
感谢任何帮助。
以下 TreeView Xaml 的相关部分:
<TreeView ItemsSource="{Binding Folders.ObservableTree}" Name="FoldersTreeView"
AutomationProperties.AutomationId="foldersview_treeview_folders" TabIndex="0" PreviewMouseRightButtonDown="OnPreviewMouseRightButtonDown"
VirtualizingStackPanel.CleanUpVirtualizedItem="VirtualizingStackPanel_OnCleanUpVirtualizedItem"
ScrollViewer.VerticalScrollBarVisibility="Auto"
ScrollViewer.IsDeferredScrollingEnabled ="True"
VirtualizingStackPanel.IsVirtualizing="True"
ScrollViewer.HorizontalScrollBarVisibility="Disabled"
VirtualizingStackPanel.ScrollUnit="Pixel"
VirtualizingStackPanel.VirtualizationMode="Standard"
VirtualizingPanel.IsVirtualizingWhenGrouping="True"
VirtualizingStackPanel.CacheLengthUnit="Item">
<TreeView.ItemsPanel>
<ItemsPanelTemplate>
<VirtualizingStackPanel IsItemsHost="True" CanVerticallyScroll="True"/>
</ItemsPanelTemplate>
</TreeView.ItemsPanel>
<TreeView.Template>
<ControlTemplate>
<view:ScrollViewer2 Padding="{TemplateBinding Control.Padding}" Focusable="False" Name="TreeViewScrollViewer"
CanContentScroll="True">
<ItemsPresenter SnapsToDevicePixels="{TemplateBinding UIElement.SnapsToDevicePixels}" />
</view:ScrollViewer2>
</ControlTemplate>
</TreeView.Template>
最佳答案
仅当 ItemsPresenter
中的所有项目都有效时,虚拟化才能正常工作。 (并且 TreeView
实现为具有嵌套 ItemsPresenter
的 ItemsPresenters
)具有相同的高度。与 TreeView
通常情况并非如此。
这样做的主要原因是,因为它是虚拟化的,所以它必须估计某些本来可以精确测量的东西:
VirtualizationStackPanel
将假设所有 child 与当前可见的 child 具有相同的高度,并根据此估计所需的高度(而不是实际测量所有 child ),这将报告给 ScrollViewer
,如果子项的高度可变,则此估计值可能会相差很大,并且会根据滚动位置而变化,从而导致滚动条不断调整大小。
关于wpf - Treeview 虚拟化和不稳定的滚动,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/42132989/