使用 JAI 加载 JPEG2000 图像

Loading JPEG2000 Images using JAI

我想使用 Java JAI 加载 jpeg2000 图像 (.jp2)。

我已经在使用旧的 JAI 版本,它仍然支持 jpeg2000。我从 scihub.copernicus.eu 下载了这些图片。这些文件相当大(高达 100 MB)。我尝试了几种不同的方法:

  1. 使用 java 标准方法是这样的:

    public class Main {
        public static void main(String[] args) throws IOException {
            String path = "C:\temp\B2.jp2";
            File inputFile = new File(path);
            Image result = ImageIO.read(inputFile);
        }
    }
    

以下堆栈跟踪发生异常:

    Exception in thread "main" java.lang.RuntimeException: An uncaught runtime exception has occurred
        at com.sun.media.imageioimpl.plugins.jpeg2000.J2KReadState.initializeRead(J2KReadState.java:708)
        at com.sun.media.imageioimpl.plugins.jpeg2000.J2KReadState.<init>(J2KReadState.java:209)
        at com.sun.media.imageioimpl.plugins.jpeg2000.J2KImageReader.read(J2KImageReader.java:449)
        at javax.imageio.ImageIO.read(ImageIO.java:1448)
        at javax.imageio.ImageIO.read(ImageIO.java:1308)
        at Main.main(Main.java:16)
    Caused by: java.io.IOException: File too long.
        at jj2000.j2k.fileformat.reader.FileFormatReader.readFileFormat(FileFormatReader.java:207)
        at com.sun.media.imageioimpl.plugins.jpeg2000.J2KReadState.initializeRead(J2KReadState.java:418)
        ... 5 more

我希望获得 JPEP2000 文件的 BufferedImage。

  1. 这是JAI默认加载图片的方式

    public class Main {
        public static void main(String[] args) throws IOException {
            String path = "C:\temp\B2.jp2";
            File inputFile = new File(path);
            RenderedOp image = JAI.create("fileload", inputFile.getPath());
            Image result = image.getAsBufferedImage();
        }
    }
    

但是变量图像不包含任何数据: 方法 getAsBufferedImage() 抛出以下异常:

Exception in thread "main" java.lang.RuntimeException: - Unable to render RenderedOp for this operation.
    at javax.media.jai.RenderedOp.createInstance(RenderedOp.java:827)
    at javax.media.jai.RenderedOp.createRendering(RenderedOp.java:867)
    at javax.media.jai.RenderedOp.getColorModel(RenderedOp.java:2242)
    at javax.media.jai.PlanarImage.getAsBufferedImage(PlanarImage.java:2498)
    at javax.media.jai.PlanarImage.getAsBufferedImage(PlanarImage.java:2546)
    at Main.main(Main.java:15)

任何其他图片格式都可以。您使用什么 JAI 库来加载 JPEG2000 文件? Javax 或 github 或任何其他提供的库?您的代码是什么样的?

我认为 "problem" 是您尝试读取的特定文件。并不是文件太大,而是 "boxes" 大小之一。

JPEG 2000 文件格式基于 ISO base media file format (ISO BMFF), which is a container format made up of "boxes" of data. It seems that your specific JPEG 2000 file contains a "box" type (a box with extended length) that the original authors of JJ2000 (the Java JPEG 2000 Reference Implementation that JAI and most, if not all, Java based decoders are based upon) didn't bother to support(另外,文件的这一部分实际上不允许使用这种类型的框,我还没有详细阅读规范)。

使用 JPEG 2000 或其他(本机)实现的本机 JAI 插件可能会更好。

由于 ISO BMFF 有详细记录,因此可以修复或修补 JAI FileFormatReader class 以支持这些扩展框。