Help! No constructor of "Callable" matches the signature "Callable(String, Node, String)"

Hello, I have been following a tutorial for top down shooter enemy ai, and have come across this error in the code in the main scene: Line 7:No constructor of “Callable” matches the signature “Callable(String, Node, String)”.

Here is the code for the main scene (level 1) where i got the error,

extends Node2D

@onready var bullet_manager = $bulletmanager
@onready var player = $player

func _ready() -> void:
	GlobalSignals.connect(Callable("bullet_fired", bullet_manager, "handle_bullet_spawned"))


this is the code for the player:

extends CharacterBody2D
class_name Player

signal player_fired_bullet(bullet, position, direction)

@export var speed: float = 100
@export var accel: float = 10



@onready var weapon = $weapon
@onready var health_stat = $Health

@onready var anim_sprite: AnimatedSprite2D = $AnimatedSprite2D as AnimatedSprite2D


func _ready() -> void:
	weapon.connect("weapon_fired", shoot)



func _physics_process(_delta: float) -> void:
	var direction: Vector2 = Input.get_vector("move_left", "move_right", "move_up", "move_down")
	
	velocity.x = move_toward(velocity.x, speed * direction.x, accel)
	velocity.y = move_toward(velocity.y, speed * direction.y, accel)
	
	look_at(get_global_mouse_position())
	move_and_slide()


func _unhandled_input(event: InputEvent) -> void:
	if event.is_action_pressed("shoot"):
		weapon.shoot()
		
		
		
		
		
func shoot(bullet_instance, location: Vector2, direction: Vector2):
	emit_signal("player_fired_bullet", bullet_instance, location, direction)
		
		
		
		
func handle_hit():
	health_stat.health -= 20
	print('ouch!', health_stat.health)

this is the code for the enemy:

extends CharacterBody2D

@onready var health_stat = $Health
@onready var ai = $AI
@onready var weapon = $weapon

func _ready() -> void:
	ai.initialize(self, weapon)

func handle_hit():
	health_stat.health -= 20
	if health_stat.health <= 0:
		queue_free()


this is the code for the enemy AI:

extends Node2D


signal state_changed(new_state)


enum State {
	PATROL,
	ENGAGE
}


@onready var player_detection_zone = $playerdetectionzone

var current_state: int = State.PATROL : set = set_state
var actor = null
var player: Player = null
var weapon: Weapon = null


func _process(delta: float) -> void:
	match current_state:
		State.PATROL:
			pass
		State.ENGAGE:
			if player != null and weapon != null:
				actor.rotation = actor.global_position.direction_to(player.global_position).angle()
				weapon.shoot()
			else:
				print('in the engage state but no weapon or player')
		_:
			
			print("ERROR: FOUND A STATE FOR OUR ENEMY THAT SHOULD NOT EXIST")


func initialize(actor,  weapon: Weapon):
	self.actor = actor
	self.weapon = weapon







func set_state(new_state: int):
	if new_state == current_state:
		return
		
	current_state = new_state
	emit_signal("state_changed", current_state)
	




func _on_playerdetectionzone_body_entered(body: Node) -> void:
	if body.is_in_group("player"):
		set_state(State.ENGAGE)
		player = body

here is the code for the bullet:

extends Area2D
class_name Bullet
@export var speed: int = 15

@onready var kill_timer = $killtimer

var direction := Vector2.ZERO

func _ready() -> void:
	kill_timer.start()

func _physics_process(delta: float) -> void:
	if direction != Vector2.ZERO:
		var velocity = direction * speed
		
		global_position += velocity

func set_direction(direction: Vector2):
	self.direction = direction
	rotation += direction.angle()


func _on_killtimer_timeout() -> void:
	queue_free()


func _on_body_entered(body: Node) -> void:
	if body.has_method("handle_hit"):
		body.handle_hit()
		queue_free()

here is the code for the bullet manager:

extends Node2D

func handle_bullet_spawned(bullet: Bullet, position: Vector2, direction: Vector2):
	add_child(bullet)
	bullet.global_position = position
	bullet.set_direction(direction)

here is the code for the weapon:

extends Node2D
class_name Weapon

signal weapon_fired(bullet, location, direction)

@export var Bullet :PackedScene 


@onready var end_of_gun = $endofgun
@onready var gun_direction = $gundirection
@onready var attack_cooldown = $attackcooldown
@onready var animation_player = $AnimationPlayer

# Called when the node enters the scene tree for the first time.
func shoot():
	if attack_cooldown.is_stopped() and Bullet != null:
		var bullet_instance = Bullet.instantiate()
		var direction = (gun_direction.global_position - end_of_gun.global_position).normalized()
		emit_signal("weapon_fired", bullet_instance, end_of_gun.global_position, direction)
		attack_cooldown.start()
		animation_player.play("muzzleflash")

here is the code for the GlobalSignals:

extends Node


signal bullet_fired(bullet, position, direction)


here is the code for the health:

extends Node2D


@export var health: int = 100 : set = _set_state, get = _get_state

	

func _set_state(new_health):
	health = clamp(new_health, 0, 100)



func _get_state():
	return health

here is the link to the tutorial i have been following:

the tutorial uses a version of godot 3, and i have been using godot 4. I have been changing some of the code for it to work in godot 4.

I would really appreciate some help, thank you!

Try:

GlobalSignals.bullet_fired.connect(bullet_manager.handle_bullet_spawned)

I recommend you read the documentation about signals in 4.0: Using signals — Godot Engine (stable) documentation in English

1 Like

Thank you for your help!
:slight_smile:

This topic was automatically closed 30 days after the last reply. New replies are no longer allowed.