0

I've built a Java application that loads an image at runtime. The location of the image is fixed relative to the project.

I would like to be able to run the program from both within Eclipse and the command line and for it to load the image correctly. However, I can only do one or the other but not both. This seems like such a trivial thing to want to do but I can't find out how to do it.

The project is set up so that it creates a bin directory for the output and puts the image in a resources sub-folder. This is fine when running from the command line as I can write my code to look in that sub folder for the file.

But when I run the program from within eclipse the current working directory is different.

What am I missing?

TIA

Update - adding some code

This is what I had originally:

BufferedImage awtImage = ImageIO.read(new File(System.getProperty("user.dir") +  "/resources/image-name.png"));

Following the advice in the comments I am trying to use getResourceAsStream but I don't know what to pass to the File constructor.

InputStream temp = MyClass.class.getResourceAsStream("resources/image-name.png");
BufferedImage awtImage = ImageIO.read(new File(???));

The resource is being found because temp is not null.

ksl
  • 4,519
  • 11
  • 65
  • 106
  • How are you retrieving the image? Post your code, please. – Héctor Jan 19 '15 at 16:23
  • The java.io.File class will take a URI as a constructor argument; Try just using `ImageIO.read(new File(MyClass.class.getResource("resources/image-name.png");` – arcy Jan 19 '15 at 17:03
  • I managed to get it working by using `ImageIO.read(new File(MyClass.class.getResource("resources/image-name.png").getFile());`. Thanks for the help @arcy. If you add your comment as an answer I can accept it. – ksl Jan 21 '15 at 13:26

3 Answers3

0

I think there's 2 solutions.
1) you specify an absolute path
2) your image is in the classpath so you could load it via :

YouClass.class.getResourceAsStream("YourImg.png");
vincent
  • 1,214
  • 12
  • 22
  • I don't want to specify an absolute path @vincent so I expect using `getResourceAsStream' is the correct option as @arcy has also mentioned that. As I responded to that comment - I'm a java newbie so I'm unfamiliar with getResourceAsStream(). I'm looking for examples of how I can create a File object from one of these. Is that possible? – ksl Jan 19 '15 at 16:43
  • here is an example to use getResourceAsStream : http://stackoverflow.com/questions/1464291/how-to-really-read-text-file-from-classpath-in-java and here is an example on how to make a relation between File and FileInputStream : http://www.mkyong.com/java/how-to-read-file-in-java-fileinputstream/ – vincent Jan 19 '15 at 16:50
0

The working directory, if that's really what you mean, is not a great place to load an image from. It appears that you have an image that you would distribute with your finished program so that the program could use it. In that case, I suggest that you use Class.getResourceAsStream(), and put the image in the directory with (or near) that class.

EDIT:

Here is code I used in one of my programs for a similar purpose:

ImageIcon expandedIcon = null;
// ...
    expandedIcon = new ImageIcon(TreeIcon.class.getResource("images/Expanded.png"));

The ImageIcon class is part of Swing; I don't know if you're using that, but this should serve to show you the idea. The getResource() method takes a URL; again, you might need something a little different. But this shows the pathname relative to the path of the class on which the method is called, so if TreeIcon is in x/y/z/icons, the PNG file needs to be in x/y/z/icons/images, wherever that is on that computer.

TreeIcon is a class of mine, and its internals will not help you, so I'm not posting them. All it's doing here is providing a location for the PNG file I'm loading into an ImageIcon instance.

In addition to working on a disk with a directory structure, this also works in a jar file (which is a common way to distribute a java program or library). The jar file is just a zip file, and each file in the jar/zip file has its directory associated with it, so the image can be in the jar in the correct directory just as the java classes are in their directories.

getResourceAsStream() returns a stream; if you want to use that byte stream to load as an image, find a class that converts an stream to something your image class can use as a constructor or in a load method and hook them up. This is a common thing to have to figure out with Java i/o, unfortunately there is no cookbook way to do it across all images and situations, so we can't just tell you what it is.

EDIT 2:

As from the comment, try:

ImageIO.read(new File(MyClass.class.getResource("resources/image-name.png");

arcy
  • 12,845
  • 12
  • 58
  • 103
  • Thanks for the advice @arcy. I'm a java newbie so I'm unfamiliar with `getResourceAsStream()`. I'm looking for examples of how I can create a File object from one of these. Is that possible? – ksl Jan 19 '15 at 16:41
0

I set up my Eclipse projects like this.

Directories

The input directory is added to the classpath (JavaBuildPath in Eclipse).

Java Build Path

Finally, you access the image and / or text files like this.

private BufferedImage getIconImage() {
    try {
        return ImageIO.read(getClass().getResourceAsStream(
                "/StockMarket.png"));
    } catch (IOException e) {
        e.printStackTrace();
        return null;
    }
}
Gilbert Le Blanc
  • 50,182
  • 6
  • 67
  • 111