How to add an image to a JPanel?


I have a JPanel to which I'd like to add JPEG and PNG images that I generate on the fly.

All the examples I've seen so far in the Swing Tutorials, specially in the Swing examples use ImageIcons.

I'm generating these images as byte arrays, and they are usually larger than the common icon they use in the examples, at 640x480.

  1. Is there any (performance or other) problem in using the ImageIcon class to display an image that size in a JPanel?
  2. What's the usual way of doing it?
  3. How to add an image to a JPanel without using the ImageIcon class?

Edit: A more careful examination of the tutorials and the API shows that you cannot add an ImageIcon directly to a JPanel. Instead, they achieve the same effect by setting the image as an icon of a JLabel. This just doesn't feel right...

1/9/2014 3:21:30 PM

Accepted Answer

Here's how I do it (with a little more info on how to load an image):

import java.awt.Graphics;
import java.awt.image.BufferedImage;
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.imageio.ImageIO;
import javax.swing.JPanel;

public class ImagePanel extends JPanel{

    private BufferedImage image;

    public ImagePanel() {
       try {                
          image = File("image name and path"));
       } catch (IOException ex) {
            // handle exception...

    protected void paintComponent(Graphics g) {
        g.drawImage(image, 0, 0, this); // see javadoc for more info on the parameters            

10/18/2016 11:45:57 PM

Fred Haslam's way works fine. I had trouble with the filepath though, since I want to reference an image within my jar. To do this, I used:

BufferedImage wPic ="snow.png"));
JLabel wIcon = new JLabel(new ImageIcon(wPic));

Since I only have a finite number (about 10) images that I need to load using this method, it works quite well. It gets file without having to have the correct relative filepath.


I think there is no need to subclass of anything. Just use a Jlabel. You can set an image into a Jlabel. So, resize the Jlabel then fill it with an image. Its OK. This is the way I do.


You can avoid rolling your own Component subclass completely by using the JXImagePanel class from the free SwingX libraries.



JLabel imgLabel = new JLabel(new ImageIcon("path_to_image.png"));

You can subclass JPanel - here is an extract from my ImagePanel, which puts an image in any one of 5 locations, top/left, top/right, middle/middle, bottom/left or bottom/right:

protected void paintComponent(Graphics gc) {

    Dimension                           cs=getSize();                           // component size

    if(mmImage!=null) { gc.drawImage(mmImage,(((cs.width-mmSize.width)/2)       +mmHrzShift),(((cs.height-mmSize.height)/2)        +mmVrtShift),null); }
    if(tlImage!=null) { gc.drawImage(tlImage,(insets.left                       +tlHrzShift),(                           +tlVrtShift),null); }
    if(trImage!=null) { gc.drawImage(trImage,(cs.width-insets.right-trSize.width+trHrzShift),(                           +trVrtShift),null); }
    if(blImage!=null) { gc.drawImage(blImage,(insets.left                       +blHrzShift),(cs.height-insets.bottom-blSize.height+blVrtShift),null); }
    if(brImage!=null) { gc.drawImage(brImage,(cs.width-insets.right-brSize.width+brHrzShift),(cs.height-insets.bottom-brSize.height+brVrtShift),null); }