X-Git-Url: http://shamusworld.gotdns.org/cgi-bin/gitweb.cgi?a=blobdiff_plain;ds=sidebyside;f=src%2Fsound.cpp;h=3dcf993bbd395bb7ed3ea4064ff15c2e7f34d790;hb=9eb5812230547fd62f2413d84a0dcc9e1336be21;hp=930de351e081505acd3f19a3513c2e70590c8bd3;hpb=44a4bdffcaf520bc1681fcc0fd330460cd49129f;p=thunder diff --git a/src/sound.cpp b/src/sound.cpp index 930de35..3dcf993 100644 --- a/src/sound.cpp +++ b/src/sound.cpp @@ -13,7 +13,12 @@ #include "sound.h" #include +#include "psg.h" #include "resource.h" +#include "ym2151.h" + +#define SAMPLE_RATE 48000 +#define BUFFER_SIZE 512 // Function prototypes void SoundFunc(void *, Uint8 *, int); @@ -22,43 +27,43 @@ void SoundFunc(void *, Uint8 *, int); extern uint8_t voice_rom[]; // PCM data pointer static bool soundInitialized = false; -const float sampleBase = 22050.0/6000.0; // Btwn 5512.5 and 6000 -bool snd_go = false; -bool chan1_go = false, chan2_go = false, chan3_go = false; -bool chan4_go = false, chan5_go = false, chan6_go = false; -uint8_t * sndp1, * sndp2, * sndp3, * sndp4, * sndp5, * sndp6; -uint32_t rom_pos, end_pos; +const float sampleBase = (float)SAMPLE_RATE / 6000.0; // Voice is between 5512.5 and 6000 Hz +bool chan1_go = false, chan2_go = false; +bool chan6_go = false; +uint8_t * sndp1, * sndp2, * sndp6; uint32_t spos1, end_pos1; uint32_t spos2, end_pos2; -uint32_t spos3, end_pos3; -uint32_t spos4, end_pos4; -uint32_t spos5, end_pos5; uint32_t spos6, end_pos6; -float sample1; -uint8_t prevSamp1; -int8_t delta_x1; -float sample2; -uint8_t prevSamp2; -int8_t delta_x2; +float sample1, sample2; +int16_t prevSamp1, prevSamp2; uint16_t snd_num; -uint8_t * snd_array[3] = { sunknown, scya, scamera }; // From RESOURCE.H +// From RESOURCE.H +uint8_t * snd_array[3] = { sunknown, scya, scamera }; uint32_t snd_lens[3] = { sunknownlen, scyalen, scameralen }; - void InitSound(void) { + if (YMInit(3579580, SAMPLE_RATE)) + { + printf("SOUND: Could not init YM2151 emulator!\n"); + return; + } + + InitPSG(SAMPLE_RATE); + SDL_AudioSpec desired, obtained; - desired.freq = 22050; - desired.format = AUDIO_U8; + desired.freq = SAMPLE_RATE; + desired.format = AUDIO_S16; desired.channels = 1; - desired.samples = 1024; + desired.samples = BUFFER_SIZE * 2; // Size is in BYTES, so x2 desired.callback = SoundFunc; desired.userdata = NULL; - // Also, should check to see if it got the hardware it needed, correct sample size, etc. + + // Also, should check to see if it got the hardware it needed, correct sample size, etc. (actually, SDL guarantees we get what we asked for--I think) if (SDL_OpenAudio(&desired, &obtained) < 0) { soundInitialized = false; - printf("Couldn't open audio: %s\n", SDL_GetError()); + printf("SOUND: Couldn't open audio: %s\n", SDL_GetError()); return; } @@ -67,22 +72,14 @@ void InitSound(void) soundInitialized = true; } - void SpawnSound(int type, int snd, int channel/* = 0*/) { - extern uint32_t psg_lens[16]; - extern uint8_t * psg_adrs[16]; - extern uint32_t voc_lens[32]; - extern uint8_t * voc_adrs[32]; - extern uint32_t fm_lens[14]; - extern uint8_t * fm_adrs[14]; - if (!soundInitialized) return; snd_num = snd; -// SpawnMsg(MSHOWNUMS); + // Voice type sounds... if (type == GAMESOUND) { // Will that do it??? Yes!!! @@ -122,39 +119,6 @@ void SpawnSound(int type, int snd, int channel/* = 0*/) chan2_go = true; } } - else if (type == PSGSOUND) - { - if (snd_num & 0x10) // Second channel? - { - spos3 = 0; - end_pos3 = psg_lens[snd_num & 0x0F]; - sndp3 = psg_adrs[snd_num & 0x0F]; - chan3_go = true; - - if (spos3 == end_pos3) - chan3_go = false; // No sound loaded, so don't do it! - } - else // First channel - { - spos4 = 0; - end_pos4 = psg_lens[snd_num & 0x0F]; - sndp4 = psg_adrs[snd_num & 0x0F]; - chan4_go = true; - - if (spos4 == end_pos4) - chan4_go = false; // No sound loaded, so don't do it! - } - } - else if (type == FMSOUND) - { - spos5 = 0; - end_pos5 = fm_lens[snd_num]; - sndp5 = fm_adrs[snd_num]; - chan5_go = true; - - if (spos5 == end_pos5) - chan5_go = false; // No sound loaded, so don't do it! - } else if (type == USERSOUND) { spos6 = 0; @@ -164,133 +128,103 @@ void SpawnSound(int type, int snd, int channel/* = 0*/) } } - -void SoundFunc(void * userdata, Uint8 * buff, int num) +void SoundFunc(void * userdata, Uint8 * buffer, int num) { + // We do num / 2 because num is in BYTES, and the buffer uses signed WORDs. + YM2151UpdateOne(buffer, num / 2); + UpdatePSG(buffer, num / 2); + // 0-22 different sounds... - uint16_t cnt = 0, sample; + uint16_t cnt = 0; uint8_t start_samp1, end_samp1, start_samp2, end_samp2; - uint8_t samp1 = 128, samp2 = 128, samp3 = 128, - samp4 = 128, samp5 = 128, samp6 = 128; // Zero samples... + int16_t samp1 = 0, samp2 = 0, samp6 = 0; // Zero samples... - // Kill sound... - memset(buff, 128, num); + if (!(chan1_go || chan2_go || chan6_go)) + return; - if (chan1_go || chan2_go || chan3_go || chan4_go || chan5_go || chan6_go) + while (cnt != (num / 2)) { - while (cnt != num) + if (chan1_go) { - if (chan1_go) + if (sample1 < 1) { - if (sample1 < 1) + uint8_t voiceSample = voice_rom[spos1++]; + samp1 = ((int16_t)voiceSample - 128) * 160; + + // Kill channel 1 if done... + if (voiceSample == 0xFF) { - samp1 = voice_rom[spos1++]; - - // Kill channel 1 if done... - if (samp1 == 0xFF) - { - chan1_go = false; - samp1 = 128; - } - // RLE compression... - else if (samp1 == 0x00) - { - // # of repeats - sample1 += (float)voice_rom[spos1++] * sampleBase; - // Get last good sample - samp1 = prevSamp1; - } - else - // Keep fractional part intact - sample1 += sampleBase; + chan1_go = false; + samp1 = 0; } - - prevSamp1 = samp1; // Save last sample value - sample1 -= 1.0; // Decrement repeat counter + // RLE compression... + else if (voiceSample == 0x00) + { + // # of repeats + sample1 += (float)voice_rom[spos1++] * sampleBase; + // Get last good sample + samp1 = prevSamp1; + } + else + // Keep fractional part intact + sample1 += sampleBase; } + prevSamp1 = samp1; // Save last sample value + sample1 -= 1.0; // Decrement repeat counter + } + // Stretching 5KHz samples to 22KHz: // numRepeats = 4; // 6KHz -> 22KHz: 22/6 repeats... - if (chan2_go) - { - if (sample2 < 1) - { - samp2 = voice_rom[spos2++]; - - if (samp2 == 0xFF) - { - chan2_go = false; - samp2 = 128; // Kill channel 2 if done... - } - else if (samp2 == 0x00) // RLE compression... - { - sample2 += (float)voice_rom[spos2++] * sampleBase; // # of repeats - samp2 = prevSamp2; - } - else - sample2 += sampleBase; - } - -// Delta-X values were making the samples sound like crap... -// start_samp2 += delta_x2; - prevSamp2 = samp2; - sample2 -= 1.0; - } - - if (chan3_go) + if (chan2_go) + { + if (sample2 < 1) { - samp3 = sndp3[spos3++]; + uint8_t voiceSample = voice_rom[spos2++]; + samp2 = ((int16_t)voiceSample - 128) * 160; - if (spos3 == end_pos3) + if (voiceSample == 0xFF) { - chan3_go = false; - samp3 = 128; // Kill channel 3 if done... + chan2_go = false; + samp2 = 128; // Kill channel 2 if done... } - } - - if (chan4_go) - { - samp4 = sndp4[spos4++]; - - if (spos4 == end_pos4) + else if (voiceSample == 0x00) // RLE compression... { - chan4_go = false; - samp4 = 128; // Kill channel 4 if done... + sample2 += (float)voice_rom[spos2++] * sampleBase; // # of repeats + samp2 = prevSamp2; } + else + sample2 += sampleBase; } - if (chan5_go) - { - samp5 = sndp5[spos5++]; +// Delta-X values were making the samples sound like crap... +// start_samp2 += delta_x2; + prevSamp2 = samp2; + sample2 -= 1.0; + } - if (spos5 == end_pos5) - { - chan5_go = false; - samp5 = 128; // Kill channel 5 if done... - } - } + if (chan6_go) + { + samp6 = sndp6[spos6++]; - if (chan6_go) + if (spos6 == end_pos6) { - samp6 = sndp6[spos6++]; - - if (spos6 == end_pos6) - { - chan6_go = false; - samp6 = 128; // Kill channel 6... - } + chan6_go = false; + samp6 = 0; // Kill channel 6... } + } - // Mix 'em... - sample = samp1 + samp2 + samp3 + samp4 + samp5 + samp6 - 640; + // Mix 'em... + int32_t sample = samp1 + samp2 + samp6; + sample += ((int16_t *)buffer)[cnt]; - // If it overflowed, clip it - if (sample & 0xFF00) - sample = (sample & 0x8000 ? 0x00 : 0xFF); + // If it overflowed, clip it + if (sample > 32767) + sample = 32767; + else if (sample < -32767) + sample = -32767; - buff[cnt++] = sample; - } + ((int16_t *)buffer)[cnt++] = (int16_t)sample; } } -