derkork / godot-statecharts

A state charts extension for Godot 4
MIT License
734 stars 35 forks source link

expression_guard "Expression execute error" #39

Closed Granshmeyr closed 11 months ago

Granshmeyr commented 11 months ago

For some reason I get the following errors when using an ExpressionGuard:

E 0:00:02:0229   expression_guard.gd:35 @ is_satisfied(): self can't be used because instance is null (not passed)
  <C++ Error>    Condition "p_show_error" is true. Returning: Variant()
  <C++ Source>   core/math/expression.cpp:1507 @ execute()
  <Stack Trace>  expression_guard.gd:35 @ is_satisfied()
                 transition.gd:51 @ evaluate_guard()
                 state.gd:97 @ _state_enter()
                 compound_state.gd:52 @ _state_enter()
                 compound_state.gd:52 @ _state_enter()
                 parallel_state.gd:68 @ _state_enter()
E 0:00:02:0229   expression_guard.gd:37 @ is_satisfied(): Expression execute error: self can't be used because instance is null (not passed) for expression: lastMovement == "moveUp"
  <C++ Source>   ./core/variant/variant_utility.cpp:905 @ push_error()
  <Stack Trace>  expression_guard.gd:37 @ is_satisfied()
                 transition.gd:51 @ evaluate_guard()
                 state.gd:97 @ _state_enter()
                 compound_state.gd:52 @ _state_enter()
                 compound_state.gd:52 @ _state_enter()
                 parallel_state.gd:68 @ _state_enter()

Regardless, the statechart still functions as expected. There is just a little bloat in the Debugger. This is how I'm calling set_expression_property in my C# script:

void OnPlayerStop(Movement movement)
{
    string value = movement switch
    {
        Movement.Up => "moveUp",
        Movement.Down => "moveDown",
        Movement.Left => "moveLeft",
        Movement.Right => "moveRight",
        _ => "moveDown"
    };

    stateChart.Call("set_expression_property", "lastMovement", value);
    stateChart.Call("send_event", "stop");
}

My node tree looks like this: image ToIdleUp properties: image

derkork commented 11 months ago

This would seem to be an initialization problem. When the guard is evaluated, the lastMovement property is not set to anything, so the expression cannot find it and you get this error message. You can fix this by initializing this property maybe in the _Ready function of your player, so it is ensured that the property has some value whenever the guard is evaluated:

    public override void _Ready()
    {
        stateChart.Call("set_expression_property", "lastMovement", "none");
    }