Search code examples
javaimageiconsimageicon

Why does Java have both an Image class and an Icon class?


Java has both an Image class and an Icon class. The implementation of these I see most often is ImageIcon, which merges them. But why are there separate classes for Images and Icons at all? Isn't an icon just a type of image?


Solution

  • Altough there are similarities, Icon and Image have completely different use cases. An image can be used in place of an Icon, but an Icon cannot necessarily be used in place of an Image.

    Icon has just three methods and there isn't anything you can do with an Icon except querying it for its nominal size and telling it to paint itself to a Graphics target. Implementing an Icon from scratch is simple, because it has a single purpose: represent a rectangularly bounded something that can be painted.

    Image on the other hand, while it doesn't expose too many methods itself, has methods that expose further, complex API's. For example the getGraphics()-method, which gets you a huge API to draw into the image. Implementing an image from scratch isn't trivial because it offers many capabilities. The image itself can be painted, but it can also be painted to.

    Think of Icon as a simplest interface for representing an Icon, while Image is the toolshed for manipulating images. There is no reason to require all the baggage that comes from Image for the simple task of representing an Icon. This gives you the freedom to use anything for an Icon, its easy to implement (for example) Icons for choosing a Color not based on an actual Image (just create your own ColorIcon that takes a Color and paints with that color). That would become very complex if everywhere where an Icon is actually accepted, required a full blown Image.

    The reason you see ImageIcon used so often is that its extremely simple to use (so examples for Icons use it), and conceptually using an Image that can be created with a simple painting program for an Icon is also very simple. And in most cases it accomplishes what the creator wants, display some symbol/icon on a button, for example.

    Its not necessarily the most generic/best approach - if you want your program to adapt gracefully to a wide range of display resolutions, a scalable vector image would be a better choice (or at least multiple images in different sizes, selected dynamically based on display resolution). And thanks to the very simple Icon API its easy to wire up anything that can be painted for use as an Icon, allowing you to choose whatever representation fits your needs best.