【问题标题】:How can I DoubleBuffer a winforms Treeview?我怎样才能双缓冲一个winforms Treeview?
【发布时间】:2011-05-25 02:15:05
【问题描述】:

我有一个标准的 winforms treeview 控件,每当我将鼠标悬停在表单上的任何其他控件上时,它都会不断闪烁。我想双缓冲树视图以减少闪烁,但我不知道该怎么做。 有人可以告诉我如何实现我的目标吗?

非常感谢

【问题讨论】:

标签: vb.net winforms treeview


【解决方案1】:

在开发财务软件的某些部分时,由于相同的情况,我不得不实现双缓冲 TreeView。 .NET 中的 TreeView 实现是一个非常粗略的实现,但这是我解决它的方法:

 Public Class DoubleBufferedTreeView
    Inherits System.Windows.Forms.TreeView

    Public Sub New()
        ' This call is required by the Windows Form Designer.
        InitializeComponent()

        ' Add any initialization after the InitializeComponent() call.
        Me.SetStyle(ControlStyles.OptimizedDoubleBuffer, True)
        Me.SetStyle(ControlStyles.AllPaintingInWmPaint, True)
        Me.UpdateStyles()
    End Sub
End Class

我以这种方式实现它的另一个原因是因为我必须做一些自定义绘图来显示用户拖放 TreeNode 的位置,所以我做了一些自定义绘图以在节点之间显示一个栏。

DoubleBuffering 不是一个完全可靠的解决方案,因为 TreeView 会轻微闪烁,但这是我当时能够得到的最好的解决方案。我也不想像其他人所说的那样暂停 TreeView,因为我仍然希望 TreeView 执行其布局和正常操作,即使用户可能正在使用 UI 的不同部分。

PS。代码几乎与 C# 相同。

【讨论】:

  • 不幸的是,您的代码根本没有任何效果。树视图仍然闪烁。
【解决方案2】:

这里的所有答案都是错误的。 Treeview 忽略

SetStyle(ControlStyles.AllPaintingInWmPaint,  true);
SetStyle(ControlStyles.OptimizedDoubleBuffer, true);

完全。

并且使用BeginUpdate()SuspendLayout() 不会改变任何东西。

Hans Passant 在这里给出了正确答案:Treeview flickering?

【讨论】:

    【解决方案3】:

    除了像 Int3 所说的那样激活双缓冲之外,我建议您在执行导致闪烁的处理时暂时暂停布局逻辑。

    您需要先调用 SuspendLayout 以停止在 UI 中构建完整的树内容。 完成处理后,使用 ResumeLayout() 再次启动布局逻辑。 带有代码示例的 SuspendLayout 的 MSDN 文档是 here

    private void buildTreeContent()
    {
       // Suspend the form layout and add two buttons.
       this.SuspendLayout();
    
       // Do your work here
       // ...
    
       // Make the Form do paint the layout again.
       this.ResumeLayout();
    }
    

    这应该有助于大量闪烁,因为构建树元素会消耗资源,我们在项目中已经多次这样做了。

    另一种方法是使用 Windows 消息。 这在另一个 SO thread 中有更深入的解释。

    【讨论】:

    • 树视图正在从 HDD 的内容中填充。在填充过程中没有闪烁,整个过程不到一秒钟。所以暂停/恢复布局对我没有帮助。当鼠标悬停在其他控件上并且没有触发涉及树视图的事件时,会发生树视图闪烁。
    • 这个答案是错误的。 SuspendLayout() 不会改变任何东西。当我只选择一个节点时,我的树视图会完全闪烁,而不是当树中填充有节点时。
    【解决方案4】:

    DoubleBuffer 不影响 .NET 中的 Treeview。如果您的目的是减少绘制 TreeView 时的闪烁,那么我建议您看看BeginUpdateEndUpdate

    我遇到了类似的问题,并尝试对表单进行双重缓冲,希望它能解决我的树视图问题。事实证明,设置DoubleBuffered 属性不会影响TreeView 控件。

    希望这会有所帮助。有用的link

    【讨论】:

    • 你为什么要发布这个非解决方案?
    【解决方案5】:

    希望您对 C# 代码没问题,因为它是微不足道的。 DoubleBuffer 实际上是 Control 的受保护属性。因此,您只能从声明类或派生类访问它。 下面的 sn -p 将帮助您了解如何设置此属性。

    public sealed class MyNonFlickringTreeView:Treeview
    {
     public MyNonFlickringTreeView()
       {
          this.DoubleBuffered=true;
       }
    }
    

    【讨论】:

    • 树视图没有 DoubleBuffer 属性。
    • 看起来 DoubleBuffered 对 TreeView 不起作用/没有实现
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2011-04-12
    • 2023-01-19
    • 2019-09-01
    • 1970-01-01
    • 1970-01-01
    • 2021-11-12
    相关资源
    最近更新 更多