java - 如何有效地扩展 JFrame 的内容 Java?

标签 java swing bufferedimage scaling

我正在寻找一种方法来正确缩放(几乎)所有 JFrame 的内容。到目前为止,我尝试过的所有解决方案都在渲染速度方面存在巨大不足。我正在寻找的速度类似于您在智能手机上缩放内容时的速度。

JFrame 的内容应该可以快速重新缩放并保持缩放,即使您用新内容过度绘制 JFrame 也是如此。它还应该足够灵活,以便让您选择要重绘的 BufferedImage(这基本上是我正在绘制的唯一类型,我不绘制任何其他“形状”)。我正在使用普通图形进行绘制,resp。 Graphics2D 对象。

我之前尝试过的是 Graphic2D 的缩放方法并使用 AffineTransformat 对象分别缩放每个 BufferedImage:

    g.scale(scalingFactorX, scalingFactorY);

或者:

    BufferedImage img = someImageToScale();
    AffineTransform scaleTransform = AffineTransform.getScaleInstance(scalingFactorX, scalingFactorY);
    AffineTransformOp bilinearScaleOp = new AffineTransformOp(scaleTransform,
            AffineTransformOp.TYPE_NEAREST_NEIGHBOR);

    return bilinearScaleOp.filter(img, new BufferedImage(targetWidth, targetHeight,
            BufferedImage.TYPE_INT_ARGB));

其中 scalingFactorX/Y 是内容应该缩放的因素和 targetWidth,resp。 targetHeight 表示 BufferedImage 的结果(缩放)尺寸。

这两种方法都相当慢,这似乎是因为在这两种情况下,每一帧,内容的缩放版本都必须重新计算。我觉得我在这里遗漏了一些非常明显的东西。

最佳答案

虽然 drawImage() 可以对图像重新取样,但它必须每次 paintComponent() 被调用。按照建议here , AffineTransformOp 让您选择插值类型;使用满足您的图像质量要求的最快的。对图像进行令人满意的重采样后,确保在特定 Graphics 上下文中渲染时​​不会无意中对图像进行第二次重采样。覆盖 getPreferredSize()使目标组件与重新采样的图像大小相同,如这些 examples 所示.

My images are only 32x32, but there are a large amount of them (~500).

考虑使用 flyweight pattern只渲染可见图像。 JTableJList 是示例,如概述here .

Are there performance benefits or other advantages to using separate components?

您可能需要原型(prototype)和 profile可以肯定的是,也许通过比较代表性的例子:

  • 典型的基于组件的示例包括引用的基于按钮的游戏 here ,或检查的国际象棋游戏here , herehere .

  • 基于图 block 的 game引用here展示了一个单一的拼贴面板和多个附属面板,它们都听一个常见的游戏模型。

关于java - 如何有效地扩展 JFrame 的内容 Java?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/32634968/

相关文章:

java - 模拟父类(super class)方法调用

java - 查找任意两个列表值之和是否等于给定值

java - 如何完全摆脱 JPanel 及其中的所有内容?

java - 将焦点设置在 JDateChooser 上

Java - 删除低于某个 alpha 值的像素

java - 为java SQL Date添加小时,分钟和秒

java - 从hibernate sql join获取多个实体

java - 如何缩放 BufferedImage

java - 为什么同一个 JComponent 对象多次添加无法显示?

java - 在屏幕上快速收集图像并读取像素