# Audio Service

## Purpose
- Owns the shared runtime audio service used by gameplay and UI systems.
- Provides a separate one-shot SFX path with a designer-friendly catalog.
- Keeps global audio playback and configuration outside feature-specific code.

## Public Entry Points
- `IAudioService -> AudioService` — full playback API: `Play(in AudioRequest)`, `Stop(handle, fadeOutSeconds)`, channel pause/volume, snapshot weight blending, async clip loading.
- `ISfxPlayer -> SfxPlayer` — lightweight one-shot/loop entry keyed by `SfxId`; resolves clips and channels from `SfxCatalogSO`.
- `SfxCatalogSO` (Core static data) — ScriptableObject of `SfxId -> (AudioClip, AudioChannel, volume, pitch, loop)` entries.
- `SfxId` (Core enum) — current entries: `WiperUp`, `WiperDown`, `BlinkerTick`, `GearShift`, `ReverseBeep`.
- `AudioChannel` (Core enum) — `Sfx`, `VehicleSfx`, `AISfx`, `Engine`, `PassengerChatter`, `Music`, `Ambience`, `Weather`, `BGM`, `UI`, `Radio`. Each maps to a mixer group on `AudioService`’s mixer.
- `AudioRequest`, `AudioHandle`, `AudioPlayMode` — Core DTOs used by both `IAudioService` and `ISfxPlayer`.

## Registration
- `AudioService` is serialized on `RootLifetimeScope` and registered as `IAudioService` via `RegisterComponent`.
- `ISfxPlayer -> SfxPlayer` is registered as `Singleton` on `RootLifetimeScope` with the serialized `SfxCatalogSO` parameter.

## Mixer Channels
- Channels are addressed by enum; pause/volume changes go through `IAudioService.SetChannelPaused` / `SetChannelVolume`.
- New gameplay sounds should pick the most specific channel (e.g. `AudioChannel.Radio` for the in-game music player, `AudioChannel.Ambience` for environment loops/thunder, `AudioChannel.Weather` for rain/storm visuals).
- Snapshot blending (`SetSnapshotWeights`, `TransitionSnapshotWeights`) is available for scene-level mixes.

## Dependencies
- Registered from the App/root scope and consumed through Core audio contracts.
- Should stay infrastructure-only and not branch on feature-specific rules.

## Extension Notes
- Put shared playback helpers here; leave feature-owned mix rules in the feature when they are not broadly reusable.
- When adding a new SFX, register the `SfxId` in Core, add a `SfxCatalogSO` entry, and call `ISfxPlayer.Play` from the feature rather than constructing `AudioRequest`s by hand.
- If a new audio capability must cross assemblies, expose it through Core instead of direct concrete references.
