diff --git a/assets/Audio/Enemy SFX/metal-click-SBA-300020615.mp3 b/assets/Audio/Enemy SFX/metal-click-SBA-300020615.mp3 new file mode 100644 index 0000000..8f853c8 Binary files /dev/null and b/assets/Audio/Enemy SFX/metal-click-SBA-300020615.mp3 differ diff --git a/assets/Audio/Enemy SFX/metal-click-SBA-300020615.mp3.import b/assets/Audio/Enemy SFX/metal-click-SBA-300020615.mp3.import new file mode 100644 index 0000000..7007e16 --- /dev/null +++ b/assets/Audio/Enemy SFX/metal-click-SBA-300020615.mp3.import @@ -0,0 +1,19 @@ +[remap] + +importer="mp3" +type="AudioStreamMP3" +uid="uid://bex03362rghym" +path="res://.godot/imported/metal-click-SBA-300020615.mp3-7eb2db5acaa426a587347c1ea39ec36a.mp3str" + +[deps] + +source_file="res://assets/Audio/Enemy SFX/metal-click-SBA-300020615.mp3" +dest_files=["res://.godot/imported/metal-click-SBA-300020615.mp3-7eb2db5acaa426a587347c1ea39ec36a.mp3str"] + +[params] + +loop=false +loop_offset=0 +bpm=0 +beat_count=0 +bar_beats=4 diff --git a/assets/Audio/Enemy SFX/servo-motor-SBA-300109173.mp3 b/assets/Audio/Enemy SFX/servo-motor-SBA-300109173.mp3 new file mode 100644 index 0000000..276a9c8 Binary files /dev/null and b/assets/Audio/Enemy SFX/servo-motor-SBA-300109173.mp3 differ diff --git a/assets/Audio/Enemy SFX/servo-motor-SBA-300109173.mp3.import b/assets/Audio/Enemy SFX/servo-motor-SBA-300109173.mp3.import new file mode 100644 index 0000000..a9bb2ec --- /dev/null +++ b/assets/Audio/Enemy SFX/servo-motor-SBA-300109173.mp3.import @@ -0,0 +1,19 @@ +[remap] + +importer="mp3" +type="AudioStreamMP3" +uid="uid://d0n46ursprjjs" +path="res://.godot/imported/servo-motor-SBA-300109173.mp3-1ba0a3432b1f206fca66c5964a15347b.mp3str" + +[deps] + +source_file="res://assets/Audio/Enemy SFX/servo-motor-SBA-300109173.mp3" +dest_files=["res://.godot/imported/servo-motor-SBA-300109173.mp3-1ba0a3432b1f206fca66c5964a15347b.mp3str"] + +[params] + +loop=false +loop_offset=0 +bpm=0 +beat_count=0 +bar_beats=4 diff --git a/assets/Audio/Enemy SFX/sliding-metal-noise-SBA-300054992.mp3 b/assets/Audio/Enemy SFX/sliding-metal-noise-SBA-300054992.mp3 new file mode 100644 index 0000000..7f74bce Binary files /dev/null and b/assets/Audio/Enemy SFX/sliding-metal-noise-SBA-300054992.mp3 differ diff --git a/assets/Audio/Enemy SFX/sliding-metal-noise-SBA-300054992.mp3.import b/assets/Audio/Enemy SFX/sliding-metal-noise-SBA-300054992.mp3.import new file mode 100644 index 0000000..c0cdbe3 --- /dev/null +++ b/assets/Audio/Enemy SFX/sliding-metal-noise-SBA-300054992.mp3.import @@ -0,0 +1,19 @@ +[remap] + +importer="mp3" +type="AudioStreamMP3" +uid="uid://doenadrocnym" +path="res://.godot/imported/sliding-metal-noise-SBA-300054992.mp3-08c3aa04bd0f29a16cb71c90c7c125bb.mp3str" + +[deps] + +source_file="res://assets/Audio/Enemy SFX/sliding-metal-noise-SBA-300054992.mp3" +dest_files=["res://.godot/imported/sliding-metal-noise-SBA-300054992.mp3-08c3aa04bd0f29a16cb71c90c7c125bb.mp3str"] + +[params] + +loop=false +loop_offset=0 +bpm=0 +beat_count=0 +bar_beats=4 diff --git a/assets/spider2.tscn b/assets/spider2.tscn index d06be23..6b71b8e 100644 --- a/assets/spider2.tscn +++ b/assets/spider2.tscn @@ -1,4 +1,4 @@ -[gd_scene load_steps=78 format=4 uid="uid://djr7vnr1hcx82"] +[gd_scene load_steps=87 format=4 uid="uid://djr7vnr1hcx82"] [ext_resource type="Script" uid="uid://cdofgtwevbray" path="res://scripts/spider.gd" id="1_7e7fe"] [ext_resource type="PackedScene" uid="uid://h5ojldugfyyu" path="res://assets/bullet_enemy.tscn" id="2_aew5r"] @@ -14,14 +14,20 @@ [ext_resource type="Script" uid="uid://bgxdpmc0ra6ic" path="res://scripts/enemy_die.gd" id="9_6mvds"] [ext_resource type="Texture2D" uid="uid://chiol2whyb84t" path="res://assets/Models/SubstancePainterTest/spider-LOW_spider1.gunbarrel_Metallic.png" id="9_cwyr0"] [ext_resource type="PackedScene" uid="uid://41iv1ualpttf" path="res://assets/damage_number.tscn" id="9_rmegy"] -[ext_resource type="AudioStream" uid="uid://0n251thxlnnp" path="res://assets/Audio/cannon-fire-single-shot-blast-explosion-SBA-300098885.wav" id="10_2qmhc"] [ext_resource type="Script" uid="uid://cr3wdhodxqf3f" path="res://scripts/EnemyAttack.gd" id="10_gicen"] [ext_resource type="Texture2D" uid="uid://c7bdujukdjajv" path="res://assets/Models/SubstancePainterTest/spider-LOW_spider1.gunbarrel_Normal.png" id="10_wpql0"] [ext_resource type="Texture2D" uid="uid://d0w0lon4smlhm" path="res://assets/Models/SubstancePainterTest/spider-LOW_spider1.gunbarrel_Roughness.png" id="11_6mvds"] +[ext_resource type="Script" uid="uid://dcnmjisrxf5iv" path="res://scripts/EnemyReload.gd" id="11_ekglj"] [ext_resource type="Material" uid="uid://cc0el8wu0au85" path="res://assets/materials/OutlineMat.tres" id="13_ee4im"] [ext_resource type="Texture2D" uid="uid://dn3b6uw8xr63m" path="res://assets/Textures/Smoke/smoketest_v1_0043.png" id="14_alcfd"] [ext_resource type="Material" uid="uid://844q0haim4uh" path="res://assets/spider2_body.tres" id="14_gicen"] [ext_resource type="PackedScene" uid="uid://2mct75k6xcia" path="res://assets/stunned_stars.tscn" id="18_ippdt"] +[ext_resource type="AudioStream" uid="uid://fa2k0hkmt0nq" path="res://assets/Audio/Weapons/7Mag Bolt Action Rifle/Gunshots/7Mag Bolt Action Rifle - Gunshot A 001.wav" id="23_fborx"] +[ext_resource type="AudioStream" uid="uid://bex03362rghym" path="res://assets/Audio/Enemy SFX/metal-click-SBA-300020615.mp3" id="24_ekglj"] +[ext_resource type="AudioStream" uid="uid://03y840g5f326" path="res://assets/Audio/Weapons/7Mag Bolt Action Rifle/Gunshots/7Mag Bolt Action Rifle - Gunshot A 002.wav" id="24_nhal8"] +[ext_resource type="AudioStream" uid="uid://bsfhh126bteon" path="res://assets/Audio/Weapons/7Mag Bolt Action Rifle/Gunshots/7Mag Bolt Action Rifle - Gunshot A 003.wav" id="25_aasxo"] +[ext_resource type="AudioStream" uid="uid://d0n46ursprjjs" path="res://assets/Audio/Enemy SFX/servo-motor-SBA-300109173.mp3" id="25_lr3lm"] +[ext_resource type="AudioStream" uid="uid://br3tyu6cmgyy2" path="res://assets/Audio/Weapons/7Mag Bolt Action Rifle/Gunshots/7Mag Bolt Action Rifle - Gunshot A 004.wav" id="26_1b3cb"] [sub_resource type="ViewportTexture" id="ViewportTexture_87l3v"] viewport_path = NodePath("SubViewport") @@ -796,9 +802,29 @@ size = Vector3(0.816284, 0.725159, 0.75531) height = 0.356583 radius = 0.207031 +[sub_resource type="AudioStreamRandomizer" id="AudioStreamRandomizer_ycipa"] +random_pitch = 1.1 +streams_count = 4 +stream_0/stream = ExtResource("23_fborx") +stream_1/stream = ExtResource("24_nhal8") +stream_2/stream = ExtResource("25_aasxo") +stream_3/stream = ExtResource("26_1b3cb") + +[sub_resource type="AudioStreamRandomizer" id="AudioStreamRandomizer_ekglj"] +random_pitch = 1.1 +random_volume_offset_db = 0.3 +streams_count = 1 +stream_0/stream = ExtResource("24_ekglj") + +[sub_resource type="AudioStreamRandomizer" id="AudioStreamRandomizer_4ecf4"] +random_pitch = 1.1 +streams_count = 1 +stream_0/stream = ExtResource("25_lr3lm") + [node name="spider" type="CharacterBody3D" node_paths=PackedStringArray("nav_agent") groups=["enemy", "persist"]] collision_layer = 8 collision_mask = 521 +up_direction = Vector3(0.0449994, 0.998987, 0) script = ExtResource("1_7e7fe") nav_agent = NodePath("NavigationAgent3D") bullet = ExtResource("2_aew5r") @@ -834,6 +860,12 @@ script = ExtResource("10_gicen") enemy = NodePath("../..") enemy_targets = [NodePath("../../body/backTarget")] +[node name="Reload" type="Node" parent="StateMachine" node_paths=PackedStringArray("reload_sound", "enemy", "enemy_targets")] +script = ExtResource("11_ekglj") +reload_sound = NodePath("../../AUIDO/Reload") +enemy = NodePath("../..") +enemy_targets = [NodePath("../../body/backTarget")] + [node name="HealthBarSprite" parent="." node_paths=PackedStringArray("character") instance=ExtResource("7_87l3v")] transform = Transform3D(0.254412, 0, 0, 0, 0.561068, 0, 0, 0, 1, 0, 2.41498, 0) billboard = 2 @@ -1051,8 +1083,17 @@ one_shot = true [node name="AUIDO" type="Node3D" parent="."] [node name="Fire" type="AudioStreamPlayer3D" parent="AUIDO"] -stream = ExtResource("10_2qmhc") -volume_db = 10.0 +stream = SubResource("AudioStreamRandomizer_ycipa") +volume_db = 5.0 +pitch_scale = 0.7 + +[node name="Reload" type="AudioStreamPlayer3D" parent="AUIDO"] +stream = SubResource("AudioStreamRandomizer_ekglj") + +[node name="Servo" type="AudioStreamPlayer3D" parent="AUIDO"] +stream = SubResource("AudioStreamRandomizer_4ecf4") +volume_db = -2.5 +unit_size = 5.0 [connection signal="body_entered" from="body/backTarget" to="body/backTarget" method="_on_body_entered"] [connection signal="body_part_hit" from="body/backTarget" to="." method="_on_area_3d_body_part_hit"] diff --git a/project.godot b/project.godot index bdaed21..f2b8dd6 100644 --- a/project.godot +++ b/project.godot @@ -12,7 +12,7 @@ config_version=5 config/name="First Person Test" config/tags=PackedStringArray("fps") -run/main_scene="uid://bk4pn4k7n51ux" +run/main_scene="uid://f7e0v1r6ra6c" config/features=PackedStringArray("4.4", "Forward Plus") config/icon="uid://6svuq1l83al5" diff --git a/scripts/EnemyAttack.gd b/scripts/EnemyAttack.gd index 8d8e1c6..348f51e 100644 --- a/scripts/EnemyAttack.gd +++ b/scripts/EnemyAttack.gd @@ -3,10 +3,20 @@ class_name EnemyAttack var heartbeat : float = 3.0 +@export var mag_size = 5 +@export var between_shot_time : Vector2 = Vector2(.5,2.0) +@export var reload_time : float = 7.0 + + @onready var player = get_tree().current_scene.player -func _Enter(): +var ammo +var shot_timer = 0.0 + +func Enter(): + super() update_waypoint() + ammo = mag_size func update_waypoint(): enemy.nav_agent.set_target_position(player.global_position) @@ -16,10 +26,24 @@ func Update(delta): heartbeat -= delta else: update_waypoint() + #fire if player in view + if ammo > 0: + if shot_timer > 0: + shot_timer -= delta + else: + if enemy.turret_look_next.is_colliding() and enemy.turret_look_next.get_collider().is_in_group("player"): + shot_timer = randf_range(between_shot_time.x,between_shot_time.y) + ammo -= 1 + enemy.turret_material.emission_enabled = true + await get_tree().create_timer(.1).timeout + attack() + else: + await get_tree().create_timer(.5).timeout + Transitioned.emit(self,"reload") func Physics_Update(delta): enemy.turret_look_next.look_at(player.global_position) - enemy.turret_look.look_at(player.global_position) + enemy.turret_look.rotation = lerp(enemy.turret_look.rotation,enemy.turret_look_next.rotation,delta * enemy.turret_look_speed) var destination = enemy.nav_agent.get_next_path_position() var local_destination = destination - enemy.global_position @@ -29,3 +53,36 @@ func Physics_Update(delta): enemy.spider_look_next.look_at(destination) var look_target = enemy.spider_look_next.global_rotation.y enemy.global_rotation.y = lerp(enemy.global_rotation.y,look_target,delta * 3) + +func attack(): + fire(enemy.barrel_1) + enemy.smoke.emitting = true + await get_tree().create_timer(.1).timeout # makes it too hard lol + fire(enemy.barrel_2) + enemy.smoke_2.emitting = true + enemy.turret_material.emission_enabled = false + +func reload(): + await get_tree().create_timer(reload_time).timeout + ammo = mag_size + +func fire(barrel): + var instance_bullet = enemy.bullet.instantiate() + instance_bullet.position = barrel.global_position + instance_bullet.transform.basis = barrel.global_transform.basis + instance_bullet.bullet_speed = enemy.bullet_speed + instance_bullet.bullet_drop = enemy.bullet_drop + instance_bullet.random_spread_amt = enemy.random_spread_amt + instance_bullet.bullet_damage = enemy.bullet_damage + instance_bullet.fired_by = enemy + instance_bullet.target_type = enemy.enemy_type + get_tree().get_root().add_child(instance_bullet) + enemy.audio_fire.play() + spawn_casing() + +func spawn_casing(): + var instance_casing = enemy.casing.instantiate() + instance_casing.position = enemy.casing_ejector.global_position + instance_casing.transform.basis = enemy.casing_ejector.global_transform.basis + instance_casing.player_velocity = enemy.velocity * enemy.transform.basis + get_tree().get_root().add_child(instance_casing) diff --git a/scripts/EnemyIdle.gd b/scripts/EnemyIdle.gd index 1bf7e89..0717ca4 100644 --- a/scripts/EnemyIdle.gd +++ b/scripts/EnemyIdle.gd @@ -1,6 +1,7 @@ extends EnemyState class_name EnemyIdle +@export var idle_speed : float = 1.5 var move_direction : Vector3 var scan_direction : float @@ -19,11 +20,12 @@ func randomize_wander(): wander_time = randf_range(1,3) func randomize_turret_scan(): - scan_direction = randf_range(-TURRET_TURN_AMT,TURRET_TURN_AMT) - scan_time = randf_range(5,10) + scan_direction = -scan_direction -func _Enter(): +func Enter(): + super() randomize_wander() + scan_direction = TURRET_TURN_AMT func Update(delta: float): if wander_time > 0: @@ -42,12 +44,12 @@ func Physics_Update(delta : float): var local_destination = destination - enemy.global_position var direction = local_destination.normalized() if enemy.global_position.distance_to(local_destination) > 1: - enemy.velocity = direction * move_speed + enemy.velocity = direction * idle_speed enemy.spider_look_next.look_at(destination) var look_target = enemy.spider_look_next.global_rotation.y enemy.global_rotation.y = lerp(enemy.global_rotation.y,look_target,delta * 3) - enemy.turret_look.rotation.y = lerp(enemy.turret_look.rotation.y,deg_to_rad(scan_direction),delta) + enemy.turret_look.rotation.y = lerp(enemy.turret_look.rotation.y,enemy.spider_look_next.rotation.y + deg_to_rad(scan_direction),delta * enemy.turret_look_speed) if enemy.turret_look.is_colliding() and enemy.turret_look.get_collider() is Player: Transitioned.emit(self,"attack") diff --git a/scripts/EnemyReload.gd b/scripts/EnemyReload.gd new file mode 100644 index 0000000..a1312c6 --- /dev/null +++ b/scripts/EnemyReload.gd @@ -0,0 +1,57 @@ +extends EnemyState +class_name EnemyReload + +@export var reload_time : float = 7.0 +@export var reload_sound : AudioStreamPlayer3D +@export var run_distance : float = 3 + +@onready var player = get_tree().current_scene.player + +var heartbeat : float = 3.0 +var remaining_bullets + +func Enter(): + super() + remaining_bullets = enemy.max_ammo + enemy.servo_audio.play() + +func Exit(): + super() + enemy.servo_audio.play() + +func update_waypoint(): + var direction = (player.global_position - enemy.global_position).normalized() + enemy.nav_agent.set_target_position(direction * run_distance) + +func Update(delta): + if heartbeat > 0: + heartbeat -= delta + else: + update_waypoint() + + if remaining_bullets > 0: + if !reload_sound.is_playing() and !enemy.servo_audio.is_playing(): + remaining_bullets -= 1 + reload_sound.play() + else: + finished_reload() + + +func Physics_Update(delta): + enemy.turret_look_next.look_at(player.global_position) + enemy.turret_look.rotation = lerp(enemy.turret_look.rotation,Vector3(deg_to_rad(90),0,0),delta * enemy.turret_look_speed) + + var destination = enemy.nav_agent.get_next_path_position() + var local_destination = destination - enemy.global_position + var direction = local_destination.normalized() + if enemy.global_position.distance_to(local_destination) > 1: + enemy.velocity = direction * move_speed + enemy.spider_look_next.look_at(player.global_position) + var look_target = enemy.spider_look_next.global_rotation.y + enemy.global_rotation.y = lerp(enemy.global_rotation.y,look_target,delta * 3) + +func finished_reload(): + if enemy.turret_look_next.is_colliding() and enemy.turret_look_next.get_collider() is Player: + Transitioned.emit(self,"attack") + else: + Transitioned.emit(self,"idle") diff --git a/scripts/EnemyReload.gd.uid b/scripts/EnemyReload.gd.uid new file mode 100644 index 0000000..3b0eaee --- /dev/null +++ b/scripts/EnemyReload.gd.uid @@ -0,0 +1 @@ +uid://dcnmjisrxf5iv diff --git a/scripts/spider.gd b/scripts/spider.gd index 3349079..93fc494 100644 --- a/scripts/spider.gd +++ b/scripts/spider.gd @@ -7,6 +7,8 @@ var player var last_enemy : bool = false @export var start_health = 3 @export var SPEED = 3.0 +@export var turret_look_speed = 6 +@export var max_ammo = 5 @export var loot_amount = 2 @export var nav_agent : NavigationAgent3D @@ -17,7 +19,6 @@ var last_enemy : bool = false @export var bullet_drop = .1 @export var random_spread_amt = .01 @export var bullet_damage = 1 -@export var turret_look_speed = 6 @export var die_particles : Resource @export var damage_number : Resource @export_group("Taunts") @@ -54,6 +55,7 @@ $body/leg4/foot4/foot4outline, $body/leg4/leg4outline, $body/bodyoutline] @onready var health_bar_sprite: Sprite3D = $HealthBarSprite +@onready var servo_audio: AudioStreamPlayer3D = $AUIDO/Servo var gravity = 9.8 @@ -86,45 +88,6 @@ func _ready(): func _process(delta): move_and_slide() -func _on_prefire_timer_timeout(): - fire(barrel_1) - smoke.emitting = true - await get_tree().create_timer(.01).timeout # makes it too hard lol - fire(barrel_2) - smoke_2.emitting = true - turret_material.emission_enabled = false - prefire_timer.stop() - postfire_timer.start() - - -func _on_postfire_timer_timeout(): - if turret_look_next.is_colliding() and turret_look_next.get_collider().is_in_group("player") and !stunned: - prefire_timer.start() - turret_material.emission_enabled = true - else: - postfire_timer.start() - - -func fire(barrel): - var instance_bullet = bullet.instantiate() - instance_bullet.position = barrel.global_position - instance_bullet.transform.basis = barrel.global_transform.basis - instance_bullet.bullet_speed = bullet_speed - instance_bullet.bullet_drop = bullet_drop - instance_bullet.random_spread_amt = random_spread_amt - instance_bullet.bullet_damage = bullet_damage - instance_bullet.fired_by = self - instance_bullet.target_type = enemy_type - get_tree().get_root().add_child(instance_bullet) - audio_fire.play() - spawn_casing() - -func spawn_casing(): - var instance_casing = casing.instantiate() - instance_casing.position = casing_ejector.global_position - instance_casing.transform.basis = casing_ejector.global_transform.basis - instance_casing.player_velocity = velocity * transform.basis - get_tree().get_root().add_child(instance_casing) func stun(): state_machine.on_child_transition(state_machine.current_state,"stunned")