Files
XCEngine/docs/used/XCEngine音频模块架构设计.md
ssdfasd 16e2065c6c Unified logging: Replace LogSystem with EditorConsoleSink
- Created EditorConsoleSink (implements ILogSink interface)
- EditorConsoleSink stores logs in memory buffer (max 1000 entries)
- Added to Debug::Logger in Application::Initialize()
- ConsolePanel now reads from EditorConsoleSink via static GetInstance()
- Removed separate LogSystem singleton
- Removed editor/src/Core/LogEntry.h (no longer needed)

Now Editor and Engine share the same Debug::Logger, with ConsolePanel
displaying logs via EditorConsoleSink.
2026-03-25 16:13:02 +08:00

1641 lines
47 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# XCEngine - 音频模块架构设计文档
> **借鉴 Unity 音频架构概念设计**
---
## 音频流程图
```
┌─────────────────────────────────────────────────────────────────────────────────────┐
│ 音频流程 │
└─────────────────────────────────────────────────────────────────────────────────────┘
┌─────────────┐ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐
│ AudioSource │────▶│ Spatialize │────▶│ EffectChain │────▶│ Output │
│ 声源组件 │ │ 3D空间化 │ │ 效果链 │ │ 音频输出 │
└─────────────┘ └─────────────┘ └─────────────┘ └─────────────┘
│ │ │ │
▼ ▼ ▼ ▼
┌─────────────┐ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐
│ AudioClip │ │ HRTF │ │ FFT │ │ AudioBackend│
│ 音频资源 │ │ 头部相关传输 │ │ 傅里叶变换 │ │ 音频后端 │
└─────────────┘ └─────────────┘ └─────────────┘ └─────────────┘
│ │
▼ ▼
┌─────────────┐ ┌─────────────┐
│ Reverbation │ │ WASAPI │
│ 混响效果 │ │ OpenAL │
└─────────────┘ │ CoreAudio │
└─────────────┘
流程说明:
1. AudioSourceComponent 负责播放 AudioClip管理播放状态
2. AudioListenerComponent 接收声音计算3D空间化参数
3. Spatialize 根据 Listener 位置计算 panning、distance attenuation、doppler
4. EffectChain 处理 DSP 效果链FFT、Reverb、EQ等
5. AudioBackend 抽象层负责与具体音频API交互
6. 最终输出到音频设备
```
```
┌─────────────────────────────────────────────────────────────────────────────────────┐
│ AudioBackend 抽象层架构 │
└─────────────────────────────────────────────────────────────────────────────────────┘
┌─────────────────┐
│ AudioSystem │ 音频系统入口
└────────┬────────┘
┌───────────────────────┼───────────────────────┐
│ │ │
┌──────▼──────┐ ┌──────▼──────┐ ┌──────▼──────┐
│ WASAPIBackend│ │OpenALBackend │ │CoreAudioBackend│
└──────┬──────┘ └──────┬──────┘ └──────┬──────┘
│ │ │
└───────────────────────┼───────────────────────┘
┌────────▼────────┐
│ IAudioBackend │ 抽象音频后端接口
└────────┬────────┘
┌──────────────────────────────────┼──────────────────────────────────┐
│ │ │ │ │ │ │
┌────▼────┐ ┌───▼────┐ ┌────▼┐ ┌──▼────┐ ┌───▼───┐ ┌───▼────┐ ┌──▼────┐
│AudioBuffer│ │AudioBus │ │Fence│ │Mixer │ │Effect │ │HRTF │ │Resampler│
│ 音频缓冲 │ │ 音频总线 │ │围栏 │ │ 混音器 │ │ 效果 │ │ 空间化 │ │ 重采样 │
└──────────┘ └────────┘ └─────┘ └────────┘ └───────┘ └────────┘ └────────┘
```
> **重要声明**:本架构借鉴 Unity 音频系统的核心概念与设计模式,包括:
> - `AudioSourceComponent` / `AudioListenerComponent` - 声源与监听器组件
> - `AudioClip` / `AudioMixer` - 音频资源与混音器
> - `EffectChain` - 效果器链
> - `Spatializer` - 3D空间化处理器
> - `AudioBackend` - 音频后端抽象
>
> **注**Unity底层C++音频架构未公开本设计基于公开API概念与通用音频引擎模式实现。
>
> 版本: 1.0
> 日期: 2026-03-20
> 目标: 构建专业级游戏引擎音频系统
---
## 第一章 核心类型定义
### 1.1 音频基础类型
```cpp
namespace XCEngine {
namespace Audio {
// ============================================
// 前置类型定义
// ============================================
enum class AudioResourceType {
AudioClip,
AudioMixer,
AudioBank
};
enum class AudioLoadState {
Unloaded,
Loading,
Loaded,
Failed
};
enum class AudioFormat {
Unknown,
WAV,
OGG,
MP3,
FLAC,
AAC
};
enum class SpeakerMode {
Mono,
Stereo,
Surround51,
Surround71,
Surround51_2,
Surround71_2
};
enum class AudioChannel {
FrontLeft,
FrontRight,
FrontCenter,
LFE,
BackLeft,
BackRight,
SideLeft,
SideRight
};
struct AudioConfig {
uint32_t sampleRate = 48000;
uint16_t channels = 2;
uint16_t bitsPerSample = 16;
SpeakerMode speakerMode = SpeakerMode::Stereo;
uint32_t bufferSize = 8192;
uint32_t bufferCount = 2;
};
// ============================================
// 3D 音频参数
// ============================================
struct Audio3DParams {
float dopplerLevel = 1.0f;
float speedOfSound = 343.0f;
float minDistance = 1.0f;
float maxDistance = 500.0f;
float panLevel = 1.0f;
float spread = 0.0f;
float reverbZoneMix = 1.0f;
};
enum class PanMode {
Pan3D,
Pan2D
};
enum class VolumeSource {
Direct,
Path Occlusion,
Transmission,
Obstruction
};
// ============================================
// 音频缓冲区描述
// ============================================
struct AudioBufferDesc {
uint32_t size = 0;
uint32_t channels = 2;
uint32_t sampleRate = 48000;
uint16_t bitsPerSample = 16;
bool isFloat = false;
bool isCompressed = false;
AudioFormat format = AudioFormat::Unknown;
};
// ============================================
// 播放状态
// ============================================
enum class PlayState {
Stopped,
Playing,
Paused
};
enum class StopMode {
Immediate,
AllowFadeOut
};
// ============================================
// 空间化参数
// ============================================
struct SpatializerParams {
float azimuth = 0.0f;
float elevation = 0.0f;
float distance = 0.0f;
float volumeDb = 0.0f;
float panCartesianX = 0.0f;
float panCartesianY = 0.0f;
bool isOccluded = false;
bool isObstructed = false;
};
} // namespace Audio
} // namespace XCEngine
```
### 1.2 IAudioResource 基类
```cpp
namespace XCEngine {
namespace Audio {
class IAudioResource {
public:
virtual ~IAudioResource() = default;
virtual void SetName(const String& name) { m_name = name; }
virtual const String& GetName() const { return m_name; }
virtual AudioResourceType GetType() const = 0;
virtual AudioLoadState GetLoadState() const { return m_loadState; }
virtual bool IsValid() const { return m_loadState == AudioLoadState::Loaded; }
virtual void Load() = 0;
virtual void Unload() = 0;
virtual int GetRefCount() const { return m_refCount.load(); }
virtual void AddRef() { m_refCount.fetch_add(1); }
virtual void Release() {
if (m_refCount.fetch_sub(1) == 1) {
delete this;
}
}
protected:
IAudioResource() : m_loadState(AudioLoadState::Unloaded), m_memoryUsage(0) {}
String m_name;
AudioLoadState m_loadState;
uint64_t m_memoryUsage;
std::atomic<int32_t> m_refCount{1};
};
} // namespace Audio
} // namespace XCEngine
```
---
## 第二章 音频资源
### 2.1 AudioClip
```cpp
namespace XCEngine {
namespace Audio {
class AudioClip : public IAudioResource {
public:
AudioClip();
AudioClip(const String& filePath);
~AudioClip();
AudioResourceType GetType() const override { return AudioResourceType::AudioClip; }
void Load() override;
void Unload() override;
// 音频数据访问
const int16_t* GetData() const { return m_data.data(); }
int16_t* GetData() { return m_data.data(); }
const float* GetDataFloat() const { return m_dataFloat.data(); }
float* GetDataFloat() { return m_dataFloat.data(); }
uint32_t GetDataSize() const { return m_dataSize; }
uint32_t GetSampleCount() const { return m_sampleCount; }
uint32_t GetChannelCount() const { return m_channels; }
uint32_t GetSampleRate() const { return m_sampleRate; }
uint16_t GetBitsPerSample() const { return m_bitsPerSample; }
float GetDuration() const { return m_duration; }
AudioFormat GetFormat() const { return m_format; }
bool IsCompressed() const { return m_isCompressed; }
bool IsStreamed() const { return m_isStreamed; }
// 频谱数据查询
bool HasFrequencyData() const { return m_hasFrequencyData; }
const float* GetFrequencyData() const { return m_frequencyData.data(); }
uint32_t GetFrequencyDataSize() const { return m_frequencyData.size(); }
// 资源路径
void SetResourcePath(const String& path) { m_resourcePath = path; }
const String& GetResourcePath() const { return m_resourcePath; }
private:
void ProcessWavFile();
void DecodeCompressedData();
void GenerateFrequencyData();
void ConvertToFloat();
private:
std::vector<int16_t> m_data;
std::vector<float> m_dataFloat;
std::vector<float> m_frequencyData;
uint32_t m_dataSize = 0;
uint32_t m_sampleCount = 0;
uint16_t m_channels = 2;
uint32_t m_sampleRate = 48000;
uint16_t m_bitsPerSample = 16;
float m_duration = 0.0f;
AudioFormat m_format = AudioFormat::Unknown;
bool m_isCompressed = false;
bool m_isStreamed = false;
bool m_hasFrequencyData = false;
String m_resourcePath;
};
} // namespace Audio
} // namespace XCEngine
```
### 2.2 AudioMixer
```cpp
namespace XCEngine {
namespace Audio {
class AudioMixer : public IAudioResource {
public:
AudioMixer();
~AudioMixer();
AudioResourceType GetType() const override { return AudioResourceType::AudioMixer; }
void Load() override;
void Unload() override;
// 混音器参数
float GetVolume() const { return m_volume; }
void SetVolume(float volume, float fadeTime = 0.0f);
bool IsMuted() const { return m_isMuted; }
void SetMuted(bool muted) { m_isMuted = muted; }
// 子混音器组
class MixerGroup* GetGroup(const String& name);
class MixerGroup* CreateGroup(const String& name);
void RemoveGroup(const String& name);
const std::map<String, std::unique_ptr<MixerGroup>>& GetGroups() const { return m_groups; }
// 输出混音器
void SetOutputMixer(AudioMixer* mixer);
AudioMixer* GetOutputMixer() const { return m_outputMixer; }
private:
float m_volume = 1.0f;
bool m_isMuted = false;
std::map<String, std::unique_ptr<MixerGroup>> m_groups;
AudioMixer* m_outputMixer = nullptr;
};
class MixerGroup {
public:
MixerGroup(const String& name);
~MixerGroup();
const String& GetName() const { return m_name; }
float GetVolume() const { return m_volume; }
void SetVolume(float volume, float fadeTime = 0.0f);
bool IsMuted() const { return m_isMuted; }
void SetMuted(bool muted) { m_isMuted = muted; }
bool IsSoloed() const { return m_isSoloed; }
void SetSoloed(bool soloed) { m_isSoloed = soloed; }
// 效果器
void AddEffect(IAudioEffect* effect, size_t index = SIZE_MAX);
void RemoveEffect(IAudioEffect* effect);
void SetEffectEnabled(IAudioEffect* effect, bool enabled);
const std::vector<IAudioEffect*>& GetEffects() const { return m_effects; }
// 音频处理
void Process(float* buffer, uint32_t sampleCount, uint32_t channels);
private:
String m_name;
float m_volume = 1.0f;
bool m_isMuted = false;
bool m_isSoloed = false;
std::vector<IAudioEffect*> m_effects;
};
} // namespace Audio
} // namespace XCEngine
```
### 2.3 AudioBank (用于分段加载)
```cpp
namespace XCEngine {
namespace Audio {
class AudioBank : public IAudioResource {
public:
AudioBank();
~AudioBank();
AudioResourceType GetType() const override { return AudioResourceType::AudioBank; }
void Load() override;
void Unload() override;
// 事件触发
void TriggerEvent(const String& eventName);
void TriggerEvent(int eventId);
// 获取嵌入的音频片段
AudioClip* GetClip(const String& name);
AudioClip* GetClip(int id);
const std::map<String, AudioClip*>& GetAllClips() const { return m_clips; }
private:
std::map<String, AudioClip*> m_clips;
std::map<String, int> m_eventMap;
};
} // namespace Audio
} // namespace XCEngine
```
---
## 第三章 DSP 效果系统
### 3.1 IAudioEffect 接口
```cpp
namespace XCEngine {
namespace Audio {
class IAudioEffect {
public:
virtual ~IAudioEffect() = default;
virtual const char* GetName() const = 0;
virtual void Process(float* buffer, uint32_t sampleCount, uint32_t channels) = 0;
virtual void SetEnabled(bool enabled) { m_enabled = enabled; }
virtual bool IsEnabled() const { return m_enabled; }
virtual void SetParameter(const char* name, float value) = 0;
virtual float GetParameter(const char* name) const = 0;
virtual size_t GetParameterCount() const = 0;
virtual const char* GetParameterName(size_t index) const = 0;
protected:
bool m_enabled = true;
};
} // namespace Audio
} // namespace XCEngine
```
### 3.2 FFTFilter (频谱分析)
```cpp
namespace XCEngine {
namespace Audio {
class FFTFilter : public IAudioEffect {
public:
FFTFilter(size_t fftSize = 1024);
~FFTFilter();
const char* GetName() const override { return "FFTFilter"; }
void Process(float* buffer, uint32_t sampleCount, uint32_t channels) override;
void SetEnabled(bool enabled) override;
void SetFFTSize(size_t size);
size_t GetFFTSize() const { return m_fftSize; }
void SetParameter(const char* name, float value) override;
float GetParameter(const char* name) const override;
size_t GetParameterCount() const override;
const char* GetParameterName(size_t index) const override;
// 频谱数据访问
const float* GetMagnitudeSpectrum() const { return m_magnitudeSpectrum.data(); }
const float* GetPhaseSpectrum() const { return m_phaseSpectrum.data(); }
size_t GetSpectrumSize() const { return m_spectrumSize; }
// 设置时域核(用于滤波)
void SetTimeDomainKernel(const std::vector<float>& kernel);
void AddTimeDomainKernel(const std::vector<float>& kernel);
// 频域核
void SetFreqDomainKernel(const std::vector<float>& kernel);
void AddFreqDomainKernel(const std::vector<float>& kernel);
private:
void Init();
void ComplexVectorProduct(const std::vector<kiss_fft_cpx>& inputA,
const std::vector<kiss_fft_cpx>& inputB,
std::vector<kiss_fft_cpx>* result);
void InverseFFTScaling(std::vector<float>* signal);
private:
size_t m_fftSize;
size_t m_spectrumSize;
bool m_analysisMode = true;
std::vector<float> m_magnitudeSpectrum;
std::vector<float> m_phaseSpectrum;
std::vector<float> m_filterState;
std::vector<float> m_window;
bool m_kernelDefined = false;
std::vector<kiss_fft_scalar> m_kernelTimeDomainBuffer;
std::vector<kiss_fft_cpx> m_kernelFreqDomainBuffer;
int m_bufferSelector = 0;
std::vector<std::vector<kiss_fft_scalar>> m_signalTimeDomainBuffer;
std::vector<std::vector<kiss_fft_cpx>> m_signalFreqDomainBuffer;
std::vector<kiss_fft_cpx> m_filteredFreqDomainBuffer;
kiss_fftr_cfg m_forwardFFT = nullptr;
kiss_fftr_cfg m_inverseFFT = nullptr;
};
} // namespace Audio
} // namespace XCEngine
```
### 3.3 Reverbation (混响)
```cpp
namespace XCEngine {
namespace Audio {
class Reverbation : public IAudioEffect {
public:
Reverbation(int blockSize = 1024, int samplingRate = 48000, float reverbTime = 2.0f);
~Reverbation();
const char* GetName() const override { return "Reverbation"; }
void Process(float* buffer, uint32_t sampleCount, uint32_t channels) override;
void SetParameter(const char* name, float value) override;
float GetParameter(const char* name) const override;
size_t GetParameterCount() const override;
const char* GetParameterName(size_t index) const override;
// 混响参数
void SetReverbTime(float seconds);
float GetReverbTime() const { return m_reverbTime; }
void SetDecay(float decay) { m_decay = decay; }
float GetDecay() const { return m_decay; }
void SetPreDelay(float ms);
float GetPreDelay() const { return m_preDelayMs; }
void SetHighFreqDamping(float ratio);
float GetHighFreqDamping() const { return m_highFreqDamping; }
// 脉冲响应
const std::vector<float>& GetImpulseResponseLeft() const { return m_impulseResponseLeft; }
const std::vector<float>& GetImpulseResponseRight() const { return m_impulseResponseRight; }
float GetQuietPeriod() const { return m_quietPeriodSec; }
private:
void RenderImpulseResponse(int blockSize, int samplingRate, float reverbTime);
static float FloatRand();
private:
int m_blockSize;
float m_reverbTime = 2.0f;
float m_decay = 0.7f;
float m_preDelayMs = 20.0f;
float m_highFreqDamping = 0.5f;
std::vector<float> m_impulseResponseLeft;
std::vector<float> m_impulseResponseRight;
float m_quietPeriodSec;
std::unique_ptr<FFTFilter> m_leftReverbFilter;
std::unique_ptr<FFTFilter> m_rightReverbFilter;
std::vector<float> m_reverbInput;
std::vector<float> m_reverbOutputLeft;
std::vector<float> m_reverbOutputRight;
int m_reverbOutputReadPos = 0;
};
} // namespace Audio
} // namespace XCEngine
```
### 3.4 EQ (均衡器)
```cpp
namespace XCEngine {
namespace Audio {
class Equalizer : public IAudioEffect {
public:
Equalizer();
~Equalizer();
const char* GetName() const override { return "Equalizer"; }
void Process(float* buffer, uint32_t sampleCount, uint32_t channels) override;
void SetParameter(const char* name, float value) override;
float GetParameter(const char* name) const override;
size_t GetParameterCount() const override;
const char* GetParameterName(size_t index) const override;
// 频段控制
enum class Band {
LowPass,
HighPass,
BandPass,
Notch,
LowShelf,
HighShelf,
Peaking
};
void SetBand(size_t index, Band type, float frequency, float gainDb, float Q);
void SetBandEnabled(size_t index, bool enabled);
struct BandParams {
Band type = Band::Peaking;
float frequency = 1000.0f;
float gainDb = 0.0f;
float Q = 1.0f;
bool enabled = true;
};
const BandParams& GetBand(size_t index) const { return m_bands[index]; }
private:
void UpdateCoefficients(size_t index);
void ProcessBand(float* buffer, uint32_t sampleCount, size_t bandIndex);
private:
static constexpr size_t MaxBands = 10;
std::array<BandParams, MaxBands> m_bands;
std::array<std::array<float, 5>, MaxBands> m_coefficients;
std::vector<float> m_x1, m_x2, m_y1, m_y2;
};
} // namespace Audio
} // namespace XCEngine
```
### 3.5 Dynamics (动态效果器)
```cpp
namespace XCEngine {
namespace Audio {
class Compressor : public IAudioEffect {
public:
Compressor();
~Compressor();
const char* GetName() const override { return "Compressor"; }
void Process(float* buffer, uint32_t sampleCount, uint32_t channels) override;
void SetParameter(const char* name, float value) override;
float GetParameter(const char* name) const override;
size_t GetParameterCount() const override;
const char* GetParameterName(size_t index) const override;
void SetThreshold(float db);
float GetThreshold() const { return m_thresholdDb; }
void SetRatio(float ratio);
float GetRatio() const { return m_ratio; }
void SetAttack(float ms);
float GetAttack() const { return m_attackMs; }
void SetRelease(float ms);
float GetRelease() const { return m_releaseMs; }
float GetGainReduction() const { return m_gainReduction; }
private:
float m_thresholdDb = -20.0f;
float m_ratio = 4.0f;
float m_attackMs = 10.0f;
float m_releaseMs = 100.0f;
float m_gainReduction = 0.0f;
float m_envelope = 0.0f;
};
class Limiter : public IAudioEffect {
public:
Limiter();
~Limiter();
const char* GetName() const override { return "Limiter"; }
void Process(float* buffer, uint32_t sampleCount, uint32_t channels) override;
void SetParameter(const char* name, float value) override;
float GetParameter(const char* name) const override;
size_t GetParameterCount() const override;
const char* GetParameterName(size_t index) const override;
void SetCeiling(float db);
float GetCeiling() const { return m_ceilingDb; }
void SetRelease(float ms);
float GetRelease() const { return m_releaseMs; }
private:
float m_ceilingDb = -0.3f;
float m_releaseMs = 50.0f;
float m_envelope = 0.0f;
};
} // namespace Audio
} // namespace XCEngine
```
---
## 第四章 3D 空间音频
### 4.1 SpatializerParams 空间化参数
```cpp
namespace XCEngine {
namespace Audio {
struct SpatializerParams {
Vector3 listenerPosition;
Quaternion listenerRotation;
Vector3 listenerVelocity;
Vector3 sourcePosition;
Vector3 sourceVelocity;
Quaternion sourceRotation;
Audio3DParams params;
float GetDistanceAttenuation() const;
float GetPan() const;
float GetDopplerShift() const;
};
```
### 4.2 HRTF 空间化
```cpp
namespace XCEngine {
namespace Audio {
class HRTF {
public:
HRTF();
~HRTF();
// 方向设置
void SetDirection(int elevation, int azimuth);
void GetDirection(int& elevation, int& azimuth);
// HRTF 脉冲响应
void GetLeftEarTimeHRTF(std::vector<float>& data);
void GetLeftEarFreqHRTF(std::vector<float>& data);
void GetRightEarTimeHRTF(std::vector<float>& data);
void GetRightEarFreqHRTF(std::vector<float>& data);
// 空间化处理
void Process(const float* input, float* outputLeft, float* outputRight,
size_t sampleCount, size_t channels);
// 淡入淡出处理
void ApplyFadeWindow(const std::vector<float>& blockLast,
const std::vector<float>& blockNext,
std::vector<float>* fadeResult);
// 重采样
void Resample(const float* input, float* output, size_t inputSize,
size_t outputSize, size_t channels);
private:
void BuildReacherTree();
int SearchNearestIndex(int elevation, int azimuth);
double CalculateSphereDistance(int elev1, int azim1, int elev2, int azim2);
private:
int m_realAzimuth = 0;
int m_realElevation = 0;
int m_azimuth = 0;
int m_elevation = 0;
bool m_isSwapLeftRight = false;
int m_directionIndex = 0;
using ResampledHRTFT = std::vector<float>;
using ResampledHRTFPairT = std::pair<ResampledHRTFT, ResampledHRTFT>;
std::vector<ResampledHRTFPairT> m_hrtfResampledTimeDomain;
std::vector<ResampledHRTFPairT> m_hrtfResampledFreqDomain;
std::map<int, std::pair<std::vector<int>, std::vector<int>>> m_hrtfDirections;
std::unique_ptr<FFTFilter> m_filter;
std::unique_ptr<FFTFilter> m_hrtfFilterLeft;
std::unique_ptr<FFTFilter> m_hrtfFilterRight;
std::vector<float> m_fadeWindow;
};
} // namespace Audio
} // namespace XCEngine
```
### 4.3 DopplerEffect 多普勒效应
```cpp
namespace XCEngine {
namespace Audio {
class DopplerEffect {
public:
DopplerEffect();
~DopplerEffect();
void SetSpeedOfSound(float metersPerSecond);
float GetSpeedOfSound() const { return m_speedOfSound; }
void SetDopplerLevel(float level);
float GetDopplerLevel() const { return m_dopplerLevel; }
float CalculatePitchShift(const Vector3& sourceVelocity,
const Vector3& listenerVelocity,
const Vector3& sourceToListener);
private:
float m_speedOfSound = 343.0f;
float m_dopplerLevel = 1.0f;
};
} // namespace Audio
} // namespace XCEngine
```
### 4.4 OcclusionSystem 遮蔽系统
```cpp
namespace XCEngine {
namespace Audio {
class OcclusionSystem {
public:
OcclusionSystem();
~OcclusionSystem();
// 遮蔽计算
float CalculateOcclusion(const Vector3& sourcePos, const Vector3& listenerPos,
const std::vector<Vector3>& obstaclePositions);
float CalculateObstruction(const Vector3& sourcePos, const Vector3& listenerPos,
const Vector3& obstaclePos);
// 遮蔽参数
void SetOcclusionHighFreqAbsorption(float value);
float GetOcclusionHighFreqAbsorption() const { return m_occlusionHighFreqAbsorb; }
void SetObstructionHighFreqDamping(float value);
float GetObstructionHighFreqDamping() const { return m_obstructionHighFreqDamp; }
private:
float m_occlusionHighFreqAbsorb = 0.5f;
float m_obstructionHighFreqDamp = 0.5f;
};
} // namespace Audio
} // namespace XCEngine
```
---
## 第五章 音频后端抽象层
### 5.1 IAudioBackend 接口
```cpp
namespace XCEngine {
namespace Audio {
class IAudioBackend {
public:
virtual ~IAudioBackend() = default;
// 初始化与销毁
virtual bool Initialize(const AudioConfig& config) = 0;
virtual void Shutdown() = 0;
// 设备查询
virtual String GetDeviceName() const = 0;
virtual void GetAvailableDevices(std::vector<String>& devices) = 0;
virtual bool SetDevice(const String& deviceName) = 0;
// 混音器控制
virtual float GetMasterVolume() const = 0;
virtual void SetMasterVolume(float volume) = 0;
virtual bool IsMuted() const = 0;
virtual void SetMuted(bool muted) = 0;
// 播放控制
virtual void Start() = 0;
virtual void Stop() = 0;
virtual void Suspend() = 0;
virtual void Resume() = 0;
// 音频处理
virtual void ProcessAudio(float* buffer, uint32_t bufferSize,
uint32_t channels, uint32_t sampleRate) = 0;
// 状态查询
virtual bool IsRunning() const = 0;
virtual AudioConfig GetConfig() const = 0;
};
} // namespace Audio
} // namespace XCEngine
```
### 5.2 WASAPI 后端
```cpp
namespace XCEngine {
namespace Audio {
namespace WASAPI {
class WASAPIBackend : public IAudioBackend {
public:
WASAPIBackend();
~WASAPIBackend() override;
bool Initialize(const AudioConfig& config) override;
void Shutdown() override;
String GetDeviceName() const override;
void GetAvailableDevices(std::vector<String>& devices) override;
bool SetDevice(const String& deviceName) override;
float GetMasterVolume() const override;
void SetMasterVolume(float volume) override;
bool IsMuted() const override;
void SetMuted(bool muted) override;
void Start() override;
void Stop() override;
void Suspend() override;
void Resume() override;
void ProcessAudio(float* buffer, uint32_t bufferSize,
uint32_t channels, uint32_t sampleRate) override;
bool IsRunning() const override { return m_isRunning; }
AudioConfig GetConfig() const override { return m_config; }
private:
MMRESULT InitDevice();
MMRESULT InitClient();
MMRESULT InitBuffer();
static DWORD WINAPI AudioThreadProc(LPVOID lpParameter);
void AudioThread();
void OnAudioCallback(HWAVEOUT hwo, UINT uMsg, DWORD_PTR dwInstance,
DWORD_PTR dwParam1, DWORD_PTR dwParam2);
static void CALLBACK StaticAudioCallback(HWAVEOUT hwo, UINT uMsg,
DWORD_PTR dwInstance,
DWORD_PTR dwParam1, DWORD_PTR dwParam2);
private:
bool m_isRunning = false;
std::thread m_audioThread;
AudioConfig m_config;
WAVEFORMATEX m_waveFormat = {};
HWAVEOUT m_hWaveOut = nullptr;
HANDLE m_hEvent = nullptr;
std::vector<float> m_mixBuffer;
uint32_t m_mixBufferSize = 0;
std::vector<WAVEOUTCAPS> m_waveOutCaps;
String m_deviceName;
IAudioEffect* m_masterEffect = nullptr;
};
} // namespace WASAPI
} // namespace Audio
} // namespace XCEngine
```
### 5.3 OpenAL 后端
```cpp
namespace XCEngine {
namespace Audio {
namespace OpenAL {
class OpenALBackend : public IAudioBackend {
public:
OpenALBackend();
~OpenALBackend() override;
bool Initialize(const AudioConfig& config) override;
void Shutdown() override;
String GetDeviceName() const override;
void GetAvailableDevices(std::vector<String>& devices) override;
bool SetDevice(const String& deviceName) override;
float GetMasterVolume() const override;
void SetMasterVolume(float volume) override;
bool IsMuted() const override;
void SetMuted(bool muted) override;
void Start() override;
void Stop() override;
void Suspend() override;
void Resume() override;
void ProcessAudio(float* buffer, uint32_t bufferSize,
uint32_t channels, uint32_t sampleRate) override;
bool IsRunning() const override { return m_isRunning; }
AudioConfig GetConfig() const override { return m_config; }
private:
bool m_isRunning = false;
AudioConfig m_config;
ALCdevice* m_device = nullptr;
ALCcontext* m_context = nullptr;
ALuint m_source = 0;
ALuint m_buffers[2];
std::vector<float> m_mixBuffer;
};
} // namespace OpenAL
} // namespace Audio
} // namespace XCEngine
```
---
## 第六章 音频系统核心
### 6.1 AudioSystem
```cpp
namespace XCEngine {
namespace Audio {
class AudioSystem {
public:
static AudioSystem& Get();
void Initialize(const AudioConfig& config);
void Shutdown();
void Update(float deltaTime);
// 后端控制
void SetBackend(std::unique_ptr<IAudioBackend> backend);
IAudioBackend* GetBackend() const { return m_backend.get(); }
// 设备控制
String GetCurrentDevice() const;
void SetDevice(const String& deviceName);
void GetAvailableDevices(std::vector<String>& devices);
// 全局混音控制
float GetMasterVolume() const;
void SetMasterVolume(float volume);
bool IsMuted() const;
void SetMuted(bool muted);
// 音频处理
void ProcessAudio(float* buffer, uint32_t sampleCount, uint32_t channels);
// 资源管理
AudioClip* LoadAudioClip(const String& filePath);
void UnloadAudioClip(AudioClip* clip);
AudioMixer* CreateMixer(const String& name);
void DestroyMixer(AudioMixer* mixer);
// 空间化
void SetListenerTransform(const Vector3& position, const Quaternion& rotation);
void SetListenerVelocity(const Vector3& velocity);
const Vector3& GetListenerPosition() const { return m_listenerPosition; }
const Quaternion& GetListenerRotation() const { return m_listenerRotation; }
const Vector3& GetListenerVelocity() const { return m_listenerVelocity; }
// 统计信息
struct Stats {
uint32_t activeSources;
uint32_t totalSources;
uint64_t memoryUsage;
float cpuUsage;
};
const Stats& GetStats() const { return m_stats; }
private:
AudioSystem() = default;
~AudioSystem() = default;
AudioSystem(const AudioSystem&) = delete;
AudioSystem& operator=(const AudioSystem&) = delete;
void ProcessSource(AudioSourceComponent* source);
void ApplyGlobalEffects(float* buffer, uint32_t sampleCount, uint32_t channels);
private:
std::unique_ptr<IAudioBackend> m_backend;
Vector3 m_listenerPosition = Vector3::Zero();
Quaternion m_listenerRotation = Quaternion::Identity();
Vector3 m_listenerVelocity = Vector3::Zero();
std::vector<std::unique_ptr<AudioClip>> m_loadedClips;
std::map<String, std::unique_ptr<AudioMixer>> m_mixers;
std::vector<AudioSourceComponent*> m_activeSources;
Stats m_stats = {};
float m_deltaTime = 0.0f;
};
} // namespace Audio
} // namespace XCEngine
```
### 6.2 AudioSourceComponent
```cpp
namespace XCEngine {
namespace Components {
class AudioSourceComponent : public Component {
public:
AudioSourceComponent();
~AudioSourceComponent();
// 播放控制
void Play();
void Pause();
void Stop(StopMode mode = StopMode::Immediate);
bool IsPlaying() const { return m_playState == Audio::PlayState::Playing; }
bool IsPaused() const { return m_playState == Audio::PlayState::Paused; }
// 音频剪辑
void SetClip(Audio::AudioClip* clip);
Audio::AudioClip* GetClip() const { return m_clip; }
// 播放参数
void SetVolume(float volume);
float GetVolume() const { return m_volume; }
void SetPitch(float pitch);
float GetPitch() const { return m_pitch; }
void SetPan(float pan);
float GetPan() const { return m_pan; }
// 循环
void SetLooping(bool loop);
bool IsLooping() const { return m_isLooping; }
// 3D 空间化
void SetSpatialize(bool spatialize);
bool IsSpatialize() const { return m_spatialize; }
void Set3DParams(const Audio::Audio3DParams& params);
const Audio::Audio3DParams& Get3DParams() const { return m_3DParams; }
void SetDopplerLevel(float level);
float GetDopplerLevel() const { return m_3DParams.dopplerLevel; }
void SetSpread(float spread);
float GetSpread() const { return m_3DParams.spread; }
void SetReverbZoneMix(float mix);
float GetReverbZoneMix() const { return m_3DParams.reverbZoneMix; }
// 混音器
void SetOutputMixer(Audio::AudioMixer* mixer);
Audio::AudioMixer* GetOutputMixer() const { return m_outputMixer; }
// 播放位置
void SetTime(float seconds);
float GetTime() const;
float GetDuration() const;
// 能量检测
float GetEnergy() const { return m_energy; }
void StartEnergyDetect();
void StopEnergyDetect();
bool IsEnergyDetecting() const { return m_isEnergyDetecting; }
// Component 虚函数
void Update(float deltaTime) override;
void OnEnable() override;
void OnDisable() override;
void OnDestroy() override;
private:
void Apply3DAttenuation();
void ProcessEffects(float* buffer, uint32_t sampleCount);
void UpdateEnergy(const float* buffer, uint32_t sampleCount);
private:
Audio::AudioClip* m_clip = nullptr;
Audio::AudioMixer* m_outputMixer = nullptr;
PlayState m_playState = PlayState::Stopped;
bool m_isLooping = false;
float m_volume = 1.0f;
float m_pitch = 1.0f;
float m_pan = 0.0f;
bool m_spatialize = true;
Audio::Audio3DParams m_3DParams;
// 播放状态
uint64_t m_samplePosition = 0;
double m_lastingTime = 0.0;
// 能量检测
bool m_isEnergyDetecting = false;
float m_energy = 0.0f;
float m_maxEnergy = 5.0f;
std::deque<float> m_energyHistory;
// 效果链
std::vector<Audio::IAudioEffect*> m_effects;
std::unique_ptr<Audio::HRTF> m_hrtf;
std::unique_ptr<Audio::DopplerEffect> m_doppler;
// 输出缓冲
static constexpr size_t BufferSize = 8192;
std::vector<float> m_outputBuffer;
};
} // namespace Components
} // namespace XCEngine
```
### 6.3 AudioListenerComponent
```cpp
namespace XCEngine {
namespace Components {
class AudioListenerComponent : public Component {
public:
AudioListenerComponent();
~AudioListenerComponent();
// 能量检测
float GetEnergy() const { return m_energy; }
const float* GetFrequencyData() const { return m_frequencyData.data(); }
size_t GetFrequencyDataSize() const { return m_frequencyData.size(); }
// 全局参数
void SetMasterVolume(float volume);
float GetMasterVolume() const { return m_masterVolume; }
void SetMute(bool mute);
bool IsMute() const { return m_mute; }
// 空间化参数
void SetDopplerLevel(float level);
float GetDopplerLevel() const { return m_dopplerLevel; }
void SetSpeedOfSound(float metersPerSecond);
float GetSpeedOfSound() const { return m_speedOfSound; }
// 混响
void SetReverbLevel(float level);
float GetReverbLevel() const { return m_reverbLevel; }
void SetReverb(Audio::AudioMixer* reverb);
Audio::AudioMixer* GetReverb() const { return m_reverb; }
// Component 虚函数
void Update(float deltaTime) override;
private:
float m_masterVolume = 1.0f;
bool m_mute = false;
float m_dopplerLevel = 1.0f;
float m_speedOfSound = 343.0f;
float m_reverbLevel = 1.0f;
Audio::AudioMixer* m_reverb = nullptr;
float m_energy = 0.0f;
std::vector<float> m_frequencyData;
};
} // namespace Components
} // namespace XCEngine
```
---
## 第七章 事件系统
### 7.1 AudioEvent
```cpp
namespace XCEngine {
namespace Audio {
class AudioEvent {
public:
AudioEvent() = default;
AudioEvent(const String& name) : m_name(name) {}
using Callback = std::function<void()>;
using FloatCallback = std::function<void(float)>;
uint64_t Subscribe(Callback callback);
uint64_t Subscribe(FloatCallback callback, float param);
void Unsubscribe(uint64_t id);
void ProcessUnsubscribes();
void Invoke() const;
void Invoke(float param) const;
void Clear();
const String& GetName() const { return m_name; }
void SetName(const String& name) { m_name = name; }
private:
struct ListenerBase {
virtual ~ListenerBase() = default;
virtual void Call() = 0;
virtual void CallFloat(float) = 0;
};
template<typename Func>
struct Listener : ListenerBase {
Listener(Func&& f) : func(std::move(f)) {}
void Call() override { func(); }
void CallFloat(float) override {
if constexpr (std::is_invocable_v<Func, float>) {
func(0.0f);
} else {
func();
}
}
Func func;
};
String m_name;
std::vector<std::pair<uint64_t, std::unique_ptr<ListenerBase>>> m_listeners;
std::vector<uint64_t> m_pendingUnsubscribes;
uint64_t m_nextId = 0;
};
} // namespace Audio
} // namespace XCEngine
```
### 7.2 AudioEventSystem
```cpp
namespace XCEngine {
namespace Audio {
class AudioEventSystem {
public:
static AudioEventSystem& Get();
void Initialize();
void Shutdown();
// 事件创建
AudioEvent* CreateEvent(const String& name);
AudioEvent* GetEvent(const String& name);
AudioEvent* GetEvent(uint64_t id);
void DestroyEvent(const String& name);
void DestroyEvent(uint64_t id);
// 触发事件
void TriggerEvent(const String& name);
void TriggerEvent(uint64_t id);
void TriggerEvent(const String& name, float param);
void TriggerEvent(uint64_t id, float param);
// 订阅
uint64_t Subscribe(const String& eventName, AudioEvent::Callback callback);
uint64_t Subscribe(const String& eventName, AudioEvent::FloatCallback callback, float param);
// 状态
bool HasEvent(const String& name) const;
bool HasEvent(uint64_t id) const;
size_t GetEventCount() const { return m_events.size(); }
private:
AudioEventSystem() = default;
~AudioEventSystem() = default;
std::map<String, std::unique_ptr<AudioEvent>> m_events;
std::map<uint64_t, AudioEvent*> m_idToEvent;
uint64_t m_nextEventId = 0;
};
} // namespace Audio
} // namespace XCEngine
```
---
## 第八章 资源管理集成
### 8.1 AudioClipLoader
```cpp
namespace XCEngine {
namespace Resources {
class AudioClipLoader : public IResourceLoader {
public:
AudioClipLoader();
~AudioClipLoader() override;
bool CanLoad(const String& extension) const override;
IResource* Load(const String& filePath) override;
bool LoadAsync(const String& filePath, std::function<void(IResource*)> callback) override;
void Unload(IResource* resource) override;
// 获取支持的文件格式
static const std::vector<String>& GetSupportedExtensions();
private:
static std::vector<String> s_supportedExtensions;
};
} // namespace Resources
} // namespace XCEngine
```
### 8.2 ResourceManager 集成
```cpp
namespace XCEngine {
namespace Resources {
// 在 ResourceManager 中添加音频相关接口
template<>
class ResourceHandle<Audio::AudioClip> {
public:
ResourceHandle() = default;
explicit ResourceHandle(Audio::AudioClip* resource);
Audio::AudioClip* Get() const { return m_resource; }
Audio::AudioClip* operator->() const { return m_resource; }
explicit operator bool() const { return m_resource != nullptr; }
private:
Audio::AudioClip* m_resource = nullptr;
};
} // namespace Resources
} // namespace XCEngine
```
---
## 第九章 目录结构
```
XCEngine/
├── engine/ # 引擎核心库
│ ├── include/XCEngine/
│ │ ├── Audio/ # 音频模块
│ │ │ ├── AudioSystem.h # 音频系统入口
│ │ │ ├── AudioConfig.h # 配置结构
│ │ │ ├── AudioTypes.h # 基础类型定义
│ │ │ ├── IAudioBackend.h # 后端抽象接口
│ │ │ ├── AudioBackendFactory.h # 后端工厂
│ │ │ │
│ │ │ ├── AudioClip.h # 音频剪辑资源
│ │ │ ├── AudioMixer.h # 混音器
│ │ │ ├── AudioBank.h # 音频银行
│ │ │ │
│ │ │ ├── IAudioEffect.h # 效果器接口
│ │ │ ├── FFTFilter.h # FFT频谱分析
│ │ │ ├── Reverbation.h # 混响效果
│ │ │ ├── Equalizer.h # 均衡器
│ │ │ ├── Compressor.h # 压缩器
│ │ │ ├── Limiter.h # 限制器
│ │ │ ├── DopplerEffect.h # 多普勒效应
│ │ │ ├── OcclusionSystem.h # 遮蔽系统
│ │ │ │
│ │ │ ├── Spatializer.h # 空间化处理
│ │ │ ├── HRTF.h # HRTF实现
│ │ │ │
│ │ │ ├── AudioEvent.h # 音频事件
│ │ │ ├── AudioEventSystem.h # 事件系统
│ │ │ │
│ │ │ ├── WASAPI/
│ │ │ │ └── WASAPIBackend.h # WASAPI后端
│ │ │ └── OpenAL/
│ │ │ └── OpenALBackend.h # OpenAL后端
│ │ │ │
│ │ │ └── XCEngineAudio.h # 主头文件
│ │ │
│ │ └── Components/
│ │ ├── AudioSourceComponent.h # 声源组件
│ │ └── AudioListenerComponent.h # 监听器组件
│ │
│ └── src/Audio/
│ ├── AudioSystem.cpp
│ ├── AudioClip.cpp
│ ├── AudioMixer.cpp
│ ├── FFTFilter.cpp
│ ├── Reverbation.cpp
│ ├── Equalizer.cpp
│ ├── HRTF.cpp
│ ├── DopplerEffect.cpp
│ ├── OcclusionSystem.cpp
│ ├── AudioEventSystem.cpp
│ ├── WASAPI/
│ │ └── WASAPIBackend.cpp
│ └── OpenAL/
│ └── OpenALBackend.cpp
├── mvs/ # 示例应用
│ └── Music fluctuations/ # 音频示例(参考)
│ ├── source/
│ │ ├── audio/ # 基础音频
│ │ ├── audio3d/ # 3D音频
│ │ ├── kissfft/ # FFT库
│ │ └── libsamplerate/ # 重采样库
│ └── res/ # 音频资源
└── tests/Audio/ # 音频模块测试
├── AudioSystemTest.cpp
├── AudioClipTest.cpp
├── SpatializerTest.cpp
└── HRTFTest.cpp
```
---
## 附录:实现优先级
### 第一阶段 - 基础音频
1. AudioSystem 核心框架
2. AudioClip 资源加载WAV格式
3. AudioSourceComponent 播放控制
4. AudioListenerComponent 监听器
5. WASAPI 后端实现
### 第二阶段 - 3D 空间音频
1. HRTF 空间化
2. DopplerEffect 多普勒效应
3. OcclusionSystem 遮蔽系统
4. 距离衰减
### 第三阶段 - 效果系统
1. FFTFilter 频谱分析
2. Reverbation 混响
3. Equalizer 均衡器
4. Compressor/Limiter 动态效果
5. 效果链系统
### 第四阶段 - 混音与事件
1. AudioMixer 混音器
2. AudioEvent 事件系统
3. AudioBank 分段加载
4. OpenAL 后端实现
### 第五阶段 - 优化与扩展
1. 资源异步加载
2. 性能优化
3. profiler 集成
4. 更多音频格式支持