Ok I see.
They use a slightly different method because they want the users to actual call a two separate static functions to subscribe and unsubscribe in another static class. The argument to pass through them is an Action (in c#), which means that in my Playmaker action (yeah, I've got to make a distinction here for the sake of clarity for anyone who reads this) I will simply have the method that needs to be triggered that will have the same signature. Not a big deal.
I had a expected a complicated structure but going with the solution where everything stays within one action is much better, it remains more FSM-ish.
However, I expected the action to have to remain active. I couldn't see how the script that defines an action could receive any callback if the action had already ran its course.
I mean, wouldn't the part that is waiting for a signal (the subscriber to the c# event delegate) need to be in OnUpdate(){} block?
When the subscriber is part of a script that is glued as a component to a game object and said game object remains active in the scene, then the script and therefore its code portion that is the subscriber remains receptive to any signal. Once the game object is deactivated, the script becomes dormant and can't hear anything.
In your example, how could SendFsmEvent() be "triggerable" at any time since the action will be be read only once (one cycle) and then deactivate itself as the flow continues its course through the hosting state and then outside of said state?
Something like this:
using UnityEngine;
namespace HutongGames.PlayMaker.Actions
{
[ActionCategory(ActionCategory.Events)]
public class SubscribeToMyScriptEvent : FsmStateAction
{
// The FSM event to be sent when the script event is triggered
public FsmBool abort;
public FsmEvent sendEvent;
public MyScript myScriptDirect;
public override void Reset()
{
abort = false;
}
public override void OnEnter()
{
// Subscribing to a event on a Global Script (static)
myScriptDirect.OnMyEvent += SendFsmEvent;
}
public override void OnUpdate()
{
// Keeps the action active to receive the callback
// Quits if FsmBool abort becomes true
if (abort.Value)
{
Finish();
}
}
private void SendFsmEvent()
{
// send FSM Event when Unity Event is triggered
Fsm.Event(sendEvent);
Finish();
}
public override void OnExit()
{
// Unsubscribing the event
myScriptDirect.OnMyEvent -= SendFsmEvent;
}
}
}
I suppose technically that each action we shove into a FSM state is an instance of the class that defines said action. So we shouldn't approach this as if the original action script were a scriptable object?
I'm new to this but I may understand that such a script (scriptable object) is a kind of static static, or super static script that doesn't even need to be in a scene, it's directly accessible in the assets. Big IF on my part there. I could be totally wrong about it.
So the subscriber belongs to the action that's in a state, it doesn't belong to the mother script. That's why I try to keep the action active at all time, and that's also why I considered going with a proxy solution where a script acts as a component on a game object and communicates with a FSM, preferably on the same game object.