【问题标题】:getResource(String name) returns null?getResource(String name) 返回 null?
【发布时间】:2014-07-14 10:54:46
【问题描述】:

首先,我想说明这个问题与这里的问题非常相似:getResources() returns an empty Enumeration。我之所以选择这个问题,是因为我的问题更多是关于 JAR 文件的问题,并且因为前一个问题尚未得到回答。此外,这在技术上完全是一种不同的方法(getResource(String) 而不是 getResources())。现在已经不碍事了……

当我的代码在 Runnable JAR 文件中时,我从代码中收到一条神秘的错误消息,但是当我在 Eclipse 中测试项目时,这根本不会发生。错误信息是:

Exception in thread "main" java.lang.ExceptionInInitializerError
    at com.wierd0games.Under.graphics.Sprite.<clinit>(Sprite.java:13)
    at com.wierd0games.Under.main.Main.<init>(Main.java:53)
    at com.wierd0games.Under.main.Main.main(Main.java:57)
Caused by: java.lang.IllegalArgumentException: input == null!
    at javax.imageio.ImageIO.read(ImageIO.java:1388)
    at com.wierd0games.Under.graphics.SpriteSheet.load(SpriteSheet.java:27)
    at com.wierd0games.Under.graphics.SpriteSheet.<init>(SpriteSheet.java:22)
    at com.wierd0games.Under.graphics.SpriteSheet.<clinit>(SpriteSheet.java:13)
    ... 3 more

根据我对这个错误的解释,问题出在第 13 行的 Sprite 类中。在这里,我创建了我的第一个 Sprite:

public static Sprite frog=new Sprite(0, 0, 64, SpriteSheet.frog);

那么错误的第二部分意味着真正的问题出在SpriteSheet类中,该类是由Sprite对象青蛙的初始化所调用的。我唯一一次使用 ImageIO.read 是在函数 load() {} 中:

private void load() {
    try {
        BufferedImage image=ImageIO.read(SpriteSheet.class.getResource(path));
        int w=image.getWidth();
        int h=image.getHeight();
        image.getRGB(0, 0, w, h, pixels, 0, w);
    }
    catch (IOException e) {
        e.printStackTrace();
    }
}

... 其中 path 是一个字符串,即"/textures/spritesheetFrog.png",因为 Sprite Sheet 位于名为 textures 的文件夹中,并且名为 spritesheetFrog.png。

因此,如果错误是说输入为空,我是否正确,因为函数 getReasource(String) 出于某种原因返回空?有谁知道为什么会发生这种情况,为什么它只发生在 Runnable JAR 中,最重要的是,如何解决它?


编辑:这是我的类的层次结构:

src
    com.wierd0games.under.graphics (this is a package)
        Sprite
        SpriteSheet
res
    textures
        spritesheetFrog.png

如果 SpriteSheet 是我的调用类,为什么 /textures/spritesheetFrog.png 不起作用?第一个斜线应该让它回到开头,然后它应该去 spritesheetFrog.png,对吧?如果没有,有人可以解释为什么这不起作用以及它应该是什么?


编辑:为避免混淆,res 文件夹不位于源代码中,它是独立的,但包含在构建路径中。


编辑:好的,我在 Eclipse 中更改了我的层次结构,因此纹理确实在源代码之下。我想我也会在这里更新它,因为我还没有得到帮助我解决这个问题的答案。

src
    com.wierd0games.under.graphics (this is a package)
        Sprite
        SpriteSheet
    textures
        spritesheetFrog.png

【问题讨论】:

  • 我猜 Runnable JAR 使用了不同的类加载器,它不支持(正确?)getResource 方法。
  • 对于您使用的路径,textures 应该是src 的直接子代。更多详情请见this answer
  • 打开罐子。相对于根的资源在哪里?
  • @SotiriosDelimanolis 我更新了它以显示层次结构
  • 在 Eclipse 中,srcres 是源文件夹吗?

标签: java eclipse jar getresource


【解决方案1】:

根据您对问题的描述和问题中的 cmets,似乎 res 目录在 Eclipse 中未定义为“源文件夹”。您将res 旁边的图标描述为“三本小书”,这很奇怪,因为这个图标暗示res 是一个类路径容器。您如何设法将res 定义为 Classpath Container 我无法理解(请告诉我们!),但无论如何,Classpath Container 不会导出到 JAR。

您应该撤消为项目定义res 所做的一切,并正确地重新定义它:

  1. 在项目的根目录下创建res 文件夹。
  2. 右键单击它,选择“构建路径”->“用作源文件夹”
  3. 再次导出您的 JAR。

【讨论】:

  • 我很确定这是我第一次将它添加到构建路径的方式,但我会尝试再做一次,以防万一。另外,为了澄清起见, res 文件夹不仅仅是三本书,如引用的库和 JRE 系统库,它是三本书(比屏幕上只有它们时更小),后面有一个马尼拉文件夹他们。
  • 把屏幕截图放在某处并提供链接怎么样?
  • 好主意!这是链接:sites.google.com/site/wierd0games/ludum-dare-under 另外,请注意我将实际文件移动到了一个名为 textures 的新文件夹中,以便它位于 src 下以尝试解决问题。 res 旁边的图标在我移动它之前是一样的。
  • @WiErD0 我以前从未见过这个图标,自从它首次发布以来,我一直在使用 Eclipse 进行开发......当你删除 res 中的所有文件时会发生什么(但保持res 活着)?图标有变化吗?
  • 不,文件夹纹理现在已被删除,即使它没有任何内容,它仍然具有相同的图标。另外,我有 Eclipse Kepler 版本,如果这会有所作为的话。
猜你喜欢
  • 2010-10-12
  • 2015-07-04
  • 2021-12-15
  • 2014-12-07
  • 1970-01-01
  • 2014-12-24
  • 2017-08-12
相关资源
最近更新 更多