I’ve run into a case where I have a network control script which will broadcast an event has occured but it also responds to the same event.
The event (for example, lets say Jump()) is broadcast so that all components have a chance to respond and take appropriate action.
My problem is that when a RPC comes in to say “Jump!” - I want to be able to use BroadcastMessage to relay that Jump() event to all objects in the hierarchy. This works, except that it will create an infinite loop since Jump() also exists on the network control script.
Is there a way to tell if either (a) i’m receiving a broadcast message from myself or (b) of ensuring the message only gets received by scripts other than the receiver ?
I’m using built-in c# event handling with delegates and as part of the contract for each event handler, the sending cmoponent name is sent which allows for guarding against circular cases.
I’d prefer to be able to know the name of the script calling and being sent too so this parameter is unnecessary - that might be doable by requesting a “key” to register the event with and manually traversing the list of registered event handlers and excluding any with the same key - that’ll probably be my next move to streamline the contract on this code and move out the need for guard conditions in client code.
`
// – This is the event manager class which allows for the in-game events
using UnityEngine;
using System.Collections;
public class Events : MonoBehaviour
{
//public EventHandler eventWithEmptyDelegate = delegate{};
private static Events _instance;
public static Events Instance
{
get
{
if( _instance == null )
{
_instance = ( Events )FindObjectOfType( typeof( Events ) );
if( _instance == null )
{
Debug.Log( "No 'Events' Singleton was found, creating a new instance." );
_instance = ( new GameObject( "Events" ) ).AddComponent<Events>( );
}
}
return _instance;
}
}
public delegate void FireWeaponDelegate( string sender, RaycastHit hit );
public event FireWeaponDelegate FireWeapon;
public void OnFireWeapon( string sender, RaycastHit hit )
{
if( FireWeapon != null )
{
FireWeapon( sender, hit );
}
}
}
// – example of registering event handler
Events.Instance.FireWeapon += OnFireWeapon;
// – example of guarding against circular refs
public void OnFireWeapon( string sender, RaycastHit hit )
{
// do not process this if it’s sender name is the same as this script
if( sender == “NetworkControlSync” ) return;
// remaining code here ...
}
// – example of firing an event
Events.Instance.OnFireWeapon( “NetworkControlSync”, hit );
`