2011-08-01 23 views
3

我所拥有的是大量需要在较大图像(如镶嵌图)中放置在一起的帧。图像的所需位置是已知的。在Java中使用ImageIO编写TIFF的平铺输出

有很多图像,所以将它们全部加载到内存中是最不切实际的。

基于这里的一些其他答案,我能够覆盖RenderedImage中的方法(特别是getData(rect)),以加载适当的数据并返回它。

这工作得很好,但图像编写器总是调用getData并请求数据行。在我看来,我应该能够改变ImageWriterParam来调用单个tile,但是当我尝试write函数仍然要求从getData单行。

我该如何强制这个使用tile并调用getTile来代替。

BufferedOutputStream bos=null; 
try { 
    bos = new BufferedOutputStream(new FileOutputStream(new File("test2.tiff"))); 

    ImageWriter writer =(ImageWriter) ImageIO.getImageWritersBySuffix("tif").next(); 

    ImageOutputStream ios=null 

    ios = ImageIO.createImageOutputStream(bos); 

    writer.setOutput(ios); 
    ImageWriteParam param = writer.getDefaultWriteParam(); 
    param.setTilingMode(ImageWriteParam.MODE_DEFAULT); 

    RenderedImage mosaic = new MosaicImage(imageFiles[]); 

    writer.write(null,new IIOImage(mosaic,null,null),param); 

    } catch (FileNotFoundException ex) { 

    } 

注意在使用本然而,当我可以使用param.setTilingMode(ImageWriteParam.MODE_EXPLICIT);setTiling(w,h,xoff,yoff);

writer.write仍然在我的图像调用getData(rect),很烦人不要求通过w,h指定大小的矩形。它调用一个大小是由一些随机量不同的矩形(大概来自东西)

例如,如果我用setTiling(100,100,0,0);

人们所期望的,即使它不从图像调用getTile中,传递给getData的矩形应该是(0,0,100,100),但是它会传递Rectangle(0,0,96,96),它不是图像宽度的倍数或任何我能想到的。

感谢所有帮助

回答

3

如果您对下TileWidth和TileLength领域的TIFF 6.0规格读了,你会发现文字

TileWidth必须是16的倍数。这个限制提高在一些图形环境中的性能,并增强与JPEG等压缩方案的兼容性 。

与TileLength类似。 100x100不能被16整除,但96x96是,我敢打赌是TIFF编码器尽力满足你的要求。

+0

哇,伟大的侦探工作,这解释了我看到的奇怪行为。这也不幸意味着我不能像我所希望的那样用瓷砖书写我的马赛克,但是感谢你的帮助。 – David

+0

如果右边和底边贴砖不合身,则会假定它们被填充。换句话说,这不是一个问题,你的图像大小不是你的瓷砖大小的确切倍数。如果您的图像尺寸为128x128,则645x645的图像将在文件中编码6x6的图块,并且会浪费一些空间,但这非常有效。 – BitBank