Why do I get "Nonexistent function"?
The error
Section titled “The error”You’ll see something like one of these in the Debugger panel. The function and node names will be your own:
Which cause is it?
Section titled “Which cause is it?”| What’s happening | Go to |
|---|---|
The base is a node you didn’t expect, like TileMapLayer or StaticBody2D | The wrong node got the call |
The base is PackedScene | Calling the scene instead of the instance |
| The base is your node and the function is right there in the script | The script isn’t on that node |
| Everything looks right | A typo |
The example scene
Section titled “The example scene”The player has a take_damage() function. The enemy is an Area2D that calls it on whatever enters.
MainNode2D
PlayerCharacterBody2D
has take_damage()
EnemyArea2D
calls take_damage()
WallsTileMapLayer
The wrong node got the call
Section titled “The wrong node got the call”The variable holds a different node than you think. Here, body is whatever touched the enemy. Most of the time that’s the player, but when the enemy touches the walls, body is the TileMapLayer, and a TileMapLayer has no take_damage():
extends Area2D
func _on_body_entered(body: Node2D) -> void: body.take_damage(10)using Godot;
public partial class Enemy : Area2D{ private void OnBodyEntered(Node2D body) { ((Player)body).TakeDamage(10); }}Fix: check before you call.
func _on_body_entered(body: Node2D) -> void: body.take_damage(10) if body.has_method("take_damage"): body.take_damage(10)private void OnBodyEntered(Node2D body){ ((Player)body).TakeDamage(10); if (body is Player player) player.TakeDamage(10);}get_parent() causes the same surprise. It returns whatever the parent is right now, so moving a script to a different node silently changes what get_parent() points at.
Calling the scene instead of the instance
Section titled “Calling the scene instead of the instance”A PackedScene is the blueprint. It has no take_damage() and no position. You need to instantiate() it first, then call things on the result:
const ENEMY := preload("res://enemy.tscn")
func spawn() -> void: ENEMY.set_target(player) var enemy := ENEMY.instantiate() enemy.set_target(player) add_child(enemy)The script isn’t on that node
Section titled “The script isn’t on that node”The function is in player.gd, but player.gd has to be attached to the node you’re calling. Select the node in the Scene dock and look at the script icon on the right of its name. If it’s missing, or shows a different file, that’s the problem. It often happens after duplicating a scene or dragging a script onto the wrong node.
If the node is an instance of another scene (player.tscn), the script lives in that scene. Open it and check there.
A typo
Section titled “A typo”Function names are case-sensitive and exact: take_damage, takeDamage and take_dmg are three different functions. Copy the name from the definition rather than retyping it. The script editor underlines calls it can’t resolve on nodes with a known type, so give your variables types where you can:
var player = $Playervar player: Player = $PlayerStill stuck?
Section titled “Still stuck?”The error names the base node’s class, not its name. If it says in base 'Node2D', work out which Node2D that is: put print(body.name) or print(body.get_path()) on the line above the call and run again. Once you know which node it is, the fix is usually obvious.