0 votes

When I tried to parse enemy data the one that involves enum, it always gives the default value here the code:

    func parse_enemy_data():
        var new_enemy
        print("Enemy class: ", data.enemy_class)  #Return 1
        match data.enemy_class:
            0:     # Class normal
                new_enemy = enemy_normal_resource.instance()
                new_enemy.enemy_class = 0
            1:     # Class mid
                new_enemy = enemy_mid_resource.instance()
                new_enemy.enemy_class = 1
            2:     # Class high
                new_enemy = enemy_high_resource.instance()
                new_enemy.enemy_class = 2
            _:
                push_error("Invalid enemy class.")
        enemy_container.add_child(new_enemy)
        ...

Here's how the data structure looks like:

{"drop_item":"GOLD","enemy_class":1,"health":100,"name":"Enemy","pos_x":1052.812622,"pos_y":467.378937,"score":3}

Why this is happened? Thanks for your time.

in Engine by (45 points)

It works however if I use if statement instead. If possible I want to use this statement instead since it was cleaner and easy to read.

2 Answers

+1 vote
Best answer

I found that the issue roots in the value type, when I check the type of the data I tried to match it turns out to be.

TYPE_REAL = 3, Variable is of type float (real).

instead of

TYPE_INT = 2, Variable is of type int.

I don't know that Godot by default store enum value in TYPEREAL instead of TYPEINT, here's how I declare my enum:

enum EnemyClass{
NORMAL,
MID,
HIGH,
}

so knowing that I simply need to explicitly tell Godot to match it in TYPE_INT:

match int(data.enemy_class):

And finally it works perfectly well. I don't know why in if statement it works anyway without me explicitly transform the value into integer.

Edit

Godot does not treat enum as float, it just that I use built-in parse_json function that parses all numeric values as float. And as @Magso said below The if statement works because it can work with both datatypes. That's it, becareful with that thing.

by (45 points)
edited by

This could be a bug, specifying a value without a decimal place should declare as an int.

"enemy_class":1 #should be int
"enemy_class":1.0 #should be float

The if statement works because it can work with both datatypes but a match statement expects an int.

If it is, the bug probably somewhere between on how they implement to_json
or parse_json. And how it still printed as integer is really confusing.

0 votes

Your code works exactly as intended when I tested it like this:

func _ready():
    var data = {"drop_item":"GOLD","enemy_class":1,"health":100,"name":"Enemy","pos_x":1052.812622,"pos_y":467.378937,"score":3}
    print("Enemy class: ", data.enemy_class)  #Return 1
    match data.enemy_class:
        0:     # Class normal
            print(0)
        1:     # Class mid
            print(1)
        2:     # Class high
            print(2)
        _:
            print("default)")
by (10,868 points)

I don't get it, I just ran the test and yes it works as it should be. But my code still gives me the same error, I tried to double-check everything including how the flow works and nothing seems wrong.. debugger says it is match 1 but it goes to the default case. Any idea why this is happen?

No, I don't see any obvious issue. Is the project available somewhere to look at?

Yes, that's fine I got the problem already, thanks for your support.

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 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 webmaster@godotengine.org with your username.