mirror of
https://github.com/raysan5/raygui.git
synced 2026-02-03 04:39:18 -05:00
Make some functions more versatile
Avoid depending on global variables to make functions portable
This commit is contained in:
@ -146,15 +146,19 @@ static char currentPath[256]; // Path to current working folder
|
|||||||
//----------------------------------------------------------------------------------
|
//----------------------------------------------------------------------------------
|
||||||
// Module Functions Declaration
|
// Module Functions Declaration
|
||||||
//----------------------------------------------------------------------------------
|
//----------------------------------------------------------------------------------
|
||||||
static void ResetParams(void); // Reset sound parameters
|
static void ResetParams(WaveParams *params); // Reset wave parameters
|
||||||
static void GenerateWave(WaveParams params); // Generate wave data and update sound
|
static Wave GenerateWave(WaveParams params,
|
||||||
|
int sampleRate,
|
||||||
|
int sampleSize,
|
||||||
|
int channels); // Generate wave data from parameters
|
||||||
static void GeneratePlay(void); // Generate wave data and play sound
|
static void GeneratePlay(void); // Generate wave data and play sound
|
||||||
|
|
||||||
static void LoadSoundParams(const char *fileName); // Load sound parameters from file
|
static WaveParams LoadSoundParams(const char *fileName); // Load sound parameters from file
|
||||||
static void SaveSoundParams(const char *fileName); // Save sound parameters to file
|
static void SaveSoundParams(const char *fileName, WaveParams params); // Save sound parameters to file
|
||||||
static void SaveWAV(const char *fileName, Wave wave); // Export sound to .wav file
|
|
||||||
static void DrawWave(Rectangle bounds, Color color); // Draw wave data using lines
|
static void SaveWAV(const char *fileName, Wave wave); // Export sound to .wav file
|
||||||
static const char *GetExtension(const char *fileName); // Get extension from filename
|
static void DrawWave(Wave wave, Rectangle bounds, Color color); // Draw wave data using lines
|
||||||
|
static const char *GetExtension(const char *fileName); // Get extension from filename
|
||||||
|
|
||||||
// Buttons functions
|
// Buttons functions
|
||||||
static void BtnPickupCoin(void); // Generate sound: Pickup/Coin
|
static void BtnPickupCoin(void); // Generate sound: Pickup/Coin
|
||||||
@ -187,8 +191,8 @@ int main(int argc, char *argv[])
|
|||||||
if ((strcmp(GetExtension(argv[i]), "rfx") == 0) ||
|
if ((strcmp(GetExtension(argv[i]), "rfx") == 0) ||
|
||||||
(strcmp(GetExtension(argv[i]), "sfs") == 0))
|
(strcmp(GetExtension(argv[i]), "sfs") == 0))
|
||||||
{
|
{
|
||||||
LoadSoundParams(argv[i]);
|
params = LoadSoundParams(argv[i]);
|
||||||
GenerateWave(params);
|
Wave mwave = GenerateWave(params, 44100, 32, 1);
|
||||||
|
|
||||||
argv[i][strlen(argv[i]) - 3] = 'w';
|
argv[i][strlen(argv[i]) - 3] = 'w';
|
||||||
argv[i][strlen(argv[i]) - 2] = 'a';
|
argv[i][strlen(argv[i]) - 2] = 'a';
|
||||||
@ -196,7 +200,8 @@ int main(int argc, char *argv[])
|
|||||||
|
|
||||||
//printf("output name: %s\n", argv[i]);
|
//printf("output name: %s\n", argv[i]);
|
||||||
|
|
||||||
SaveWAV(argv[i], wave);
|
SaveWAV(argv[i], mwave);
|
||||||
|
UnloadWave(mwave);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -350,7 +355,7 @@ int main(int argc, char *argv[])
|
|||||||
sound = LoadSoundFromWave(wave);
|
sound = LoadSoundFromWave(wave);
|
||||||
SetSoundVolume(sound, volumeValue);
|
SetSoundVolume(sound, volumeValue);
|
||||||
|
|
||||||
ResetParams();
|
ResetParams(¶ms);
|
||||||
|
|
||||||
Rectangle waveRec = { 13, 421, 473, 50 };
|
Rectangle waveRec = { 13, 421, 473, 50 };
|
||||||
|
|
||||||
@ -380,7 +385,12 @@ int main(int argc, char *argv[])
|
|||||||
if ((CheckCollisionPointRec(GetMousePosition(), (Rectangle){ 265, 65, 105, 360 })) && (IsMouseButtonReleased(MOUSE_LEFT_BUTTON)))
|
if ((CheckCollisionPointRec(GetMousePosition(), (Rectangle){ 265, 65, 105, 360 })) && (IsMouseButtonReleased(MOUSE_LEFT_BUTTON)))
|
||||||
{
|
{
|
||||||
if (playOnChangeValue) GeneratePlay();
|
if (playOnChangeValue) GeneratePlay();
|
||||||
else GenerateWave(params);
|
else
|
||||||
|
{
|
||||||
|
UnloadWave(wave);
|
||||||
|
wave = GenerateWave(params, 44100, 32, 1); // Generate wave from parameters
|
||||||
|
UpdateSound(sound, wave.data, wave.sampleCount); // Update sound buffer with new data
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
BeginDrawing();
|
BeginDrawing();
|
||||||
@ -550,12 +560,12 @@ int main(int argc, char *argv[])
|
|||||||
|
|
||||||
#if defined(RENDER_WAVE_TO_TEXTURE)
|
#if defined(RENDER_WAVE_TO_TEXTURE)
|
||||||
BeginTextureMode(waveTarget);
|
BeginTextureMode(waveTarget);
|
||||||
DrawWave((Rectangle){ 0, 0, waveTarget.texture.width, waveTarget.texture.height }, MAROON);
|
DrawWave(wave, (Rectangle){ 0, 0, waveTarget.texture.width, waveTarget.texture.height }, MAROON);
|
||||||
EndTextureMode();
|
EndTextureMode();
|
||||||
|
|
||||||
DrawTextureEx(waveTarget.texture, (Vector2){ waveRec.x, waveRec.y }, 0.0f, 0.5f, WHITE);
|
DrawTextureEx(waveTarget.texture, (Vector2){ waveRec.x, waveRec.y }, 0.0f, 0.5f, WHITE);
|
||||||
#else
|
#else
|
||||||
DrawWave(waveRec, MAROON);
|
DrawWave(wave, waveRec, MAROON);
|
||||||
#endif
|
#endif
|
||||||
DrawRectangleLines(waveRec.x, waveRec.y, waveRec.width, waveRec.height, GuiLinesColor());
|
DrawRectangleLines(waveRec.x, waveRec.y, waveRec.width, waveRec.height, GuiLinesColor());
|
||||||
DrawRectangle(waveRec.x, waveRec.y + waveRec.height/2, waveRec.width, 1, LIGHTGRAY);
|
DrawRectangle(waveRec.x, waveRec.y + waveRec.height/2, waveRec.width, 1, LIGHTGRAY);
|
||||||
@ -619,54 +629,56 @@ int main(int argc, char *argv[])
|
|||||||
//--------------------------------------------------------------------------------------------
|
//--------------------------------------------------------------------------------------------
|
||||||
// Module Functions Definitions (local)
|
// Module Functions Definitions (local)
|
||||||
//--------------------------------------------------------------------------------------------
|
//--------------------------------------------------------------------------------------------
|
||||||
static void ResetParams()
|
static void ResetParams(WaveParams *params)
|
||||||
{
|
{
|
||||||
// Wave type
|
// Wave type
|
||||||
params.waveTypeValue = 0;
|
params->waveTypeValue = 0;
|
||||||
|
|
||||||
// Wave envelope params
|
// Wave envelope params
|
||||||
params.attackTimeValue = 0.0f;
|
params->attackTimeValue = 0.0f;
|
||||||
params.sustainTimeValue = 0.3f;
|
params->sustainTimeValue = 0.3f;
|
||||||
params.sustainPunchValue = 0.0f;
|
params->sustainPunchValue = 0.0f;
|
||||||
params.decayTimeValue = 0.4f;
|
params->decayTimeValue = 0.4f;
|
||||||
|
|
||||||
// Frequency params
|
// Frequency params
|
||||||
params.startFrequencyValue = 0.3f;
|
params->startFrequencyValue = 0.3f;
|
||||||
params.minFrequencyValue = 0.0f;
|
params->minFrequencyValue = 0.0f;
|
||||||
params.slideValue = 0.0f;
|
params->slideValue = 0.0f;
|
||||||
params.deltaSlideValue = 0.0f;
|
params->deltaSlideValue = 0.0f;
|
||||||
params.vibratoDepthValue = 0.0f;
|
params->vibratoDepthValue = 0.0f;
|
||||||
params.vibratoSpeedValue = 0.0f;
|
params->vibratoSpeedValue = 0.0f;
|
||||||
//params.vibratoPhaseDelay = 0.0f;
|
//params->vibratoPhaseDelay = 0.0f;
|
||||||
|
|
||||||
// Tone change params
|
// Tone change params
|
||||||
params.changeAmountValue = 0.0f;
|
params->changeAmountValue = 0.0f;
|
||||||
params.changeSpeedValue = 0.0f;
|
params->changeSpeedValue = 0.0f;
|
||||||
|
|
||||||
// Square wave params
|
// Square wave params
|
||||||
params.squareDutyValue = 0.0f;
|
params->squareDutyValue = 0.0f;
|
||||||
params.dutySweepValue = 0.0f;
|
params->dutySweepValue = 0.0f;
|
||||||
|
|
||||||
// Repeat params
|
// Repeat params
|
||||||
params.repeatSpeedValue = 0.0f;
|
params->repeatSpeedValue = 0.0f;
|
||||||
|
|
||||||
// Phaser params
|
// Phaser params
|
||||||
params.phaserOffsetValue = 0.0f;
|
params->phaserOffsetValue = 0.0f;
|
||||||
params.phaserSweepValue = 0.0f;
|
params->phaserSweepValue = 0.0f;
|
||||||
|
|
||||||
// Filter params
|
// Filter params
|
||||||
params.lpfCutoffValue = 1.0f;
|
params->lpfCutoffValue = 1.0f;
|
||||||
params.lpfCutoffSweepValue = 0.0f;
|
params->lpfCutoffSweepValue = 0.0f;
|
||||||
params.lpfResonanceValue = 0.0f;
|
params->lpfResonanceValue = 0.0f;
|
||||||
params.hpfCutoffValue = 0.0f;
|
params->hpfCutoffValue = 0.0f;
|
||||||
params.hpfCutoffSweepValue = 0.0f;
|
params->hpfCutoffSweepValue = 0.0f;
|
||||||
//params.filterOn = false;
|
//params->filterOn = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Generates new wave data and updates sound buffer
|
// Generates new wave data and updates sound buffer
|
||||||
// NOTE: Operates on global variables: sound, wave
|
// NOTE: Operates on global variables: sound, wave
|
||||||
static void GenerateWave(WaveParams params)
|
static Wave GenerateWave(WaveParams params, int sampleRate, int sampleSize, int channels)
|
||||||
{
|
{
|
||||||
|
#define MAX_WAVE_LENGTH_SECONDS 10 // 10 seconds
|
||||||
|
|
||||||
// Configuration parameters for generation
|
// Configuration parameters for generation
|
||||||
// NOTE: Those parameters are calculated from selected values
|
// NOTE: Those parameters are calculated from selected values
|
||||||
int phase;
|
int phase;
|
||||||
@ -766,14 +778,17 @@ static void GenerateWave(WaveParams params)
|
|||||||
if (params.repeatSpeedValue == 0.0f) repeatLimit = 0;
|
if (params.repeatSpeedValue == 0.0f) repeatLimit = 0;
|
||||||
//----------------------------------------------------------------------------------------
|
//----------------------------------------------------------------------------------------
|
||||||
|
|
||||||
|
// NOTE: We reserve enough space for up to 10 seconds of wave audio at given sample rate
|
||||||
|
// By default we use float size samples, they are converted to desired sample size at the end
|
||||||
|
float *buffer = (float *)malloc(MAX_WAVE_LENGTH_SECONDS*sampleRate*sizeof(float));
|
||||||
bool generatingSample = true;
|
bool generatingSample = true;
|
||||||
float *buffer = (float *)wave.data;
|
int sampleCount = 0;
|
||||||
|
|
||||||
for (int i = 0; i < MAX_WAVE_LENGTH*wave.sampleRate; i++)
|
for (int i = 0; i < MAX_WAVE_LENGTH_SECONDS*sampleRate; i++)
|
||||||
{
|
{
|
||||||
if (!generatingSample)
|
if (!generatingSample)
|
||||||
{
|
{
|
||||||
wave.sampleCount = i;
|
sampleCount = i;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -893,22 +908,18 @@ static void GenerateWave(WaveParams params)
|
|||||||
{
|
{
|
||||||
if (fp < squareDuty) sample = 0.5f;
|
if (fp < squareDuty) sample = 0.5f;
|
||||||
else sample = -0.5f;
|
else sample = -0.5f;
|
||||||
|
|
||||||
} break;
|
} break;
|
||||||
case 1: // Sawtooth wave
|
case 1: // Sawtooth wave
|
||||||
{
|
{
|
||||||
sample = 1.0f - fp*2;
|
sample = 1.0f - fp*2;
|
||||||
|
|
||||||
} break;
|
} break;
|
||||||
case 2: // Sine wave
|
case 2: // Sine wave
|
||||||
{
|
{
|
||||||
sample = sinf(fp*2*PI);
|
sample = sinf(fp*2*PI);
|
||||||
|
|
||||||
} break;
|
} break;
|
||||||
case 3: // Noise wave
|
case 3: // Noise wave
|
||||||
{
|
{
|
||||||
sample = noiseBuffer[phase*32/period];
|
sample = noiseBuffer[phase*32/period];
|
||||||
|
|
||||||
} break;
|
} break;
|
||||||
default: break;
|
default: break;
|
||||||
}
|
}
|
||||||
@ -951,29 +962,45 @@ static void GenerateWave(WaveParams params)
|
|||||||
//------------------------------------------------------------------------------------
|
//------------------------------------------------------------------------------------
|
||||||
|
|
||||||
// Accumulate samples in the buffer
|
// Accumulate samples in the buffer
|
||||||
if (wave.data != NULL)
|
if (ssample > 1.0f) ssample = 1.0f;
|
||||||
{
|
if (ssample < -1.0f) ssample = -1.0f;
|
||||||
if (ssample > 1.0f) ssample = 1.0f;
|
|
||||||
if (ssample < -1.0f) ssample = -1.0f;
|
|
||||||
|
|
||||||
*buffer++ = ssample;
|
*buffer++ = ssample; //buffer[i] = ssample;
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Update sound buffer with new data
|
// TODO: Convert wave to desired format... or do it on generation!
|
||||||
UpdateSound(sound, wave.data, wave.sampleCount);
|
Wave wave;
|
||||||
|
|
||||||
|
wave.sampleCount = sampleCount;
|
||||||
|
wave.sampleRate = sampleRate;
|
||||||
|
wave.sampleSize = sampleSize; // default: 32 bit -> float
|
||||||
|
wave.channels = channels;
|
||||||
|
|
||||||
|
wave.data = malloc(wave.sampleCount*wave.sampleSize/8);
|
||||||
|
|
||||||
|
// TODO: Format buffer data properly depending on sampleSize, now it only works for 32bit data!
|
||||||
|
memcpy(wave.data, buffer, wave.sampleCount*wave.sampleSize/8);
|
||||||
|
|
||||||
|
free(buffer);
|
||||||
|
|
||||||
|
return wave;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Generate wave, update sound and play sound
|
// Generate wave, update sound and play sound
|
||||||
static void GeneratePlay(void)
|
static void GeneratePlay(void)
|
||||||
{
|
{
|
||||||
GenerateWave(params);
|
UnloadWave(wave);
|
||||||
|
wave = GenerateWave(params, 44100, 32, 1); // Generate wave from parameters
|
||||||
|
UpdateSound(sound, wave.data, wave.sampleCount); // Update sound buffer with new data
|
||||||
|
|
||||||
PlaySound(sound);
|
PlaySound(sound);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Load .rfx (rFXGen) or .sfs (sfxr) sound parameters file
|
// Load .rfx (rFXGen) or .sfs (sfxr) sound parameters file
|
||||||
static void LoadSoundParams(const char* fileName)
|
static WaveParams LoadSoundParams(const char* fileName)
|
||||||
{
|
{
|
||||||
|
WaveParams params = { 0 };
|
||||||
|
|
||||||
if (strcmp(GetExtension(fileName),"sfs") == 0)
|
if (strcmp(GetExtension(fileName),"sfs") == 0)
|
||||||
{
|
{
|
||||||
FILE *file = fopen(fileName, "rb");
|
FILE *file = fopen(fileName, "rb");
|
||||||
@ -1063,10 +1090,11 @@ static void LoadSoundParams(const char* fileName)
|
|||||||
fclose(rfxFile);
|
fclose(rfxFile);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return params;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Save .rfx (rFXGen) or .sfs (sfxr) sound parameters file
|
// Save .rfx (rFXGen) or .sfs (sfxr) sound parameters file
|
||||||
static void SaveSoundParams(const char* fileName)
|
static void SaveSoundParams(const char* fileName, WaveParams params)
|
||||||
{
|
{
|
||||||
if (strcmp(GetExtension(fileName),"sfs") == 0)
|
if (strcmp(GetExtension(fileName),"sfs") == 0)
|
||||||
{
|
{
|
||||||
@ -1145,7 +1173,7 @@ static void SaveSoundParams(const char* fileName)
|
|||||||
// NOTE: For proper visualization, MSAA x4 is recommended, alternatively
|
// NOTE: For proper visualization, MSAA x4 is recommended, alternatively
|
||||||
// it should be rendered to a bigger texture and then scaled down with
|
// it should be rendered to a bigger texture and then scaled down with
|
||||||
// bilinear/trilinear texture filtering
|
// bilinear/trilinear texture filtering
|
||||||
static void DrawWave(Rectangle bounds, Color color)
|
static void DrawWave(Wave wave, Rectangle bounds, Color color)
|
||||||
{
|
{
|
||||||
float sample, sampleNext;
|
float sample, sampleNext;
|
||||||
float currentSample = 0.0f;
|
float currentSample = 0.0f;
|
||||||
@ -1247,7 +1275,7 @@ static void SaveWAV(const char *fileName, Wave wave)
|
|||||||
// Generate sound: Pickup/Coin
|
// Generate sound: Pickup/Coin
|
||||||
static void BtnPickupCoin(void)
|
static void BtnPickupCoin(void)
|
||||||
{
|
{
|
||||||
ResetParams();
|
ResetParams(¶ms);
|
||||||
|
|
||||||
params.startFrequencyValue = 0.4f + frnd(0.5f);
|
params.startFrequencyValue = 0.4f + frnd(0.5f);
|
||||||
params.attackTimeValue = 0.0f;
|
params.attackTimeValue = 0.0f;
|
||||||
@ -1267,7 +1295,7 @@ static void BtnPickupCoin(void)
|
|||||||
// Generate sound: Laser shoot
|
// Generate sound: Laser shoot
|
||||||
static void BtnLaserShoot(void)
|
static void BtnLaserShoot(void)
|
||||||
{
|
{
|
||||||
ResetParams();
|
ResetParams(¶ms);
|
||||||
|
|
||||||
params.waveTypeValue = rnd(2);
|
params.waveTypeValue = rnd(2);
|
||||||
|
|
||||||
@ -1318,7 +1346,7 @@ static void BtnLaserShoot(void)
|
|||||||
// Generate sound: Explosion
|
// Generate sound: Explosion
|
||||||
static void BtnExplosion(void)
|
static void BtnExplosion(void)
|
||||||
{
|
{
|
||||||
ResetParams();
|
ResetParams(¶ms);
|
||||||
|
|
||||||
params.waveTypeValue = 3;
|
params.waveTypeValue = 3;
|
||||||
|
|
||||||
@ -1368,7 +1396,7 @@ static void BtnExplosion(void)
|
|||||||
// Generate sound: Powerup
|
// Generate sound: Powerup
|
||||||
static void BtnPowerup(void)
|
static void BtnPowerup(void)
|
||||||
{
|
{
|
||||||
ResetParams();
|
ResetParams(¶ms);
|
||||||
|
|
||||||
if (rnd(1)) params.waveTypeValue = 1;
|
if (rnd(1)) params.waveTypeValue = 1;
|
||||||
else params.squareDutyValue = frnd(0.6f);
|
else params.squareDutyValue = frnd(0.6f);
|
||||||
@ -1401,7 +1429,7 @@ static void BtnPowerup(void)
|
|||||||
// Generate sound: Hit/Hurt
|
// Generate sound: Hit/Hurt
|
||||||
static void BtnHitHurt(void)
|
static void BtnHitHurt(void)
|
||||||
{
|
{
|
||||||
ResetParams();
|
ResetParams(¶ms);
|
||||||
|
|
||||||
params.waveTypeValue = rnd(2);
|
params.waveTypeValue = rnd(2);
|
||||||
if (params.waveTypeValue == 2) params.waveTypeValue = 3;
|
if (params.waveTypeValue == 2) params.waveTypeValue = 3;
|
||||||
@ -1421,7 +1449,7 @@ static void BtnHitHurt(void)
|
|||||||
// Generate sound: Jump
|
// Generate sound: Jump
|
||||||
static void BtnJump(void)
|
static void BtnJump(void)
|
||||||
{
|
{
|
||||||
ResetParams();
|
ResetParams(¶ms);
|
||||||
|
|
||||||
params.waveTypeValue = 0;
|
params.waveTypeValue = 0;
|
||||||
params.squareDutyValue = frnd(0.6f);
|
params.squareDutyValue = frnd(0.6f);
|
||||||
@ -1440,7 +1468,7 @@ static void BtnJump(void)
|
|||||||
// Generate sound: Blip/Select
|
// Generate sound: Blip/Select
|
||||||
static void BtnBlipSelect(void)
|
static void BtnBlipSelect(void)
|
||||||
{
|
{
|
||||||
ResetParams();
|
ResetParams(¶ms);
|
||||||
|
|
||||||
params.waveTypeValue = rnd(1);
|
params.waveTypeValue = rnd(1);
|
||||||
if (params.waveTypeValue == 0) params.squareDutyValue = frnd(0.6f);
|
if (params.waveTypeValue == 0) params.squareDutyValue = frnd(0.6f);
|
||||||
@ -1546,7 +1574,7 @@ static void BtnLoadSound(void)
|
|||||||
|
|
||||||
if (fileName != NULL)
|
if (fileName != NULL)
|
||||||
{
|
{
|
||||||
LoadSoundParams(fileName);
|
params = LoadSoundParams(fileName);
|
||||||
//GeneratePlay();
|
//GeneratePlay();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1564,7 +1592,7 @@ static void BtnSaveSound(void)
|
|||||||
const char *filters[] = { "*.rfx", "*.sfs" };
|
const char *filters[] = { "*.rfx", "*.sfs" };
|
||||||
const char *fileName = tinyfd_saveFileDialog("Save sound parameters file", currrentPathFile, 2, filters, "Sound Param Files (*.rfx, *.sfs)");
|
const char *fileName = tinyfd_saveFileDialog("Save sound parameters file", currrentPathFile, 2, filters, "Sound Param Files (*.rfx, *.sfs)");
|
||||||
|
|
||||||
if (fileName != NULL) SaveSoundParams(fileName);
|
if (fileName != NULL) SaveSoundParams(fileName, params);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Export current sound as .wav
|
// Export current sound as .wav
|
||||||
|
|||||||
Reference in New Issue
Block a user