diff --git a/panda/src/audio/audio_load_st.cxx b/panda/src/audio/audio_load_st.cxx index 62750726c7..0c3f5ff899 100644 --- a/panda/src/audio/audio_load_st.cxx +++ b/panda/src/audio/audio_load_st.cxx @@ -397,18 +397,23 @@ void AudioLoadSt(AudioTraits::SampleClass** sample, #ifdef AUDIO_USE_WIN32 +#include "audio_win_traits.h" + void AudioDestroySt(AudioTraits::SampleClass* sample) { delete sample; } void AudioLoadSt(AudioTraits::SampleClass** sample, AudioTraits::PlayerClass** player, - AudioTraits::DeleteSampleFunc** destroy, Filename) { - audio_cat->warning() << "win32 doesn't support reading raw data yet" - << endl; - *sample = (AudioTraits::SampleClass*)0L; - *player = (AudioTraits::PlayerClass*)0L; - *destroy = AudioDestroySt; + AudioTraits::DeleteSampleFunc** destroy, Filename filename) { + unsigned char* buf; + unsigned long len; + read_file(filename, &buf, len); + if (buf != (unsigned char*)0L) { + *sample = WinSample::load_raw(buf, len); + *player = WinPlayer::get_instance(); + *destroy = AudioDestroySt; + } } #else /* AUDIO_USE_WIN32 */ diff --git a/panda/src/audio/audio_load_wav.cxx b/panda/src/audio/audio_load_wav.cxx index a6fb2cc208..5192bbf019 100644 --- a/panda/src/audio/audio_load_wav.cxx +++ b/panda/src/audio/audio_load_wav.cxx @@ -78,6 +78,8 @@ void AudioDestroyWav(AudioTraits::SampleClass* sample) { void AudioLoadWav(AudioTraits::SampleClass** sample, AudioTraits::PlayerClass** player, AudioTraits::DeleteSampleFunc** destroy, Filename) { + audio_cat->error() << "Linux driver does not natively support WAV." + << " Try the 'st' loader." << endl; *sample = new NullSample(); *player = new NullPlayer(); *destroy = AudioDestroyWav; diff --git a/panda/src/audio/audio_win_traits.cxx b/panda/src/audio/audio_win_traits.cxx index 6e33c401fa..b1fe7ccc78 100644 --- a/panda/src/audio/audio_win_traits.cxx +++ b/panda/src/audio/audio_win_traits.cxx @@ -87,7 +87,7 @@ static void initialize(void) { ZeroMemory(&wfx, sizeof(WAVEFORMATEX)); wfx.wFormatTag = WAVE_FORMAT_PCM; wfx.nChannels = 2; - wfx.nSamplesPerSec = 22050; + wfx.nSamplesPerSec = audio_mix_freq; wfx.wBitsPerSample = 16; wfx.nBlockAlign = wfx.wBitsPerSample / 8 * wfx.nChannels; wfx.nAvgBytesPerSec = wfx.nSamplesPerSec * wfx.nBlockAlign; @@ -393,6 +393,56 @@ WinSample* WinSample::load_wav(Filename filename) { return ret; } +WinSample* WinSample::load_raw(unsigned char* data, unsigned long size) { + WinSample* ret = (WinSample*)0L; + + initialize(); + + // synth a wav header for this data + WAVEFORMATEX wavInfo; + ZeroMemory(&wavInfo, sizeof(WAVEFORMATEX)); + wavInfo.wFormatTag = WAVE_FORMAT_PCM; + wavInfo.nChannels = 2; + wavInfo.nSamplesPerSec = audio_mix_freq; + wavInfo.wBitsPerSample = 16; + wavInfo.nBlockAlign = wavInfo.wBitsPerSample / 8 * wavInfo.nChannels; + wavInfo.nAvgBytesPerSec = wavInfo.nSamplesPerSec * wavInfo.nBlockAlign; + + if (data = (unsigned char*)0L) + return ret; + + // create a direct sound channel for this data + ret = new WinSample(); + DSBUFFERDESC dsbdDesc; + ZeroMemory(&dsbdDesc, sizeof(DSBUFFERDESC)); + dsbdDesc.dwSize = sizeof(DSBUFFERDESC); + dsbdDesc.dwFlags = DSBCAPS_STATIC | DSBCAPS_GLOBALFOCUS; + dsbdDesc.dwBufferBytes = size; + dsbdDesc.lpwfxFormat = &wavInfo; + dsbdDesc.lpwfxFormat->cbSize = sizeof(wavInfo); + HRESULT result = soundDirectSound->CreateSoundBuffer(&dsbdDesc, + &(ret->_channel), NULL); + if (FAILED(result)) { + delete ret; + ret = (WinSample*)0L; + } + if (ret) { + BYTE* dst = NULL; + dst = ret->lock(); + try { + memcpy(dst, data, size); + } + catch (...) { + delete ret; + ret = (WinSample*)0L; + } + if (ret) + ret->unlock(); + delete [] data; + return ret; + } +} + void WinSample::destroy(AudioTraits::SampleClass* sample) { delete sample; } diff --git a/panda/src/audio/audio_win_traits.h b/panda/src/audio/audio_win_traits.h index c5659e49cf..8300a54959 100644 --- a/panda/src/audio/audio_win_traits.h +++ b/panda/src/audio/audio_win_traits.h @@ -32,6 +32,7 @@ public: BYTE* lock(void); void unlock(void); static WinSample* load_wav(Filename); + static WinSample* load_raw(unsigned char*, unsigned long); static void destroy(AudioTraits::SampleClass*); // these are used by the player INLINE LPDIRECTSOUNDBUFFER get_channel(void);