Added AudioEmitter helper method for multi-channel emitter setup
This commit is contained in:
Родитель
e4e316998f
Коммит
cd9a386518
|
@ -317,7 +317,7 @@ void DynamicSoundEffectInstance::SetPan(float pan)
|
|||
}
|
||||
|
||||
|
||||
void DynamicSoundEffectInstance::Apply3D(const AudioListener& listener, const AudioEmitter& emitter, bool rhcoords)
|
||||
void DynamicSoundEffectInstance::Apply3D(const X3DAUDIO_LISTENER& listener, const X3DAUDIO_EMITTER& emitter, bool rhcoords)
|
||||
{
|
||||
pImpl->mBase.Apply3D(listener, emitter, rhcoords);
|
||||
}
|
||||
|
@ -381,6 +381,12 @@ int DynamicSoundEffectInstance::GetPendingBufferCount() const noexcept
|
|||
}
|
||||
|
||||
|
||||
unsigned int DynamicSoundEffectInstance::GetChannelCount() const noexcept
|
||||
{
|
||||
return pImpl->mBase.GetChannelCount();
|
||||
}
|
||||
|
||||
|
||||
const WAVEFORMATEX* DynamicSoundEffectInstance::GetFormat() const noexcept
|
||||
{
|
||||
return pImpl->GetFormat();
|
||||
|
|
|
@ -505,7 +505,11 @@ uint32_t DirectX::GetDefaultChannelMask(int channels) noexcept
|
|||
|
||||
|
||||
_Use_decl_annotations_
|
||||
void DirectX::CreateIntegerPCM(WAVEFORMATEX* wfx, int sampleRate, int channels, int sampleBits) noexcept
|
||||
void DirectX::CreateIntegerPCM(
|
||||
WAVEFORMATEX* wfx,
|
||||
int sampleRate,
|
||||
int channels,
|
||||
int sampleBits) noexcept
|
||||
{
|
||||
int blockAlign = channels * sampleBits / 8;
|
||||
|
||||
|
@ -522,7 +526,10 @@ void DirectX::CreateIntegerPCM(WAVEFORMATEX* wfx, int sampleRate, int channels,
|
|||
|
||||
|
||||
_Use_decl_annotations_
|
||||
void DirectX::CreateFloatPCM(WAVEFORMATEX* wfx, int sampleRate, int channels) noexcept
|
||||
void DirectX::CreateFloatPCM(
|
||||
WAVEFORMATEX* wfx,
|
||||
int sampleRate,
|
||||
int channels) noexcept
|
||||
{
|
||||
int blockAlign = channels * 4;
|
||||
|
||||
|
@ -539,7 +546,12 @@ void DirectX::CreateFloatPCM(WAVEFORMATEX* wfx, int sampleRate, int channels) no
|
|||
|
||||
|
||||
_Use_decl_annotations_
|
||||
void DirectX::CreateADPCM(WAVEFORMATEX* wfx, size_t wfxSize, int sampleRate, int channels, int samplesPerBlock) noexcept(false)
|
||||
void DirectX::CreateADPCM(
|
||||
WAVEFORMATEX* wfx,
|
||||
size_t wfxSize,
|
||||
int sampleRate,
|
||||
int channels,
|
||||
int samplesPerBlock) noexcept(false)
|
||||
{
|
||||
if (wfxSize < (sizeof(WAVEFORMATEX) + 32 /*MSADPCM_FORMAT_EXTRA_BYTES*/))
|
||||
{
|
||||
|
@ -578,7 +590,13 @@ void DirectX::CreateADPCM(WAVEFORMATEX* wfx, size_t wfxSize, int sampleRate, int
|
|||
|
||||
#ifdef DIRECTX_ENABLE_XWMA
|
||||
_Use_decl_annotations_
|
||||
void DirectX::CreateXWMA(WAVEFORMATEX* wfx, int sampleRate, int channels, int blockAlign, int avgBytes, bool wma3) noexcept
|
||||
void DirectX::CreateXWMA(
|
||||
WAVEFORMATEX* wfx,
|
||||
int sampleRate,
|
||||
int channels,
|
||||
int blockAlign,
|
||||
int avgBytes,
|
||||
bool wma3) noexcept
|
||||
{
|
||||
wfx->wFormatTag = static_cast<WORD>((wma3) ? WAVE_FORMAT_WMAUDIO3 : WAVE_FORMAT_WMAUDIO2);
|
||||
wfx->nChannels = static_cast<WORD>(channels);
|
||||
|
@ -595,7 +613,14 @@ void DirectX::CreateXWMA(WAVEFORMATEX* wfx, int sampleRate, int channels, int bl
|
|||
|
||||
#ifdef DIRECTX_ENABLE_XMA2
|
||||
_Use_decl_annotations_
|
||||
void DirectX::CreateXMA2(WAVEFORMATEX* wfx, size_t wfxSize, int sampleRate, int channels, int bytesPerBlock, int blockCount, int samplesEncoded) noexcept(false)
|
||||
void DirectX::CreateXMA2(
|
||||
WAVEFORMATEX* wfx,
|
||||
size_t wfxSize,
|
||||
int sampleRate,
|
||||
int channels,
|
||||
int bytesPerBlock,
|
||||
int blockCount,
|
||||
int samplesEncoded) noexcept(false)
|
||||
{
|
||||
if (wfxSize < sizeof(XMA2WAVEFORMATEX))
|
||||
{
|
||||
|
@ -709,7 +734,7 @@ void SoundEffectInstanceBase::SetPan(float pan)
|
|||
}
|
||||
|
||||
|
||||
void SoundEffectInstanceBase::Apply3D(const AudioListener& listener, const AudioEmitter& emitter, bool rhcoords)
|
||||
void SoundEffectInstanceBase::Apply3D(const X3DAUDIO_LISTENER& listener, const X3DAUDIO_EMITTER& emitter, bool rhcoords)
|
||||
{
|
||||
if (!voice)
|
||||
return;
|
||||
|
@ -796,3 +821,73 @@ void SoundEffectInstanceBase::Apply3D(const AudioListener& listener, const Audio
|
|||
}
|
||||
|
||||
|
||||
//======================================================================================
|
||||
// AudioEmitter helper
|
||||
//======================================================================================
|
||||
|
||||
namespace
|
||||
{
|
||||
// **Note these constants came from xact3d3.h in the legacy DirectX SDK**
|
||||
//
|
||||
// Supported speaker positions, represented as azimuth angles.
|
||||
//
|
||||
// Here's a picture of the azimuth angles for the 8 cardinal points,
|
||||
// seen from above. The emitter's base position is at the origin 0.
|
||||
//
|
||||
// FRONT
|
||||
// | 0 <-- azimuth
|
||||
// |
|
||||
// 7pi/4 \ | / pi/4
|
||||
// \ | /
|
||||
// LEFT \|/ RIGHT
|
||||
// 3pi/2-------0-------pi/2
|
||||
// /|\
|
||||
// / | \
|
||||
// 5pi/4 / | \ 3pi/4
|
||||
// |
|
||||
// | pi
|
||||
// BACK
|
||||
//
|
||||
|
||||
constexpr float LEFT_AZIMUTH = 3 * X3DAUDIO_PI / 2;
|
||||
constexpr float RIGHT_AZIMUTH = X3DAUDIO_PI / 2;
|
||||
constexpr float FRONT_LEFT_AZIMUTH = 7 * X3DAUDIO_PI / 4;
|
||||
constexpr float FRONT_RIGHT_AZIMUTH = X3DAUDIO_PI / 4;
|
||||
constexpr float FRONT_CENTER_AZIMUTH = 0.0f;
|
||||
constexpr float LOW_FREQUENCY_AZIMUTH = X3DAUDIO_2PI;
|
||||
constexpr float BACK_LEFT_AZIMUTH = 5 * X3DAUDIO_PI / 4;
|
||||
constexpr float BACK_RIGHT_AZIMUTH = 3 * X3DAUDIO_PI / 4;
|
||||
constexpr float BACK_CENTER_AZIMUTH = X3DAUDIO_PI;
|
||||
|
||||
constexpr float c_channelAzimuths[9][8] =
|
||||
{
|
||||
/* 0 */ { 0.f, 0.f, 0.f, 0.f, 0.f, 0.f, 0.f, 0.f },
|
||||
/* 1 */ { 0.f, 0.f, 0.f, 0.f, 0.f, 0.f, 0.f, 0.f },
|
||||
/* 2 */ { FRONT_LEFT_AZIMUTH, FRONT_RIGHT_AZIMUTH, 0.f, 0.f, 0.f, 0.f, 0.f, 0.f },
|
||||
/* 2.1 */ { FRONT_LEFT_AZIMUTH, FRONT_RIGHT_AZIMUTH, LOW_FREQUENCY_AZIMUTH, 0.f, 0.f, 0.f, 0.f, 0.f },
|
||||
/* 4.0 */ { FRONT_LEFT_AZIMUTH, FRONT_RIGHT_AZIMUTH, BACK_LEFT_AZIMUTH, BACK_RIGHT_AZIMUTH, 0.f, 0.f, 0.f, 0.f },
|
||||
/* 4.1 */ { FRONT_LEFT_AZIMUTH, FRONT_RIGHT_AZIMUTH, LOW_FREQUENCY_AZIMUTH, BACK_LEFT_AZIMUTH, BACK_RIGHT_AZIMUTH, 0.f, 0.f, 0.f },
|
||||
/* 5.1 */ { FRONT_LEFT_AZIMUTH, FRONT_RIGHT_AZIMUTH, FRONT_CENTER_AZIMUTH, LOW_FREQUENCY_AZIMUTH, BACK_LEFT_AZIMUTH, BACK_RIGHT_AZIMUTH, 0.f, 0.f },
|
||||
/* 6.1 */ { FRONT_LEFT_AZIMUTH, FRONT_RIGHT_AZIMUTH, FRONT_CENTER_AZIMUTH, LOW_FREQUENCY_AZIMUTH, BACK_LEFT_AZIMUTH, BACK_RIGHT_AZIMUTH, BACK_CENTER_AZIMUTH, 0.f },
|
||||
/* 7.1 */ { FRONT_LEFT_AZIMUTH, FRONT_RIGHT_AZIMUTH, FRONT_CENTER_AZIMUTH, LOW_FREQUENCY_AZIMUTH, BACK_LEFT_AZIMUTH, BACK_RIGHT_AZIMUTH, LEFT_AZIMUTH, RIGHT_AZIMUTH }
|
||||
};
|
||||
}
|
||||
|
||||
void AudioEmitter::EnableDefaultMultiChannel(unsigned int channels, float radius)
|
||||
{
|
||||
if (channels > XAUDIO2_MAX_AUDIO_CHANNELS)
|
||||
throw std::invalid_argument("Invalid channel count");
|
||||
|
||||
ChannelCount = channels;
|
||||
ChannelRadius = radius;
|
||||
pChannelAzimuths = EmitterAzimuths;
|
||||
|
||||
if (channels <= 8)
|
||||
{
|
||||
memcpy(EmitterAzimuths, &c_channelAzimuths[channels][0], sizeof(float) * 8);
|
||||
}
|
||||
else
|
||||
{
|
||||
memset(EmitterAzimuths, 0, sizeof(float) * size_t(channels));
|
||||
}
|
||||
}
|
||||
|
|
|
@ -63,14 +63,19 @@ namespace DirectX
|
|||
|
||||
|
||||
// Helpers for creating various wave format structures
|
||||
void CreateIntegerPCM(_Out_ WAVEFORMATEX* wfx, int sampleRate, int channels, int sampleBits) noexcept;
|
||||
void CreateFloatPCM(_Out_ WAVEFORMATEX* wfx, int sampleRate, int channels) noexcept;
|
||||
void CreateADPCM(_Out_writes_bytes_(wfxSize) WAVEFORMATEX* wfx, size_t wfxSize, int sampleRate, int channels, int samplesPerBlock) noexcept(false);
|
||||
void CreateIntegerPCM(_Out_ WAVEFORMATEX* wfx,
|
||||
int sampleRate, int channels, int sampleBits) noexcept;
|
||||
void CreateFloatPCM(_Out_ WAVEFORMATEX* wfx,
|
||||
int sampleRate, int channels) noexcept;
|
||||
void CreateADPCM(_Out_writes_bytes_(wfxSize) WAVEFORMATEX* wfx, size_t wfxSize,
|
||||
int sampleRate, int channels, int samplesPerBlock) noexcept(false);
|
||||
#ifdef DIRECTX_ENABLE_XWMA
|
||||
void CreateXWMA(_Out_ WAVEFORMATEX* wfx, int sampleRate, int channels, int blockAlign, int avgBytes, bool wma3) noexcept;
|
||||
void CreateXWMA(_Out_ WAVEFORMATEX* wfx,
|
||||
int sampleRate, int channels, int blockAlign, int avgBytes, bool wma3) noexcept;
|
||||
#endif
|
||||
#ifdef DIRECTX_ENABLE_XMA2
|
||||
void CreateXMA2(_Out_writes_bytes_(wfxSize) WAVEFORMATEX* wfx, size_t wfxSize, int sampleRate, int channels, int bytesPerBlock, int blockCount, int samplesEncoded) noexcept(false);
|
||||
void CreateXMA2(_Out_writes_bytes_(wfxSize) WAVEFORMATEX* wfx, size_t wfxSize,
|
||||
int sampleRate, int channels, int bytesPerBlock, int blockCount, int samplesEncoded) noexcept(false);
|
||||
#endif
|
||||
|
||||
// Helper for computing pan volume matrix
|
||||
|
@ -208,7 +213,7 @@ namespace DirectX
|
|||
}
|
||||
}
|
||||
|
||||
void Pause() noexcept
|
||||
void Pause() noexcept
|
||||
{
|
||||
if (voice && state == PLAYING)
|
||||
{
|
||||
|
@ -264,7 +269,7 @@ namespace DirectX
|
|||
|
||||
void SetPan(float pan);
|
||||
|
||||
void Apply3D(const AudioListener& listener, const AudioEmitter& emitter, bool rhcoords);
|
||||
void Apply3D(const X3DAUDIO_LISTENER& listener, const X3DAUDIO_EMITTER& emitter, bool rhcoords);
|
||||
|
||||
SoundState GetState(bool autostop) noexcept
|
||||
{
|
||||
|
@ -294,6 +299,11 @@ namespace DirectX
|
|||
return static_cast<int>(xstate.BuffersQueued);
|
||||
}
|
||||
|
||||
unsigned int GetChannelCount() const noexcept
|
||||
{
|
||||
return mDSPSettings.SrcChannelCount;
|
||||
}
|
||||
|
||||
void OnCriticalError() noexcept
|
||||
{
|
||||
if (voice)
|
||||
|
|
|
@ -316,7 +316,7 @@ void SoundEffectInstance::SetPan(float pan)
|
|||
}
|
||||
|
||||
|
||||
void SoundEffectInstance::Apply3D(const AudioListener& listener, const AudioEmitter& emitter, bool rhcoords)
|
||||
void SoundEffectInstance::Apply3D(const X3DAUDIO_LISTENER& listener, const X3DAUDIO_EMITTER& emitter, bool rhcoords)
|
||||
{
|
||||
pImpl->mBase.Apply3D(listener, emitter, rhcoords);
|
||||
}
|
||||
|
@ -335,6 +335,12 @@ SoundState SoundEffectInstance::GetState() noexcept
|
|||
}
|
||||
|
||||
|
||||
unsigned int SoundEffectInstance::GetChannelCount() const noexcept
|
||||
{
|
||||
return pImpl->mBase.GetChannelCount();
|
||||
}
|
||||
|
||||
|
||||
IVoiceNotify* SoundEffectInstance::GetVoiceNotify() const noexcept
|
||||
{
|
||||
return pImpl.get();
|
||||
|
|
|
@ -823,7 +823,7 @@ void SoundStreamInstance::SetPan(float pan)
|
|||
}
|
||||
|
||||
|
||||
void SoundStreamInstance::Apply3D(const AudioListener& listener, const AudioEmitter& emitter, bool rhcoords)
|
||||
void SoundStreamInstance::Apply3D(const X3DAUDIO_LISTENER& listener, const X3DAUDIO_EMITTER& emitter, bool rhcoords)
|
||||
{
|
||||
pImpl->mBase.Apply3D(listener, emitter, rhcoords);
|
||||
}
|
||||
|
@ -847,6 +847,12 @@ SoundState SoundStreamInstance::GetState() noexcept
|
|||
}
|
||||
|
||||
|
||||
unsigned int SoundStreamInstance::GetChannelCount() const noexcept
|
||||
{
|
||||
return pImpl->mBase.GetChannelCount();
|
||||
}
|
||||
|
||||
|
||||
IVoiceNotify* SoundStreamInstance::GetVoiceNotify() const noexcept
|
||||
{
|
||||
return pImpl.get();
|
||||
|
|
|
@ -155,7 +155,7 @@ namespace
|
|||
|
||||
case TAG_WMA:
|
||||
{
|
||||
static const uint32_t aWMABlockAlign[] =
|
||||
static const uint32_t aWMABlockAlign[17] =
|
||||
{
|
||||
929,
|
||||
1487,
|
||||
|
@ -177,7 +177,7 @@ namespace
|
|||
};
|
||||
|
||||
uint32_t dwBlockAlignIndex = wBlockAlign & 0x1F;
|
||||
if (dwBlockAlignIndex < std::size(aWMABlockAlign))
|
||||
if (dwBlockAlignIndex < 17)
|
||||
return aWMABlockAlign[dwBlockAlignIndex];
|
||||
}
|
||||
break;
|
||||
|
@ -205,7 +205,7 @@ namespace
|
|||
|
||||
case TAG_WMA:
|
||||
{
|
||||
static const uint32_t aWMAAvgBytesPerSec[] =
|
||||
static const uint32_t aWMAAvgBytesPerSec[7] =
|
||||
{
|
||||
12000,
|
||||
24000,
|
||||
|
@ -218,7 +218,7 @@ namespace
|
|||
// bitrate = entry * 8
|
||||
|
||||
uint32_t dwBytesPerSecIndex = wBlockAlign >> 5;
|
||||
if (dwBytesPerSecIndex < std::size(aWMAAvgBytesPerSec))
|
||||
if (dwBytesPerSecIndex < 7)
|
||||
return aWMAAvgBytesPerSec[dwBytesPerSecIndex];
|
||||
}
|
||||
break;
|
||||
|
|
14
Inc/Audio.h
14
Inc/Audio.h
|
@ -599,6 +599,8 @@ namespace DirectX
|
|||
XMStoreFloat3(reinterpret_cast<XMFLOAT3*>(&Position), newPos);
|
||||
}
|
||||
}
|
||||
|
||||
void __cdecl EnableDefaultMultiChannel(unsigned int channels, float radius = 1.f);
|
||||
};
|
||||
|
||||
|
||||
|
@ -623,12 +625,14 @@ namespace DirectX
|
|||
void __cdecl SetPitch(float pitch);
|
||||
void __cdecl SetPan(float pan);
|
||||
|
||||
void __cdecl Apply3D(const AudioListener& listener, const AudioEmitter& emitter, bool rhcoords = true);
|
||||
void __cdecl Apply3D(const X3DAUDIO_LISTENER& listener, const X3DAUDIO_EMITTER& emitter, bool rhcoords = true);
|
||||
|
||||
bool __cdecl IsLooped() const noexcept;
|
||||
|
||||
SoundState __cdecl GetState() noexcept;
|
||||
|
||||
unsigned int __cdecl GetChannelCount() const noexcept;
|
||||
|
||||
IVoiceNotify* __cdecl GetVoiceNotify() const noexcept;
|
||||
|
||||
private:
|
||||
|
@ -667,12 +671,14 @@ namespace DirectX
|
|||
void __cdecl SetPitch(float pitch);
|
||||
void __cdecl SetPan(float pan);
|
||||
|
||||
void __cdecl Apply3D(const AudioListener& listener, const AudioEmitter& emitter, bool rhcoords = true);
|
||||
void __cdecl Apply3D(const X3DAUDIO_LISTENER& listener, const X3DAUDIO_EMITTER& emitter, bool rhcoords = true);
|
||||
|
||||
bool __cdecl IsLooped() const noexcept;
|
||||
|
||||
SoundState __cdecl GetState() noexcept;
|
||||
|
||||
unsigned int __cdecl GetChannelCount() const noexcept;
|
||||
|
||||
IVoiceNotify* __cdecl GetVoiceNotify() const noexcept;
|
||||
|
||||
private:
|
||||
|
@ -713,7 +719,7 @@ namespace DirectX
|
|||
void __cdecl SetPitch(float pitch);
|
||||
void __cdecl SetPan(float pan);
|
||||
|
||||
void __cdecl Apply3D(const AudioListener& listener, const AudioEmitter& emitter, bool rhcoords = true);
|
||||
void __cdecl Apply3D(const X3DAUDIO_LISTENER& listener, const X3DAUDIO_EMITTER& emitter, bool rhcoords = true);
|
||||
|
||||
void __cdecl SubmitBuffer(_In_reads_bytes_(audioBytes) const uint8_t* pAudioData, size_t audioBytes);
|
||||
void __cdecl SubmitBuffer(_In_reads_bytes_(audioBytes) const uint8_t* pAudioData, uint32_t offset, size_t audioBytes);
|
||||
|
@ -733,6 +739,8 @@ namespace DirectX
|
|||
|
||||
const WAVEFORMATEX* __cdecl GetFormat() const noexcept;
|
||||
|
||||
unsigned int __cdecl GetChannelCount() const noexcept;
|
||||
|
||||
private:
|
||||
// Private implementation.
|
||||
class Impl;
|
||||
|
|
Загрузка…
Ссылка в новой задаче