Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/342.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 图形2D性能问题_Java_Performance_Graphics2d - Fatal编程技术网

Java 图形2D性能问题

Java 图形2D性能问题,java,performance,graphics2d,Java,Performance,Graphics2d,我对Java的图形库还不熟悉,但我仍在了解它的局限性。下面我为Grid类提供了一个draw函数,它将二维瓷砖阵列绘制为填充矩形 这与问题无关,但scale和offset参数用于调整网格的平铺和平铺大小变量,以便在屏幕上以正确的位置和比例绘制 我的问题是,当tiles变量相当大时,这种延迟是否正常?在屏幕上没有任何网格的情况下,我通常可以获得大约500 fps的速度,而在瓷砖网格[10][10]到[50][50]的情况下,速度不会明显降低。但在瓷砖[1000][1000]或总共1000000个要绘

我对Java的图形库还不熟悉,但我仍在了解它的局限性。下面我为Grid类提供了一个draw函数,它将二维瓷砖阵列绘制为填充矩形

这与问题无关,但scale和offset参数用于调整网格的平铺和平铺大小变量,以便在屏幕上以正确的位置和比例绘制

我的问题是,当tiles变量相当大时,这种延迟是否正常?在屏幕上没有任何网格的情况下,我通常可以获得大约500 fps的速度,而在瓷砖网格[10][10]到[50][50]的情况下,速度不会明显降低。但在瓷砖[1000][1000]或总共1000000个要绘制的矩形时,fps下降到7

我知道一百万是很多,但它们毕竟只是矩形,我的电脑可以在完全设置下玩Skyrim这样的游戏,没问题。我可以想象Skyrim中有超过一百万个多边形,它们有各种各样的高分辨率纹理和照明,所以,为什么一百万个灰色正方形会成为这样的问题?Java的图形库真的很差吗?我是不是期望太高了?或者,正如我所怀疑的,有没有更好的方法来画这样的东西

如果这很重要,我可以提供主类的paintComponent,但这只是对_Grid.draw()的调用,所以我认为问题不在那里

public Graphics draw(Graphics g, double scale, Point offset) {

    Graphics2D g2 = (Graphics2D) g;

    for(int i = 0; i != this.tiles.length; i++) {
        for(int j = 0; j != this.tiles[0].length; j++) {

            boolean draw = true;

            if(this.tiles[i][j].type.equals("EMPTY")) {
                draw = false;
            } else if(this.tiles[i][j].type.equals("PATH")) {
                g2.setColor(Color.LIGHT_GRAY);
            } else if(this.tiles[i][j].type.equals("WALL")) {
                g2.setColor(Color.DARK_GRAY);
            }

            if(draw) {
                g2.fillRect((int)((this.xPos+i*this.tileSize)*scale + offset.x), 
                            (int)((this.yPos+j*this.tileSize)*scale + offset.y), 
                            (int)(this.tileSize*scale), 
                            (int)(this.tileSize*scale));
            }
        }
    }

    return g2;

}

Java的
buffereImage
类速度很慢。这是众所周知的事实。如果你想做快速图像处理,那么它是错误的工具使用

此外,像Skyrim这样的游戏使用图形卡来完成大部分工作,使用Java图像,所有这些都是在CPU中完成的


<>你应该认真研究一下游戏框架——有2D的,比如SLIK2D和3D的,比如JMunKiGeangy3。

< P> >你可以考虑的一些事情:

>P>如果原始代码<>图形< /COD>对象是由<代码> BuffeReimdie创建的,请考虑使用<代码> FraveIsgs。正如其他人所说,这个draw方法中的所有事情都是通过Swing事件调度线程在CPU上进行的,因此您只能使用一个CPU进行绘制(除非您在某处生成更多线程)
VolatileImage
用于双缓冲时,利用了图形硬件的优势,并且可以更快地完成这类工作

  • 您正在进行大量的字符串比较,这可能非常缓慢。我会考虑重构您的<代码>类型字段作为自定义<代码> EnUM<代码>,然后让该<代码> EnUM <代码>定义它自己的<代码>绘制< /COD>方法,该方法采用<代码>图形< /代码>对象并绘制它自己。这样,您就可以调用
    this.tyles[i][j].type.draw(g2)
    并依靠后期绑定来绘制右彩色矩形,从而消除了
    字符串的比较

  • 确保你只画屏幕上的东西。我对你的
    平铺
    数组一无所知,但如果它比实际渲染到屏幕上的要大得多,你可能会浪费很多CPU周期

  • 这听起来可能很傻,但实际上,您正在进行的内存访问是实际需要的两倍。我假设您在源代码中的某个地方定义了
    Tile[][]tiles…
    。在外部循环中,通过编写类似于
    Tile[]row=tiles[i]的内容,首先获取行
    ,然后在内部循环中,通过调用
    行[j]来获取类型。键入
    。这将在迭代平铺数组时将内存访问计数减少一半


  • 你正在使用一种非常不优化的方法来绘制矩形。Skyrim正在使用一种惊人的优化方式。不要比较两者(或使用LWJGL)。Skyrim是否每次绘制新帧时都渲染整个世界?不,它采用了一种叫做。不要把宝贵的处理时间浪费在绘制玩家看不到的矩形上。这是一个开始。除了4之外,所有好的建议都是非常快的,因为数组查找速度非常快,不过如果数组很大,您可能会看到缓存一致性方面的一些改进。@TimB我想冗余数组访问在优化过程中不会花费任何成本,但使用
    row
    至少会让它更具可读性。@maaartinus是的,尽管我不喜欢假设各种JVM会或不会进行哪些优化。有些比其他好:)。即使它没有被优化,但它的成本很小。是的,slick2D似乎是一种方式。。。刚刚使用它的图像类将fps从7增加到7000:P谢谢你