摆动刷新周期
Posted
技术标签:
【中文标题】摆动刷新周期【英文标题】:Swing refresh cycle 【发布时间】:2012-12-29 18:44:20 【问题描述】:我试图了解何时使用 revalidate/repaint/pack。
令人惊讶的是,我没有找到非常详细的幕后文档(请随意链接)。
到目前为止,我已经明白这都是 RepaintManager 的责任。
paint/repaint 指的是被视为脏/干净的东西 pack/validate/revalidate 指的是什么是有效的This article on Oracle 解释说,调用重绘会在 Event Dispatcher 线程上将作业排入队列,该线程将依次调用组件上的 paintImmediately()(这会重绘组件)。
This trail表示是否有效与LayoutManager相关联。这完全取决于组件的大小而不是内容。
-
当您移动/调整组件大小并在更改其内容时重新绘制时,您是否应该调用 revalidate?
pack() 方法真的是一个你不应该调用的已弃用的东西吗?
上述任何说法是否有误?
【问题讨论】:
【参考方案1】:这里有一些你需要调用这些方法的基本情况(我介绍了基础知识,但我可能错过了一些需要调用这些方法的其他情况)。
-
您应该在容器上调用
revalidate()
时:添加一个或多个组件,删除一个或多个组件,更改一个或多个包含组件的约束(约束或 XXXSize(),尽管后者不是推荐),更改了容器的LayoutManager
。
您应该在想要重新绘制该组件(及其后代)时调用repaint()
。最终,这将调用 paintComponent()
(对于基本小部件,这将委托给 XXXUI.paint())、paintBorder()
和 paintChildren()
(至少在 Swing 中)
pack()
实际上将窗口的大小设置为其首选大小。您通常应该在使窗口可见之前调用它。您可以稍后调用它,但这会给用户带来奇怪的体验(我不知道有多少应用程序会在显示后调整其窗口大小)
使用revalidate()
和repaint()
的主要优点是它们可以自行合并。这意味着如果您多次调用repaint()
,则绘画只会执行一次。
【讨论】:
你能根据它所暗示的变化来定义绘画吗?我开始怀疑我是否完全理解这意味着什么。 @kotoko 我不确定我得到了你想要的答案(写你的评论)。当你绘画时(paintComponent()
方法的实现),这意味着你画线、圆(填充或不填充)、矩形(填充或不填充)、图像、文本等......(你可以实际调用的所有操作在Graphics/Graphics2D
)。
我试图了解什么方法触发了什么。现在我明白了(经验法则):布局/组件相关操作会影响是否有效(您的 1.); Graphics/Graphics2D 操作影响是否脏。
我发现了一个与您所说的相反的示例:带有支架面板的 splitPane,当我在支架面板上执行 removeAll() 时,在我重新绘制之前没有任何更新。
@kotoko 它与我在回答中所说的相矛盾吗?我可能没有直接说的是,几乎任何时候你调用revalidate()
,repaint()
也应该在之后调用(但相反的情况并非如此)以上是关于摆动刷新周期的主要内容,如果未能解决你的问题,请参考以下文章