如何在Godot的3D平台中提高分数



下面是;你的第一个3D游戏";Godot文档教程。我正在做一些小改动来制作我自己的游戏(Crash Bandicoot重制版(。我目前在";记分和重放";章

主要区别在于我的障碍物已经在场景中,而教程中的障碍物是随机生成的

这是附在我关卡场景中的脚本:

extends Node
export (PackedScene) var obstacle_scene

func _start():
var obstacle = obstacle_scene.instance()
obstacle.connect("squashed", $UserInterface/ScoreLabel, "_on_Obstacle_squashed")

请注意,在编辑器中,我的obstacle_scene已连接到我的Obstruct.tscn.

这是UserInterface/ScoreLabel:附带的代码

extends Label
var score = 0
func _on_Obstacle_squashed():
score += 1
text = "Score: %s" % score

预期结果:每次跳到场景中已经存在的立方体上时,我都想提高分数与教程不同,我不是随机生成障碍物(或者教程中称之为"暴徒"(。

实际结果:我可以成功地运行游戏,没有错误,但跳过障碍物不会改变分数。

我希望我提供了足够的信息,但如果有必要,我很乐意分享更多的代码。

是否调用过squashed信号?

否则,将永远不会调用_on_Obstacle_Squashed()函数。

我相信函数_start根本没有运行,因为你没有共享任何调用它的代码,我在链接的教程中找不到它……你可能想使用_ready


还有另一个问题:_start中的代码实例化场景(创建一个新实例(并连接它。但这个新实例从未添加到场景中。

需要明确的是,一个场景可以有多个实例。例如,一些可以添加到编辑器中,另一些可以从代码中创建。这些实例中的每一个都可以发出信号。如果你想使用这些信号,你需要将它们连接起来。

如果您已经从编辑器中添加了实例,那么也可以从编辑器中连接它们的信号。转到信号选项卡上的节点面板,双击您想要的信号,Godot将显示一个窗口,您可以在其中指定将信号连接到的位置。


也可以通过代码连接编辑器上创建的实例的信号……然而,我重申,这不是你正在做的。您正在通过调用instance方法创建一个新实例。这个新实例不同于从编辑器中添加的任何实例。相反,您将从场景树中获得实例,例如使用get_node$语法。

例如:

func _ready() -> void:
$obstacle.connect("squashed", $UserInterface/ScoreLabel, "_on_Obstacle_squashed")

对于每一个例子,你都必须这样做:

func _ready() -> void:
$obstacle.connect("squashed", $UserInterface/ScoreLabel, "_on_Obstacle_squashed")
$obstacle2.connect("squashed", $UserInterface/ScoreLabel, "_on_Obstacle_squashed")
$obstacle3.connect("squashed", $UserInterface/ScoreLabel, "_on_Obstacle_squashed")
# …

另一方面,如果您从代码中创建实例,则无法从编辑器中连接它们,您唯一的选择是用代码连接它们。正如教程所做的。因此,我们可以在教程中举一个例子:

var mob = mob_scene.instance()
# …
add_child(mob)
mob.connect("squashed", $UserInterface/ScoreLabel, "_on_Mob_squashed")

正如您所看到的,它使用instance方法创建了一个新实例。然后使用add_child方法将其作为运行此脚本的节点的子节点添加到场景树中。最后它连接信号。


无论如何,我想把你推向另一个方向:你可以创建一个信号总线(事件总线(。这是Godot项目中的常见模式。

我们的见解是,一个物体可以让另一个物体发出它们的信号。

您所做的是创建一个新的脚本,扩展Node,并使用您想要的信号。例如:

extends Node
signal squashed

而不是自动加载。要执行此操作,请在"自动加载"选项卡上投影设置,然后选择脚本并为其命名。我称之为SignalBus

现在,在您的代码中,您可以发出该信号,例如:

func squash():
SignalBus.emit_signal("squashed")
queue_free()

你可以连接并处理这个信号:

func _ready() -> void:
SignalBus.connect("squashed", self, "_on_squashed")

func _on_squashed() -> void:
prints("Something")

或者,在您的情况下:

func _ready() -> void:
SignalBus.connect("squashed", $UserInterface/ScoreLabel, "_on_Obstacle_squashed")

这里的技巧是,立方体没有"squashed"信号,SignalBus有信号,立方体告诉SignalBus发射信号。所以你不必连接场景的实例(同样,没有信号(,但你只需要连接SignalBus,因为它实际上是在发射信号。

相关内容

  • 没有找到相关文章

最新更新