1

使用 Java 2D 可以创建的图像的最大尺寸是多少?

我使用的是 Windows 7 Pro 64 位操作系统和 JDK 1.6.0_33,64 位版本。我可以创建一个最大为 5 MB 的 BufferedImage。除此之外,我得到了 OutOfMemoryError。

请指导我如何使用 Java 2D 或 JAI 创建更大尺寸的图像。

这是我的尝试。

import java.awt.Graphics2D;    
import java.awt.image.BufferedImage;     
import java.io.File;    
import javax.imageio.ImageIO;    

public class CreateBiggerImage
{
private String fileName = "images/107.gif";
private String outputFileName = "images/107-Output.gif";

public CreateBiggerImage()
{
    try
    {
        BufferedImage image = readImage(fileName);
        ImageIO.write(createImage(image, 9050, 9050), "GIF", new File(System.getProperty("user.dir"), outputFileName));
    }
    catch (Exception ex)
    {
        ex.printStackTrace();
    }
}

private BufferedImage readImage(String fileName) throws Exception
{
    BufferedImage image = ImageIO.read(new File(System.getProperty("user.dir"), fileName));
    return image;
}

private BufferedImage createImage(BufferedImage image, int outputWidth, int outputHeight) throws Exception
{
    int actualImageWidth = image.getWidth();
    int actualImageHeight = image.getHeight();

    BufferedImage imageOutput = new BufferedImage(outputWidth, outputHeight, BufferedImage.TYPE_INT_RGB);
    Graphics2D g2d = imageOutput.createGraphics();
    for (int width = 0; width < outputWidth; width += actualImageWidth)
    {
        for (int height = 0; height < outputHeight; height += actualImageHeight)
        {
            g2d.drawImage(image, width, height, null);
        }
    }
    g2d.dispose();

    return imageOutput;
}

public static void main(String[] args)
{
    new CreateBiggerImage();
}
}
4

1 回答 1

2

您可以使用 Java 2D 创建的图像的“最大尺寸”取决于很多事情......所以我会在这里做一些假设(如果我错了,请纠正我):

  • “大小”是指尺寸(宽度 x 高度),而不是内存消耗
  • 通过“图像”,您的意思是BufferedImage

有了这些假设,理论限制由(width * height * bits per pixel / bits in transfer type) == Integer.MAX_VALUE(换句话说,您可以创建的最大数组)给出。例如,对于TYPE_INT_RGBor TYPE_INT_ARGB,您将使用每像素 32 位,传输类型也是 32 位。因为TYPE_3BYTE_RGB您将使用每像素 24 位,但传输类型只有 8 位,因此最大尺寸实际上更小。

理论上,您可以创建更大的 tiled RenderedImages。或者使用Raster带有多个波段(多个数组)的自定义 s。

无论如何,您的限制因素将是可用的连续内存。

为了克服这个问题,我创建了一个DataBuffer 实现,它使用内存映射文件将图像数据存储在 JVM 堆之外。这完全是实验性的,但我已经成功创建了BufferedImages where width * height ~= Integer.MAX_VALUE / 4。性能不是很好,但对于某些应用程序可能是可以接受的。

于 2013-08-27T20:24:38.053 回答