Instancing a Scene Multiple Times for Different Effects
Asked Answered
Z

8

0

Beginner GODOT. Learning the basics and messing around with the engine to learn. I'm trying something out and feel like maybe I'm going about it the wrong way. Here is essentially what I'm trying to do:

Player moves, triggers an enemy to fall and block their path. Then their health pops up above the enemy's head and three cards pop up over the player's head. Each with a random number generated on the card. You click the card and it subtracts the number on the card from the enemy health until it reaches 0 and then they disappear.

I have accomplished almost all of this. I was able to get the move, the trigger, the blocking. The health pops up. The issue is with the cards. I was able to make it so I can instance a single card, that generates a number to the label. And when you click the card, it subtracts the health, and they queue free.

But I cannot figure out how to make both cards work. I currently have it set up that the card has a signal that when clicked, it emits the signal. The main script connects to that signal. But when you create all three, then regardless of which one you click, they all emit the signal and all three cards subtract from the health instead of just the one clicked. I'm assuming there is a better method to all of this.

Zootoxin answered 7/12, 2023 at 21:33 Comment(0)
M
0

Zootoxin Can you show us how you instantiate the cards, connect to the signal and how you emit the signal after a click?

Meekins answered 7/12, 2023 at 21:45 Comment(0)
Z
0

Meekins

This is my code for instancing the cards.

`func create_new_cards():
new_card_1 = card.instantiate()
new_card_2 = card.instantiate()
new_card_3 = card.instantiate()

new_card_1.name = "Card 1"
new_card_1.global_position.x = player.global_position.x - 50
new_card_1.global_position.y = player.global_position.y - 200
new_card_2.name = "Card 2"
new_card_2.global_position.x = player.global_position.x
new_card_2.global_position.y = player.global_position.y - 200
new_card_3.name = "Card 3"
new_card_3.global_position.x = player.global_position.x + 50
new_card_3.global_position.y = player.global_position.y - 200

var card_label_1 = new_card_1.get_node("Number UI/Number")
card_label_1.text = str(card_number_1)
var card_label_2 = new_card_2.get_node("Number UI/Number")
card_label_2.text = str(card_number_2)
var card_label_3 = new_card_3.get_node("Number UI/Number")
card_label_3.text = str(card_number_3)	

new_card_1.connect("card_clicked", damage_enemy)
new_card_2.connect("card_clicked", damage_enemy)
new_card_3.connect("card_clicked", damage_enemy)	
add_child(new_card_1)
add_child(new_card_2)
add_child(new_card_3)`

And this is the code I put for the card scene:

extends RigidBody2D
signal card_clicked

@onready var sprite = $Sprite2D

func _ready():
set_process_input(true)

func set_card_number(value):
$"Number UI/Number".text = str(value)

func _on_area_2d_mouse_entered():
sprite.modulate = Color.BLUE

func _on_area_2d_mouse_exited():
sprite.modulate = Color.WHITE

func _input(event):
if event is InputEventMouseButton and event.is_pressed():
emit_signal("card_clicked")

Zootoxin answered 7/12, 2023 at 21:49 Comment(0)
M
0

Zootoxin Your problem is this:

func _input(event):
    if event is InputEventMouseButton and event.is_pressed():
        emit_signal("card_clicked")

Each card checks if a mouse button is pressed but it does not check which card is clicked. You need to check if the click was on the current card and only emit a signal for this card.

Meekins answered 7/12, 2023 at 21:56 Comment(0)
Z
0

Meekins

Do you know how to I would specify which card is clicked? I assume that would be in the coding for the specific cards opposed to the main script.

Zootoxin answered 7/12, 2023 at 22:6 Comment(0)
Z
0

And thank you!

Zootoxin answered 7/12, 2023 at 22:7 Comment(0)
W
0

You could simply make a callback function for every card, but it's rather stupid if you have too many cards or card types.
So a better solution is to make cardclick callback signal function take a few parameters such as card-id and card-type etc.

Wherry answered 8/12, 2023 at 6:12 Comment(0)
M
0

Zootoxin Have your "card_clicked" signal return the point value or any other information you need:

signal card_clicked(points: int)

@export var point_value: int

# ...

# some callback that gets notified when a card has been clicked
func _on_clicked():
    card_clicked.emit(point_value)
Meekins answered 8/12, 2023 at 10:8 Comment(0)
Z
0

Great. Thank you! I’ll research all this and see if I can figure it out.

Zootoxin answered 8/12, 2023 at 20:7 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.