Java fillRect()不一致

Java fillRect()不一致,java,performance,paint,graphics2d,fill,Java,Performance,Paint,Graphics2d,Fill,可疑的fillRect()速度 好吧,让我直说吧。Java通过迭代数组并将rgb值更改为指定颜色来填充矩形。如果它所做的只是更改颜色,那么如果它所做的只是更改数组中的整数,那么为什么Texturepaint如此昂贵?在两者之间更改整数需要时间注册吗 使用setPaint(新颜色())进行快速fillRect()操作 setPaint(new Color(0,0,0)); fillRect(0,0,frame.getWidth(),frame.getHeight()); // Around 10

可疑的fillRect()速度

好吧,让我直说吧。Java通过迭代数组并将rgb值更改为指定颜色来填充矩形。如果它所做的只是更改颜色,那么如果它所做的只是更改数组中的整数,那么为什么Texturepaint如此昂贵?在两者之间更改整数需要时间注册吗

使用setPaint(新颜色())进行快速fillRect()操作

setPaint(new Color(0,0,0));
fillRect(0,0,frame.getWidth(),frame.getHeight());

// Around 100+ fps repainting with timer set to zero milliseconds.
setPaint(new TexturePaint(image, rectangle));
fillRect(0,0,frame.getWidth(),frame.getHeight());

// Around 20+ fps repainting with timer set to zero milliseconds.
使用setPaint(新的TexturePaint())执行慢速fillRect()操作

setPaint(new Color(0,0,0));
fillRect(0,0,frame.getWidth(),frame.getHeight());

// Around 100+ fps repainting with timer set to zero milliseconds.
setPaint(new TexturePaint(image, rectangle));
fillRect(0,0,frame.getWidth(),frame.getHeight());

// Around 20+ fps repainting with timer set to zero milliseconds.
从中可以看到,Graphics将此功能委托给子类

我的实现似乎使用了,这又一次将它委托给了,有很多实现。如果可能,可以使用OpenGL将此功能委托给图形卡。使用本机X调用,如下所示:

native void XFillRect(long pXSData, long xgc,
                      int x, int y, int w, int h);

public void fillRect(SunGraphics2D sg2d,
                     int x, int y, int width, int height)
{
    SunToolkit.awtLock();
    try {
        long xgc = validate(sg2d);
        XFillRect(sg2d.surfaceData.getNativeOps(), xgc,
                  x+sg2d.transX, y+sg2d.transY, width, height);
    } finally {
        SunToolkit.awtUnlock();
    }
}
使用以下代码:

public synchronized void fillRect(SunGraphics2D sg2d,
                                  int x, int y, int width, int height) {
    SunToolkit.awtLock();
    try {
        validateSurface(sg2d);

        XRSurfaceData xrsd = (XRSurfaceData) sg2d.surfaceData;

        x += sg2d.transform.getTranslateX();
        y += sg2d.transform.getTranslateY();

        tileManager.addRect(x, y, width, height);
        tileManager.fillMask(xrsd);

    } finally {
        SunToolkit.awtUnlock();
    }
}
我向您展示了这段代码,因为它不仅仅是在数组中设置颜色。您的里程数将因平台和JRE而异


由于我不知道您使用的是哪种渲染器/填充管,我只能建议您查看自己的代码,这并不难。

正如StackOverflowException已经指出的那样:“引擎盖下”发生的事情远远不止填充数组。Java为在任意平台上绘图提供的便利并不是免费的:Sun/Oracle的工程师们努力让它对用户来说如此简单。但即使只是填充一个数组:在一种情况下,数组将填充一个常量值。在另一种情况下,每个数组项的值必须从您在
TexturePaint
中使用的图像中读取。如何加载此图像?@Marco13 ImageIO.read(this.getClass().getResource(“image.png”);是否有可能从图像中提取rgb阵列并直接读取?实际上我已经试过了,但是你必须逐像素填充。可以直接从图像中读取RGB阵列,但只有在某些条件下,当你想使用
TexturePaint
时,这对你没有帮助。我仍然不知道您为什么要使用这个,但还记得我们在中的讨论(我仍然“坚持”;-)。我仍然认为应该有一个没有
TexturePaint
的解决方案,它可以大大加快速度。但是,您可能希望在加载图像后直接尝试将图像转换为ARGB图像,使用来自的
convertToARGB
方法…这是一种实用方法,我已经在各种答案中发布过。在加载
ImageIO
后直接绘制图像时,绘制PNG(尤其是包含透明度的PNG)的性能非常低,这是一个相当常见的问题。如果您愿意,您可以向上投票链接的答案,或者(因为这一个主要是关于ARGB格式的性能优势)我们已经在我上面链接的另一个问题中讨论过这一点,它已经在这里显示了“避免在评论中讨论”的警告。简短的总结:我根本不明白你为什么使用
TexturePaint
,因为它看起来(!)就像你只是用
TexturePaint
填充矩形,因此,你可以使用
Graphics\drawImage
而不是
TexturePaint
。对于进一步的讨论/建议,论坛或聊天更合适。我不知道您的代码,但根据我的经验,主要是关于您自己的代码。可能有一种方法可以加快某个平台的渲染速度,但在所有平台上加快渲染速度将是一件困难的事情。最后,使用TexturePaint,您所做的不仅仅是使用颜色。网上有一些关于这方面的信息。见和。我不会用Java2D开发游戏/图形密集型应用程序。你真的应该试试@StoneAgeCoder:此外,您应该分析您的代码,并查看您使用的实现以及它花费的时间。这可能会帮助您解决性能问题。但看看JLWGL,否则……OpenGL比Java2D低很多。这是一件好事,因为它使成本显而易见,并为您提供了大量的灵活性。这需要时间来开始,但是像java.awt.geom.Area这样的东西不会成为问题。除了有人可能已经编写了一个类似的库之外,它是开源的,所以如果您只需要这个文件,您可以将它复制到您的项目中。我建议不要这样做,也不要自己为自己的项目实现类似的类,因此要熟悉代码,并且可以始终使用原始类作为参考。;)你可以。尽管java.geom.Area看起来没有那么复杂,并且可能与AWT的其余部分耦合得太紧密。我会自己写。当然,我会使用LWJGL,但我会自己写所有必要的实用程序,比如Area。这似乎不是一件大事。另一个选择是使用LibGDX,如果您想保持高水平。他们有很好的工具,很棒的平台独立性(PC(Mac是PC)、Android、iOS、HTML/JS等)和大量文档。