Moved wave format conversion code to the sound lowlevel base class and added
format conversion support to the ALSA and OSS sound modules.
This commit is contained in:
parent
e37498025e
commit
2c621601cb
@ -320,24 +320,30 @@ int bx_sound_alsa_c::alsa_pcm_write()
|
||||
return BX_SOUNDLOW_OK;
|
||||
}
|
||||
|
||||
int bx_sound_alsa_c::sendwavepacket(int length, Bit8u data[], bx_pcm_param_t *param)
|
||||
int bx_sound_alsa_c::sendwavepacket(int length, Bit8u data[], bx_pcm_param_t *src_param)
|
||||
{
|
||||
if (memcmp(param, &pcm_param, sizeof(bx_pcm_param_t)) != 0) {
|
||||
startwaveplayback(param->samplerate, param->bits, param->channels == 2,
|
||||
param->format);
|
||||
pcm_param = *param;
|
||||
int len2;
|
||||
|
||||
if (memcmp(src_param, &pcm_param, sizeof(bx_pcm_param_t)) != 0) {
|
||||
startwaveplayback(src_param->samplerate, 16, 1, 1);
|
||||
pcm_param = *src_param;
|
||||
cvt_mult = 1;
|
||||
if (src_param->bits == 8) cvt_mult = 2;
|
||||
if (src_param->channels == 1) cvt_mult *= 2;
|
||||
}
|
||||
len2 = length * cvt_mult;
|
||||
if (!alsa_pcm[0].handle) {
|
||||
// Alert indicating that caller is probably erroneous
|
||||
BX_ERROR(("sendwavepacket(): pcm is not open"));
|
||||
return BX_SOUNDLOW_ERR;
|
||||
}
|
||||
if ((alsa_pcm[0].audio_bufsize+length) <= BX_SOUND_ALSA_BUFSIZE) {
|
||||
memcpy(audio_buffer[0]+alsa_pcm[0].audio_bufsize, data, length);
|
||||
alsa_pcm[0].audio_bufsize += length;
|
||||
} else {
|
||||
if ((alsa_pcm[0].audio_bufsize+len2) > BX_SOUND_ALSA_BUFSIZE) {
|
||||
len2 = BX_SOUND_ALSA_BUFSIZE - alsa_pcm[0].audio_bufsize;
|
||||
BX_ERROR(("ALSA: audio buffer overflow"));
|
||||
return BX_SOUNDLOW_ERR;
|
||||
}
|
||||
if (len2 > 0) {
|
||||
convert_wavedata(data, length, audio_buffer[0]+alsa_pcm[0].audio_bufsize, len2, src_param);
|
||||
alsa_pcm[0].audio_bufsize += len2;
|
||||
}
|
||||
if (alsa_pcm[0].audio_bufsize < alsa_pcm[0].alsa_bufsize) {
|
||||
return BX_SOUNDLOW_OK;
|
||||
|
@ -44,7 +44,7 @@ public:
|
||||
|
||||
virtual int openwaveoutput(const char *wavedev);
|
||||
virtual int startwaveplayback(int frequency, int bits, bx_bool stereo, int format);
|
||||
virtual int sendwavepacket(int length, Bit8u data[], bx_pcm_param_t *param);
|
||||
virtual int sendwavepacket(int length, Bit8u data[], bx_pcm_param_t *src_param);
|
||||
virtual int stopwaveplayback();
|
||||
virtual int closewaveoutput();
|
||||
|
||||
|
@ -191,18 +191,26 @@ int bx_sound_linux_c::startwaveplayback(int frequency, int bits, bx_bool stereo,
|
||||
return BX_SOUNDLOW_OK;
|
||||
}
|
||||
|
||||
int bx_sound_linux_c::sendwavepacket(int length, Bit8u data[], bx_pcm_param_t *param)
|
||||
int bx_sound_linux_c::sendwavepacket(int length, Bit8u data[], bx_pcm_param_t *src_param)
|
||||
{
|
||||
if (memcmp(param, &pcm_param, sizeof(bx_pcm_param_t)) != 0) {
|
||||
startwaveplayback(param->samplerate, param->bits, param->channels == 2,
|
||||
param->format);
|
||||
pcm_param = *param;
|
||||
int len2;
|
||||
Bit8u *tmpbuffer;
|
||||
|
||||
if (memcmp(src_param, &pcm_param, sizeof(bx_pcm_param_t)) != 0) {
|
||||
startwaveplayback(src_param->samplerate, 16, 1, 1);
|
||||
pcm_param = *src_param;
|
||||
cvt_mult = 1;
|
||||
if (src_param->bits == 8) cvt_mult = 2;
|
||||
if (src_param->channels == 1) cvt_mult *= 2;
|
||||
}
|
||||
if (wave_fd[0] == -1) {
|
||||
return BX_SOUNDLOW_ERR;
|
||||
}
|
||||
|
||||
int ret = write(wave_fd[0], data, length);
|
||||
len2 = length * cvt_mult;
|
||||
tmpbuffer = (Bit8u*)malloc(len2);
|
||||
convert_wavedata(data, length, tmpbuffer, len2, src_param);
|
||||
int ret = write(wave_fd[0], tmpbuffer, len2);
|
||||
free(tmpbuffer);
|
||||
if (ret == length) {
|
||||
return BX_SOUNDLOW_OK;
|
||||
} else {
|
||||
|
@ -41,7 +41,7 @@ public:
|
||||
|
||||
virtual int openwaveoutput(const char *wavedev);
|
||||
virtual int startwaveplayback(int frequency, int bits, bx_bool stereo, int format);
|
||||
virtual int sendwavepacket(int length, Bit8u data[], bx_pcm_param_t *param);
|
||||
virtual int sendwavepacket(int length, Bit8u data[], bx_pcm_param_t *src_param);
|
||||
virtual int stopwaveplayback();
|
||||
virtual int closewaveoutput();
|
||||
|
||||
|
@ -89,6 +89,49 @@ int bx_sound_lowlevel_c::startwaveplayback(int frequency, int bits, bx_bool ster
|
||||
return BX_SOUNDLOW_OK;
|
||||
}
|
||||
|
||||
void bx_sound_lowlevel_c::convert_wavedata(Bit8u *src, int srcsize, Bit8u *dst, int dstsize, bx_pcm_param_t *param)
|
||||
{
|
||||
int i, j;
|
||||
Bit8u xor_val;
|
||||
|
||||
xor_val = (param->format & 1) ? 0x00 : 0x80;
|
||||
if (param->bits == 16) {
|
||||
if ((param->format & 1) && (param->channels == 2)) {
|
||||
memcpy(dst, src, dstsize);
|
||||
} else if (param->channels == 2) {
|
||||
j = 0;
|
||||
for (i = 0; i < srcsize; i+=2) {
|
||||
dst[j++] = src[i];
|
||||
dst[j++] = src[i+1] ^ xor_val;
|
||||
}
|
||||
} else {
|
||||
j = 0;
|
||||
for (i = 0; i < srcsize; i+=2) {
|
||||
dst[j++] = src[i];
|
||||
dst[j++] = src[i+1] ^ xor_val;
|
||||
dst[j++] = src[i];
|
||||
dst[j++] = src[i+1] ^ xor_val;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
if (param->channels == 2) {
|
||||
j = 0;
|
||||
for (i = 0; i < srcsize; i++) {
|
||||
dst[j++] = 0;
|
||||
dst[j++] = src[i] ^ xor_val;
|
||||
}
|
||||
} else {
|
||||
j = 0;
|
||||
for (i = 0; i < srcsize; i++) {
|
||||
dst[j++] = 0;
|
||||
dst[j++] = src[i] ^ xor_val;
|
||||
dst[j++] = 0;
|
||||
dst[j++] = src[i] ^ xor_val;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
int bx_sound_lowlevel_c::sendwavepacket(int length, Bit8u data[], bx_pcm_param_t *param)
|
||||
{
|
||||
if (memcmp(param, &pcm_param, sizeof(bx_pcm_param_t)) != 0) {
|
||||
|
@ -89,12 +89,17 @@ public:
|
||||
virtual int register_wave_callback(void *, get_wave_cb_t wd_cb) {return -1;}
|
||||
virtual void unregister_wave_callback(int callback_id) {}
|
||||
protected:
|
||||
void convert_wavedata(Bit8u *src, int srcsize, Bit8u *dst, int dstsize, bx_pcm_param_t *param);
|
||||
|
||||
bx_pcm_param_t pcm_param;
|
||||
int cvt_mult;
|
||||
|
||||
int cb_count;
|
||||
struct {
|
||||
void *device;
|
||||
get_wave_cb_t cb;
|
||||
} get_wave[BX_MAX_WAVE_CALLBACKS];
|
||||
|
||||
int record_timer_index;
|
||||
int record_packet_size;
|
||||
sound_record_handler_t record_handler;
|
||||
|
@ -151,49 +151,6 @@ int bx_sound_sdl_c::startwaveplayback(int frequency, int bits, bx_bool stereo, i
|
||||
return BX_SOUNDLOW_OK;
|
||||
}
|
||||
|
||||
void bx_sound_sdl_c::convert_wavedata(Bit8u *src, int srcsize, Bit8u *dst, int dstsize, bx_pcm_param_t *param)
|
||||
{
|
||||
int i, j;
|
||||
Bit8u xor_val;
|
||||
|
||||
xor_val = (param->format & 1) ? 0x00 : 0x80;
|
||||
if (param->bits == 16) {
|
||||
if ((param->format & 1) && (param->channels == 2)) {
|
||||
memcpy(dst, src, dstsize);
|
||||
} else if (param->channels == 2) {
|
||||
j = 0;
|
||||
for (i = 0; i < srcsize; i+=2) {
|
||||
dst[j++] = src[i];
|
||||
dst[j++] = src[i+1] ^ xor_val;
|
||||
}
|
||||
} else {
|
||||
j = 0;
|
||||
for (i = 0; i < srcsize; i+=2) {
|
||||
dst[j++] = src[i];
|
||||
dst[j++] = src[i+1] ^ xor_val;
|
||||
dst[j++] = src[i];
|
||||
dst[j++] = src[i+1] ^ xor_val;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
if (param->channels == 2) {
|
||||
j = 0;
|
||||
for (i = 0; i < srcsize; i++) {
|
||||
dst[j++] = 0;
|
||||
dst[j++] = src[i] ^ xor_val;
|
||||
}
|
||||
} else {
|
||||
j = 0;
|
||||
for (i = 0; i < srcsize; i++) {
|
||||
dst[j++] = 0;
|
||||
dst[j++] = src[i] ^ xor_val;
|
||||
dst[j++] = 0;
|
||||
dst[j++] = src[i] ^ xor_val;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
int bx_sound_sdl_c::sendwavepacket(int length, Bit8u data[], bx_pcm_param_t *src_param)
|
||||
{
|
||||
int ret = BX_SOUNDLOW_OK;
|
||||
|
@ -42,11 +42,9 @@ public:
|
||||
virtual void unregister_wave_callback(int callback_id);
|
||||
void get_wave_data(Bit8u *stream, int len);
|
||||
private:
|
||||
void convert_wavedata(Bit8u *src, int srcsize, Bit8u *dst, int dstsize, bx_pcm_param_t *param);
|
||||
bx_bool WaveOpen;
|
||||
SDL_AudioSpec fmt;
|
||||
int pcm_callback_id;
|
||||
int cvt_mult;
|
||||
};
|
||||
|
||||
#endif // BX_WITH_SDL || BX_WITH_SDL2
|
||||
|
Loading…
x
Reference in New Issue
Block a user