# AGENTS.md — AudioSystem (OCES)

## Project

Unity 2022.3.62f3, URP, C#. Custom audio & haptic middleware under the namespace **OCES**.

## Architecture

```
Assets/Scripts/OCES/
├── Audio/
│   ├── Generated/       ← AUTO-GENERATED, do not edit
│   └── HandWritten/     ← hand-written runtime code
│       ├── LongAudio/   ← music & ambience systems
│       └── Editor/      ← AudioImportTool
├── Haptic/
│   ├── Generated/       ← AUTO-GENERATED, do not edit
│   └── Handwritten/     ← hand-written runtime code
├── Metronome.cs         ← demo/test helper
├── PlaySoundBind.cs     ← UI bind helpers
├── SetStateBind.cs
└── SetPropertyBind.cs
```

## Generated code boundary — critical

Everything under `Assets/Scripts/OCES/*/Generated/` is auto-generated from Excel data tables. Every file has the header comment: `auto generated by tools(注意:千万不要手动修改本文件)`.

- **Generated files**: data classes (`AudioObject`, `AudioGroup`, `MusicSegment`, etc.), config loader tables, `AudioConsts.cs` (Cues IDs, NameDictionaries, Parameters enums), `FileManager.cs`
- **If you need to change data**: edit the source `.xlsx` in `DataTables/`, then re-run the ExcelTool to regenerate `.bytes` configs + C# classes
- **Partial class pattern**: `AudioObject.cs` and config classes exist in both `Generated/` (serialization) and `HandWritten/` (runtime logic like switch resolution). Add runtime methods to the `HandWritten/` partial, never to `Generated/`

## Data pipeline

```
DataTables/*.xlsx   (gitignored, source of truth for game data)
       ↓  ExcelTool
Resources/AudioData/*.bytes   ← binary configs loaded at runtime via AudioConfigLoader
Resources/HapticData/*.bytes
       ↓  also generates
Assets/Scripts/OCES/*/Generated/*.cs   ← C# data classes + AudioConsts
```

`Tools/` and `DataTables/` are gitignored. The Excel tool and source spreadsheets live outside version control.

## Duplicate types — intentional

`FileManager` and `IBinarySerializable` exist independently in both `OCES.Audio` and `OCES.Haptic` namespaces. They are not shared. When adding haptic code, use `OCES.Haptic.IBinarySerializable`; for audio, use `OCES.Audio.IBinarySerializable`.

## AudioMixer group paths

The mixer hierarchy is hard-referenced by path strings. These must match exactly:

- `Master/Regular/SFX` — default SFX group
- `Master/Regular/Voice` — voice group
- `Master/SFX_Accent` — accent SFX
- `Master/Regular/Music` — music pool
- `Master/Regular/SFX/Ambience` — ambience pool

## API conventions

- `AudioSystem.Instance.Play(uint audioId)` is the primary API. Use `Cues.Play_*` constants from `AudioConsts.cs`.
- `Play(string)` is `[Obsolete]` — string-based lookup is ambiguous for shared/duplicate names.
- `AudioSystem.Instance.SetState<TEnum>(TEnum state)` drives music/ambience switching. New state enums must be registered via `StateGroupRegistry.Register<TEnum>(typeId)` in `Parameters.EnumIds.RegisterAllGameState()`.
- `HapticSystem.Instance.Play(uint hapticId)` is typically called automatically by SfxSystem when an `AudioObject.Haptic` field is set; direct calls are for debugging only.

## Editor tools

- **AudioImportTool**: batch-applies import settings (sample rate, compression, load type) to all audio files in `Resources/Audios/`. Menu: `Tools/Audio/Apply Audio Import Settings`. CLI entry: `OCES.Audio.AudioImportTool.RunCli`.
- **ExcelTool** (commented out menu item): `Assets/Editor/ExcelTool.cs` — invokes external shell script to regenerate data from Excel. Currently disabled (`[UnityEditor.MenuItem]` is commented out).

## Third-party dependencies

- **DOTween** (`Assets/Scripts/DG/DOTween/`) — used for low-pass filter tweening and cross-fades
- **NiceVibrations / Lofelt** (`Assets/Scripts/Lofelt/NiceVibrations/`) — haptic feedback with native plugins per platform (`Assets/Plugins/{Android,iOS,macOS,Windows}/`)

## Audio file naming conventions

- `au_sfx_*` — sound effects
- `au_bgm_*` — background music
- `au_music_*` — music segments (used by the interactive music system)
- `au_stream.ogg` — streaming audio

## Resources paths

- Audio clips: `Resources/Audios/` (loaded via `Resources.Load<AudioClip>`)
- Audio configs: `Resources/AudioData/` (loaded via `AudioConfigLoader.Load<T>`)
- Haptic configs: `Resources/HapticData/`
- Haptic clips: `Resources/Haptics/` (`.haptic` files for advanced haptic playback)
