From 043c46842a1f23472646757c70d900cc62dd71b2 Mon Sep 17 00:00:00 2001 From: myin Date: Sat, 11 Nov 2023 11:12:50 +0100 Subject: [PATCH] split projectile + hitbox, fixes for bullets --- godot/src/base-system/combat/HitBox.gd | 8 ++- godot/src/base-system/combat/Hurtbox.gd | 1 + .../src/base-system/spawner/AreaSpawner2D.gd | 2 +- .../src/base-system/spawner/DeathSpawner2D.gd | 4 +- godot/src/base-system/spawner/Spawner2D.gd | 4 +- godot/src/character/Trident.gd | 1 - godot/src/character/bomb_bullet.gd | 6 +- godot/src/character/bomb_bullet.tscn | 34 +++++++---- godot/src/character/bomb_enemy.tscn | 6 +- godot/src/character/enemy_bullet.gd | 5 +- godot/src/character/enemy_bullet.tscn | 36 ++++++++--- godot/src/character/projectile.gd | 61 ++++++++++--------- godot/src/character/trident.tscn | 44 +++++++++---- godot/src/game.gd | 9 +-- godot/src/game.tscn | 4 +- godot/src/props/bomb_bullet_death.tscn | 2 +- 16 files changed, 142 insertions(+), 85 deletions(-) diff --git a/godot/src/base-system/combat/HitBox.gd b/godot/src/base-system/combat/HitBox.gd index de8750e..e9e3635 100644 --- a/godot/src/base-system/combat/HitBox.gd +++ b/godot/src/base-system/combat/HitBox.gd @@ -1,6 +1,8 @@ class_name HitBox extends Area2D +signal hit() + @export var damage := 1 @export var damage_value: NumberValue @export var knockback_force := 0 @@ -14,4 +16,8 @@ func _ready(): func _do_damage(area: HurtBox): var dmg = damage_value.get_value() if damage_value else damage var knockback_dir = global_position.direction_to(area.global_position) - return area.damage(dmg, knockback_dir * knockback_force) + + var did_hit = area.damage(dmg, knockback_dir * knockback_force) + if did_hit: + hit.emit() + return did_hit diff --git a/godot/src/base-system/combat/Hurtbox.gd b/godot/src/base-system/combat/Hurtbox.gd index 74291af..4cac6b1 100644 --- a/godot/src/base-system/combat/Hurtbox.gd +++ b/godot/src/base-system/combat/Hurtbox.gd @@ -32,3 +32,4 @@ func damage(dmg: int, knockback_force: Vector2): frame_freeze.freeze() get_tree().create_timer(invincible_time).timeout.connect(func(): invincible = false) + return true diff --git a/godot/src/base-system/spawner/AreaSpawner2D.gd b/godot/src/base-system/spawner/AreaSpawner2D.gd index 1d6d4b9..2aee0a2 100644 --- a/godot/src/base-system/spawner/AreaSpawner2D.gd +++ b/godot/src/base-system/spawner/AreaSpawner2D.gd @@ -11,4 +11,4 @@ func spawn(): for i in count: var start = dir.rotated(-spread/2) var d = start.rotated(i * spread/count) - _create(d * center_offset) + _create(d * center_offset, Vector2.RIGHT.angle_to(d)) diff --git a/godot/src/base-system/spawner/DeathSpawner2D.gd b/godot/src/base-system/spawner/DeathSpawner2D.gd index 1dcbda7..0746b67 100644 --- a/godot/src/base-system/spawner/DeathSpawner2D.gd +++ b/godot/src/base-system/spawner/DeathSpawner2D.gd @@ -7,12 +7,12 @@ extends Node2D func _ready(): if health: - health.zero_health.connect(func(): _create()) + health.zero_health.connect(func(): spawn()) func _should_spawn(): return spawn_chance == null or randf() <= spawn_chance.get_value() -func _create(): +func spawn(): if not _should_spawn(): return diff --git a/godot/src/base-system/spawner/Spawner2D.gd b/godot/src/base-system/spawner/Spawner2D.gd index 9f564fe..0f376e0 100644 --- a/godot/src/base-system/spawner/Spawner2D.gd +++ b/godot/src/base-system/spawner/Spawner2D.gd @@ -12,9 +12,9 @@ func _ready(): func spawn(): return _create() -func _create(offset_dir = offset * Vector2.RIGHT.rotated(global_rotation)): +func _create(offset_dir = offset * Vector2.RIGHT.rotated(global_rotation), rot = global_rotation): var eff = scene.instantiate() eff.global_position = global_position + offset_dir - eff.global_rotation = global_rotation + eff.global_rotation = rot get_tree().current_scene.add_child(eff) return eff diff --git a/godot/src/character/Trident.gd b/godot/src/character/Trident.gd index ebf0c29..dc0680f 100644 --- a/godot/src/character/Trident.gd +++ b/godot/src/character/Trident.gd @@ -5,7 +5,6 @@ extends Projectile @onready var player_detect = $PlayerDetect var target: Node2D -var velocity := Vector2.ZERO var player: Node2D func _physics_process(delta): diff --git a/godot/src/character/bomb_bullet.gd b/godot/src/character/bomb_bullet.gd index 778c2cc..3ab9716 100644 --- a/godot/src/character/bomb_bullet.gd +++ b/godot/src/character/bomb_bullet.gd @@ -3,18 +3,14 @@ extends Projectile @export var speed: ValueProvider @onready var hurtbox = $Hurtbox -@onready var death_spawner_2d = $DeathSpawner2D -@onready var health = $Health func _ready(): ignored.append(hurtbox) super._ready() - - health.zero_health.connect(func(): queue_free()) func _physics_process(delta): translate(dir * speed.get_value() * delta) global_rotation = Vector2.RIGHT.angle_to(dir) func _on_hurtbox_knockback(dir): - death_spawner_2d.global_rotation = Vector2.RIGHT.angle_to(dir) + death_spawner.global_rotation = Vector2.RIGHT.angle_to(dir) diff --git a/godot/src/character/bomb_bullet.tscn b/godot/src/character/bomb_bullet.tscn index f169f6b..6b00093 100644 --- a/godot/src/character/bomb_bullet.tscn +++ b/godot/src/character/bomb_bullet.tscn @@ -1,4 +1,4 @@ -[gd_scene load_steps=16 format=3 uid="uid://bjoxmq8nco7tj"] +[gd_scene load_steps=18 format=3 uid="uid://bjoxmq8nco7tj"] [ext_resource type="Script" path="res://src/character/bomb_bullet.gd" id="1_w8slh"] [ext_resource type="Script" path="res://src/base-system/combat/DelayedDamage.gd" id="3_f7q0i"] @@ -7,6 +7,7 @@ [ext_resource type="Script" path="res://src/base-system/combat/health.gd" id="5_fqps8"] [ext_resource type="Script" path="res://src/base-system/spawner/DeathSpawner2D.gd" id="6_xn0k5"] [ext_resource type="PackedScene" uid="uid://demmj5vw7sf6i" path="res://src/props/bomb_bullet_death.tscn" id="7_2qm82"] +[ext_resource type="Script" path="res://src/base-system/combat/HitBox.gd" id="9_i6l0c"] [ext_resource type="Script" path="res://src/nodes/MirrorValue.gd" id="13_4j2ad"] [sub_resource type="CircleShape2D" id="CircleShape2D_58gh8"] @@ -51,21 +52,21 @@ animations = [{ [sub_resource type="CircleShape2D" id="CircleShape2D_uma4k"] radius = 9.0 -[node name="BombBullet" type="Area2D" node_paths=PackedStringArray("speed", "collision_shape", "hurt_collision", "raycast")] +[sub_resource type="CircleShape2D" id="CircleShape2D_rbo4n"] +radius = 8.0 + +[node name="BombBullet" type="Area2D" node_paths=PackedStringArray("speed", "collision_shape", "hurt_collision", "raycast", "death_spawner", "hit_box", "health")] collision_layer = 0 -collision_mask = 56 +collision_mask = 32 script = ExtResource("1_w8slh") speed = NodePath("SpeedValue") max_reflections = 2 collision_shape = NodePath("CollisionShape2D") hurt_collision = NodePath("Hurtbox/CollisionShape2D") raycast = NodePath("RayCast2D") -damage = 2 -knockback_force = 200 - -[node name="DamageValue" type="Node" parent="."] -script = ExtResource("13_4j2ad") -mirror_value = 4.0 +death_spawner = NodePath("DeathSpawner2D") +hit_box = NodePath("HitBox") +health = NodePath("Health") [node name="SpeedValue" type="Node" parent="."] script = ExtResource("13_4j2ad") @@ -90,9 +91,8 @@ frame_progress = 0.485157 [node name="Health" type="Node" parent="."] script = ExtResource("5_fqps8") -[node name="DeathSpawner2D" type="Node2D" parent="." node_paths=PackedStringArray("health")] +[node name="DeathSpawner2D" type="Node2D" parent="."] script = ExtResource("6_xn0k5") -health = NodePath("../Health") scene = ExtResource("7_2qm82") [node name="Hurtbox" type="Area2D" parent="." node_paths=PackedStringArray("health")] @@ -111,4 +111,16 @@ collision_mask = 32 collide_with_areas = true collide_with_bodies = false +[node name="HitBox" type="Area2D" parent="." node_paths=PackedStringArray("damage_value")] +script = ExtResource("9_i6l0c") +damage_value = NodePath("DamageValue") +knockback_force = 200 + +[node name="DamageValue" type="Node" parent="HitBox"] +script = ExtResource("13_4j2ad") +mirror_value = 4.0 + +[node name="CollisionShape2D" type="CollisionShape2D" parent="HitBox"] +shape = SubResource("CircleShape2D_rbo4n") + [connection signal="knockback" from="Hurtbox" to="." method="_on_hurtbox_knockback"] diff --git a/godot/src/character/bomb_enemy.tscn b/godot/src/character/bomb_enemy.tscn index 9f0c9f6..21d2fea 100644 --- a/godot/src/character/bomb_enemy.tscn +++ b/godot/src/character/bomb_enemy.tscn @@ -1,8 +1,9 @@ -[gd_scene load_steps=4 format=3 uid="uid://c0mbhp0aqksh1"] +[gd_scene load_steps=5 format=3 uid="uid://c0mbhp0aqksh1"] [ext_resource type="PackedScene" uid="uid://mt5fy2ohtmg5" path="res://src/character/enemy.tscn" id="1_v1rsa"] [ext_resource type="Texture2D" uid="uid://b2qgqsafbeyaq" path="res://assets/Enemy__Jellyfish_Normal.png" id="2_euxkn"] [ext_resource type="Texture2D" uid="uid://dy31gsft2yhng" path="res://assets/Enemy__Jellyfish_Mirror.png" id="3_leutj"] +[ext_resource type="PackedScene" uid="uid://bjoxmq8nco7tj" path="res://src/character/bomb_bullet.tscn" id="4_o3ox8"] [node name="BombEnemy" instance=ExtResource("1_v1rsa")] value = 3 @@ -24,3 +25,6 @@ value = 2.0 [node name="MirrorValue" parent="FireRateTimer" index="0"] mirror_value = 3.5 value = 5.0 + +[node name="BulletSpawner" parent="." index="14"] +scene = ExtResource("4_o3ox8") diff --git a/godot/src/character/enemy_bullet.gd b/godot/src/character/enemy_bullet.gd index 17d3eca..a98006a 100644 --- a/godot/src/character/enemy_bullet.gd +++ b/godot/src/character/enemy_bullet.gd @@ -1,14 +1,13 @@ extends Projectile @export var speed: ValueProvider + @onready var hurtbox = $Hurtbox -@onready var health = $Health +@onready var death_spawner_2d = $DeathSpawner2D func _ready(): ignored.append(hurtbox) super._ready() - - health.zero_health.connect(func(): queue_free()) func _physics_process(delta): translate(dir * speed.get_value() * delta) diff --git a/godot/src/character/enemy_bullet.tscn b/godot/src/character/enemy_bullet.tscn index 633f068..02687a3 100644 --- a/godot/src/character/enemy_bullet.tscn +++ b/godot/src/character/enemy_bullet.tscn @@ -1,4 +1,4 @@ -[gd_scene load_steps=10 format=3 uid="uid://ddfl18bx24sfj"] +[gd_scene load_steps=12 format=3 uid="uid://ddfl18bx24sfj"] [ext_resource type="Script" path="res://src/character/enemy_bullet.gd" id="1_m5cyv"] [ext_resource type="Texture2D" uid="uid://d8ap1t3wascc" path="res://assets/Bubble.png" id="2_lmg1q"] @@ -7,6 +7,7 @@ [ext_resource type="Script" path="res://src/base-system/spawner/DeathSpawner2D.gd" id="3_y2eun"] [ext_resource type="PackedScene" uid="uid://cnk6fkkr62eva" path="res://src/props/enemy_bullet_death.tscn" id="5_jy5q3"] [ext_resource type="Script" path="res://src/nodes/MirrorValue.gd" id="7_jof7a"] +[ext_resource type="Script" path="res://src/base-system/combat/HitBox.gd" id="8_w36so"] [sub_resource type="CircleShape2D" id="CircleShape2D_5521j"] radius = 6.0 @@ -14,20 +15,21 @@ radius = 6.0 [sub_resource type="CircleShape2D" id="CircleShape2D_k5472"] radius = 4.12311 -[node name="EnemyBullet" type="Area2D" node_paths=PackedStringArray("speed", "collision_shape", "hurt_collision", "raycast")] +[sub_resource type="CircleShape2D" id="CircleShape2D_mqd7s"] +radius = 5.0 + +[node name="EnemyBullet" type="Area2D" node_paths=PackedStringArray("speed", "collision_shape", "hurt_collision", "raycast", "death_spawner", "hit_box", "health")] collision_layer = 0 -collision_mask = 56 +collision_mask = 32 script = ExtResource("1_m5cyv") speed = NodePath("SpeedValue") max_reflections = 2 collision_shape = NodePath("CollisionShape2D") hurt_collision = NodePath("Hurtbox/CollisionShape2D") raycast = NodePath("RayCast2D") -knockback_force = 100 - -[node name="DamageValue" type="Node" parent="."] -script = ExtResource("7_jof7a") -mirror_value = 2.0 +death_spawner = NodePath("DeathSpawner2D") +hit_box = NodePath("HitBox") +health = NodePath("Health") [node name="SpeedValue" type="Node" parent="."] script = ExtResource("7_jof7a") @@ -37,9 +39,8 @@ value = 80.0 [node name="Health" type="Node" parent="."] script = ExtResource("2_ppbv3") -[node name="DeathSpawner2D" type="Marker2D" parent="." node_paths=PackedStringArray("health")] +[node name="DeathSpawner2D" type="Marker2D" parent="."] script = ExtResource("3_y2eun") -health = NodePath("../Health") scene = ExtResource("5_jy5q3") [node name="Sprite2D" type="Sprite2D" parent="."] @@ -65,3 +66,18 @@ target_position = Vector2(20, 0) collision_mask = 32 collide_with_areas = true collide_with_bodies = false + +[node name="HitBox" type="Area2D" parent="." node_paths=PackedStringArray("damage_value")] +collision_layer = 0 +collision_mask = 24 +script = ExtResource("8_w36so") +damage_value = NodePath("DamageValue") +knockback_force = 100 + +[node name="DamageValue" type="Node" parent="HitBox"] +script = ExtResource("7_jof7a") +mirror_value = 2.0 +value = 1.0 + +[node name="CollisionShape2D" type="CollisionShape2D" parent="HitBox"] +shape = SubResource("CircleShape2D_mqd7s") diff --git a/godot/src/character/projectile.gd b/godot/src/character/projectile.gd index 9d38cdd..6a68852 100644 --- a/godot/src/character/projectile.gd +++ b/godot/src/character/projectile.gd @@ -1,5 +1,5 @@ class_name Projectile -extends HitBox +extends Area2D signal reflect(dir) @@ -11,48 +11,51 @@ signal reflect(dir) @export var hurt_collision: CollisionShape2D @export var raycast: RayCast2D -const MIRROR_LAYER = 1 << 5 +@export var death_spawner: DeathSpawner2D +@export var hit_box: HitBox +@export var health: Health var reflected := 0 var ignored = [] func _ready(): - if disable_initial_hit: - _temp_disable_collision() +# if disable_initial_hit: +# _temp_disable_collision() + + if hit_box: + hit_box.hit.connect(_remove) + if health: + health.zero_health.connect(_remove) dir = dir.rotated(global_rotation) area_entered.connect(func(area): if area in ignored: return - if area is Mirror: - if reflected > max_reflections and max_reflections >= 0: - _remove() - else: - if raycast and raycast.is_colliding(): - set_physics_process(false) - hide() - var effect_pos = await area.create_mirror_effect(raycast.get_collision_point(), dir) - global_position = effect_pos - set_physics_process(true) - show() - - dir = dir.bounce(area.get_normal()) - global_rotation = Vector2.RIGHT.angle_to(dir) - reflected += 1 - reflect.emit(dir) - elif area is HurtBox: - if _do_damage(area): - _remove() - else: + if reflected > max_reflections and max_reflections >= 0: _remove() + else: + if raycast and raycast.is_colliding(): + set_physics_process(false) + hide() + var effect_pos = await area.create_mirror_effect(raycast.get_collision_point(), dir) + global_position = effect_pos + set_physics_process(true) + show() + + dir = dir.bounce(area.get_normal()) + global_rotation = Vector2.RIGHT.angle_to(dir) + reflected += 1 + reflect.emit(dir) ) -func _temp_disable_collision(): - _disable_hit() - get_tree().create_timer(0.1).timeout.connect(func(): collision_shape.disabled = false) # prevent player from hitting himself +#func _temp_disable_collision(): +# _disable_hit() +# get_tree().create_timer(0.1).timeout.connect(func(): collision_shape.disabled = false) # prevent player from hitting himself -func _disable_hit(): - collision_shape.set_deferred("disabled", true) +#func _disable_hit(): +# collision_shape.set_deferred("disabled", true) func _remove(): + if death_spawner: + death_spawner.spawn() queue_free() diff --git a/godot/src/character/trident.tscn b/godot/src/character/trident.tscn index 8b94b74..c28e584 100644 --- a/godot/src/character/trident.tscn +++ b/godot/src/character/trident.tscn @@ -1,4 +1,4 @@ -[gd_scene load_steps=10 format=3 uid="uid://chfrm1aqrag7x"] +[gd_scene load_steps=12 format=3 uid="uid://chfrm1aqrag7x"] [ext_resource type="Script" path="res://src/character/Trident.gd" id="1_uombx"] [ext_resource type="Texture2D" uid="uid://co2wlkxnutets" path="res://assets/Trident_Normal.png" id="2_d65tq"] @@ -7,6 +7,7 @@ [ext_resource type="Script" path="res://src/character/MirrorSprite2D.gd" id="4_od2uf"] [ext_resource type="Script" path="res://src/base-system/FreeOnEnterArea2D.gd" id="5_ibpd5"] [ext_resource type="Script" path="res://src/nodes/MirrorValue.gd" id="7_jaq63"] +[ext_resource type="Script" path="res://src/base-system/combat/HitBox.gd" id="8_atedw"] [sub_resource type="RectangleShape2D" id="RectangleShape2D_str41"] size = Vector2(4, 24) @@ -14,28 +15,24 @@ size = Vector2(4, 24) [sub_resource type="CircleShape2D" id="CircleShape2D_bddqt"] radius = 6.08276 -[node name="Trident" type="Area2D" node_paths=PackedStringArray("speed", "collision_shape", "raycast", "damage_value")] +[sub_resource type="RectangleShape2D" id="RectangleShape2D_c0uui"] +size = Vector2(8, 12) + +[node name="Trident" type="Area2D" node_paths=PackedStringArray("speed", "collision_shape", "raycast", "hit_box")] collision_layer = 0 -collision_mask = 112 +collision_mask = 32 script = ExtResource("1_uombx") speed = NodePath("SpeedValue") disable_initial_hit = false collision_shape = NodePath("CollisionShape2D") raycast = NodePath("RayCast2D") -damage = 4 -damage_value = NodePath("DmgValue") -knockback_force = 120 +hit_box = NodePath("HitBox") [node name="SpeedValue" type="Node" parent="."] script = ExtResource("7_jaq63") mirror_value = 350.0 value = 250.0 -[node name="DmgValue" type="Node" parent="."] -script = ExtResource("7_jaq63") -mirror_value = 7.0 -value = 4.0 - [node name="Sprite2D" type="Sprite2D" parent="."] rotation = 1.5708 texture = ExtResource("2_d65tq") @@ -69,3 +66,28 @@ stream = ExtResource("4_f6rth") volume_db = -10.0 pitch_scale = 0.7 autoplay = true + +[node name="HitBox" type="Area2D" parent="." node_paths=PackedStringArray("damage_value")] +position = Vector2(9, 0) +collision_layer = 0 +collision_mask = 16 +script = ExtResource("8_atedw") +damage_value = NodePath("DmgValue") +knockback_force = 120 + +[node name="DmgValue" type="Node" parent="HitBox"] +script = ExtResource("7_jaq63") +mirror_value = 7.0 +value = 4.0 + +[node name="CollisionShape2D" type="CollisionShape2D" parent="HitBox"] +shape = SubResource("RectangleShape2D_c0uui") + +[node name="BubbleHit" type="Area2D" parent="."] +position = Vector2(9, 0) +collision_layer = 0 +collision_mask = 64 +script = ExtResource("8_atedw") + +[node name="CollisionShape2D" type="CollisionShape2D" parent="BubbleHit"] +shape = SubResource("RectangleShape2D_c0uui") diff --git a/godot/src/game.gd b/godot/src/game.gd index 507c75a..18c1308 100644 --- a/godot/src/game.gd +++ b/godot/src/game.gd @@ -6,12 +6,13 @@ const ROOM = preload("res://src/props/room.tscn") @onready var player = $Player @onready var music_player = $MusicPlayer -const value_increase := 1.5 -const kill_increase := 1.8 +@export var enemy_value := 5.0 +@export var enemy_kills := 5.0 + +@export var value_increase := 1.5 +@export var kill_increase := 1.8 var previous_dir := Vector2.ZERO -var enemy_value := 5.0 -var enemy_kills := 5.0 var room_dirs := [Vector2.UP, Vector2.LEFT, Vector2.RIGHT, Vector2.DOWN] var _logger = Logger.new("Game") diff --git a/godot/src/game.tscn b/godot/src/game.tscn index bb94832..e0c135d 100644 --- a/godot/src/game.tscn +++ b/godot/src/game.tscn @@ -1,10 +1,9 @@ -[gd_scene load_steps=10 format=3 uid="uid://di8g8e6s34cik"] +[gd_scene load_steps=9 format=3 uid="uid://di8g8e6s34cik"] [ext_resource type="Script" path="res://src/game.gd" id="1_fscq0"] [ext_resource type="AudioStream" uid="uid://cj3tphknhrawu" path="res://assets/sound/Sparkle.mp3" id="4_rug7x"] [ext_resource type="AudioStream" uid="uid://bygqjhqr85tjf" path="res://assets/sound/危機.mp3" id="5_3pgwk"] [ext_resource type="PackedScene" uid="uid://dlby6flxkmnjs" path="res://src/character/player.tscn" id="6_2xq02"] -[ext_resource type="PackedScene" uid="uid://chfrm1aqrag7x" path="res://src/character/trident.tscn" id="8_r0538"] [sub_resource type="Animation" id="Animation_880qs"] length = 0.001 @@ -152,7 +151,6 @@ position_smoothing_enabled = true [node name="Player" parent="." instance=ExtResource("6_2xq02")] z_index = 10 -projectile_scene = ExtResource("8_r0538") [node name="BGM" type="AudioStreamPlayer" parent="."] process_mode = 3 diff --git a/godot/src/props/bomb_bullet_death.tscn b/godot/src/props/bomb_bullet_death.tscn index 99f410c..8747e8d 100644 --- a/godot/src/props/bomb_bullet_death.tscn +++ b/godot/src/props/bomb_bullet_death.tscn @@ -58,6 +58,6 @@ autoplay = true [node name="AreaSpawner2D" type="Node2D" parent="."] script = ExtResource("4_t027f") -spread = 180 +center_offset = 20 autostart = true scene = ExtResource("5_4mf5t")