b0c83af092
Complete replacement of the tactical-shooter project with the netfox-cs-sample (MIT) — a CS 1.6 inspired multiplayer FPS built with Godot 4 and netfox. ## What's new - Full CS-style gameplay: teams (T/CT), rounds, economy, buy menu - 6 weapons: Knife, Glock, USP, AK-47, M4A1, AWP - Bomb plant/defuse with 2 bombsites - Flashbang & smoke grenades - Proper netfox rollback netcode at 64 tick - Network popup UI for host/join - HUD, crosshair, round timer, scoreboard - All netfox singletons registered as autoloads (works in exported builds) ## Architecture - Listen-server (host from client, no dedicated server binary) - Multiplayer-fps game lives at examples/multiplayer-fps/ - Netfox addons registered as autoloads for exported build compat - Godot 4.7 with Forward+ renderer ## Removed - Old headless-server architecture (client_main, server_main, player.gd, etc.) - Custom netfox bootstrap with ENet fallback - Old ChaffGames FPS template (2,420 lines, 844 KB) - SimulationServer GDExtension stub - Godot-jolt physics (netfox sample uses default Godot physics) - Duplicate weapon_data.gd, anti_cheat.gd, round_manager.gd, etc. - Server browser API Python venv (87 MB) - test_range map and modular assets ## Preserved - Git history - Server config at config/default_server_config.cfg - Windows export preset - Build directory (gitignored) Co-authored-by: naxIO <naxIO@users.noreply.github.com>
163 lines
7.6 KiB
Plaintext
163 lines
7.6 KiB
Plaintext
[gd_scene load_steps=28 format=3 uid="uid://wi4owat0bml3"]
|
|
|
|
[ext_resource type="Script" path="res://examples/forest-brawl/scripts/brawler-controller.gd" id="1_np8na"]
|
|
[ext_resource type="Script" path="res://examples/forest-brawl/scripts/brawler-input.gd" id="2_m3v43"]
|
|
[ext_resource type="Script" path="res://examples/forest-brawl/scripts/play-random-3d.gd" id="3_rcsmp"]
|
|
[ext_resource type="Script" path="res://examples/forest-brawl/scripts/brawler-weapon.gd" id="4_0hvdj"]
|
|
[ext_resource type="AudioStream" uid="uid://cih2i8xa2v2is" path="res://examples/forest-brawl/sounds/fall1.wav" id="4_mw5vb"]
|
|
[ext_resource type="PackedScene" uid="uid://8sru5hge6spx" path="res://examples/forest-brawl/scenes/bomb-projectile.tscn" id="5_a4qop"]
|
|
[ext_resource type="AudioStream" uid="uid://4oilc8k83mmt" path="res://examples/forest-brawl/sounds/fall2.wav" id="5_kqmf5"]
|
|
[ext_resource type="AudioStream" uid="uid://b03phi3tfl21k" path="res://examples/forest-brawl/sounds/whoosh.wav" id="6_gh8ps"]
|
|
[ext_resource type="AudioStream" uid="uid://cegpnj82f4gio" path="res://examples/forest-brawl/sounds/fall3.wav" id="6_jc44e"]
|
|
[ext_resource type="Script" path="res://addons/netfox/rollback/rollback-synchronizer.gd" id="7_cmfmx"]
|
|
[ext_resource type="PackedScene" uid="uid://fctd5hkxnf2y" path="res://examples/forest-brawl/models/player/bomber-guy.glb" id="7_ij3cr"]
|
|
[ext_resource type="Script" path="res://addons/netfox/tick-interpolator.gd" id="8_pj7o0"]
|
|
|
|
[sub_resource type="AnimationNodeAnimation" id="AnimationNodeAnimation_gdp4i"]
|
|
animation = &"Float"
|
|
|
|
[sub_resource type="AnimationNodeBlend2" id="AnimationNodeBlend2_qv2tk"]
|
|
|
|
[sub_resource type="AnimationNodeAnimation" id="AnimationNodeAnimation_rss6c"]
|
|
animation = &"Idle"
|
|
|
|
[sub_resource type="AnimationNodeAnimation" id="AnimationNodeAnimation_7lmj4"]
|
|
animation = &"Run"
|
|
|
|
[sub_resource type="AnimationNodeAnimation" id="AnimationNodeAnimation_7yjg4"]
|
|
animation = &"Strafe_L"
|
|
|
|
[sub_resource type="AnimationNodeAnimation" id="AnimationNodeAnimation_v2fmc"]
|
|
animation = &"Strafe_R"
|
|
|
|
[sub_resource type="AnimationNodeAnimation" id="AnimationNodeAnimation_tp0nc"]
|
|
animation = &"Backpedal"
|
|
|
|
[sub_resource type="AnimationNodeBlendSpace2D" id="AnimationNodeBlendSpace2D_blhbt"]
|
|
blend_point_0/node = SubResource("AnimationNodeAnimation_rss6c")
|
|
blend_point_0/pos = Vector2(0, 0)
|
|
blend_point_1/node = SubResource("AnimationNodeAnimation_7lmj4")
|
|
blend_point_1/pos = Vector2(0, 1)
|
|
blend_point_2/node = SubResource("AnimationNodeAnimation_7yjg4")
|
|
blend_point_2/pos = Vector2(1, 0)
|
|
blend_point_3/node = SubResource("AnimationNodeAnimation_v2fmc")
|
|
blend_point_3/pos = Vector2(-1, 0)
|
|
blend_point_4/node = SubResource("AnimationNodeAnimation_tp0nc")
|
|
blend_point_4/pos = Vector2(0, -1)
|
|
min_space = Vector2(-4, -1)
|
|
max_space = Vector2(4, 1)
|
|
|
|
[sub_resource type="AnimationNodeTimeScale" id="AnimationNodeTimeScale_2k2qg"]
|
|
|
|
[sub_resource type="AnimationNodeAnimation" id="AnimationNodeAnimation_w05vo"]
|
|
animation = &"Throw"
|
|
|
|
[sub_resource type="AnimationNodeOneShot" id="AnimationNodeOneShot_byyqa"]
|
|
filter_enabled = true
|
|
filters = ["rig/Skeleton3D:DEF-breast.L", "rig/Skeleton3D:DEF-breast.R", "rig/Skeleton3D:DEF-forearm.L", "rig/Skeleton3D:DEF-forearm.L.001", "rig/Skeleton3D:DEF-forearm.R", "rig/Skeleton3D:DEF-forearm.R.001", "rig/Skeleton3D:DEF-hand.L", "rig/Skeleton3D:DEF-hand.R", "rig/Skeleton3D:DEF-shoulder.L", "rig/Skeleton3D:DEF-shoulder.R", "rig/Skeleton3D:DEF-spine", "rig/Skeleton3D:DEF-spine.001", "rig/Skeleton3D:DEF-spine.002", "rig/Skeleton3D:DEF-spine.003", "rig/Skeleton3D:DEF-spine.004", "rig/Skeleton3D:DEF-spine.005", "rig/Skeleton3D:DEF-spine.006", "rig/Skeleton3D:DEF-upper_arm.L", "rig/Skeleton3D:DEF-upper_arm.L.001", "rig/Skeleton3D:DEF-upper_arm.R", "rig/Skeleton3D:DEF-upper_arm.R.001"]
|
|
fadein_time = 0.2
|
|
fadeout_time = 0.2
|
|
|
|
[sub_resource type="AnimationNodeTimeScale" id="AnimationNodeTimeScale_ofns8"]
|
|
|
|
[sub_resource type="AnimationNodeBlendTree" id="AnimationNodeBlendTree_8to0y"]
|
|
graph_offset = Vector2(-680.797, -57.1155)
|
|
nodes/Float/node = SubResource("AnimationNodeBlend2_qv2tk")
|
|
nodes/Float/position = Vector2(-80, 0)
|
|
"nodes/Float Anim/node" = SubResource("AnimationNodeAnimation_gdp4i")
|
|
"nodes/Float Anim/position" = Vector2(-280, 120)
|
|
nodes/Move/node = SubResource("AnimationNodeBlendSpace2D_blhbt")
|
|
nodes/Move/position = Vector2(-480, -40)
|
|
nodes/MoveScale/node = SubResource("AnimationNodeTimeScale_2k2qg")
|
|
nodes/MoveScale/position = Vector2(-280, -40)
|
|
nodes/Throw/node = SubResource("AnimationNodeOneShot_byyqa")
|
|
nodes/Throw/position = Vector2(100, 20)
|
|
"nodes/Throw Anim/node" = SubResource("AnimationNodeAnimation_w05vo")
|
|
"nodes/Throw Anim/position" = Vector2(-280, 260)
|
|
nodes/ThrowScale/node = SubResource("AnimationNodeTimeScale_ofns8")
|
|
nodes/ThrowScale/position = Vector2(-100, 260)
|
|
nodes/output/position = Vector2(320, 80)
|
|
node_connections = [&"output", 0, &"Throw", &"Float", 0, &"MoveScale", &"Float", 1, &"Float Anim", &"MoveScale", 0, &"Move", &"Throw", 0, &"Float", &"Throw", 1, &"ThrowScale", &"ThrowScale", 0, &"Throw Anim"]
|
|
|
|
[sub_resource type="CapsuleShape3D" id="CapsuleShape3D_qgusj"]
|
|
radius = 0.25
|
|
height = 1.0
|
|
|
|
[sub_resource type="SceneReplicationConfig" id="SceneReplicationConfig_4cjl8"]
|
|
properties/0/path = NodePath(".:player_name")
|
|
properties/0/spawn = true
|
|
properties/0/sync = false
|
|
properties/0/watch = true
|
|
properties/1/path = NodePath(".:visible")
|
|
properties/1/spawn = true
|
|
properties/1/sync = false
|
|
properties/1/watch = true
|
|
|
|
[node name="Brawler" type="CharacterBody3D" groups=["Brawlers"]]
|
|
platform_on_leave = 2
|
|
platform_floor_layers = 0
|
|
script = ExtResource("1_np8na")
|
|
speed = 4.0
|
|
death_depth = 16.0
|
|
respawn_time = 8.0
|
|
|
|
[node name="bomber-guy" parent="." instance=ExtResource("7_ij3cr")]
|
|
transform = Transform3D(0.5, 0, 0, 0, 0.5, 0, 0, 0, 0.5, 0, -0.5, 0)
|
|
|
|
[node name="AnimationTree" type="AnimationTree" parent="."]
|
|
tree_root = SubResource("AnimationNodeBlendTree_8to0y")
|
|
anim_player = NodePath("../bomber-guy/AnimationPlayer")
|
|
active = true
|
|
parameters/Float/blend_amount = 0.0
|
|
parameters/Move/blend_position = Vector2(0, 0)
|
|
parameters/MoveScale/scale = 1.0
|
|
parameters/Throw/active = false
|
|
parameters/Throw/internal_active = false
|
|
parameters/Throw/request = 0
|
|
parameters/ThrowScale/scale = 1.0
|
|
|
|
[node name="CollisionShape3D" type="CollisionShape3D" parent="."]
|
|
shape = SubResource("CapsuleShape3D_qgusj")
|
|
|
|
[node name="Nametag" type="Label3D" parent="."]
|
|
transform = Transform3D(1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 1, 0)
|
|
pixel_size = 0.0007
|
|
billboard = 1
|
|
fixed_size = true
|
|
text = "Nameless Brawler"
|
|
width = 128.0
|
|
|
|
[node name="Fall Sound" type="AudioStreamPlayer3D" parent="."]
|
|
script = ExtResource("3_rcsmp")
|
|
sounds = Array[AudioStream]([ExtResource("4_mw5vb"), ExtResource("5_kqmf5"), ExtResource("6_jc44e")])
|
|
|
|
[node name="Input" type="Node" parent="."]
|
|
script = ExtResource("2_m3v43")
|
|
|
|
[node name="Weapon" type="Node3D" parent="."]
|
|
transform = Transform3D(1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0.5)
|
|
script = ExtResource("4_0hvdj")
|
|
projectile = ExtResource("5_a4qop")
|
|
fire_cooldown = 0.5
|
|
|
|
[node name="AudioStreamPlayer3D" type="AudioStreamPlayer3D" parent="Weapon"]
|
|
stream = ExtResource("6_gh8ps")
|
|
|
|
[node name="RollbackSynchronizer" type="Node" parent="." node_paths=PackedStringArray("root")]
|
|
script = ExtResource("7_cmfmx")
|
|
root = NodePath("..")
|
|
enable_prediction = true
|
|
state_properties = Array[String]([":transform", ":velocity", ":speed", ":mass"])
|
|
full_state_interval = 24
|
|
diff_ack_interval = 4
|
|
input_properties = Array[String](["Input:movement", "Input:aim"])
|
|
enable_input_broadcast = false
|
|
|
|
[node name="MultiplayerSynchronizer" type="MultiplayerSynchronizer" parent="."]
|
|
replication_config = SubResource("SceneReplicationConfig_4cjl8")
|
|
|
|
[node name="TickInterpolator" type="Node" parent="." node_paths=PackedStringArray("root")]
|
|
script = ExtResource("8_pj7o0")
|
|
root = NodePath("..")
|
|
properties = Array[String]([":transform"])
|