+2 votes

Sometimes I need to store enums integer value to file. When I load this value, I get integer.
How can I cast that value to enum type to use in match sentence?

  1. Enums in GDScript can't be used in typed var declaration like

    var myvar : G.MYENUM = G.MYENUM.VALUE1

    or

    var myvar := G.MYENUM.VALUE_1

(Especially when enum declared, for example, in singleton G)

  1. There's no possibility to cast by "as" for the same reason

    match myintvar as G.MY_ENUM:

  2. match interpretes equal int and enum values as different ones (unlike == operator)

P.S. If I use enums of constants with int values I have to use if/elif/else sentence instead of match

SOLVED!
The reason was misunderstanding the type of var in match (I got it from parsejson() function, that parses all numeric values as floats and there are no methods to distinquish type of variable in debugger)
Moreover the to
json() function converts enum values to strings and i do not know how to convert them back after parse_json() call.

in Engine by (16 points)
edited by

match interpretes equal int and enum values as different ones

...what exactly do you mean, or else, could you provide a code snippet of what's not working for you? I tried what I thought you were asking about with the following script:

tool
extends EditorScript

enum my_enum { ONE=1, TWO=2, THREE=3 }

func _run():
  for i in [1,2,3]:
    print("comparing " + str(i))
    match i:
      1:
        print("1")
        continue
      2:
        print("2")
        continue
      3:
        print("3")
        continue
      my_enum.ONE:
        print("my_enum.ONE")
        continue
      my_enum.TWO:
        print("my_enum.TWO")
        continue
      my_enum.THREE:
        print("my_enum.THREE")
        continue

func _ready() -> void:
  pass

...when run, it prints:

comparing 1
1
my_enum.ONE
comparing 2
2
my_enum.TWO
comparing 3
3
my_enum.THREE

...which is exactly what one would expect, and also exactly what you're asking for, that is, if I've understood you correctly.

Thanks for reply!
My mistake was in misunderstanding work of tojson/parsejson

In singleton named G:

enum RockHolderType {
    NO_ROCK = 0,
    OBLIGATORY_STAR = 1,
    COMET = 2,
    BLACK_HOLE = 3,
    ROCK = 4,
}

In main code:

func check_result():
    for k in [ G.RockHolderType.NO_ROCK, 
                G.RockHolderType.OBLIGATORY_STAR,
                G.RockHolderType.COMET, 
                G.RockHolderType.BLACK_HOLE,
                G.RockHolderType.COMET, 
                G.RockHolderType.ROCK ]:
        print("\nValue k = ", k)
        var x = { k = k }
        var json = to_json(x)
        var s = parse_json(json)
        var j = s["k"]
        match j:
            G.RockHolderType.NO_ROCK:
                print ("(NO_ROCK) j = ", j)
            G.RockHolderType.ROCK:
                print ("(ROCK) j = ", j)
            G.RockHolderType.OBLIGATORY_STAR:
                print ("(STAR) j = ", j)
            G.RockHolderType.COMET:
                print ("(COMET) j = ", j)
            G.RockHolderType.BLACK_HOLE:
                print ("(BLACK_HOLE) j = ", j)
            _:
                print("NOT IN ENUM j = ", j)
        print("But!")
        if j == G.RockHolderType.NO_ROCK:
                print ("(NO_ROCK) j = ", j)
        elif j == G.RockHolderType.ROCK:
                print ("(ROCK) j = ", j)
        elif j == G.RockHolderType.OBLIGATORY_STAR:
                print ("(STAR) j = ", j)
        elif j == G.RockHolderType.COMET:
                print ("(COMET) j = ", j)
        elif j == G.RockHolderType.BLACK_HOLE:
                print ("(BLACK_HOLE) j = ", j)
        else:
            print("else j = ", j)

Result:

Value k = 0
NOT IN ENUM j = 0
But!
(NO_ROCK) j = 0

Value k = 1
NOT IN ENUM j = 1
But!
(STAR) j = 1

Value k = 2
NOT IN ENUM j = 2
But!
(COMET) j = 2

Value k = 3
NOT IN ENUM j = 3
But!
(BLACK_HOLE) j = 3

Value k = 2
NOT IN ENUM j = 2
But!
(COMET) j = 2

Value k = 4
NOT IN ENUM j = 4
But!
(ROCK) j = 4

Looks like wrong behaviour, but actually parsejson returns TYPEREAL value.
When debugging, I can't see the type of j variable, if it has integer value (no decimal point or something else). Not good:(

P.S. Enums in GDScript is some kind of evil.

for l in G.RockHolderType:
        print("\nValue l = ", l, ", typeof(l) == TYPE_STRING is ", typeof(l) == TYPE_STRING)

Result:

Value l = NO_ROCK, typeof(l) == TYPE_STRING is True

Value l = OBLIGATORY_STAR, typeof(l) == TYPE_STRING is True

Value l = COMET, typeof(l) == TYPE_STRING is True

Value l = BLACK_HOLE, typeof(l) == TYPE_STRING is True

Value l = ROCK, typeof(l) == TYPE_STRING is True        

IMHO these string values is useless. I don't know how to convert them to origin int

Ok, that's pretty important.

Adding an int cast to the following line

var j = s["k"]

so that it becomes

var j = int(s["k"])

fixes the output for me. Is that perhaps the answer you were looking for? If so, you may want to update your question with all the new information.

Please log in or register to answer this question.

Welcome to Godot Engine Q&A, where you can ask questions and receive answers from other members of the community.

Please make sure to read Frequently asked questions and How to use this Q&A? before posting your first questions.
Social login is currently unavailable. If you've previously logged in with a Facebook or GitHub account, use the I forgot my password link in the login box to set a password for your account. If you still can't access your account, send an email to [email protected] with your username.