Game Development Community

Event System feedback

by David House · in Torque Game Builder · 11/10/2007 (5:37 am) · 5 replies

I have created a new behavior to serve as an Event System for our games. So the idea here is that you might want to spawn/move/etc objects at certain times, including some random intervals and iterations. We are using this system to build all of our levels. There is also the ability to call a script method before moving on to the next event step (so at the end of the level we wait until all the enemies are dead before going to the next level).

The way this works is you add a SceneObject to the game, then assign it the eventSystem behavior. It has three properties:
eventData - Datablock that contains the event steps
initialDelay - time to delay before the event system starts
finishedMethod - the method to call when all the steps have been completed

The datablocks look something like this:

new t2dSceneObjectDatablock(fishAnimation)
{
	numEventSystems = 3;
	eventSystem[0] = "startGameData";
	eventSystem[1] = "level1Data";
	eventSystem[2] = "endGameData";
};

new t2dSceneObjectDatablock(level1Data)
{
	initialDelay = 1000;
	numSteps = 2;

	stepDelay[0] = 100;
	stepRepeat[0] = 2;
	stepRepeatDelay[0] = 1000;
	stepMethod[0] = "createFish(%this,\"-10 -10\");";

	stepDelay[1] = 500;
	stepRepeat[1] = 2;
	stepRepeatDelay[1] = 5000;
	stepMethod[1] = "createFish(%this,\"-10 10\");";
};

The fishAnimation datablock is the main entry point into the event system. It contains a list of eventSystems in the order they should play. In our game we have a start and end system, plus one for each level.

In the level1Data datablock, it defines the steps. There is an initialDelay, and a stepDelay so you can control timing. You can repeat steps, and the stepMethod contains the code you want to execute for each step. There is also a checkMethod you can set for a step to do some kind of check before allowing the step to execute.

So you can use this for defining your levels, or building cinematics. I have 2 questions for you:
1- Is this something anyone else would want to use? If so, I'll submit it for inclusion in the Behavior list
2- Are there some improvements I can make in the datablock section? I hate having to put the number of steps and number of event systems in there. It is just something that can introduce a bug. But it is difficult to determine the number of elements in an array, so explicitly setting it seemed to be the best option.

Feedback appreciated.

#1
11/10/2007 (7:36 pm)
It is late, and I am tired. I cannot make out what it is your event system does. The things I am familiar with may be confusing me. I understand the scheduler in TGB, and I understand the concepts of events as things that happen upon some trigger - be that by time, some state being achieved, or such. I am also familiar with a message bus. For example, I have created a pub/sub messaging bus in my game using behaviors.

Could you possibly provide an example. It could be that I am completely overlooking a use case that your event system handles. At which case, yes, I am interested in learning more.
#2
11/11/2007 (8:57 am)
Yeah, I agree that an Example would be helpful. I'll just use the game we are working on right now as our example. We are building a simple space shooter. The game is broken out into levels, and each level requires a certain number (or random) of enemies to be killed before moving on to the next level. So the highlevel summary:

GameStart
- display the game start message
- wait for 2 seconds
- hide the game start message
- move to level 1

Level1
- display the level 1 message
- wait for 1 second
- hide the level 1 message
- start spawning basic enemy (random number of enemies)
- wait until all the enemies have been killed

Level2...Levelx
- same as Level1, with different types of enemies, numbers, etc

EndGame
- display end game message
- wait for 2 seconds
- return to main menu

So with this even system behavior you can do all the above and have the control/scheduling from a single set of datablocks. Obviously you can also do this with a bunch of schedule calls and some custom code. By putting all that information in datablocks, you can easily add/remove sections of the game. Want to swap Level2 with Level3? Just rename the datablocks and you are done.

In the behavior, each one of the sections above is an event system (GameStart,Level1,Level2,EndGame). Within an event system there are steps. The steps are the bullet points in the list above. Each step is basically a bit of code that is evaluated. It can be repeated a specific or random number of times. And it can also call a 'Check' method to see if the step should run or not.

Really this is just a big linear state machine that allows you to string a very complex set of steps together. This system would also be good to use for a cinematic sequence. Thinking of a simple cinematic sequence:

Intro
- display title
- wait for 3 seconds
- fade out title

Character entrance
- add character 1 to the far left
- start character 1 walking to the middle of the screen
- add character 2 to the far right
- start character 2 walking to the middle of the screen
- wait for characters to finish movement

Chat sequence
- show dialog box for character 1 saying 'Hello'
- wait for 1 second
- hide dialog box
- show dialog box for character 2 saying 'Go away'
- wait for 2 seconds
- hide dialog box
- show dialog box for character 1 saying '!!!!!!!'
- wait for 2 seconds
- hide dialog box

Again, it is just a series of linear steps. With all the information required sitting in a set of datablocks, it is easy to adjust timing, order, etc. Not saying that there aren't other ways of doing the same thing (probably better as well). Just what I've come up with so far.

Hope this helps a bit. Keep the feedback coming because if there is a better way of handling this I'd like to know.
#3
11/13/2007 (8:17 am)
I think this is exactly what script languages are intended for, "scripting" events in response to triggers.

But I don't see how it helps to contain this in a behavior. It could just as easily be a scriptobject / script class.

Containing all the scheduling into one object or behavior 'might' make things more organized but I'm not totally convinced.

Normally you would just use global variables and global functions to trigger game events, now you have abstracted the trigger from the event by one, but what exactly does this accomplish?
#4
11/13/2007 (7:06 pm)
The only thing that putting this in a behavior gives you is just 1 less thing to do in script. It uses the OnAddToScene, so you don't have to put in any extra script to 'start' it. Of course, you may want to wait before starting it, so that might not be an advantage. I may look at doing it just with script and not with a behavior.

I still think encapsulating this kind of stuff in a series of datablocks is a decent way to handle this kind of task. Sure, you can do it all with a series of functions and schedules in script. One of the reasons I built this was to help some of my team that are not developers. Teaching them how to organize this stuff in datablocks was a little easier. Also I think this approach is closer to a data driven game rather than just script driven. But obviously that is a matter of taste.

I'll abandon this as a behavior for now. Seems like just keeping it in script is good enough and the behavior doesn't provide anything important. Now the state machine AI behavior I'm working on does make sense to stay a behavior.

Thanks for the input.
#5
11/14/2007 (2:38 pm)
We felt the same need for something like that, but if I'm not mistaken, everything is in a script object. I honestly have no idea on how it is scripted though.

I also don't see the point in having it on a behavior, but I admit I didn't read the thread completely.