WPF StackPanel 性能

WPF StackPanel performance

我们使用 WPF 编写了一个新项目,但在前几次测试之后,我注意到当数据源中有数千个对象时,ComboBox 元素的性能很差。我解决了(在向我的新老板祈祷之后)使用:

<ComboBox.ItemsPanel>   
    <ItemsPanelTemplate>
        <VirtualizingStackPanel />  
    </ItemsPanelTemplate>
</ComboBox.ItemsPanel>

我想知道StackPanel控件如果有几百个自定义元素(只有一个标签和两个按钮的UserControl)会不会容易出现这种问题。 UserControl 以这种方式添加到代码中 two/tree 应用中的位置:

foreach (var obj in myList)
{
    MyUserControl muc = new MyUserControl(obj);
    myStackPanel.Add(muc);
}

谁能告诉我我们是否会 运行 遇到问题 and/or 如果有办法告诉 StackPanel 重用缓存的对象?

P.S。我是 Apple-swift 开发人员,刚刚进入 Windows 并从事一份可怕的新工作...

我假设当您谈论在 StackPanel 中显示 “几百个自定义元素” 时,您想要添加滚动条以使所有元素适合场景。

普遍的问题是一次渲染许多项目(或它们的容器)会影响渲染性能,正如人们所预料的那样。您已经 运行 解决了您 ComboBox 的这个问题。

您想要的是只为可见项目创建容器,而不是为所有成百上千的项目创建容器。这称为 UI 虚拟化。 UI虚拟化的核心是一个ScrollViewer和一个VirtualizingStackPanel(或者一般的VirtualizingPanel),其中ScrollViewer定义可见区域,VirtualizingPanel 根据滚动输入控制容器 generation/recycling。

您很可能想将 StackPanel 替换为 ListBox
ListBox 垂直堆叠项目,默认情况下有一个 ScrollViewerStackPanel 没有)。由于 ListBox 的默认 PanelVirtualizingStackPanel,它支持 UI 虚拟化(默认启用),因此您可以在不影响渲染的情况下显示“无限”项目性能(只要这些项目容器的可视化树不是过于复杂)。 另外,尽量不要一项一项地添加。这将触发完整的渲染通道,特别是对于不支持 UI 虚拟化的控件,如 StackPanel。尝试一次或至少分批添加所有项目,这对于 StackPanel 是不可能的。它是错误主机的另一个原因。 Optimizing performance: Controls