Skip to content

Broadcasting

Grisgram edited this page Dec 29, 2023 · 27 revisions

The Broadcasting subsystem in raptor consists of three main components:

Class Description
Sender This is your main object.
The Sender is kind of a radio-station, sending out broadcasts to all listening receivers.
Just create a new Sender() and add receivers to it.
NOTE: gml-raptor creates one Sender in the GAMECONTROLLER object. It can be accessed through the BROADCASTER macro. This macro will always point to a valid Sender.
Receiver When using the add_receiver function of your sender, a receiver is built with the given name, message_filter and callback.
The callback will receive one parameter, a Broadcast instance.
It offers these three values:
from - The sender of the broadcast
title - The message title/name
data - (optional) additional data struct
Use remove_receiver with its name to stop receiving messages in its callback.
Broadcast Use the send function on a sender to send out a broadcast message.
It contains three members:
from - the sender of the broadcast
title - the name of the broadcast (this one must pass the message_filter of a receiver)
data - optional struct that holds any additional data for this broadcast.

How to use the subsystem: If you want to send something, just call
BROADCASTER.send(your_sender|self, "your_message", [your_data_struct]).

Here is a small example:

var snd = new Sender();
snd.add_receiver(self, "achievement_counter", "*_died", my_achievement_counter_function);

... when a monster dies you could invoke

snd.send(self, "dragon_died");

Naming your messages and receivers

It is very important to know, that the names of your receivers must be system-wide unique!
If you add a receiver with an already existing name, it will replace the former one.

⚠️ Keep in mind: Adding a receiver with the same name as an existing one, will replace the existing. So take care, how you name your receivers, as this can be a useful feature, or a trap, depending on how you use it.
As an example, naming a receiver "active_weapon" might be a good idea, as any weapon that gets activated could just add itself as a receiver under the same name and replacing the so-far active weapon with itself in one go.
On the other hand, naming a receiver in a monster "active_weapon" is a bad idea, when there are many monsters on the screen, they would permanently replace each other for the broadcast. To have a unique name for each instance, consider using the macro MY_NAME as part of the receiver name, like MY_NAME + "active_weapon", as this resolves to the object name plus the instance id and it always delivers a unique string for one object instance.

raptor also uses the broadcasting system internally, all its messages are prefixed with __raptor_<message_name> to avoid collisions with your own custom messages.
However, it might be handy to listen to some of the raptor-internal messages, as some of them can be of interest for your running game.
You can find the full list of internal messages at Raptor-internal broadcasts.

The message_filter

In larger games, there are many messages sent through the senders and a receiver normally does not need to catch all of them. As an example, the achievement receiver in the code shown above shall only count, when a monster dies, so it receives only messages that end with _died.

The title of a message is a string defined by you. So you should set up a naming system for your messages to make them filterable.

Supported filter types

The message_filter uses the string_match function from the string utilities script, which is also part of raptor. This function supports four types of wildcards:

Wildcard Syntax Description
*anything * at the beginning Matches all string that end with "anything"
anything* * at the end Matches all string that start with "anything"
*anything* * at the beginning and the end Matches all string that contain "anything"
anything No * at all Exact match

The constructors

Sender

var snd = new Sender();

The Sender has no constructor parameters. You can create as many as you like.

Receiver


⚠️ PRO TIPP
If your callback function returns true, this receiver will be removed after processing the message. This is a comfortable shortcut to remove a receiver, after its work is done. As an example, if the achievement "Kill 100 Monsters" is reached, this receiver no longer must count dying monsters, so it can be removed.
Instead of keeping the receiver in an instance variable and then referencing it from within the callback, simply return true, when the work is done.

If the callback function doesn't return anything, the receiver stays in the queue (which is the default).


Broadcast

__broadcast(_from, _title, _data = undefined)

var bc = new __broadcast(self, "my-cool-event", { eventData : someCoolArray });

You do not have to create __broadcast instances for yourself, they are shown here, as the callback of a receiver gets one of these as its only parameter. You can access the members of the broadcast in the callback:

BROADCASTER.add_receiver(self, "kill_monsters_achievement_counter", "*_died",
    function(broadcast) {
        // Here you can access all data in the broadcast like this:
        // broadcast.from  --> contains the sender of the message
        // broadcast.title --> the title of the message (like "dragon_died")
        // broadcast.data  --> an optional data struct containing additional info or <undefined>
    }

Getting started

Raptor Modules

Clone this wiki locally