= Multi Trigger = == Author == [wiki:DamianFrick "Damian Frick"] == Description == MultiTriggers are (just as Triggers) objects which react to certain events. They offer all the functionality that Triggers do with one significant difference. A Trigger hast just one state, it can either be triggered or not triggered, it doesn't discriminate between who's triggering it. A MultiTrigger on the other hand has a distinct state (triggered or not triggered) for each entity that is defined as being able to trigger said MultiTrigger. [[BR]]This difference becomes significant, when for example you want a DistanceTrigger to trigger a QuestEffectBeacon to hand out a Quest to any Pawn that enters its range. With a simple DistanceTrigger (as opposed to the more complex DistanceMultiTrigger) the first Pawn to be in range would trigger it an receive the Quest, however if a second Pawn would enter the range, while the first Pawn still is in the range nothing would happen and even after the first Pawn left nothing would happen, since all the time the DistanceTrigger would just be triggered. In contrast with a DistanceMultiTrigger the first Pawn would enter the range and the DistanceMultiTrigger would have the state triggered for this exact Pawn (but for none else) and thus the pawn would receive the Quest and when the second Pawn enters the range the state of the DistanceMultiTrigger for that second Pawn would change to triggered and it would receive the Quest as well. == When to use MultiTriggers == Consequentially you would use MultiTriggers (instead of Triggers), when it is important that the trigger has different states for each triggering entity and when that fact is essential in the concept of the object that reacts to the triggering. However you should not just use MultiTrigger instead of Trigger, when in doubt, because MultiTrigger produces significantly more overhead than Trigger due to the added complexity. == Detailed Description == In more detail: A Trigger is an object that can either be active or inactive, with a specified behavior how to switch between the two. A MultiTrigger generalizes that behavior for multiple objects triggering the trigger. A MultiTrigger can be active or inactive for any object triggering it, with the state for each object being completely independent of the state for other objects. Each time a switch occurs an Event is fired with, as the originator a MultiTriggerContainer, containing a pointer to the MultiTrigger that caused the Event and a pointer to the object that caused the trigger to change it's activity. This way the entity that reacts to the MultiTrigger triggering receives the information it needs about the entity that triggered the MultiTrigger. [[BR]][[BR]] Also, just as with Triggers, MultiTriggers can be nested. {{{ }}} [[BR]]MultiTriggers also allow for additional complexity which can be added through the choice of the parameters explained (briefly) below. But first you must understand a small implementational detail. There is a distinction between the MultiTrigger being triggered (there is the state 'triggered' for that) and the MultiTrigger being active (for that is the state 'activity'). From the outside only the activity is visible. The state 'triggered' tells us whether the trigger is actually triggered, but it could pretend (for some reason, some of which we will see shortly) to be triggered (or to the outside, active), while it in fact isn't. The standard behavior is, that the activity changes, when the MultiTrigger transits from being triggered to not being triggered or the other way around. So to the inside a MultiTrigger being active is synonymous to the MultiTrigger being triggered to the outside. [[BR]][[BR]] The parameters of the MultiTrigger are: === delay === The delay is the time in seconds, that the trigger waits until it reacts (i.e. changes it's state) to the triggering condition being fulfilled. Internally this is handled by a state queue coupled with a counter for each state that is delayed and the state becomes active when the counter runs out. This allows the MultiTrigger to work even if the delay changes. However if the delay changes it only affects newly arriving states not the ones already in the queue. [[BR]]Default is 0. === switch === Switch is a boolean, if true the MultiTrigger is in switch-mode, meaning, that the activity changes only when the trigger is triggered, not when it is un-triggered. This means, that now the activity only changes, when the trigger changes from not being triggered to being triggered but not the other way around. [[BR]]Default is false. === stayactive === Stay active is also a boolean, if true the MultiTrigger stays active after it has been activated as many times as specified by the parameter activations. In essence this means, that after the last time it is activated it cannot be deactivated. [[BR]]Default is false. === activations === Activations is the number of times the MultiTrigger can be activated until the trigger can't be triggered anymore. [[BR]]Default is -1, which denotes infinity. === invert === Invert is a boolean, if true the trigger is in invert-mode, meaning, that if the triggering condition is fulfilled the MultiTrigger will have the state not triggered and and if the condition is not fulfilled it will have the state triggered. In short it inverts the behavior of the MultiTrigger. [[BR]]Default is false. === simultaneousTriggerers === The number of simultaneous triggerers limits the number of objects that are allowed to trigger the MultiTrigger at the same time. Or more precisely, the number of distinct objects the MultiTrigger has 'triggered' states for, at each point in time. [[BR]]Default is -1, which denotes infinity. === mode === The mode describes how the MultiTrigger acts in relation to all the MultiTriggers (its children), that are appended to it. There are 3 modes: 'and', meaning that the MultiTrigger can only be triggered if all the appended MultiTriggers are active. 'or', meaning that the MultiTrigger can only be triggered if at least one of the appended MultiTriggers is active. And 'xor', meaning that the MultiTrigger can only be triggered if one and only one appended MultiTrigger is active. Note, that I wrote 'can only be active', that implies, that there is an additional condition to the activity of the MultiTrigger and that is the fulfillment of the triggering condition (the MultiTrigger itself doesn't have one, but all derived classes should). Also bear in mind, that the activity of a MultiTrigger is still coupled to the object that triggered it. [[BR]]The default is 'and'. === broadcast === Broadcast is a boolean, if true the MultiTrigger is in broadcast-mode, meaning, that all trigger events that are caused by no originator (originator is NULL) are broadcast as having come from every possible originator, or more precisely as having come from all objects that are specified targets of this MultiTrigger. [[BR]]Default is false. === target === The target describes the kind of objects that are allowed to trigger this MultiTrigger. The parameter has to be set to the class name of the class that is allowed to trigger the MultiTrigger. [[BR]]The default is 'Pawn'. == How to use MultiTriggers == == Sub-types of MultiTriggers == === EventMultiTrigger === An EventMultiTrigger can either be used to broadcast an event that does not come from a MultiTrigger to all entities that are targets of the EventMutliTrigger or, more in line with its prototype the EventTrigger, to be triggered for an entity when an event that was caused by said entity comes in. [[BR]][[BR]]A common usage would look like this: {{{ }}} === DistanceMultiTrigger === A DistanceMultiTrigger is the MultiTrigger equivalent of the DistanceTrigger and works just the same way. It triggers (now separately for each object triggering it, since it's a MultiTrigger) whenever an object that is a target of the DistanceMultiTrigger is in the specified range. [[BR]]Two additional parameters can be specified for the DistanceMultiTrigger are the 'distance', which defines the maximum distance at which an object still triggers the DistanceMultiTrigger, and the 'targetname'. [[BR]]Setting the 'targename' puts the DistanceMultiTrigger in single-target mode. In this mode the DistanceMultiTrigger can only be triggered by objects that have a DistanceTriggerBeacon with the name specified by 'targetname' directly attached. For the single-target mode to work the target of the DistanceMultiTrigger has to be set to 'DistanceTriggerBeacon'. [[BR]][[BR]] A common usage (without DistanceTriggerBeacon) would look like this: {{{ }}} With DistanceTriggerBeacon it would look like this: {{{ }}} == Classtree ==