diff --git a/AGRARIAN_DEVELOPMENT_ROADMAP.md b/AGRARIAN_DEVELOPMENT_ROADMAP.md index 5ad8ed9..6c40ce7 100644 --- a/AGRARIAN_DEVELOPMENT_ROADMAP.md +++ b/AGRARIAN_DEVELOPMENT_ROADMAP.md @@ -845,7 +845,7 @@ Target deliverable: A small group can join a server, spawn into one biome, gathe - [x] Add fire suppression hooks for rain, water carrying, dirt/sand, cleared firebreaks, and future firefighting tools. Added shared server-side suppression hooks plus water, dirt/sand, firebreak, and tool wrappers that raise suppression pressure, reduce ignition risks, reduce active fire intensity, shrink spread radius, and let rain/water drain fuel. - [x] Persist active grass, forest, and structure fires across save/load without corrupting world state. Extended campfire persistence coverage for ignition flags, ignition risk scores, active grass/forest/structure fire intensities, spread radius, and suppression pressure so save/load recovery preserves active and partially suppressed fire state. - [x] Add QA coverage for safe campfires, unsafe campfires, vegetation spread, shelter ignition, suppression, and save/load recovery. Added a fire-risk QA coverage document and verifier requiring safe/unsafe campfire, vegetation spread, shelter ignition, suppression, and save/load recovery scenarios plus the supporting fire-risk verification scripts. -- [ ] Add weather sounds. +- [x] Add weather sounds. Formalized the existing placed weather audio controller as the MVP weather-sound path, documenting rain, wind, storm, clear ambient, and biome loop slots plus verification that weather playback follows replicated weather state, provider wind speed, and day/night state while remaining silent until assets are assigned. - [ ] Add wildlife sounds. - [ ] Add UI sounds. - [ ] Add mix settings. diff --git a/Docs/Audio/WeatherSounds.md b/Docs/Audio/WeatherSounds.md new file mode 100644 index 0000000..85d4f11 --- /dev/null +++ b/Docs/Audio/WeatherSounds.md @@ -0,0 +1,24 @@ +# MVP Weather Sounds + +Weather sounds are owned by `AAgrarianWeatherAudioController`, which is placed +in the Ground Zero demo map as `AGR_DemoWeatherAudioController`. + +The controller exposes these sound slots: + +- `RainLoopSound` +- `WindLoopSound` +- `StormLoopSound` +- `ClearAmbientSound` +- `BiomeAmbientLoopSound` + +The MVP weather audio path is intentionally asset-agnostic. The packaged build +remains silent until placeholder or final loops are assigned, but the runtime +logic already follows server-replicated weather state, provider wind speed, and +day/night state. Rain, wind, and storm volumes fade independently so weather can +move from clear coastal ambience to rain, cold wind, or storm without changing +gameplay code. + +Final assets should remain grounded and local to Ground Zero: coastal wind, +distant surf, light rain on brush, heavier storm gusts, and subtle night/day +texture. Weather audio must support the non-ray-traced default investor build +and headless multiplayer server builds by keeping actual playback client-side. diff --git a/Docs/TechnicalDesignDocument.md b/Docs/TechnicalDesignDocument.md index a01693b..f988458 100644 --- a/Docs/TechnicalDesignDocument.md +++ b/Docs/TechnicalDesignDocument.md @@ -316,6 +316,8 @@ because the controller is silent until loops are assigned; placeholder or final audio can be added by setting the exposed sound properties on the placed controller or a Blueprint child. +Weather sound requirements are tracked in `Docs/Audio/WeatherSounds.md`. + Player movement audio starts with native footstep placeholders on `AAgrarianGameCharacter`. The character owns a spatialized `FootstepAudioComponent` plus assignable walk, sprint, crouch, and prone sound diff --git a/Scripts/verify_weather_sounds.py b/Scripts/verify_weather_sounds.py new file mode 100644 index 0000000..0200aff --- /dev/null +++ b/Scripts/verify_weather_sounds.py @@ -0,0 +1,60 @@ +#!/usr/bin/env python3 +"""Verify MVP weather sound hooks are documented and map-placed.""" + +from pathlib import Path + + +ROOT = Path(__file__).resolve().parents[1] +DOC = ROOT / "Docs" / "Audio" / "WeatherSounds.md" +AUDIO_H = ROOT / "Source" / "AgrarianGame" / "AgrarianWeatherAudioController.h" +AUDIO_CPP = ROOT / "Source" / "AgrarianGame" / "AgrarianWeatherAudioController.cpp" +MAP_SETUP = ROOT / "Scripts" / "setup_ground_zero_demo_map.py" +ROADMAP = ROOT / "AGRARIAN_DEVELOPMENT_ROADMAP.md" + +REQUIRED = { + DOC: [ + "`AAgrarianWeatherAudioController`", + "`RainLoopSound`", + "`WindLoopSound`", + "`StormLoopSound`", + "`ClearAmbientSound`", + "`BiomeAmbientLoopSound`", + "provider wind speed", + "day/night state", + ], + AUDIO_H: [ + "TObjectPtr RainLoopSound;", + "TObjectPtr WindLoopSound;", + "TObjectPtr StormLoopSound;", + ], + AUDIO_CPP: [ + "GameState->Weather", + "GameState->ActiveWeatherInputs.WindSpeedKmh", + "ApplyComponentVolume(RainAudio, CurrentRainVolume);", + "ApplyComponentVolume(WindAudio, CurrentWindVolume);", + "ApplyComponentVolume(StormAudio, CurrentStormVolume);", + ], + MAP_SETUP: [ + "AGR_DemoWeatherAudioController", + "unreal.AgrarianWeatherAudioController", + ], + ROADMAP: [ + "[x] Add weather sounds.", + ], +} + + +def main() -> None: + missing = [] + for path, snippets in REQUIRED.items(): + text = path.read_text(encoding="utf-8") + for snippet in snippets: + if snippet not in text: + missing.append(f"{path.relative_to(ROOT)} missing {snippet!r}") + if missing: + raise SystemExit("FAILED: " + "; ".join(missing)) + print("OK: weather sound hooks are documented and map-placed.") + + +if __name__ == "__main__": + main()