971.md 6.0 KB
Newer Older
W
init  
wizardforcel 已提交
1 2 3 4 5 6 7 8 9 10
# BufferStrategy 和 BufferCapabilities

> 原文: [https://docs.oracle.com/javase/tutorial/extra/fullscreen/bufferstrategy.html](https://docs.oracle.com/javase/tutorial/extra/fullscreen/bufferstrategy.html)

## `BufferStrategy`

在 Java 2 Standard Edition 中,您不必担心视频指针或视频内存,以便充分利用双缓冲或页面翻转。添加了新类 `java.awt.image.BufferStrategy` 是为了便于以一般方式处理绘制到曲面和组件,无论使用的缓冲区数量或用于显示它们的技术如何。

缓冲策略为您提供了两种通用的绘图方法: `getDrawGraphics``show` 。当您想要开始绘图时,获取绘制图形并使用它。当您完成绘图并想要将信息显示在屏幕上时,请调用 `show` 。这两种方法旨在相当优雅地适应渲染循环:

W
wizardforcel 已提交
11
```java
W
init  
wizardforcel 已提交
12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59
BufferStrategy myStrategy;

while (!done) {
    Graphics g = myStrategy.getDrawGraphics();
    render(g);
    g.dispose();
    myStrategy.show();
}

```

还设置了缓冲策略来帮助您监控 `VolatileImage` 问题。在全屏独占模式下, `VolatileImage` 问题尤其重要,因为窗口系统有时可以收回它给你的视频内存。一个重要的例子是当用户在 Windows 中按下 `ALT + TAB` 组合键时 - 突然你的全屏程序在后台运行,你的视频内存丢失了。您可以调用 `contentsLost` 方法来查明是否发生了这种情况。同样,当窗口系统将内存返回给您时,您可以找到使用 `contentsRestored` 方法。

## `BufferCapabilities`

如前所述,不同的操作系统,甚至同一操作系统上的不同图形卡,可以使用不同的技术。这些 _ 功能 _ 为您提供,以便您可以为您的应用选择最佳技术。

`java.awt.BufferCapabilities` 封装了这些功能。每个缓冲区策略都由其缓冲区功能控制,因此为您的应用选择正确的缓冲区非常重要。要找出可用的功能,请从图形设备上可用的 `GraphicsConfiguration` 对象中调用 `getBufferCapabilities` 方法。

Java 2 Standard Edition 1.4 版中提供的功能包括:

*   `isPageFlipping`
    此功能返回此图形配置上是否有硬件页面翻转。
*   `isFullScreenRequired`
    此功能返回在尝试硬件页面翻转之前是否需要全屏独占模式。
*   `isMultiBufferAvailable`
    此功能返回硬件中是否有多个缓冲(两个或多个后缓冲区加上主表面)可用。
*   `getFlipContents`
    此功能返回用于执行硬件页面翻转的技术的提示。这很重要,因为`显示`后的后缓冲液的含量根据使用的技术而不同。返回的值可以为 null(如果 `isPageFlipping` 返回 `false` )或以下值之一。只要 `isPageFlipping` 方法返回 true,就可以为缓冲区策略指定任何值,但性能会因可用功能而异。
*   `FlipContents.COPIED`
    该值表示后缓冲区的内容被复制到主表面。 “翻转”可能是作为硬件 blt 执行的,这意味着硬件双缓冲可能是使用 blitting 而不是真正的页面翻转来完成的。这应该(理论上)比 `VolatileImage` 到主表面的速度更快,或者至少同样快,尽管你的里程可能会有所不同。后缓冲器的内容与翻转后的主表面相同。
*   `FlipContents.BACKGROUND`
    该值表示已使用背景颜色清除后缓冲区的内容。无论是真正的页面翻转还是 blt 都发生了。
*   `FlipContents.PRIOR`
    此值表示后缓冲区的内容现在是旧主曲面的内容,反之亦然。通常,此值表示发生了真正的页面翻转,但这不能保证,并且再一次,您在此操作上的里程可能会有所不同。
*   `FlipContents.UNKNOWN`
    该值表示翻转后后缓冲区的内容未定义。您可能需要尝试找到最适合您的技术(或者您可能不关心),并且每次绘制时您必须自己设置后备缓冲区的内容。

要为组件创建缓冲区策略,请调用 `createBufferStrategy` 方法,提供所需的缓冲区数(此数字包括主表面)。如果需要任何特定的缓冲技术,请提供适当的 `BufferCapabilities` 对象。请注意,当您使用此版本的方法时,如果您的选择不可用,则必须捕获 `AWTException` 。另请注意,这些方法仅适用于 `Canvas``Window`

一旦为组件创建了特定的缓冲区策略,就可以使用 `getBufferStrategy` 方法对其进行操作。请注意,此方法也仅适用于画布和窗口。

## 编程技巧

关于使用缓冲功能和缓冲策略的一些提示:

*   获取,使用和处理图形对象在`尝试...最终`子句中更加强大:

W
wizardforcel 已提交
60
    ```java
W
init  
wizardforcel 已提交
61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82
    BufferStrategy myStrategy;

    while (!done) {
        Graphics g;
        try {
            g = myStrategy.getDrawGraphics();
            render(g);
        } finally {
            g.dispose();
        }
        myStrategy.show();
    }

    ```

*   在使用缓冲策略之前检查可用功能。
*   为获得最佳效果,请在全屏独占窗口上创建缓冲区策略。在使用页面翻转之前,请确保检查 `isFullScreenRequired``isPageFlipping` 功能。
*   不要对性能做任何假设。根据需要调整代码,但请记住,不同的操作系统和图形卡具有不同的功能。描述您的应用!
*   您可能希望子组化您的组件以覆盖 `createBufferStrategy` 方法。使用算法选择最适合您的应用程序的策略。 `FlipBufferStrategy``BltBufferStrategy` 内部类受到保护,可以进行子类化。
*   不要忘记你可能会丢失你的绘图表面!在绘图之前一定要检查 `contentsLost``contentsRestored` 。丢失的所有缓冲区在恢复时都必须重绘。
*   如果在 Swing 应用程序中使用缓冲策略进行双缓冲,则可能需要关闭 Swing 组件的双缓冲,因为它们已经是双缓冲的。视频内存有些宝贵,只应在绝对必要时使用。
*   使用多个后备缓冲区可能最终会浪费。多次缓冲仅在绘图时间超过执行`节目`所花费的时间时有用。描述您的应用!