【问题标题】:How to Write Floating-Point-based Image to a file?如何将基于浮点的图像写入文件?
【发布时间】:2026-02-21 22:55:01
【问题描述】:

使用找到的代码here,我编写了存储图像数据的代码,其中每个颜色分量都是一个浮点值。

// Create a TYPE_FLOAT sample model (specifying how the pixels are stored)
SampleModel sampleModel = new PixelInterleavedSampleModel(DataBuffer.TYPE_FLOAT, options.width, options.height, 4, options.width * 4, new int[]{0,1,2,3});
// ...and data buffer (where the pixels are stored)
DataBufferFloat buffer = new DataBufferFloat(options.width * options.height * 4);

// Wrap it in a writable raster
WritableRaster raster = Raster.createWritableRaster(sampleModel, buffer, null);

// Create a color model compatible with this sample model/raster (TYPE_FLOAT)
// Note that the number of bands must equal the number of color components in the 
// color space (3 for RGB) + 1 extra band if the color model contains alpha 
ColorSpace colorSpace = ColorSpace.getInstance(ColorSpace.CS_sRGB);
ColorModel colorModel = new ComponentColorModel(colorSpace, true, false, Transparency.TRANSLUCENT, DataBuffer.TYPE_FLOAT);

// And finally create an image with this raster
BufferedImage out = new BufferedImage(colorModel, raster, colorModel.isAlphaPremultiplied(), null);
float[] backingImageData = buffer.getData();

FloatBuffer data = /*External Image Data Source...*/;
data.get(backingImageData); //Place data in image

boolean writerFound = ImageIO.write(out, "png", new File("C:\\out.png"));

但是,此代码失败,因为ImageIO 未能找到适合此自定义映像配置的写入程序(如调试时所见,其中writerFoundfalse)。怎样让ImageIO用这张图片成功写入数据?

【问题讨论】:

  • 我认为您应该将图像转换为另一种类型。查看this question
  • 发布堆栈跟踪。始终提供准确的错误消息,而不是您认为它所说的内容的释义。
  • @user207421 没有堆栈跟踪,因为没有抛出异常。当ImageIO.write 函数失败时,writerFound 为 false。
  • 那么别猜了。 Javadoc 表示“使用支持给定格式的任意ImageWriter 将图像写入File。” '如果没有找到合适的作者,则返回 false。'没有任何关于“未能找到合适的作家为此自定义图像配置”。而且我看不出BufferedImage out = ... 之后的三行有什么关系。他们来对地方了吗?
  • @user207421 cmets 非常清楚:data 表示原始位图(浮点格式),然后将其批量复制到backingImageData,然后我尝试写入。我不是在“猜测”任何东西,“如果没有找到合适的作者,则返回错误”和“找不到合适的作者”是一回事,当我很清楚我的问题时,你为什么要纠缠我的问题的精确措辞?我在说什么?

标签: java image javax.imageio


【解决方案1】:

要将包含浮点值的图像写入文件,您需要:

a) 一种允许存储浮点值的格式。大多数图像格式,包括 JPEG、PNG 或 GIF 肯定不会。我知道的最常用的文件格式是 TIFF。不过,值得注意的是浮点 TIFF 不是“基线”TIFF,因此并非所有 TIFF 软件都支持这类文件。

b) 一个 ImageIO 插件,支持用浮点数写入 TIFF。我认为 JAI 可能会起作用,而且很确定 GeoTools 会起作用。我自己的插件目前支持读取但不支持写入浮点(但如果您喜欢冒险,为此创建更改集应该相当容易)。

排序后,以下应该可以工作(假设 out 与您的代码中的浮点图像相同):

ImageIO.write(out, "TIFF", new File("C:\\out.tif"));

【讨论】:

  • JPEG XR 支持 float16 和 float32。
  • @cgohlke 没错,但 JPEG XR 是一种完全不同的格式,而不是“正常”的 JPEG。