Set a delay before another statement is executed

Hi,

I've already looked on the internet but found nothing really suitable or I don't understand.

Here's the deal:

I have a maze, with a hero and monsters in it.

When it's the monsters turn to move I call this function:

publicvoid zombieMove()

{

List <Point> path =new ArrayList<Point>();

for (Char c : game.getCharList())

{

game.setCurrentzombie(c);

path = game.findPath(this);

for(Point p : path)

{

game.setZombiePos(p);

repaint();

}

}

}

I used the A-star algorithm for the monsters to move, the findpath function returns a List<Point> with al the points the monster needs to move to. A monster is an object of the 'Char' class. On start of the game a list of monsters is created, and you can always access this list by sending a request to my domain controller (game.getCharList() ).

This works.

What I want: I want to see the monster move to its end position, so actually I need something like a delay after the repaint() method is used.

What i've already tied (without success):

//>> end part of the method

game.setZombiePos(p);

repaint();

try{

Thread.currentThread().sleep(200);

}catch (InterruptedException e){

e.printStackTrace();

}

// After this the "for(Point p : path) loop" is executed again if there are point objects left.

This sleep thing doesn't really work well for this. When it' s the monsters turn, 200 ms (it looks longer) are passed and bang!, all the monsters are at a new position in one time and I didnt( see them move.

Could someone help me out with this?

Greetz Daan

EDIT:

Another question, how can I award people with these so called 'duke stars' when they found a solution.

[2455 byte] By [D-a-a-na] at [2007-11-27 5:07:03]
# 1

I don't have the book with me that I need at the moment, but my advice is to simplify your problem with a small prototype. Build a small maze with nothing in it but one monster. Have the monster walk around the maze and fiddle with it until you get the results you want. I would have to make some guesses as to your graphical implementation before I could get any more specific. Someone else may have some insight that I don't.

PS.

puckstopper31a at 2007-7-12 10:26:02 > top of Java-index,Java Essentials,Java Programming...
# 2
Ok, I made the maze smaller with only one monster in it. The same happens, I can't see the monster moving.Greetz Daan
D-a-a-na at 2007-7-12 10:26:02 > top of Java-index,Java Essentials,Java Programming...
# 3

I guess what you need is to create a Timer, and move the monsters in response to your Timer's events.

This will allow the user to interact with your program in between the monster moves.

If you want the monsters to move without any possible user interaction, then you could read the current time, run an empty loop until your time laps has passed, and go on with the next monster move again. Here's a quick pseudo-code:

while monsters need to move

move the monsters one step

myTimeSnapshot = get the current time in milliseconds()

while myTimeSnapshot + 200ms < get the current time in milliseconds()

do nothing

Normally the first method should be preferable, as it is more user-friendly.

GJosefa at 2007-7-12 10:26:02 > top of Java-index,Java Essentials,Java Programming...
# 4
You need a different thread to see the movement. Your display/repaint happens after the last step of the monster.
PhHeina at 2007-7-12 10:26:02 > top of Java-index,Java Essentials,Java Programming...
# 5
'nother question. Is your game turn based or real time based?PS.
puckstopper31a at 2007-7-12 10:26:02 > top of Java-index,Java Essentials,Java Programming...
# 6

> You need a different thread to see the movement. Your

> display/repaint happens after the last step of the

> monster.

So it seems,

in order to manage the repaint() in need something like a repainttThread() ?

Could you tell me roughly how to do this?

Greetz Daan

D-a-a-na at 2007-7-12 10:26:02 > top of Java-index,Java Essentials,Java Programming...
# 7
> 'nother question. Is your game turn based or real> time based?> > PS.Turn based.
D-a-a-na at 2007-7-12 10:26:02 > top of Java-index,Java Essentials,Java Programming...
# 8
Read the tutorials first: http://java.sun.com/docs/books/tutorial/essential/concurrency/index.html http://java.sun.com/docs/books/tutorial/uiswing/concurrency/index.html
PhHeina at 2007-7-12 10:26:02 > top of Java-index,Java Essentials,Java Programming...
# 9

Ok, after you read the tutorials that PhHein recommended (good reading by the way) consider this. A turn is not a thing unto itself. A turn is the culmination of all of the events that go into it. To show all of those events you need to semantically break down to the turn into a more granular number of segments. Each of the things that happens in each segment/turn should be going on in its own thread and each thread needs to update the ui with its current state or whatever every segment and the ui needs to update every segment with the new information.

There are a number of ways to get there so I can't give you a "write it this way" answer. What I can tell you is that my foray into 2D Java development of this type was turn based and I approached it from this standpoint and it worked very well. Things are a bit more complicated in a real time situation.

PS.

puckstopper31a at 2007-7-12 10:26:02 > top of Java-index,Java Essentials,Java Programming...
# 10

I'm still kinda stuck actually,I'm sorry but I can't really find what I'm looking for.

I already made a runnable class

class RepaintThread implements Runnable

{

public void run()

{

repaint();

try

{

Thread.currentThread().sleep(100);

System.out.print(Thread.currentThread().getName());

}

catch (Exception e)

{

e.printStackTrace();

}

}

}

and did this in my for loop:

for(Point p : path)

{

game.setZombiePos(p);

System.out.print(Thread.currentThread().getName());

repaintThread.run();

try {

repaintThread.join();

} catch (InterruptedException e) {

// TODO Auto-generated catch block

e.printStackTrace();

}

But that doesn't really changes anything, what I need is something like a force repaint method. The repaint only happens on the last modifying of the monsters coordinates. I want it to repaint every single time in the for loop and not just at the end.

I searched the net and found that i'm not the first struggling this problem:

http://www.velocityreviews.com/forums/t136844-how-to-force-gui-updates.html

http://www.programmersheaven.com/mb/java/335878/335878/readmessage.aspx

D-a-a-na at 2007-7-12 10:26:02 > top of Java-index,Java Essentials,Java Programming...
# 11

You'll want to call start() on a thread rather than run(). Otherwise, you'll just directly execute the run() function in the current thread, effectively defeating the purpose of creating a thread :).

http://java.sun.com/docs/books/tutorial/essential/concurrency/runthread.html

By the way... have you seen Swing Timers?

http://java.sun.com/docs/books/tutorial/uiswing/misc/timer.html

kevjavaa at 2007-7-12 10:26:02 > top of Java-index,Java Essentials,Java Programming...
# 12

Calling repaint() where you are would repaint the RepaintThread, not the ui element. You might try passing a reference to the component that the RepaintThread is controlling and call repaint on that component instead. Say for example that your ui component is actually a JPanel that you're moving around in a container. Pass a reference to the JPanel or the container (try one then the other) into the constructor for RepaintThread and call its repaint instead of the Thread's repaint.

This is of course assuming that RepaintThread is not the component itself in which case boy have you badly named things. :)

PS.

puckstopper31a at 2007-7-12 10:26:02 > top of Java-index,Java Essentials,Java Programming...