playMaker

Author Topic: Why is OnEnter called again each time an event is fired?  (Read 1487 times)

Guavaman

  • Playmaker Newbie
  • *
  • Posts: 38
Why is OnEnter called again each time an event is fired?
« on: May 26, 2016, 04:16:11 PM »
This doesn't seem to make much sense to me. An Action's OnEnter gets fired every time an Fsm.Event is called causing infinite loops if you ever fire an event from within OnEnter.

Take this example:

Code: [Select]
public class TestAction : FsmStateAction {

        public bool everyFrame = true;
        public FsmEvent onTrueEvent;

        public override void Reset() {
            base.Reset();
        }

        public override void OnEnter() {
            DoUpdate(); // this will cause an infinite loop because onTrueEvent will be fired from within OnEnter, then OnEnter will run again, over and over...
            if(!everyFrame) Finish();
        }

        public override void OnUpdate() {
            DoUpdate();
        }

        public void DoUpdate() {

            // Just fire when X is pressed for testing
            if(Input.GetKeyDown(KeyCode.X)) {
                // Fire event
                if(onTrueEvent != null) Fsm.Event(onTrueEvent);
            }
        }
    }

  • Add the TestAction to the default FSM state.
  • Add a Finished event and a new state.
  • Connect the Finished event to the new state.
  • Set the onTrueEvent to Finished in the inspector.
  • Press Play.
  • Hit X to fire the event.

Result:
GameObject : FSM : Loop count exceeded maximum: 1000 Default is 1000. Override in Fsm Inspector.

Adding some debug logging reveals that for every time the onTrueEvent is fired, OnEnter is run again, causing onTrueEvent to be fired again, then OnEnter to run again, etc.

Is this behavior intentional? It doesn't make sense to me that firing an event that should initiate the transition to the next state should then cause the same calling FSM state to be entered again and OnEnter to be called on the Actions.
« Last Edit: May 26, 2016, 04:21:18 PM by Guavaman »

Alex Chouls

  • Administrator
  • Hero Member
  • *****
  • Posts: 4000
  • Official Playmaker Support
    • LinkedIn
Re: Why is OnEnter called again each time an event is fired?
« Reply #1 on: May 26, 2016, 05:22:41 PM »
I don't get an infinite loop when I test with those repro steps.

Do you have a FINISHED event back from the second state to the first state. That would cause an infinite loop...

Guavaman

  • Playmaker Newbie
  • *
  • Posts: 38
Re: Why is OnEnter called again each time an event is fired?
« Reply #2 on: May 28, 2016, 07:36:43 PM »
I don't get an infinite loop when I test with those repro steps.

Do you have a FINISHED event back from the second state to the first state. That would cause an infinite loop...

Thanks for the response. I guess I didn't have email notifications enabled.

I see what you are saying. If State 1 is ever entered again on the same frame, the GetButtonDown value will still be true and will set off an infinite loop. I posted this based on a bug report I received from a Rewired user who ran into this issue with my GetButtonDown Actions. I don't know exactly how the user was using it, but I would say it was almost certain that they were returning to the original State within the same frame to cause this infinite loop.

I see your included Input.GetButtonDown Actions do not evaluate OnEnter and always OnUpdate so they do not have this issue and cannot be re-evaluated during the same frame. I guess this would be the more appropriate way to handle input state checking.