ImageIO 找不到文件



我正在编写一个涉及图形界面的程序,我正在使用ImageIO将图像读入下面的代码中的BufferedImage(变量starImg):

public Star() {
super();
if (starImg == null) {
try {
starImg = ImageIO.read(new File("star.png"));
} catch (IOException e) {
System.out.println("There was an issue reading the file: " + e);
} catch (Exception e) {
System.out.println(e);
}
}
}

除了代码总是最终输出IO文件未找到异常消息,即使它不应该。我的 star.png 文件与我的代码位于同一文件夹中(使用 Eclipse 运行),我已经确保它是一个 png 而不是一个 jpg,并尝试了其他事情,例如将 File 更改为 FileInputStream,所以我似乎无法弄清楚为什么无法读取此图像。也许这与我正在使用 Eclipse 的事实有关,尽管我觉得这不太可能。我看过与同一问题相关的其他答案,但解决他们问题的解决方案并没有解决我的问题。

如果有人能指出我的代码中的错误,那将不胜感激。

我的 star.png 文件与我的代码位于同一文件夹中(使用 Eclipse 运行)

好吧,有你的问题。

new File("star.png")将查找进程当前工作目录。

那是哪里?谁知道呢!- 这取决于用户;应用程序从何处启动。因此,这作为一个概念被打破了:绝对不能保证它是正确的地方。

情况变得更糟 - java应用程序以jar或jmods的形式提供,并且它们所需的文件包含在其中。jar 文件或 jmod 文件中的条目不是文件new File()不可能读懂这些

结论是这个过程(创建一个文件对象,将其传递给 ImageIO.read)不能用于资源。

解决方案是要求 java 类加载系统从 VM 加载类的位置为您提供资源。如果这是来自磁盘,太好了,从那里获取它们。如果这是来自 jar 或 jmod 文件,很酷,从那里获取它们。

这是你如何做到这一点的:

URL url = Star.class.getResource("star.png");
// - OR -
try (InputStream in = Star.class.getResourceAsStream("star.png")) {
// use in here
}

只要您有一个接受 URL 对象的 API,第一个就很有用。我很确定 ImageIO.read() 就是这样一个 API。

第二个对于接受输入流的 API 很有用。ImageIO.read 也这样做 - 如果两者都可用,则基于 URL 的更简单(在这种情况下不需要尝试资源)。

请注意,这将出现在Star.class最终的同一位置,可以这么说,在 Star 的"包裹"中。如果您希望从"根"文件夹(例如 jar 的根目录)转到,请使用例如 相反"/img/star.png";这将在名为"IMG"的目录中查找文件,并且该目录必须位于"根"中。因此,如果 Star 在顶部有package com.foo;,则有一些结构(jar 文件、jmod 等)具有com目录,该结构具有foo目录,该目录具有Star.class文件。对于"/img/star.png",必须有一个名为img的目录,作为名为com的目录的同级。

Eclipse 会自动复制 src 文件夹中的非 java 文件,打个比方:它通过编译 java 文件来"复制"它们,并通过复制非 java 文件来"编译"它们。因此,这在 eclipse 中工作正常,在构建系统中也工作正常(请注意,对于 maven,有一个 dir 结构需要遵守src/main/resourcessrc/main/java

相关内容

  • 没有找到相关文章

最新更新