SuspendLayout和BeginUpdate之间的区别

13

我并没有找到一个很好的解释,来阐明Control.SuspendLayoutBeginUpdate这两种方法(通常在类似于ListViewComboBoxListBox等列表控件中看到),除了它们都会提高性能。

据我所知:

  1. 它们都暂停绘制,直到所有要显示的项目都加载完毕,并在此之后重新绘制。

  2. 通常情况下,当将控件添加到容器控件(如PanelGroupBox等)时,会调用SuspendLayout,而当将非控件项目(如对象)添加到列表控件(如ListBox)时,则使用BeginUpdate

但为什么会有这两个调用,它们做的事情又有什么不同呢?

类似地,还有ResumeLayoutEndUpdate的等效方法。

2个回答

15

它们没有共同点。 SuspendLayout关闭自动布局,这种布局由像TableLayoutPanel和FlowLayoutPanel这样的控件使用,以及从Dock、Anchor和AutoSize属性中获得的布局更新。 它对ListView、ComboBox或ListBox没有任何影响,这些控件不执行布局。 通常只在向容器中批量添加控件时使用它。 有时当自动布局使调整窗口大小变得太麻烦时也会使用它。 它确实通过暂停控件大小更新来减少重新绘制次数。

BeginUpdate停止一个控件自我重绘。 当您无法出于某种原因使用其Items.AddRange()方法时,您确实可以在像ListView或ListBox这样的控件上使用它来添加项目。


2
嗯,这就引出了一个问题,为什么非容器控件(如列表框和按钮)上会有 SuspendLayout 方法,而它们并不执行任何布局操作。我猜这是一个虚方法,在子类(如 ListBox)中没有被重写或实现,因此什么也不做。 - nawfal

5
正如您所指出的那样,BeginUpdate 是列表控件的一部分,用于添加项目。 SuspendLayout 类似,但它来自 Control 类。当您进行自定义绘制时,它非常有用。
因此,真正的区别在于绘制控件与绘制控件中的项目。如果您设置与绘制相关的属性,请使用 SuspendLayout。在添加项目的过程中,请使用 BeginUpdate
更新机制略有不同。 BeginUpdate 在添加/删除项目期间抑制绘画事件。如果您曾尝试调试 paint 事件,您可能会发现它会频繁触发。 SuspendLayout 抑制移动、调整大小等布局计算。

是的,我理解这一点。我的问题是:为什么在绘制新控件与更新现有控件的布局之间应该存在差异? - nawfal

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接