feat: bullrush branch - mekton bulls arena, HUD, NPC managers, godot_ai updates

This commit is contained in:
2026-07-01 10:39:21 +08:00
parent cc584c3251
commit b6b37b5aac
48 changed files with 2548 additions and 397 deletions
+7
View File
@@ -0,0 +1,7 @@
[gd_scene load_steps=2 format=3 uid="uid://c5xk3jdg2s11m"]
[node name="MektonBullsArena" type="Node3D"]
[node name="GridMap" type="GridMap" parent="."]
[node name="Area3D" type="Area3D" parent="."]
+29 -4
View File
@@ -17,6 +17,7 @@ var is_match_ended: bool = false
var obstacle_manager
var portal_mode_manager
var gauntlet_manager
var mekton_bulls_manager
var vfx_manager
# Minimal local state
@@ -258,7 +259,14 @@ func _init_managers():
gauntlet_manager.name = "GauntletManager"
add_child(gauntlet_manager)
gauntlet_manager.initialize(self, $EnhancedGridMap)
# Mekton Bulls manager
if LobbyManager.game_mode == "Mekton Bulls":
mekton_bulls_manager = load("res://scripts/managers/mekton_bulls_manager.gd").new()
mekton_bulls_manager.name = "MektonBullsManager"
add_child(mekton_bulls_manager)
mekton_bulls_manager.initialize(self, $EnhancedGridMap)
# Screen shake manager for impact feedback
screen_shake_manager = load("res://scripts/managers/screen_shake.gd").new()
screen_shake_manager.name = "ScreenShakeManager"
@@ -623,6 +631,8 @@ func _setup_host_game():
portal_mode_manager.setup_arena_locally()
elif LobbyManager.game_mode == "Candy Pump Survival" and gauntlet_manager:
gauntlet_manager._setup_arena()
elif LobbyManager.game_mode == "Mekton Bulls" and mekton_bulls_manager:
mekton_bulls_manager._setup_arena()
else:
# Randomize grid first to ensure Floor 0 is walkable for pre-calculation
randomize_game_grid()
@@ -728,10 +738,20 @@ func _setup_client_game():
# Initialize arena locally for Tekton Doors
if LobbyManager.game_mode == "Tekton Doors" and portal_mode_manager:
portal_mode_manager.setup_arena_locally()
# Initialize arena locally for Candy Pump Survival
# Special initialization for Gauntlet mode
if LobbyManager.game_mode == "Candy Pump Survival" and gauntlet_manager:
gauntlet_manager._apply_arena_setup()
if LobbyManager.game_mode == "Mekton Bulls" and mekton_bulls_manager:
mekton_bulls_manager.hud_node = load("res://scenes/ui/mekton_bulls_hud.tscn").instantiate()
mekton_bulls_manager.hud_node.name = "MektonBullsHUD"
add_child(mekton_bulls_manager.hud_node)
if mekton_bulls_manager.hud_node.has_method("initialize"):
mekton_bulls_manager.hud_node.initialize(mekton_bulls_manager)
if mekton_bulls_manager.hud_node.has_method("set_local_player"):
mekton_bulls_manager.hud_node.set_local_player(multiplayer.get_unique_id())
mekton_bulls_manager._apply_arena_setup()
# Ensure local player setup (UI, controls) is verified
var player_character = get_node_or_null(str(my_id))
@@ -876,10 +896,15 @@ func _start_game():
elif LobbyManager.game_mode == "Candy Pump Survival":
if gauntlet_manager:
gauntlet_manager.start_game_mode()
if goals_cycle_manager:
var match_duration = LobbyManager.get_match_duration()
goals_cycle_manager.start_match(float(match_duration), true) # Enable cycles for 3x3 pattern missions
elif LobbyManager.game_mode == "Mekton Bulls":
if mekton_bulls_manager:
mekton_bulls_manager.start_game_mode()
if goals_cycle_manager:
var match_duration = LobbyManager.get_match_duration()
goals_cycle_manager.start_match(float(match_duration))
elif goals_cycle_manager:
var match_duration = LobbyManager.get_match_duration()
goals_cycle_manager.start_match(float(match_duration))
+21
View File
@@ -0,0 +1,21 @@
[gd_scene load_steps=5 format=3 uid="uid://bull1234abcd"]
[ext_resource type="Script" uid="uid://bullscript1" path="res://scripts/npcs/mekton_bull.gd" id="1_bull"]
[ext_resource type="PackedScene" uid="uid://df7h7y7y7y7y7" path="res://scenes/static_tekton_mesh.tscn" id="2_mesh"]
[sub_resource type="BoxShape3D" id="BoxShape3D_bull"]
size = Vector3(1.5, 2.0, 1.5)
[node name="MektonBull" type="Area3D" groups=["MektonBulls"]]
collision_layer = 4
collision_mask = 2
script = ExtResource("1_bull")
[node name="CollisionShape3D" type="CollisionShape3D" parent="."]
transform = Transform3D(1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 1.0, 0)
shape = SubResource("BoxShape3D_bull")
[node name="Visuals" type="Node3D" parent="."]
[node name="Mesh" parent="Visuals" instance=ExtResource("2_mesh")]
transform = Transform3D(0.4, 0, 0, 0, 0.4, 0, 0, 0, 0.4, 0, 0, 0)
+91
View File
@@ -0,0 +1,91 @@
[gd_scene format=3 uid="uid://bullhud"]
[ext_resource type="Script" uid="uid://bullhudscript" path="res://scripts/ui/mekton_bulls_hud.gd" id="1_hud"]
[node name="MektonBullsHUD" type="Control"]
layout_mode = 3
anchors_preset = 15
anchor_right = 1.0
anchor_bottom = 1.0
grow_horizontal = 2
grow_vertical = 2
script = ExtResource("1_hud")
[node name="BullTracker" type="Control" parent="."]
anchors_preset = 0
[node name="PowerCounters" type="Control" parent="."]
anchors_preset = 0
layout_mode = 1
anchors_preset = 2
anchor_top = 1.0
anchor_bottom = 1.0
offset_top = -60.0
offset_right = 300.0
grow_vertical = 0
[node name="Label" type="Label" parent="PowerCounters"]
layout_mode = 1
anchors_preset = 15
anchor_right = 1.0
anchor_bottom = 1.0
text = "Freeze: 0 | Knock: 0"
vertical_alignment = 1
[node name="PowerPicker" type="PanelContainer" parent="."]
visible = false
layout_mode = 1
anchors_preset = 8
anchor_left = 0.5
anchor_top = 0.5
anchor_right = 0.5
anchor_bottom = 0.5
offset_left = -100.0
offset_top = -50.0
offset_right = 100.0
offset_bottom = 50.0
grow_horizontal = 2
grow_vertical = 2
[node name="HBoxContainer" type="HBoxContainer" parent="PowerPicker"]
layout_mode = 2
[node name="FreezeBtn" type="Button" parent="PowerPicker/HBoxContainer"]
layout_mode = 2
size_flags_horizontal = 3
text = "Freeze"
[node name="KnockBtn" type="Button" parent="PowerPicker/HBoxContainer"]
layout_mode = 2
size_flags_horizontal = 3
text = "Knock"
[node name="PlacementPanel" type="PanelContainer" parent="."]
visible = false
layout_mode = 1
anchors_preset = 8
anchor_left = 0.5
anchor_top = 0.5
anchor_right = 0.5
anchor_bottom = 0.5
offset_left = -200.0
offset_top = -150.0
offset_right = 200.0
offset_bottom = 150.0
grow_horizontal = 2
grow_vertical = 2
[node name="VBoxContainer" type="VBoxContainer" parent="PlacementPanel"]
layout_mode = 2
[node name="Label" type="Label" parent="PlacementPanel/VBoxContainer"]
layout_mode = 2
text = "Match Placements"
horizontal_alignment = 1
[node name="List" type="VBoxContainer" parent="PlacementPanel/VBoxContainer"]
layout_mode = 2
size_flags_vertical = 3
[connection signal="pressed" from="PowerPicker/HBoxContainer/FreezeBtn" to="." method="_on_freeze_btn_pressed"]
[connection signal="pressed" from="PowerPicker/HBoxContainer/KnockBtn" to="." method="_on_knock_btn_pressed"]