"Invalid call. Nonexistent function 'handle_movement_input' in base 'Nil'."

Godot Version

4.2.1

Question

How did I mess up?

So I’ve been following a tutorial to help me reorganize my code to use handlers, but I my game is crashing at line 33 (In the physics process where it says “movement_handler.handle_movement”). I have checked and double checked and I don’t understand why I’m getting this error.

class_name PlayerEntity
extends CharacterBody2D

@onready var anim: AnimationPlayer = $AnimationPlayer
@onready var fire_timer = $FireTimer
@onready var tracking_handler = $TrackingHandler as TrackingHandler
@onready var input_handler = $InputHandler as InputHandler
@onready var movement_handler = $MovementHandler as MovementHandler
@onready var jump_handler = $JumpHandler as JumpHandler
@onready var flip_handler = $FlipHandler as FlipHandler

@export var fire_rate : float = 1.0
@export var projectile_resource : ProjectileBaseResource = null

# Get the gravity from the project settings to be synced with RigidBody nodes.
var gravity = ProjectSettings.get_setting("physics/2d/default_gravity")

var can_fire : bool = true

func _ready():
	fire_timer.connect("timeout", set_can_fire)
	fire_timer.wait_time = fire_rate
	anim.play("idle")

func _process(_delta):
	tracking_handler.track_mouse(self)
	fire_arrow()
	

func _physics_process(delta):
	apply_gravity(delta)
	
	movement_handler.handle_movement(self, input_handler.handle_movement_input(), delta)
	jump_handler.handle_jump(self, input_handler.handle_jump_input())
	
	move_and_slide()
	
	flip_handler.handle_flip(self)

func apply_gravity(delta: float) -> void:
	if not is_on_floor():
		velocity.y += gravity * delta

func fire_arrow() -> void:
	if Input.is_action_just_pressed("fire") and can_fire == true:
		anim.play("bow_draw")
		can_fire = false
		fire_timer.start()
		print("bang!")
		SignalBus.emit_fire(projectile_resource, position, (get_global_mouse_position() - global_position).normalized())

func set_can_fire() -> void:
	can_fire = true

Here’s the movement handler script

class_name MovementHandler
extends Node2D

@export var movement_speed : int = 6000


func handle_movement(character_body : CharacterBody2D, input_dir : float, delta: float) -> void:
	handle_deceleration(character_body, delta)
	if input_dir < 0:
		character_body.velocity.x = -movement_speed * delta
		
	if input_dir > 0:
		character_body.velocity.x = movement_speed * delta
	
func handle_deceleration(character_body: CharacterBody2D, _delta: float) -> void:
	character_body.velocity.x = 0

And here’s the input handler script

class_name InputHandler
extends Node2D

func handle_movement_input() -> float:
	return Input.get_axis("ui_left", "ui_right")


func handle_jump_input() -> bool:
	return Input.is_action_just_pressed("jump")

Did you write this line manually or drag-dropped a node from the tree? Somehow input_handler is not being instantiated. If InputHandler is just a script and not a scene WITH a script attached to it, then it won’t be automatically instantiated.

Do you even need an instance of input_handler, i.e. were the methods in InputHandler meant to be static? Given current code, there’s no reason for them not to be static.

If all else fails, have you tried turning Godot off and on again? :smiley:

cheers!

1 Like

These assignments look odd. I picked a few:

Should be like this:

@onready var movement_handler : MovementHandler = $MovementHandler
@onready var jump_handler:JumpHandler = $JumpHandler
@onready var flip_handler:FlipHandler = $FlipHandler

If your handlers are not actual nodes in your tree, then you need to new() them, I’ll do one:

@onready var movement_handler : MovementHandler = movement_handler.new()

The error is hinting that ‘movement_handler’ is null, which means it’s not where or what you think it is.

hth

1 Like