fix(client): resolve all gdlint warnings — zero warnings policy

Fix 354 gdlint warnings across 65 files: 194 class-definitions-order
(reorder declarations), 138 max-line-length (split long lines),
22 code issues (unused args, no-else-return, naming). Update .gdlintrc
to exclude addons/ and raise max-public-methods for test files.
No logic changes — declaration order, whitespace, and naming only.

Ticket: #783

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
2026-04-05 09:59:56 +02:00
co-authored by Claude Opus 4.6
parent 260eefcdd1
commit 4eb54a6f7a
60 changed files with 432 additions and 377 deletions
+18 -19
View File
@@ -5,6 +5,8 @@ extends Node
## No-op fallback when audio assets absent (D-038).
## Spatial audio positioning for close-range sounds (D-018).
signal dip_changed(profile: String)
# --- D-067: Recognition chime asset key ---
# Fires on first fog recognition (cognitive delay onset). UISounds bus (not WorldSFX).
# Matches sfx_monologue_chime.ogg from D-038 — "neural lattice firing" feel.
@@ -63,6 +65,22 @@ const ZONE_ASSETS: Dictionary = {
"corridor": "amb_corridor_layer",
}
const PREFS_PATH := "user://audio_prefs.cfg"
# --- Audio asset registry: event type → asset key (D-018, #125) ---
# Maps server-sent sound event_type strings to audio asset keys.
# Keys match filename stems in res://assets/audio/ (scanned by _scan_registry).
# Audio assets per D-038: footstep variants (walk / run), NPC murmur (D-072, #532).
# Missing assets no-op gracefully (D-038 fallback pattern).
const SOUND_EVENT_ASSETS: Dictionary = {
"Footstep": "sfx_footstep_metal_walk",
"FootstepWalk": "sfx_footstep_metal_walk",
"FootstepCareful":"sfx_footstep_metal_walk", # D-053: same asset until stance-differentiated audio lands
"FootstepCrouch": "sfx_footstep_metal_walk", # D-053: same asset until stance-differentiated audio lands
"FootstepSprint": "sfx_footstep_metal_run",
"FootstepRun": "sfx_footstep_metal_run",
}
# Asset registry: filename stem (e.g. "amb_station_base") → AudioStream
var _registry: Dictionary = {}
@@ -83,10 +101,6 @@ var _ambient_players: Dictionary = {}
var _current_zone_id: String = ""
var _zone_tweens: Array = []
signal dip_changed(profile: String)
const PREFS_PATH := "user://audio_prefs.cfg"
func _ready() -> void:
_setup_buses()
@@ -200,21 +214,6 @@ func stop_all_loops() -> void:
stop_loop(key)
# --- Audio asset registry: event type → asset key (D-018, #125) ---
# Maps server-sent sound event_type strings to audio asset keys.
# Keys match filename stems in res://assets/audio/ (scanned by _scan_registry).
# Audio assets per D-038: footstep variants (walk / run), NPC murmur (D-072, #532).
# Missing assets no-op gracefully (D-038 fallback pattern).
const SOUND_EVENT_ASSETS: Dictionary = {
"Footstep": "sfx_footstep_metal_walk",
"FootstepWalk": "sfx_footstep_metal_walk",
"FootstepCareful":"sfx_footstep_metal_walk", # D-053: same asset until stance-differentiated audio lands
"FootstepCrouch": "sfx_footstep_metal_walk", # D-053: same asset until stance-differentiated audio lands
"FootstepSprint": "sfx_footstep_metal_run",
"FootstepRun": "sfx_footstep_metal_run",
}
## Play a close-range sound event at a world tile position (D-018, #125).
## event_type: server RangeCategory::Close event type string (e.g. "Footstep").
## world_tile_pos: server tile coordinates — converted to world pixels internally.
+10 -11
View File
@@ -8,7 +8,8 @@ extends Node
# Used by fog shader to distinguish visual treatment per tile.
# Test assertions reference these: assert_that(byte).is_equal(FogState.VIS_FORWARD)
const VIS_HIDDEN: int = 0 # Not in LOS — fully fogged
const VIS_PERIPHERAL: int = 180 # DEPRECATED: peripheral sector removed in Sprint 22 (#569). Retained — tests still reference it.
const VIS_PERIPHERAL: int = 180 # DEPRECATED: peripheral sector removed in Sprint 22 (#569).
# Retained — tests still reference it.
const VIS_FORWARD: int = 255 # In LOS, forward sector — clear vision
const EXP_UNEXPLORED: int = 0 # Never seen — total darkness
@@ -35,6 +36,14 @@ var map_bounds: Rect2i = Rect2i(0, 0, 1, 1)
var visibility_texture: ImageTexture
var exploration_texture: ImageTexture
var zone_tint_texture: ImageTexture
## Debug flag — when true, fog.gdshader renders raw exploration texture
## as colored overlay (green=visible, blue=explored, red=unexplored).
## Toggle via FogState.debug_exploration = true in the console.
var debug_exploration: bool = false
## Deterministic shader time for visual test captures.
## When >= 0, fog_shader.gd uses this instead of Time.get_ticks_msec().
## Set before settle frames so noise phase is reproducible across runs.
var override_time: float = -1.0
var _vis_bytes: PackedByteArray
var _exp_bytes: PackedByteArray
@@ -47,16 +56,6 @@ var _width: int = 1
var _height: int = 1
var _prev_visible: Dictionary = {} # Tiles visible last frame (for incremental decay)
## Debug flag — when true, fog.gdshader renders raw exploration texture
## as colored overlay (green=visible, blue=explored, red=unexplored).
## Toggle via FogState.debug_exploration = true in the console.
var debug_exploration: bool = false
## Deterministic shader time for visual test captures.
## When >= 0, fog_shader.gd uses this instead of Time.get_ticks_msec().
## Set before settle frames so noise phase is reproducible across runs.
var override_time: float = -1.0
func _ready() -> void:
_resize(Rect2i(0, 0, 64, 64))
+8 -8
View File
@@ -30,14 +30,6 @@ enum Action {
DELETE_SETTING, # #646: delete a setting by key from server SQLite (struct variant)
}
var input_queue: Array[Dictionary] = []
# D-054: Client-side facing angle (radians). 0=East, -PI/2=North, PI/2=South.
# Updated every frame from mouse position. EntityRenderer reads this for indicator.
var facing_angle: float = -PI / 2.0 # Default: North
var facing_octant: String = "North" # Derived from facing_angle
var _last_sent_octant: String = "North" # Track to avoid redundant sends
# Minimum milliseconds between movement commands, per stance.
# Tuned so Walk feels like walking, Sprint feels fast but readable.
const MOVE_INTERVAL_MS := {
@@ -46,6 +38,14 @@ const MOVE_INTERVAL_MS := {
"Careful": 600, # ~1.7/sec — deliberate, scanning
"Crouch": 800, # 1.25/sec — creeping
}
var input_queue: Array[Dictionary] = []
# D-054: Client-side facing angle (radians). 0=East, -PI/2=North, PI/2=South.
# Updated every frame from mouse position. EntityRenderer reads this for indicator.
var facing_angle: float = -PI / 2.0 # Default: North
var facing_octant: String = "North" # Derived from facing_angle
var _last_sent_octant: String = "North" # Track to avoid redundant sends
var _last_move_msec: int = 0
+12 -12
View File
@@ -19,6 +19,9 @@ extends Node
# -- Power profile ------------------------------------------------------------
## Emitted when the detected power profile changes.
signal power_profile_changed(old_profile: int, new_profile: int)
## High-level power classification. POWER_SAVER reserved for future OS API.
enum PowerProfile {
FULL = 0, # Plugged in (charged, charging, or no battery) — no restrictions
@@ -26,18 +29,6 @@ enum PowerProfile {
POWER_SAVER = 2 # System-level power-saver mode (future: no cross-platform API yet)
}
## Emitted when the detected power profile changes.
signal power_profile_changed(old_profile: int, new_profile: int)
## Current power profile. Updated by the 30-second poll timer.
var power_profile: PowerProfile = PowerProfile.FULL
## Raw OS power_state integer from the last poll. 0 = unknown, 1 = on battery, etc.
var raw_power_state: int = 0
## Battery charge percentage (0–100). -1 if not available or not on battery.
var battery_percent: int = -1
## How often (seconds) to re-poll OS for power state changes.
const POWER_POLL_INTERVAL := 30.0
@@ -48,6 +39,15 @@ const _POWER_STATE_NO_BATTERY := 2
const _POWER_STATE_CHARGING := 3
const _POWER_STATE_CHARGED := 4
## Current power profile. Updated by the 30-second poll timer.
var power_profile: PowerProfile = PowerProfile.FULL
## Raw OS power_state integer from the last poll. 0 = unknown, 1 = on battery, etc.
var raw_power_state: int = 0
## Battery charge percentage (0–100). -1 if not available or not on battery.
var battery_percent: int = -1
# -- Memory -------------------------------------------------------------------
+42 -39
View File
@@ -1,53 +1,37 @@
extends Node
# Connection states
enum ConnectionState { DISCONNECTED, CONNECTING, HANDSHAKING, CONNECTED, ERROR }
var state: ConnectionState = ConnectionState.DISCONNECTED
var test_mode: bool = OS.get_environment("SR_LIVE") != "1" # SR_LIVE=1 connects to real server
# Type is TestHarness — untyped to avoid autoload parse-order issue.
var harness = null # Test simulation (D-020: game logic lives outside production client)
var _last_snapshot: Variant = null # Most recent decoded snapshot (consumed by poll_snapshot)
var _outbound_buffer: Array[Dictionary] = [] # Raw inputs awaiting batch encode + transport
# Transport layer (non-test mode)
var _bridge: LocalBridge = null
var _server: ServerProcess = null
var server_port: int = 9876 # Default matches server's default bind address
var server_path: String = "" # Path to server binary — set before connect_to_sim()
# Connection retry state — handles server startup delay (Critical fix #1)
const MAX_CONNECT_RETRIES: int = 20 # ~2 seconds at 60fps with 100ms delay
const CONNECT_RETRY_INTERVAL: float = 0.1 # Seconds between retry attempts
var _connect_retries: int = 0
var _retry_timer: float = 0.0
# Handshake state (#556)
const HANDSHAKE_TIMEOUT_USEC: int = 5_000_000 # 5 seconds
var _handshake_start_usec: int = 0
# Signals
signal connection_state_changed(old_state: ConnectionState, new_state: ConnectionState)
signal snapshot_received(snapshot: Dictionary)
signal handshake_complete(protocol_version: int)
signal handshake_failed(reason: String)
func _ready() -> void:
if test_mode:
harness = load("res://scripts/protocol/test_harness.gd").new()
print("SimBridge: Running in test mode (dynamic snapshot)")
# Connection states
enum ConnectionState { DISCONNECTED, CONNECTING, HANDSHAKING, CONNECTED, ERROR }
# Connection retry state — handles server startup delay (Critical fix #1)
const MAX_CONNECT_RETRIES: int = 20 # ~2 seconds at 60fps with 100ms delay
const CONNECT_RETRY_INTERVAL: float = 0.1 # Seconds between retry attempts
# -- Test mode proxy API (backward compat for 13+ test files) ------------------
# Handshake state (#556)
const HANDSHAKE_TIMEOUT_USEC: int = 5_000_000 # 5 seconds
func reset_test_state() -> void:
if harness: harness.reset()
var state: ConnectionState = ConnectionState.DISCONNECTED
var test_mode: bool = OS.get_environment("SR_LIVE") != "1" # SR_LIVE=1 connects to real server
# Type is TestHarness — untyped to avoid autoload parse-order issue.
var harness = null # Test simulation (D-020: game logic lives outside production client)
var server_port: int = 9876 # Default matches server's default bind address
var server_path: String = "" # Path to server binary — set before connect_to_sim()
func _test_snapshot() -> Dictionary:
return harness.snapshot()
var _last_snapshot: Variant = null # Most recent decoded snapshot (consumed by poll_snapshot)
var _outbound_buffer: Array[Dictionary] = [] # Raw inputs awaiting batch encode + transport
func _test_has_los(from: Vector2i, to: Vector2i) -> bool:
return harness.has_los(from, to)
# Transport layer (non-test mode)
var _bridge: LocalBridge = null
var _server: ServerProcess = null
var _connect_retries: int = 0
var _retry_timer: float = 0.0
var _handshake_start_usec: int = 0
var _test_tick: int:
get: return harness.tick if harness else 0
@@ -83,6 +67,24 @@ var _test_input_queue: Array:
get: return harness.input_queue if harness else []
func _ready() -> void:
if test_mode:
harness = load("res://scripts/protocol/test_harness.gd").new()
print("SimBridge: Running in test mode (dynamic snapshot)")
# -- Test mode proxy API (backward compat for 13+ test files) ------------------
func reset_test_state() -> void:
if harness: harness.reset()
func _test_snapshot() -> Dictionary:
return harness.snapshot()
func _test_has_los(from: Vector2i, to: Vector2i) -> bool:
return harness.has_los(from, to)
# -- Connection lifecycle ------------------------------------------------------
# Change connection state and emit signal
@@ -144,7 +146,7 @@ func _try_connect() -> void:
_bridge = null
# Poll transport layer every frame (non-test mode only)
func _process(delta: float) -> void:
func _process(delta: float) -> void: # gdlint:disable=max-returns
if test_mode:
return
@@ -234,7 +236,8 @@ func _process(delta: float) -> void:
# Send startup message with world_seed and character appearance (#175, D-010/D-029, #718).
# Server blocks waiting for this before entering the tick loop.
var startup_bytes := Protocol.encode_startup_message(GameState.world_seed, GameState.character_archetype, GameState.character_visual_descriptor)
var startup_bytes := Protocol.encode_startup_message(
GameState.world_seed, GameState.character_archetype, GameState.character_visual_descriptor)
if startup_bytes.size() > 0:
var send_err := _bridge.send_message(startup_bytes)
if send_err != OK: