• Godot Help
  • How do I invert a boolean? "!" is working with errors

So, I have a boolean, and I need it negated. I am using "!" to do that, but it's spewing errors every frame.

E 0:00:05:0142 invert: Condition "det == 0" is true. <C++ Source> core/math/basis.cpp:47 @ invert()

What is the "correct" way to invert a boolean? or is this a bug?

That’s the correct way. Could it be that somewhere in your program you assign a non-boolean value to that variable?

Or could the error be happening elsewhere? This error message very much looks like someone trying to invert a non-invertible matrix.

    axolotl
    `extends Node3D
    @onready var anim = $door_frame/AnimationPlayer

    @export var open = false

    func _ready():
    if open:
    anim.play("open")
    else:
    anim.play_backwards("open")

    func toggleDoor(body):
    open = !open
    if open:
    anim.play("open")
    else:
    anim.play_backwards("open")`

    That is the whole script. If I remove the !open line the errors disappear (and the door stops working)
    The export part is default false.

      Try changing
      @export var open = false
      to
      @export var open: bool = false

        Nazsgull

        Open is exported. Doesn’t that mean it’s possible some other script writes to it? Or does something different based on that value?
        Or maybe for whatever reason the “open” animation cannot be played backwards?

        Nazsgull
        what i'd do is test your toggleDoor function:

        func toggleDoor(body):
            ## test variant type of "open"
            if typeof(open) == TYPE_BOOL:
                print("the mystery continues..")
            else:
                print("there's your issue :)")
            ## your own code continues here
            if open:
                anim.play("open")
            else:
                anim.play_backwards("open")

        what i'd do if i was really in your place is not worry about it:

        func toggle_door(_body) -> void:
            if open:
                 open = false
                 anim.play_backwards("open")
                 return
            open = true
            anim.play("open")
            return

        i took liberties appropriating your code. i hope that's alright. i think you get the idea.

        DaveTheCoder
        in my testing, the errors for attempting to invert most variant types are pretty specific in 4.2.1:

        • res://invert_bool.gd:6 - Invalid operands 'Dictionary' and 'Nil' in operator 'not'.
        • res://invert_bool.gd:7 - Invalid operands 'Array' and 'Nil' in operator 'not'.
        • res://invert_bool.gd:7 - Invalid operands 'String' and 'Nil' in operator 'not'.

        integers and floats makes sense if you read about constructors in the bool doc:

        func invert_int() -> void:
            ## invert a 0 integer
            var b = 0
            b = !b
            assert(typeof(b) == TYPE_BOOL && b == true)
            
            ## invert a non-zero integer
            b = 5
            b = !b
            assert(typeof(b) == TYPE_BOOL && b == false)
            return
        
        func invert_float() -> void:
            ## invert a non-zero float
            var b = 0.05
            b = !b
            assert(type_of(b) == TYPE_BOOL && b == false)
        
            ## invert an 0 float
            b = 0.0
            b = !b
            assert(type_of(b) == TYPE_BOOL && b == true)

        go ahead and run these functions. the assert methods won't complain.
        try this one too:

        func invert_float() -> void:
            ## invert an approximately 0 float
            b = 0.00000000000000000000000005
            b = !b
            assert(type_of(b) == TYPE_BOOL && b == true)
            return

        if we're talking Godot 3.5.3: bools can be constructed from seemingly anything:

        func invert_everything() -> void:
            ## this one's in the official docs
            var b = "invert this"
            b = !b
            assert(typeof(b) == TYPE_BOOL)
        
            ## but not these
            b = ["array", "of" "string"]
            b = !b
            assert(typeof(b) == TYPE_BOOL)
        
            b = null
            b = !b
            assert(typeof(b) == TYPE_BOOL)
        
            b = TextureRect.new()
            b = !b
            assert(typeof(b) == TYPE_BOOL)
            return
          a month later

          To solve the thing: ended up doing what packrat said, had errors still, and ended up remaking the scene from the ground up.

          Full class, no errors:

          `class_name Door

          @onready var anim = $AnimationPlayer

          @export var open:bool = false
          func _ready():
          if open:
          open = false
          anim.play("open")

          	return
          else:
          	open = true
          	anim.play_backwards("open")
          	return

          func toggle_door(_body) -> void:
          if open:
          open = false
          anim.play("open")
          return
          open = true
          anim.play_backwards("open")
          return
          `

            5 days later

            Nazsgull
            multi-line code is formatted like this

            ~~~
            func formatted_code_block():
            print("it's a common mistake")
            ~~~

            above is copied and pasted below without the back slash escape character "\" before each "~".

            func formatted_code_block():
                print("it's a common mistake")