- [FIX] Reajustat el buffer de só per a notes llargues, que s'havia fotut en el pas a SDL3
- [NEW] al usar play(), amb "w" es pot canviar de tipus de ona: 0: la quadrada de sempre, 1: sawtooth, 2: roido - [FIX] Al executar play() de nou no se resetejaven la duració de nota ni el tipus de ona.
This commit is contained in:
@@ -9,26 +9,69 @@ const float periods[108] = { 1348.49207, 1272.80688, 1201.37, 1133.94214, 1070.2
|
||||
static float default_length = 0.25f;
|
||||
static uint8_t volume = 64;
|
||||
static uint8_t octave = 4;
|
||||
static uint32_t tempo = 44100;
|
||||
static uint32_t tempo = tempos[4]*10;
|
||||
static uint8_t wave_type = 0;
|
||||
static char* song_ptr = NULL;
|
||||
static char* song = NULL;
|
||||
static char song[256];
|
||||
|
||||
uint8_t generate_square_wave(unsigned int i, uint16_t period, uint8_t volume) {
|
||||
return ( (i % period) < (period >> 1) ? volume : -volume );
|
||||
}
|
||||
|
||||
uint8_t generate_saw_wave(unsigned int i, uint16_t period, uint8_t volume) {
|
||||
uint16_t t = i % period;
|
||||
|
||||
// Mapea t (0..period-1) a un rango lineal -volume..+volume
|
||||
int16_t v = -volume + (2 * volume * t) / period;
|
||||
|
||||
return (int8_t)v;
|
||||
}
|
||||
|
||||
uint8_t generate_triangle_wave(unsigned int i, uint16_t period, uint8_t volume) {
|
||||
uint16_t t = i % period;
|
||||
int16_t v = (t < period/2)
|
||||
? (-volume + (2 * volume * t) / (period/2))
|
||||
: ( volume - (2 * volume * (t - period/2)) / (period/2));
|
||||
return (int8_t)v;
|
||||
}
|
||||
|
||||
uint8_t generate_periodic_noise(unsigned int i, uint16_t period, uint8_t volume) {
|
||||
static int8_t current = 0;
|
||||
|
||||
if (i % period == 0) {
|
||||
current = (rand() % (2 * volume + 1)) - volume;
|
||||
}
|
||||
|
||||
return current;
|
||||
}
|
||||
|
||||
uint8_t generate_wave(unsigned int i, uint16_t period, uint8_t volume) {
|
||||
switch (wave_type) {
|
||||
case 1: return generate_saw_wave(i, period, volume);
|
||||
case 2: return generate_periodic_noise(i, period, volume);
|
||||
default:return generate_square_wave(i, period, volume);
|
||||
}
|
||||
}
|
||||
|
||||
uint32_t interpret_note(uint8_t* buffer, const char note, const char param ) {
|
||||
const uint32_t length = ( param == -1 ? default_length : ((float)lengths[uint8_t(param)])/10000.0f ) * tempo;
|
||||
if( note == 100 ) { memset( buffer, 0, length ); return length; }
|
||||
const uint16_t period = periods[note + octave*12];
|
||||
|
||||
for( unsigned int i = 0; i < length; i++ ) buffer[i] = ( (i % period) < (period >> 1) ? volume : -volume );
|
||||
for( unsigned int i = 0; i < length; i++ ) buffer[i] = generate_wave(i, period, volume);
|
||||
return length;
|
||||
}
|
||||
|
||||
void play_init(const char* new_song) {
|
||||
default_length = 0.25f;
|
||||
volume=64;
|
||||
octave=4;
|
||||
tempo=44100;
|
||||
if (song != NULL) free(song);
|
||||
song = (char*)malloc( strlen( new_song ) + 1 );
|
||||
strcpy( song, new_song );
|
||||
tempo=tempos[4]*10;
|
||||
wave_type = 0;
|
||||
|
||||
int len = strlen( new_song ) + 1;
|
||||
if (len > 256) len = 256;
|
||||
strncpy(song, new_song, len);
|
||||
song_ptr = song;
|
||||
}
|
||||
|
||||
@@ -75,6 +118,10 @@ int32_t interpret_next_token(uint8_t* buffer) {
|
||||
param = *++*token;
|
||||
if( param >= 48 && param <= 57 ) { tempo = tempos[param - 48] * 10; ++*token; }
|
||||
return 0;
|
||||
case 'w':
|
||||
param = *++*token;
|
||||
if( param >= 48 && param <= 50 ) { wave_type = param - 48; ++*token; }
|
||||
return 0;
|
||||
case '\0':
|
||||
return -1;
|
||||
default:
|
||||
|
||||
Reference in New Issue
Block a user