保存大图像 - 光栅问题

发布于 2024-11-24 05:51:26 字数 1266 浏览 1 评论 0原文

我已经问过如何保存大图像的问题,我认为我走在正确的轨道上,但我仍然需要一些建议。

我有一个 12000 x 12000 的图像,我需要将其保存为 .png

BufferedImage 无法使用。

我已经被建议使用 RenderedImage 接口,但不知何故我无法获得所需的结果。 (我还没有使用过光栅,所以可能我弄错了)

保存图像方法的代码:

   public static void SavePanel() {

    PanelImage IMAGE = new PanelImage(panel);

    try {
        ImageIO.write(IMAGE, "png", new File(ProjectNameTxt.getText() +  ".png"));
    } catch (IOException e) {
    }

   }

以及PanelImage类的代码:

 public static class PanelImage implements RenderedImage {

    // some variables here

    public PanelImage(JImagePanel panel) {
       this.panel = panel;
    }

  public Raster getData(Rectangle rect) {

        sizex = (int) rect.getWidth();
        sizey += (int) rect.getHeight();
        image = null;
        image = new BufferedImage(
                (int) sizex,
                (int) sizey,
                BufferedImage.TYPE_INT_RGB);
        g2 = image.createGraphics();
        panel.paintComponent(g2);
        return image.getData();
    }

 // rest of the implemented methods - no problems here
 }

我注意到ImageIO一次请求一行像素(12000 x 1)。 此方法有效,但我仍然需要 BufferedImage 中的整个图像。 每次 ImageIO 调用该方法时,我都必须增加 BImage 的大小,否则我会得到“坐标超出范围!”例外,

谢谢

I already asked a Question how to save large images and I think I'm on the right track but I still need some advice.

I have an Image 12000 x 12000 and I need to save it as .png

BufferedImage can't be used.

I was already advised to use the RenderedImage interface but somehow I can't get the desired result. ( I haven't worked with rasters yet so probably I got something wrong )

Code for the saving image method:

   public static void SavePanel() {

    PanelImage IMAGE = new PanelImage(panel);

    try {
        ImageIO.write(IMAGE, "png", new File(ProjectNameTxt.getText() +  ".png"));
    } catch (IOException e) {
    }

   }

And code for the PanelImage class:

 public static class PanelImage implements RenderedImage {

    // some variables here

    public PanelImage(JImagePanel panel) {
       this.panel = panel;
    }

  public Raster getData(Rectangle rect) {

        sizex = (int) rect.getWidth();
        sizey += (int) rect.getHeight();
        image = null;
        image = new BufferedImage(
                (int) sizex,
                (int) sizey,
                BufferedImage.TYPE_INT_RGB);
        g2 = image.createGraphics();
        panel.paintComponent(g2);
        return image.getData();
    }

 // rest of the implemented methods - no problems here
 }

I noticed that the ImageIO requests one line of pixels at a time ( 12000 x 1 ).
This method is working but I still need the whole image in the BufferedImage.
I have to increase the size of the BImage each time ImageIO calls the method, otherwise I get " Coordinate out of bounds! " exeption

Thanks

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

如日中天 2024-12-01 05:51:26

这个 PNGJ 库对于读取/写入巨大图像非常有用,因为它是按顺序执行的,一次只在内存中保留一行。 (前段时间自己写的,因为我也有类似的需求)

This PNGJ library can be useful to read/write huge images, because it does it sequentially, it only keeps a line in memory at a time. (I wrote it myself a while ago, because I had a similar need)

半世晨晓 2024-12-01 05:51:26

我刚刚编写了一个 ComponentImage 的最小工作示例,它接受任意 JComponent 并可以传递给 ImageIO 进行写入。为了简洁起见,这里只包含“有趣”的部分:

public final class ComponentImage implements RenderedImage {    
    private final JComponent comp;
    private final ColorModel colorModel;
    private final SampleModel sampleModel;

    public ComponentImage(JComponent comp) {
        this.comp = comp;
            this.colorModel = comp.getColorModel();
        this.sampleModel = this.colorModel.createCompatibleWritableRaster(1, 1).
                getSampleModel();
    }
    @Override
    public ColorModel getColorModel() {
        return this.comp.getColorModel();
    }

    @Override
    public SampleModel getSampleModel() {
        return this.sampleModel;
    }
    @Override
    public Raster getData(Rectangle rect) {
        final WritableRaster raster = this.colorModel.
                createCompatibleWritableRaster(rect.width, rect.height);

        final Raster result = raster.
                createChild(0, 0, rect.width, rect.height,
                rect.x, rect.y, null);

        final BufferedImage img = new BufferedImage(
                colorModel, raster, true, null);

        final Graphics2D g2d = img.createGraphics();
        g2d.translate(-rect.x, -rect.y);
        this.comp.paintAll(g2d);
        g2d.dispose();

        return result;

    }
}

I just hacked an minimal working example for a ComponentImage, which takes an arbitrary JComponent and can be passed to ImageIO for writing. For brevity, only the "interesting" parts are included here:

public final class ComponentImage implements RenderedImage {    
    private final JComponent comp;
    private final ColorModel colorModel;
    private final SampleModel sampleModel;

    public ComponentImage(JComponent comp) {
        this.comp = comp;
            this.colorModel = comp.getColorModel();
        this.sampleModel = this.colorModel.createCompatibleWritableRaster(1, 1).
                getSampleModel();
    }
    @Override
    public ColorModel getColorModel() {
        return this.comp.getColorModel();
    }

    @Override
    public SampleModel getSampleModel() {
        return this.sampleModel;
    }
    @Override
    public Raster getData(Rectangle rect) {
        final WritableRaster raster = this.colorModel.
                createCompatibleWritableRaster(rect.width, rect.height);

        final Raster result = raster.
                createChild(0, 0, rect.width, rect.height,
                rect.x, rect.y, null);

        final BufferedImage img = new BufferedImage(
                colorModel, raster, true, null);

        final Graphics2D g2d = img.createGraphics();
        g2d.translate(-rect.x, -rect.y);
        this.comp.paintAll(g2d);
        g2d.dispose();

        return result;

    }
}
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文