在 java 中加载图像后 FPS 下降
FPS drops after loading images in java
所以,我最近问了一个关于如何在 Java (preloading images in Java) 中预加载图像的问题,效果很好!直到我去玩游戏。帧率急剧下降。我不知道那是什么,但基本上,我将整个精灵贴图加载到一个数组中。每个图像对应一个三度旋转。所以,5 度会变成 3 度图像,6 会保持 6,依此类推(我试过 Math.round 它实际上使 5 度和 4 度图像变成了 6 度图像,这就是更可取,但是速度较慢)
我正在寻找一些优化代码的方法。这是我的角度计算:
private float getAngle(double x, double y) {
float angle = (float) Math.toDegrees(Math.atan2(y - this.getCenterY(), x - this.getCenterX()));
if(angle < 0){
angle += 360;
}
return angle;
}
输入到该方法中的 x 和 y 值是执行此计算的塔所针对的敌人的中心 x 和 y 值。然后在draw方法中执行这段代码:
if(airID==Value.towerCannon && (airRow>0 && airRow<5) && angle>=0) {
if(angle==Canvas.rotatedAirMap.length) angle = 0;
g.drawImage(Canvas.rotatedAirMap[angle][level-1], x, y, width, height, null);
} else {
g.drawImage(Canvas.airMap[airRow][airID], x, y, width, height, null);
}
}
这将绘制以指定角度旋转的适当的预加载图像("angle" - 或图像标识符 - 是在塔射击时通过将角度计算结果除以三然后投射计算得出的到一个 int - 我也可以四舍五入那个值)
关于如何优化它的任何建议,这样我就不会出现如此大的帧丢失?我假设帧丢失是由于 VM 堆大小太小,但我已经增加了它,但仍然没有发生任何重大事情。任何帮助将不胜感激。
谢谢!
@VGR 这是我对你的回复所做的:
public void paintComponent(Graphics g) {
if(isFirst) { //Define stuff when isFirst is true
define(); //Sets up the image arrays
GraphicsConfiguration config = getGraphicsConfiguration();
if(config == null) {
GraphicsEnvironment env = GraphicsEnvironment.getLocalGraphicsEnvironment();
config = env.getDefaultScreenDevice().getDefaultConfiguration();
}
BufferedImage compatibleImage = config.createCompatibleImage(image.getWidth(), image.getHeight(), image.getTransparency());
g = compatibleImage.createGraphics();
isFirst = false;
}
}
这 稍快 一点,但我不得不做一些变通办法。 repaint() 在游戏循环中被调用(这个 class 实现了 runnable)所以由 repaint 方法创建的图形组件(不管怎样)是我在整个游戏中使用的图形。这是正确的方法吗?
将图像从其固有颜色模型转换为当前视频模式的颜色模型会减慢渲染速度。为避免这种情况,您可以确保每张图片都与 window 所在的屏幕兼容:
BufferedImage image = ImageIO.read(/* ... */);
GraphicsConfiguration config = getGraphicsConfiguration();
if (config == null) {
GraphicsEnvironment env = GraphicsEnvironment.getLocalGraphicsEnvironment;
config = env.getDefaultScreenDevice().getDefaultConfiguration();
}
BufferedImage compatibleImage = config.createCompatibleImage(
image.getWidth(), image.getHeight(), image.getTransparency());
Graphics2D g = compatibleImage.createGraphics();
g.drawImage(image, 0, 0, null);
g.dispose();
image = compatibleImage;
如果图片的颜色模型与当前视频模式相同,则绘制时无需翻译。甚至有可能完全由 GPU 完成绘制这样的图像。
所以,我最近问了一个关于如何在 Java (preloading images in Java) 中预加载图像的问题,效果很好!直到我去玩游戏。帧率急剧下降。我不知道那是什么,但基本上,我将整个精灵贴图加载到一个数组中。每个图像对应一个三度旋转。所以,5 度会变成 3 度图像,6 会保持 6,依此类推(我试过 Math.round 它实际上使 5 度和 4 度图像变成了 6 度图像,这就是更可取,但是速度较慢)
我正在寻找一些优化代码的方法。这是我的角度计算:
private float getAngle(double x, double y) {
float angle = (float) Math.toDegrees(Math.atan2(y - this.getCenterY(), x - this.getCenterX()));
if(angle < 0){
angle += 360;
}
return angle;
}
输入到该方法中的 x 和 y 值是执行此计算的塔所针对的敌人的中心 x 和 y 值。然后在draw方法中执行这段代码:
if(airID==Value.towerCannon && (airRow>0 && airRow<5) && angle>=0) {
if(angle==Canvas.rotatedAirMap.length) angle = 0;
g.drawImage(Canvas.rotatedAirMap[angle][level-1], x, y, width, height, null);
} else {
g.drawImage(Canvas.airMap[airRow][airID], x, y, width, height, null);
}
}
这将绘制以指定角度旋转的适当的预加载图像("angle" - 或图像标识符 - 是在塔射击时通过将角度计算结果除以三然后投射计算得出的到一个 int - 我也可以四舍五入那个值)
关于如何优化它的任何建议,这样我就不会出现如此大的帧丢失?我假设帧丢失是由于 VM 堆大小太小,但我已经增加了它,但仍然没有发生任何重大事情。任何帮助将不胜感激。
谢谢!
@VGR 这是我对你的回复所做的:
public void paintComponent(Graphics g) {
if(isFirst) { //Define stuff when isFirst is true
define(); //Sets up the image arrays
GraphicsConfiguration config = getGraphicsConfiguration();
if(config == null) {
GraphicsEnvironment env = GraphicsEnvironment.getLocalGraphicsEnvironment();
config = env.getDefaultScreenDevice().getDefaultConfiguration();
}
BufferedImage compatibleImage = config.createCompatibleImage(image.getWidth(), image.getHeight(), image.getTransparency());
g = compatibleImage.createGraphics();
isFirst = false;
}
}
这 稍快 一点,但我不得不做一些变通办法。 repaint() 在游戏循环中被调用(这个 class 实现了 runnable)所以由 repaint 方法创建的图形组件(不管怎样)是我在整个游戏中使用的图形。这是正确的方法吗?
将图像从其固有颜色模型转换为当前视频模式的颜色模型会减慢渲染速度。为避免这种情况,您可以确保每张图片都与 window 所在的屏幕兼容:
BufferedImage image = ImageIO.read(/* ... */);
GraphicsConfiguration config = getGraphicsConfiguration();
if (config == null) {
GraphicsEnvironment env = GraphicsEnvironment.getLocalGraphicsEnvironment;
config = env.getDefaultScreenDevice().getDefaultConfiguration();
}
BufferedImage compatibleImage = config.createCompatibleImage(
image.getWidth(), image.getHeight(), image.getTransparency());
Graphics2D g = compatibleImage.createGraphics();
g.drawImage(image, 0, 0, null);
g.dispose();
image = compatibleImage;
如果图片的颜色模型与当前视频模式相同,则绘制时无需翻译。甚至有可能完全由 GPU 完成绘制这样的图像。