1

I have a JButton that could have a choice of 2 different imageIcons set to it, depending on the situation.

image1Url = getClass().getResource(filename1);
image2Url = getClass().getResource(filename2);
ImageIcon image1 = new ImageIcon( image1Url , "image1")
ImageIcon image2 = new ImageIcon( image2Url , "image2")

JButton button = new JButton;

//Either image1 or image2 is set to this button depending 
//on whether the user clicks this button or whether the 
//computer sets an image there. The point is that the programme 
//then needs to respond depending upon what the image on the button is.
//I tried using...

if(button.getIcon() ==image1)
{
    //respond appropriately.
}

However this did not work. Could somebody explain to me why this does not work and if there is another way to solve this? I thought I could perhaps use the images description, but wasn't sure how to implement this. Thank you

user1788673
  • 99
  • 2
  • 7

2 Answers2

4

I would not recommend you use ==, as you are comparing the references. Unless of course, that is what you're trying to do.

I'd say the easiest way would be to set a value (e.g. a boolean) that determines what ImageIcon is currently in use, then compare against that.

Edit Sorry, I actually misunderstood the question. If you want to compare using descriptions, just do:

String desc = ((ImageIcon)button.getIcon()).getDescription();
if(desc.equals(image1.getDescription())
{
    //descriptions are the same
}
Clark
  • 1,339
  • 1
  • 7
  • 18
  • When I try to use the getDescription() method I get the following error: error:cannot find symbol symbol: method getDescription() location:interface icon. – user1788673 Nov 04 '12 at 16:34
  • I forgot to cast to ImageIcon. Oops :) – Clark Nov 04 '12 at 16:42
  • *"I'd say the easiest way would be to set a value (e.g. a boolean) that determines what ImageIcon is currently in use, then compare against that."* That sounds almost identical to some advice I offered a user in the last day or so. In fact, I'm almost sure I said it to this poster. The Q&A seems to be gone now, so I wonder if the OP intends to ask the same question again & again until they hear what they ***want*** to hear. :( +1 for your answer. – Andrew Thompson Nov 04 '12 at 16:47
2
  • works for me, there must be another issue,

  • be sure that that Icon must be instanceof ImageIcon, have to test in your code

example

import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.image.BufferedImage;
import java.io.IOException;
import java.util.Random;
import javax.swing.*;

public class JButtonAndIcon {

    private static JButton label = new JButton();
    private static Random random = new Random();
    private static ImageIcon image1; // returns null don't worry about
    private static ImageIcon image2; // returns null don't worry about
    private static Timer backTtimer;
    private static int HEIGHT = 300, WEIGHT = 200;

    public static void main(String[] args) throws IOException {
        label.setPreferredSize(new Dimension(HEIGHT, WEIGHT));
        final JButton button = new JButton("Push");
        label.setBorderPainted(false);
        label.setBorder(null);
        label.setFocusable(false);
        label.setMargin(new Insets(0, 0, 0, 0));
        label.setContentAreaFilled(false);
        //button.setLayout(new BorderLayout());
        //button.add(label);
        button.addActionListener(new ActionListener() {

            @Override
            public void actionPerformed(ActionEvent e) {
                if (label.getIcon() == image1) {
                    label.setIcon(image2);
                } else {
                    label.setIcon(image1);
                }
            }
        });
        JFrame frame = new JFrame("Test");
        frame.add(label);
        frame.add(button, BorderLayout.NORTH);
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.pack();
        startBackground();
        frame.setVisible(true);
    }

    private static void startBackground() {
        backTtimer = new javax.swing.Timer(2000, updateBackground());
        backTtimer.start();
        backTtimer.setRepeats(true);
    }

    private static Action updateBackground() {
        return new AbstractAction("Background action") {

            private static final long serialVersionUID = 1L;

            @Override
            public void actionPerformed(ActionEvent e) {
                image1 = new ImageIcon(getImage());
                label.setIcon(image1);
            }
        };
    }

    public static BufferedImage getImage() {
        int w = label.getWidth();
        int h = label.getHeight();
        GradientPaint gp = new GradientPaint(0f, 0f, new Color(
                127 + random.nextInt(128),
                127 + random.nextInt(128),
                127 + random.nextInt(128)),
                w, w,
                new Color(random.nextInt(128), 
                random.nextInt(128), random.nextInt(128)));
        BufferedImage bi = new BufferedImage(w, h, BufferedImage.TYPE_INT_RGB);
        Graphics2D g2d = bi.createGraphics();
        g2d.setPaint(gp);
        g2d.fillRect(0, 0, w, h);
        g2d.setColor(Color.BLACK);
        g2d.dispose(); // thanks notified by @trashgod
        return bi;
    }
}
mKorbel
  • 108,320
  • 17
  • 126
  • 296
  • Don't forget `g2d.dispose()`! – trashgod Nov 04 '12 at 21:14
  • @trashgod I asked a few times for reason to use dispose(), by default it could be done automatically, is there reason to override this finalization for GC – mKorbel Nov 04 '12 at 21:34
  • You are probably right in the case of `BufferedImage`; I am thinking of `VolatileImage` and other things that may allocate system resources such as [these](http://stackoverflow.com/a/2486200/230513) and [this](http://stackoverflow.com/q/6309407/230513). – trashgod Nov 04 '12 at 21:43