3

I wanted to create a calculator whose keys change color when pressed and return to their initial colors(white) after 3000 milliseconds. For that, I implemented the JButton.setBackground() method and wrote code to make the key revert to its original color after 3000 milliseconds. But instead, every time I click a calculator key, it waits 3000 ms before returning the JButton value to me, it changes color but it doesn't revert to its original color. I tried several maneuvers but without success. Here is my code for the JButton to change color for a given before returning to its initial color:

try {
    buttonOne.setBackground(Color.RED) ;
    Thread.sleep(millis:3000) ;
    buttonOne.setBackground(Color.WHITE);
} catch (InterruptedException interruptedException ) {
    InterruptedException.printStackTrace();
}
Dharman
  • 30,962
  • 25
  • 85
  • 135
  • 1
    @justsomeone: no, please delete your non-thread-safe recommendation. Original poster, the solution is not to use Java's util.Timer but rather to use a [Swing Timer](https://docs.oracle.com/javase/tutorial/uiswing/misc/timer.html). This allows for Swing thread-safe delays. A `java.util.Timer` which just someone recommended above will make changes to Swing component states *off* of the Swing event thread, and this can lead to intermittent and unpredictable threading exceptions. – Hovercraft Full Of Eels Aug 20 '21 at 23:17
  • @HovercraftFullOfEels ok thanks for the advice –  Aug 20 '21 at 23:18
  • 1
    @HovercraftFullOfEels This question was originally closed as a duplicate of: https://stackoverflow.com/questions/2464901/changing-jbutton-background-colour-temporarily. I don't know why that was picked as a duplicate. Yes the answer mentions a Timer, but it provides no code on how to use a Timer or no link to the Swing tutorial on using Timers. This answer also mentions a Timer and provide some basic code. So this is the better answer. The point of this site it not to close every question as a duplicate but to provide helpful answers. – camickr Aug 20 '21 at 23:35
  • @camickr: I guess the answers to that question, including [this one](https://stackoverflow.com/a/2465787/522444) weren't all that helpful. A shame. – Hovercraft Full Of Eels Aug 20 '21 at 23:38
  • @HovercraftFullOfEels I already stated it wasn't a good answer. I've learned over the last 11 years how to provide betters answers and attempt to do so. – camickr Aug 20 '21 at 23:39

1 Answers1

4

You don't want to use Thread.sleep() in your UI, because you want the UI to stay responsive.

Try something like this:

import javax.swing.Timer;

JButton buttonOne = new JButton("Click me");
Timer timer = new Timer(3000 ,afterButtonClicked);
timer.setRepeats(false);

ActionListener afterButtonClicked = new ActionListener() {
    public void actionPerformed(ActionEvent evt) {
        buttonOne.setBackground(Color.WHITE);
    }
};

In the action listener on your button:

buttonOne.setBackground(Color.RED);
timer.start();
H3AR7B3A7
  • 4,366
  • 2
  • 14
  • 37