UpdateGraph called in a non-running, non-paused graph. StartGraph() or StartBehaviour() should be called first.
The problem:
If we have 2 graphs on the same GameObject — let’s say a behaviour tree and an FSM — and the FSM destroys the GameObject, then we will see this warning.
Why:
As part of the clean-up process for a destroyed game object, a graph will call MonoManager.current.RemoveUpdateCall to remove our UpdateGraph callback from the MonoManager.onUpdate delegate. However, delegates are immutable when they are being called.
So, that means that our UpdateGraph is called anyway; the delegate won’t be modified to remove UpdateGraph until after the delegate has finished calling all subscribed functions. Hence the problem.
It’s kind of non-deterministic: we won’t trigger this warning if all the graphs have already run their update loop.
Visually the problem looks like this:
MonoBehaviour.onUpdate()
-> Run Poison Ability Effect Graph
—> Destroy Infantry GameObject (died by poison)
—–> (GraphOwner) Stop all graphs (Warrior AI Graph, Poison Ability Effect Graph)
-> Run Warrior AI Graph
But if for some reason it runs in this order:
MonoBehaviour.onUpdate()
-> Run Warrior AI Graph
-> Run Poison Ability Effect Graph
—> Destroy Infantry GameObject (died by poison).
—–> (GraphOwner) Stop all graphs (Warrior AI Graph, Poison Ability Effect Graph)
Then everything is seemingly fine.
Workaround:
???
I have no workarounds. I think the solution requires modifying AddUpdateCall to track subscription status via an intermediary object (EG UpdateSubscriptionStatus), so that RemoveUpdateCall can remove itself from the update loop but also mark a field as false (UpdateSubscriptionStatus.live) so we don’t try to run that callback.
That warning is not really a problem (unless of course you hate seeing warnings)., In the Graph.UpdateGraph method (which is called from MonoManager), we first check to see if the graph still “isRunning”. If so we continue executing the graph, otherwise the warning is logged. Checking the “isRunning” flag is exactly so that it accommodates the fact that UpdateGraph will be called from MonoManager due to the reasons you stated, without having to resolve into more complex solutions.
I could remove the warning from there (which was only added recently), but the actual behaviour will remain the same (hence without a harmless warning logged 🙂 ).
Oh, yeah, it definitely doesn’t cause any _functional_ errors I can see, but it does spam the NC console, which in turn causes a bit of editor lag, and also obscures other messages I want to see. Also causes confusion for users in Discord.
Removing the warning works, but then I’m sure it confuses people running the graphs manually via their own Update loop.
I don’t have any strong opinions so long as the warning isn’t triggered during normal execution, though.