你看到了吗?
每座房子的每一块砖都是一幅16x16像素的图像。
你在这里看到的是一个基于简单JavaFX的版本,在X和Y上移动了一些Imageview
,以提供“构造”的效果。
我只是使用paintComponent
将其改写为Swing
。
问题:-使用JavaFX:我的电脑有问题。你在图片上看到的花了2秒加载,然后它移动得非常慢和颠簸。-使用Swing
:我不知道如何根据亮度、阴影等调整每个块。所以看起来是这样的:
我应该选择什么方法?两者都有很大的缺点。我希望保留JavaFX方法,但也希望找到除Imageview
之外的其他方法。这不应该是一个好主意。
发布于 2013-01-23 06:22:54
有关Swing优化和实现的信息,请参阅其他答案,因为我的答案是特定于JavaFX的。
如果您坚持使用JavaFX实现,这里有几个可以尝试的东西:
:scale them upfront in the Image constructor,这样它们就不会占用太多内存,也不会(潜在地)需要额外的处理能力来处理额外的像素(只有在使用大量不同的、非常高分辨率的纹理时才需要考虑--而你似乎并没有这么做)。
例如:
Image tile = new Image("tile.png");
Group house = new Group();
house.setCache(true);
house.setCacheHint(CacheHint.SPEED);
Effect lighting = new Lighting();
for (int i = 0; i < houseWidth; i++) {
// here is the critical part => don't do new ImageView(new Image("tile.png"))
ImageView tileView = new ImageView(tile));
tileView.setEffect(lighting);
tileView.setCache(true);
tileView.setCacheHint(CacheHint.SPEED);
house.add(tileView);
}
Mantrid的建议很有趣。我相信,使用JavaFX,您不需要自己实现脏矩形算法(因为底层平台能够为您处理脏区域)。这可能是因为它是一种通用机制,它没有提供您的特定情况所需的优化级别,在这种情况下,您需要自己处理脏处理(例如,通过从场景图中删除节点并根据需要重新添加它们)。
此外,预先计算图像上的模糊/亮度等可以通过在JavaFX中定义效果,将效果应用于离屏ImageView节点,然后使用离屏ImageView节点的taking a snapshot来获得预先计算的图像。这项技术将允许您重用现有的JavaFX效果管道,而无需使用ConvolveOp机制重新实现它。也许您只需在ImageView节点上将cache设置为true并将cacheHint设置为speed,就可以获得相同的性能级别,因为我相信这在幕后会做类似的事情(即以增加内存使用量为代价来提高速度)。
JavaFX场景图非常高效,可以处理数以千计的节点。但是,您的应用程序中可能有更多的内容。如果上面的优化点对您没有帮助,那么您可能需要计算节点数,并将您的问题的引用(可能还有一些资源)发布到了解JavaFX应用程序优化细节的JavaFX开发人员所在的open-jfx mailing list。
与JavaFX 2.2中的3D场景图相比,JavaFX 8对3D scenegraphs的支持要好得多。您当前的应用程序似乎是psuedo-3d,您可以变换2D对象,单独应用照明效果,并调整每个磁贴的亮度以获得3D外观。如果是这样的话,使用完全硬件加速的3D场景图和统一的3D照明模型可能最终会表现得更好,看起来更好,更容易使用-您必须在应用程序的上下文中对其进行评估,看看是否值得将您的应用程序从2D JavaFX场景图切换到3D JavaFX场景图,或者从JavaFX切换到Swing或其他一些技术,如libgdx。
附录
Mizur的一些附加问题的答案:
那么,为什么它们如此耗电呢?
从我的回答中可以看出,性能有很多方面,所以找出一个特定的原因来解释为什么某些东西是耗电的,有时是困难的,而且通常是不可能的。有时,这是导致性能问题的各种因素的组合。最大的成功通常来自于优化在最内部循环中执行的东西,或者通过改变用于解决问题的策略。
如果他们需要这么多,请让我移动瓷砖,或请只是显示,不?
就仅为您移动的东西消耗资源而言,JavaFX场景图对此进行了一些优化,像cachehints这样的东西可以进一步提高性能。也许它们不足以满足您的特定用例或您使用系统的方式。您可能需要更改算法以减少系统负载。
有没有一种方法可以用Imageview技术生成每一座建筑的图像,然后将这些建筑图像整合到最终场景中?
可以-您可以使用多个图像和节点将建筑物渲染到屏幕外场景,使用snapshot the offscreen scene创建单个图像,然后将该图像叠加到最终场景上。
发布于 2013-01-23 05:10:42
在绘制图像之前修改图像上的模糊/亮度等
我自己还没有用过它,但是这里有一个提示-使用Swing/AWT Kernel+ConvolveOp机制:http://www.java-tips.org/java-se-tips/java.awt.image/styling-digital-images-with-convolveop.html
BufferedImage biSrc = ...
BufferedImage biDest = ...
float[] data = new float[] { 0.0625f, 0.125f, 0.0625f, 0.125f, 0.25f, 0.125f, 0.0625f, 0.125f, 0.0625f };
Kernel kernel = new Kernel(3, 3, data);
ConvolveOp convolve = new ConvolveOp(kernel, ConvolveOp.EDGE_NO_OP, null);
convolve.filter(biSrc, biDest);
操作通过3x3矩阵(数据)定义。你可以搜索一下brigthness,blur等的例子。
图片加载花了2秒钟,但它的移动非常缓慢和抖动
使用脏矩形算法:Dirty Rectangles
https://stackoverflow.com/questions/14467719
复制相似问题