UI Popup 内的虚拟化
UI Virtualization inside Popup
我无法让虚拟化在 Popup
内的 TreeView
上运行,而 TreeView
在 Popup
外完美运行。
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="*"/>
</Grid.RowDefinitions>
<ToggleButton IsChecked="{Binding ElementName=Popup, Path=IsOpen, Mode=TwoWay}"
Content="Test"/>
<TreeView Grid.Row="1" ItemsSource="{Binding Nodes}" VirtualizingPanel.IsVirtualizing="True">
<TreeView.ItemTemplate>
<HierarchicalDataTemplate ItemsSource="{Binding Children}">
<TextBlock Text="{Binding Data}"/>
</HierarchicalDataTemplate>
</TreeView.ItemTemplate>
</TreeView>
<Popup x:Name="Popup" StaysOpen="True">
<TreeView ItemsSource="{Binding Nodes}" VirtualizingPanel.IsVirtualizing="True">
<TreeView.ItemTemplate>
<HierarchicalDataTemplate ItemsSource="{Binding Children}">
<TextBlock Text="{Binding Data}"/>
</HierarchicalDataTemplate>
</TreeView.ItemTemplate>
</TreeView>
</Popup>
</Grid>
ViewModel 和节点 class
public class ViewModel
{
public ObservableCollection<Node> Nodes { get; private set; }
public ViewModel()
{
Nodes = new ObservableCollection<Node>();
Node parent = new Node("Parent");
for (int i = 0; i < 10000; i++)
parent.Children.Add(new Node(i.ToString()));
Nodes.Add(parent);
}
}
public class Node
{
public string Data { get; set; }
public List<Node> Children { get; set; }
public Node(string data)
{
Data = data;
Children = new List<Node>();
}
}
当我展开 Window 内的树的父级时,它不需要时间,而展开内部弹出窗口需要大约 20 秒。
MS 在 2010s 中确认这是一个错误,并建议使用 ControlTemplate 将 ToggleButton 和 TreeView 合并到一个控件中,但它对我没有任何影响。
想通了,您需要做的就是为 Popup 指定一个最大高度(正常高度也可以)
<Popup x:Name="Popup" StaysOpen="True" MaxHeight="500">
不太确定为什么这有帮助。如果是自动的,可能 WPF 需要做太多的大小计算。
我无法让虚拟化在 Popup
内的 TreeView
上运行,而 TreeView
在 Popup
外完美运行。
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="*"/>
</Grid.RowDefinitions>
<ToggleButton IsChecked="{Binding ElementName=Popup, Path=IsOpen, Mode=TwoWay}"
Content="Test"/>
<TreeView Grid.Row="1" ItemsSource="{Binding Nodes}" VirtualizingPanel.IsVirtualizing="True">
<TreeView.ItemTemplate>
<HierarchicalDataTemplate ItemsSource="{Binding Children}">
<TextBlock Text="{Binding Data}"/>
</HierarchicalDataTemplate>
</TreeView.ItemTemplate>
</TreeView>
<Popup x:Name="Popup" StaysOpen="True">
<TreeView ItemsSource="{Binding Nodes}" VirtualizingPanel.IsVirtualizing="True">
<TreeView.ItemTemplate>
<HierarchicalDataTemplate ItemsSource="{Binding Children}">
<TextBlock Text="{Binding Data}"/>
</HierarchicalDataTemplate>
</TreeView.ItemTemplate>
</TreeView>
</Popup>
</Grid>
ViewModel 和节点 class
public class ViewModel
{
public ObservableCollection<Node> Nodes { get; private set; }
public ViewModel()
{
Nodes = new ObservableCollection<Node>();
Node parent = new Node("Parent");
for (int i = 0; i < 10000; i++)
parent.Children.Add(new Node(i.ToString()));
Nodes.Add(parent);
}
}
public class Node
{
public string Data { get; set; }
public List<Node> Children { get; set; }
public Node(string data)
{
Data = data;
Children = new List<Node>();
}
}
当我展开 Window 内的树的父级时,它不需要时间,而展开内部弹出窗口需要大约 20 秒。
MS 在 2010s 中确认这是一个错误,并建议使用 ControlTemplate 将 ToggleButton 和 TreeView 合并到一个控件中,但它对我没有任何影响。
想通了,您需要做的就是为 Popup 指定一个最大高度(正常高度也可以)
<Popup x:Name="Popup" StaysOpen="True" MaxHeight="500">
不太确定为什么这有帮助。如果是自动的,可能 WPF 需要做太多的大小计算。