Events, processes and components simple example

    This site uses cookies. By continuing to browse this site, you are agreeing to our Cookie Policy.

    • Events, processes and components simple example

      Hello ,

      I am having difficulties grasping on how to mix Events, processes and components. Is it possible someone to make a really simple command line example on how to mix those designs using the GCC framework if it is possible without LUA or XML as it is getting really confusing.

      Thanks in advance,

      Alex
    • RE: Events, processes and components simple example

      I'm not sure exactly what you're looking for. Those three systems are completely separate from each other, so I don't know what you mean by mixing them. Can you be a little more specific with what you're having trouble understanding?

      -Rez
    • Thank you for your reply.

      I am referring to this section: Distinguishing Events from Processes in Chapter 11.
      My goal is to compose "Events" and "Processes" in a simple command line application.

      For example, we have a Player and an Enemy and the player throws a bomb. In an ideal world, the bomb would have a timer process attached to it and this will guarantee that a delayed process will take place at certain point. That process will result in an event, lets say an "explosion". So once the timer is done, the event takes place. Once the event is triggered, I would like to subtract from the health of the enemy and also take into account various parameters like, for example, distance of the enemy to the bomb.
    • Processes are used to perform some operation over time. Its purpose is to decouple things that need updates from the rest of the game so they exist as self-contained nuggets of execution. Examples: the AI loop, physics update, timers, the time of day for a simulation game, etc.

      Events are used to inform one or more other systems that something has happened. They decouple those systems from each other, which makes things cleaner. The example I used in the book was death. If a Sim dies, a number of systems probably need to know. We could go through each system and notify it, which would work, but those systems would be coupled together. If I were to remove one of those systems, I would also have to modify the death code. A better alternative is to use an event that those other systems register for. Those systems can now change or be removed without having to modify the code in death.

      Actors are basically empty containers. They don't do anything by themselves and need to be filled with components. Components provide the functionality of actors. Really, and actor is just the combination of multiple components and their behavior is defined by those components. Components should be as self contained as possible, though in practice that's much harder to do.

      A grenade is a classic example, though I'm not sure it's all that helpful. Why? Because there are so many ways to implement a grenade and there's no clear solution that I don't think it makes a great example to learn from. It also doesn't really use the systems in the most beneficial way.

      Instead, I'll use another example. On The Sims, our interaction system could be described as an extremely complex version of the process system used in game coding complete. If I click on the shower and say "take shower", an interaction is spun up which has multiple elements. Each element describes one part of the interaction and can be thought of as processes. In my shower example, the Sim will route to the shower, enter the shower, run a showering animation until some exit condition is met (usually hygiene filling up), then exit the shower. This is the perfect example of a process chain in action.

      Every Sim has a statistic component which holds all the stats that apply to that sim. Stats include motives (hunger, energy, fun, etc.), skills, age, and anything else that can be boiled down to a number. The part of the interaction where you are actively taking a shower needs to affect the Sim's hygiene motive. In this case, you would have the process hold onto a weak reference to the sim's statistic component and modify hygiene every frame.

      Various systems in the sims need to know about interactions completing. If there's a birthday party, it will need to know when the "cut the cake" interaction is done. The achievement system needs to know when a bunch of different interactions are done so we can give you an achievement for taking 1000 showers (disclaimer: not an actual achievement). Thus, at the end of any interaction, we throw an event. If a birthday party happens to be going on, it will be registered for that event and can respond to it. The same is true for the achievement system or anything else that happens to be registered. Without this, we'd have a bunch of annoying if/then logic to test for the existence of a birthday party or any other temporary object. This is very error prone.

      As for the grenade, I would probably implement it like this:
      1) Grenade spins up a delay process set for however long it should take to explode.
      2) Spin up another process that handled the explosion itself (animating the effects, etc.) and attach it to the delay.
      3) Attach this chain to the process manager.

      At the top of the explosion process (probably in OnInit()), I would find all objects that are within the radius of the explosion. Any objects that have a health component (or statistic component or whatever handles health) would have a Damage() function called on it.

      Why not use an event? You could trigger a damage event that only goes to those objects, but I don't see much reason to. The coupling is rather small, especially because of the way my engine handles component interfaces. Now, if there were a ton of other side effects, an event might make sense.

      Deciding when to use an event, process, or component is really about balance. The downside of using these systems is that it obfuscates parts of your code and makes it harder to understand and follow but it also makes it much more generic and easier to change.

      Hopefully that makes it a bit more clear how these things all fit together.

      -Rez
    • Thank you for you explanation. Is there a drawback of using processes as components on the entities. Let say we have DelayComponent with DelaySystem attached to entity. And use events directly to notify other entities if the Delay has finished, rather than using chain of processes on top of the entity component logic.