简体   繁体   中英

Change JButton background color when mouse on it (not rollover)

I created a JFrame with 5 buttons, 1 of them is a play button which user could press to play an audio file, the rest of them are the choices which user are required to choose the correct one after listening to the audio.

I want the buttons to change color when the mouse is over them.

I disabled the choice buttons then play the audio file, used SwingWorker to wait until the audio file is finished then enable the buttons again.

Firstly I used ButtonModel and changeListener to set background color. Of course they worked well when mouse rollover them after the audio clip finished playing.

But I found a problem is that, if i moved my mouse to the button while the audio was playing, the button was enabled after the audio finished but it did not change its color.

Appreciate for any help!

TLDR: There are two situations

(1) I pressed the play button, did not move the mouse pointer such that the pointer stay over the play button. AFTER the 4 buttons were enabled, I moved the mouse pointer to any one of them, the changelistener works prefectly.

(2) I pressed the play button, moved the mouse pointer to any one of the 4 buttons BEFORE the 4 buttons were enabled, the color of the buttons did not change after the buttons were enabled.

The complete demo of the JFrame is attached, it could be run perfectly with MigLayout libraries.

public class demo extends JFrame {

private JPanel contentPane, panelBtn, panelWord;
private JButton btnPlay, btnStop, btnWord0, btnWord1, btnWord2, btnWord3;
public static void main (String args[]){
    demo testing = new demo();
}

public demo(){
    super("Demonstrating problem");
    init();
    setVisible(true);
}

private void init(){
    customizedChangeListener clBtn = new customizedChangeListener();
    setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
    setBounds(100, 100, 673, 512);
    contentPane = new JPanel();
    setContentPane(contentPane);
    contentPane.setLayout(new BorderLayout(0, 0));
    panelBtn = new JPanel();
    panelBtn.setLayout(new MigLayout("", "[grow][]", ""));
    contentPane.add(panelBtn, BorderLayout.SOUTH);
    panelWord = new JPanel();
    panelWord.setLayout(new MigLayout("", "[grow,fill][grow,fill]", "[grow,fill][grow,fill]"));
    contentPane.add(panelWord, BorderLayout.CENTER);

    btnPlay = new JButton("Play");
    btnPlay.addActionListener(new playAcitonListener());
    panelBtn.add(btnPlay, "cell 0 0, align center");

    btnWord0 = new JButton("A");
    btnWord0.addChangeListener(clBtn);
    panelWord.add(btnWord0, "cell 0 0");

    btnWord1 = new JButton("B");
    btnWord1.addChangeListener(clBtn);
    panelWord.add(btnWord1, "cell 1 0");

    btnWord2 = new JButton("C");
    btnWord2.addChangeListener(clBtn);
    panelWord.add(btnWord2, "cell 0 1");

    btnWord3 = new JButton("D");
    btnWord3.addChangeListener(clBtn);
    panelWord.add(btnWord3, "cell 1 1");

    enableBtn(false);
}

private class customizedChangeListener implements ChangeListener{
    JButton rolledBtn;
    @Override
    public void stateChanged(ChangeEvent e) {
        rolledBtn = (JButton)e.getSource();
        if (rolledBtn.getModel().isRollover())
            rolledBtn.setBackground(Color.green);
        else
            rolledBtn.setBackground(UIManager.getColor("Button.background"));
    }
}

private class playAcitonListener implements ActionListener{
    JButton pressedBtn;
    @Override
    public void actionPerformed(ActionEvent e) {
        pressedBtn = (JButton)e.getSource();
        if (pressedBtn.equals(btnPlay)){
            btnPlay.setEnabled(false);
            new SwingWorker<Void ,Void>(){

                @Override
                protected Void doInBackground() throws Exception {
                    Thread.sleep(2000);
                    return null;
                }

                @Override
                protected void done() {
                    enableBtn(true);
                }
            }.execute();
        }
    }
}

private void enableBtn (boolean idx) {
    if (idx == true){
        btnWord0.setEnabled(true);
        btnWord1.setEnabled(true);
        btnWord2.setEnabled(true);
        btnWord3.setEnabled(true);
    }
    else if (idx == false){
        btnWord0.setEnabled(false);
        btnWord1.setEnabled(false);
        btnWord2.setEnabled(false);
        btnWord3.setEnabled(false);
    }
}

}

You can detect when mouse is over button or some other element with this code:

    button.addMouseListener( new MouseAdapter() {
    public void mouseEntered( MouseEvent e ) {
        // your code here (color of button)
    }
} );

And like @DebilsHnd said change color back with mouseExited().

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM