0

I am programming a game where as one image changes place with another and I want the second image to be removed after 200ms, something I really could use some help with.

I'm still a beginner and all help is appreciated! Answer as if you were talking to a five year old!

 public void setVisible(Boolean visible) {
    ImageIcon ii = new ImageIcon(this.getClass().getResource(explode));

    image = ii.getImage();

    //this.visible = visible; 
    /*WITH THIS LINE OF CODE THE EXPLODE DOES NOT SHOW AT ALL,
    I WANT TO MAKE SURE IT SHOWS BUT ONLY FOR 200MS*/
}

Thanks in advance!

guisantogui
  • 4,017
  • 9
  • 49
  • 93
  • Use a single shot Swing `Timer`.. 1) For better help sooner, post an [MCVE](http://stackoverflow.com/help/mcve). 2) One way to get image(s) for an example is to hot-link to the images seen in [this answer](http://stackoverflow.com/a/19209651/418556). – Andrew Thompson Jan 16 '14 at 11:01

2 Answers2

1

You can use a scheduled thread for it. You can use the ScheduledExcecutorService for it

private final ScheduledExecutorService scheduler = Executors.newSingleThreadScheduledExecutor();


public void displayImageFor200Ms(){
    ImageIcon ii = new ImageIcon(this.getClass().getResource(explode));
    image = ii.getImage();

    scheduler.schedule(new Runnable() {
        public void run() {  
            // remove image now!
        }
    }, 200 , TimeUnit.MILLISECONDS);
}

don't forget to shut down the scheduler when you don't need it anymore (you could use a global, pooled Scheduler for all your delayed actions and shut it down when your game is over)

dube
  • 4,898
  • 2
  • 23
  • 41
0

Since you shouldn't do these time blocking methods like Thread.sleep(200) in the EDT, here is another solution with the Timer and TimerTask classes:

public void setVisible(boolean visible) {
    ImageIcon ii = new ImageIcon(this.getClass().getResource(explode));

    // show / hide image
    ii.setVisible(visible);

    if (visible) { // only hide image, if it's previously set to visible
        new Timer().schedule(new TimerTask() {
            public void run() {
                ii.setVisible(false);
            }
        }, 200); // hide it after 200 ms
    }
}

Thanks @AndrewThompson for the advice!

bobbel
  • 3,327
  • 2
  • 26
  • 43
  • Don't block the EDT (Event Dispatch Thread) - the GUI will 'freeze' when that happens. Instead of calling `Thread.sleep(n)` implement a Swing `Timer` for repeating tasks or a `SwingWorker` for long running tasks. See [Concurrency in Swing](http://docs.oracle.com/javase/tutorial/uiswing/concurrency/) for more details. – Andrew Thompson Jan 16 '14 at 11:01
  • Thanks for this advice! I was sure, there is a better way to do this ;) – bobbel Jan 16 '14 at 11:35
  • If you edit the answer to advise a `Timer` (feel free to adapt my comment), I can delete some noise and up-vote. – Andrew Thompson Jan 16 '14 at 11:38
  • Umm.. I did state a *"**Swing** [`Timer`](http://docs.oracle.com/javase/7/docs/api/javax/swing/Timer.html)"* ;) It is handy for this task, for two reasons. 1) It has a [`setRepeats(false)`](http://docs.oracle.com/javase/7/docs/api/javax/swing/Timer.html#setRepeats%28boolean%29) method (satisfying one of the requirements in a single code line) 2) It ensures the updates to the GUI are performed on the EDT - which is important for robust GUI updates. For the moment I'll remove the down vote, but leave the comment. – Andrew Thompson Jan 16 '14 at 12:45
  • I'm sorry, that I'd misunderstood your advice! :) Anyway, this is at least a better solution than my first one ;) – bobbel Jan 16 '14 at 13:05
  • *"Anyway, this is at least a better solution than my first one"* True, and I'm feeling it is already a better answer than the question deserves, given the OP seems to have ignored my advice to post an MCVE.. – Andrew Thompson Jan 16 '14 at 13:09