Java ImageIO.read() returning null

时间:2016-02-16 18:59:49

标签: java windows nullpointerexception javax.imageio

I want to read Images (.png files) in my project, and I want this to work in a runnable .jar file too. So I wrote this little piece of code:

try {
    InputStream in;
    in = Loader.class.getClassLoader().getResourceAsStream("buttons.png");

    System.out.println(in.read() + ", Reader: " + in);          

    BufferedImage img = ImageIO.read(in);

    System.out.println(img.getHeight());

    in.close(); 
} catch (IOException e) {
    e.printStackTrace();
}

When I run it, I get the following output:

137, Reader: java.io.BufferedInputStream@15db9742
Exception in thread "main" java.lang.NullPointerException
    at test.Loader.load(Loader.java:21)
    at test.MainTest.main(MainTest.java:6)

My MainTest does nothing but running this code, so I won't include it here.

I already tested if the InputStream is null as you may have noticed. As it obviously isn't the path to my file has to be right. My question is: Why is ImageIO.read() returning null?

3 个答案:

答案 0 :(得分:3)

代码的问题是在将in传递给ImageIO.read(..)之前从System.out.println(in.read() + ", Reader: " + in); 读取的行(您正在读取第一个字节):

ImageIO

当您从流中读取一个字节时,该字节被有效地“消耗”并且不会再次被读取,因此ImageIO.read(..)将永远不会看到该字节,从而导致无法识别文件格式(PNG)。在这种情况下,null将返回in

只需删除该行,您的代码就可以正常工作了。

由于null不是137,因此文件似乎存在。您打印的值ImageIO实际上是PNG signature的第一个字节,这意味着该文件正常并且正确包含在您的JAR中。

如果你真的需要在传递给in.mark(256); // allows you to read up to 256 bytes before calling reset() System.out.println(in.read() + ", Reader: " + in); // or whatever you like to do in.reset(); // "rewind" to beginning of stream (previous mark) 之前查看流中的字节,你可以这样做:

mark()/reset()

请注意,因为并非所有流都支持boolean markSupported()方法(您可以使用UIPageViewController方法进行测试)。

答案 1 :(得分:1)

正如您在调用InputStream之前已在ImageIO.read上阅读的那样,可能会发生该功能无法正确解码图像的问题。移除对in.read()的呼叫,并测试呼叫结果。

答案 2 :(得分:0)

https://docs.oracle.com/javase/8/docs/api/javax/imageio/ImageIO.html#read-javax.imageio.stream.ImageInputStream-

如果

ImageIO.read(...)无法解码图像,则可能会返回null。检查那个案例。