How does _fixed_process() execute when using subclasses?

:information_source: Attention Topic was automatically imported from the old Question2Answer platform.
:bust_in_silhouette: Asked By shoeberto
:warning: Old Version Published before Godot 3 was released.

I have a hierarchy of entity classes where I need to be able to act on collision information differently per entity type, but I’m very confused about how _fixed_process() actually operates in the inheritance structure.

Basically, I have a higher-level entity class (SpriteEntity) that is used to handle basic motion & animation for my entity scenes, and I am now working on a subclass of it for the player character (PlayerCharacterEntity). These scripts are attached to KinematicBody2D nodes. Right now I just want to make it so that, if a PlayerCharacterEntity walks into a SpriteEntity, I can detect it and do something with it.

My confusion is mostly with how _fixed_process() works. In most languages, I would expect that by subclassing and overriding a method, I would have to explicitly invoke the base class method, but _fixed_process() appears to fire on the base class regardless. This makes the logic confusing, since when the SpriteEntity movement code is called, it will correctly detect collision, but it appears that the PlayerCharacterEntity code has only occasional knowledge as to whether a collision has occurred (race condition?)

I’ve been banging my head against this for a few days and really haven’t come out with any more understanding. Why does _fixed_process() seem to get called independently on all scripts in a class hierarchy, and how can subclasses have knowledge of collisions that are reported in a base class?

:bust_in_silhouette: Reply From: shoeberto

I found this tidbit in the GDScript documentation:

Remember that default functions like _init, and most notifications such as _enter_tree, _exit_tree, _process, _fixed_process, etc. are called in all base classes automatically. So there is only a need to call the function explicitly when overloading them in some way.

Given that KinematicBody collisions are only flagged during the _fixed_process call, my parent class that does the physics stuff needs to be considered the authoritative entry point for physics calculations - there’s just no way to have a subclass implement a _fixed_process(). But, I can still take advantage of the inheritance by defining a method that gets called at the end of the physics update and override it in the inherited classes:

SpriteEntity.gd

func _fixed_process(delta):
    self.move(self.get_movement_vector())
    self.post_process()

func post_process()
    pass

PlayerCharacterEntity.gd

func post_process()
    # do stuff
    print('foobar')

Be careful with _ready (and maybe _init) because is called on a different order than _process and others, you may want to use the same approach for that method (using an empty/nonexistent call con the parent class) to initialize variables or avoiding them at all on the parent class.

All this will change on Godot 3, hopefully.

eons | 2016-11-21 01:10