【问题标题】:The Need To Restore Graphics Original State When Overwritten paint or paintComponent覆盖paint或paintComponent时需要恢复图形原始状态
【发布时间】:2023-03-30 16:15:01
【问题描述】:

我意识到大部分Java代码都可以覆盖paint或paintComponent,它们中的大多数在更改图形对象的状态后都不会恢复图形对象的旧状态。比如setStroke、setRenderingHint...

我想知道在从方法返回之前恢复图形对象的旧状态是否是一个好习惯。例如

public void paintComponent(Graphics g) {
    super.paintComponet(g);
    Stroke oldStroke = g.getStroke();
    g.setStroke(newStroke);
    // Do drawing operation.
    g.setStroke(oldStroke);
}

这是一个好习惯吗?还是结束了?

【问题讨论】:

    标签: java swing graphics awt


    【解决方案1】:

    您根本不应该更改传入的 Graphics 对象,而应在其副本上执行所有图形操作,然后将其处置。那时根本不需要重置状态。

    public void paintComponent(Graphics g1) {
        super.paintComponent(g1);
        final Graphics2D g = (Graphics2D)g1.create();
        try {
             // ...Whole lotta drawing code...
        } finally {
             g.dispose();
        }
    }
    

    【讨论】:

    【解决方案2】:

    是的,这是一个非常好的做法。你不会在性能上付出太多(相对于实际的绘画操作),如果你是对图形上下文进行不寻常的更改。不过不要过度 - 例如,您可能不需要担心颜色设置。

    另一种方法是对图形上下文不做任何假设,并在每次绘画之前设置所有必要的属性,以防它们被设置为不可靠的东西。 尽量避免为每个操作随意创建和处置 Graphics 对象。

    修改后应始终恢复的特定属性:(因为它们会做坏事并产生意外后果):

    • 转换 - 因为对此的修改会相互叠加,并且非常非常难以重置。注意:这是由 Graphics2D 的 translate、shear、scale、rotate 和 transform 方法修改的。修改转换应谨慎使用。
    • Stroke -- 因为(至少在我的配置中),保留此默认设置比 任何设置 运行得快得多,即使等同于默认设置。别问——这是 Java2D 图形管道使用图形硬件加速默认情况的结果。
    • 剪辑:将导致仅绘制部分屏幕的奇怪错误。
    • 复合:大多数操作可能并不认为这是奇怪的事情。

    无需担心的属性:

    • 渲染提示。这些是您可以轻松设置和恢复的内容,通常您希望在应用程序运行的整个过程中以某种方式设置它们(抗锯齿等)。更改 RenderingHints 很少会破坏组件的渲染,尽管它可能会变得更丑。
    • 背景颜色和油漆颜色。无论如何,大多数事情都会在绘制之前修改这些内容。
    • 字体:同理。

    【讨论】:

    • 你应该会发现创建一个 Graphics 对象非常便宜。
    • 呃...是的,已更正。我仍然认为这不是一个好习惯,因为你永远不知道还有什么在使用 Graphics 对象,而且你会丢失 RenderingHints 等的设置。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2018-09-29
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多