I'm trying to create a game where JADE Agents are the 'enemies' and they chase a player around a maze.
So far I have: MazeView.java (uses Swing to paint various things on the screen, and lets the user interact through button presses) Enemy.java (a JADE agent that will have behaviours like search, pursue, etc.) And a few other classes doing things like generating the actual maze data structure etc.
My problem is that, while I can instantiate an Agent and paint it on the screen, for some reason I can't add any behaviours. For example, if I wanted something like this (in Enemy.java):
protected void setup() {
// Add a TickerBehaviour that does things every 5 seconds
addBehaviour(new TickerBehaviour(this, 5000) {
protected void onTick() {
// This doesn't seem to be happening?
System.out.println("5 second tick... Start new patrol/do something?");
myAgent.addBehaviour(new DoThings());
}
}); // end of addBehaviour
System.out.println("End of setup()...");
} // end of setup
When I run the code, no errors are thrown, and I can see "End of setup()..." displayed in console. So for some reason it's just not going into the addBehaviour() method at all. Even if the DoThings() behaviour didn't work (right now it just prints a message), it should at least display the "5 second tick" message before throwing an error. What is going wrong here?
I think it could be something to do with the fact that currently there is no concept of 'time' in my maze. The user presses a key, and THEN processing happens. So having an agent that does things every 5 seconds might not work when there is no real way to facilitate that in the maze? But I'm still confused as to why it just skips addBehaviour() and I don't get an error.
A possible solution might be to re-implement my maze as a constant loop that waits for input. Would that allow a concept of 'time'? Basically I'm not sure how to link the two together. I am a complete beginner with JADE.
Any ideas would be appreciated. Thanks!
I've never used Jade, but my first thought was that you are adding behaviors and then assuming that Jade will decide to run them at some point. When you say that you never see your behaviors activate, it strengthened that hypothesis.
I looked at the source and sure enough, addBehaviour()
and removeBehaviour()
simply add and remove from a collection called myScheduler
. Looking at the usages, I found a private method called activateAllBehaviours()
that looked like it ran the Behaviours. That method is called from the public doWake()
on the Agent class.
I would guess that you simply have to call doWake()
on your Agent. This is not very apparent from the JavaDoc or the examples. The examples assume that you use the jade.Boot
class and simply pass the class name of your agent to that Boot class. This results in the Agent getting added to a container that manages the "waking" and running of your Agents. Since you are running Swing for your GUI, I think that you will have to run your Agents manually, rather than the way that the examples show.
I got more curious, so I wrote my own code to create and run the Jade container. This worked for me:
Properties containerProps = new jade.util.leap.Properties();
containerProps.setProperty(Profile.AGENTS, "annoyer:myTest.MyAgent");
Profile containerProfile = new ProfileImpl(containerProps);
Runtime.instance().setCloseVM(false);
Runtime.instance().createMainContainer(containerProfile);
This automatically creates my agent of type myTest.MyAgent
and starts running it. I implemented it similar to your code snippet, and I saw messages every 5 seconds.
I think you'll want to use setCloseVM(false)
since your UI can handle closing down the JVM, not the Jade container.