单击场景->新场景, 我们将创建生物。
Mob场景将使用以下节点:
- RigidBody2D(命名为Mob)
- 动画精灵
- CollisionShape2D
- VisibilityNotifier2D(命名为Visibility)
就像我们在Player场景中一样, 不要忘记设置子项以使它们无法被选中。
在RigidBody2D属性中, 将”重力比例”设置为0, 这样生物就不会下降。此外, 在PhysicsBody2D部分下, 单击Mask属性, 然后取消选中第一个框。这样可以确保小怪不会互相碰撞。
像我们为播放器所做的那样设置AnimatedSprite。这次, 我们有三个动画:飞行, 游泳和行走。将检查器中的”播放”属性设置为”开”, 然后调整”速度(FPS)”设置, 如下所示。我们将随机选择这些动画之一, 以使小怪有一些变化。
飞:
游泳:
步行:
飞行设置为3 FPS, 游泳和步行设置为4 FPS。
像玩家图像一样, 这些暴民图像需要按比例缩小。设置AnimatedSprite的Scale属性(0.75、0.75)。
与在Player场景中一样, 为碰撞添加CapsuleShape2D。为了使形状与图像对齐, 我们需要在Node2D下将Rotation Degrees属性设置为90。
敌人剧本
将脚本添加到Mob并添加以下成员变量:
GDScript
extends RigidBody2D
export (int) var min_speed # Minimum speed range.
export (int) var max_speed # Maximum speed range.
var mob_types = ["walk", "swim", "fly"]
我们必须在min_speed和max_speed之间选择一个随机值, 以了解每个生物的移动速度(如果它们都以相同的速度运行, 那将很无聊)。在检查器中将它们设置为150和250。我们还有一个数组, 其中包含三个动画的名称, 我们将使用它们选择一个随机的动画。
现在让我们看一下脚本的其余部分。在_ready()中, 我们随机选择以下三种动画类型之一:
GDScript
func _ready():
$AnimatedSprite.animation = mob_types[randi() % mob_types.size()]
注意如果希望每次运行场景时”随机”数字的序列不同, 则必须使用randomize()。我们将在Main场景中使用randomize(), 以便在这里不再需要它。 randi()%n是获取介于0和n-1之间的随机整数的标准方法。
最后一步是让暴民在离开屏幕时将自己删除。连接可见性节点的screen_excited()信号, 添加以下代码:
GDScript
func _on_Visibility_screen_exited():
queue_free()
它完成了暴民场景。
主要场景
现在是时候将它们整合在一起了。创建一个新场景并添加一个名为Main的节点。单击”保险”按钮, 然后选择我们保存的Player.tscn。
注意请参阅实例化以了解有关实例化的更多信息。
现在将以下节点添加为Main的子节点, 并按如下所示对其进行命名(值以秒为单位):
- 计时器(名为MobTimer)-用于控制生物产生的频率。
- 计时器(名为ScoreTimer)-用于每秒增加分数。
- 计时器(名为StartTimer)-在启动之前给予延迟。
- Position2D(名称为StartPosition)-用于指示玩家的起始位置。
如下设置每个Timer节点的Wait Time属性:
- 移动计时器:0.5
- 积分时间:1
- 启动计时器:2
另外, 将StartTimer的One-Shot属性设置为(240, 450), 并将StartPosition节点的” On”设置为” On”。
产卵小怪
主要节点将产生新的生物, 我们希望它们出现在屏幕边缘的随机位置。将名为MobPath的Path2D节点添加为Main的子级。选择Path2D时, 我们将在编辑器顶部看到一些新按钮:
选择中间的一个(“添加点”), 然后通过单击以在所示的角点处添加点来绘制路径。要使点与网格对齐, 请确保已选中”与网格对齐”。该选项可以在”锁定”按钮左侧的”捕捉选项”按钮下找到,
显示为一系列三个垂直点。确保还启用了”使用快照”按钮, 该按钮位于”快照选项”的左侧。
重要
按顺时针方向绘制路径, 在我们的生物上会朝外而不是向内指向!
将点4放置在图像中后, 单击”关闭曲线”按钮, 我们的曲线将完成。
现在已经定义了路径, 添加一个pathFollow2D节点作为MobPath的子节点, 并将其命名为MobSpawnLocation。该节点将自动旋转并跟随其移动的路径, 因此我们可以使用它来选择沿路线的随机位置和方向。
主脚本
将脚本添加到Main。在脚本的顶部, 我们使用export(PackedScene)来选择我们要实例化的Mob场景。
extends Node
export (PackedScene) var Mob
var score
func _ready():
randomize()
从”文件系统”面板中将Mob.tscn拖放到Main节点的脚本变量下的Mob属性中。
接下来, 单击播放器并连接点击信号。我们要创建一个名为game_over的新函数, 该函数将处理名为game_over的新函数, 该函数将处理游戏结束时需要发生的情况。
在”连接信号”窗口底部的”方法在节点中”框中键入” game_over”。添加以下代码以及new_game函数以设置新游戏的所有内容:
func game_over():
$ScoreTimer.stop()
$MobTimer.stop()
func new_game():
score = 0
$Player.start($StartPosition.position)
$StartTimer.start()
在_on_MobTimer_timeout()中, 我们将创建一个暴民实例, 沿着Path2D选择一个随机的起始位置, 并让暴民运动。 PathFollow2D节点沿路径移动时将自动旋转, 因此我们将使用它来选择生物的方向及其位置。
请注意, 必须使用add_child()将新实例添加到场景中。
GDScript
func _on_MobTimer_timeout():
# Choose a random location on Path2D.
$MobPath/MobSpawnLocation.set_offset(randi())
# Create a Mob instance and add it to the scene.
var mob = Mob.instance()
add_child(mob)
# Set the mob's direction perpendicular to the path direction.
var direction = $MobPath/MobSpawnLocation.rotation + PI / 2
# Set the mob's position to a random location.
mob.position = $MobPath/MobSpawnLocation.position
# Add some randomness to the direction.
direction += rand_range(-PI / 4, PI / 4)
mob.rotation = direction
# Choose the velocity.
mob.set_linear_velocity(Vector2(rand_range(mob.min_speed, mob.max_speed), 0).rotated(direction))
重要
GDScript使用弧度而不是度。如果我们对使用度数感到更自在, 则需要使用deg2rad()和rad2deg()函数在两者之间进行转换
评论前必须登录!
注册