- Treballant en el canvi a JailAudio

This commit is contained in:
2024-11-25 14:20:51 +01:00
parent cddd79f05e
commit 916a24230e
5 changed files with 6012 additions and 38 deletions

View File

@@ -3,25 +3,25 @@ source = *.cpp ./lua/*.c
windows:
@echo off
g++ $(source) icon.res -Wall -Os -ffunction-sections -fdata-sections -Wl,--gc-sections -lmingw32 -lSDL2main -lSDL2 -lSDL2_mixer -mwindows -o "$(executable).exe"
g++ $(source) icon.res -Wall -Os -ffunction-sections -fdata-sections -Wl,--gc-sections -lmingw32 -lSDL2main -lSDL2 -mwindows -o "$(executable).exe"
strip -s -R .comment -R .gnu.version --strip-unneeded "$(executable).exe"
windows_debug:
@echo off
g++ $(source) -D DEBUG -g -Wall -Os -lmingw32 -lSDL2main -lSDL2 -lSDL2_mixer -o "$(executable)_debug.exe"
g++ $(source) -D DEBUG -g -Wall -Os -lmingw32 -lSDL2main -lSDL2 -o "$(executable)_debug.exe"
macos:
clang++ $(source) -Wall -Os -std=c++11 -ffunction-sections -fdata-sections -lSDL2 -lSDL2_mixer -o "$(executable)"
clang++ $(source) -Wall -Os -std=c++11 -ffunction-sections -fdata-sections -lSDL2 -o "$(executable)"
macos_debug:
clang++ $(source) -D DEBUG -g -Wall -Os -std=c++11 -ffunction-sections -fdata-sections -lSDL2 -lSDL2_mixer -o "$(executable)_debug"
clang++ $(source) -D DEBUG -g -Wall -Os -std=c++11 -ffunction-sections -fdata-sections -lSDL2 -o "$(executable)_debug"
macos_bundle:
clang++ $(source) -D MACOS_BUNDLE -Wall -Os -std=c++11 -framework SDL2 -framework SDL2_mixer -F /Library/Frameworks -ffunction-sections -fdata-sections -o mini_bundle -rpath @executable_path/../Frameworks/ -target x86_64-apple-macos10.12
clang++ $(source) -D MACOS_BUNDLE -Wall -Os -std=c++11 -framework SDL2 -F /Library/Frameworks -ffunction-sections -fdata-sections -o mini_bundle -rpath @executable_path/../Frameworks/ -target x86_64-apple-macos10.12
linux:
g++ $(source) -D LUA_USE_LINUX -Wall -Os -ffunction-sections -fdata-sections -Wl,--gc-sections -lSDL2 -lSDL2_mixer -o "$(executable)"
g++ $(source) -D LUA_USE_LINUX -Wall -Os -ffunction-sections -fdata-sections -Wl,--gc-sections -lSDL2 -o "$(executable)"
strip -s -R .comment -R .gnu.version --strip-unneeded "$(executable)"
linux_debug:
g++ $(source) -D LUA_USE_LINUX -D DEBUG -g -Wall -Os -ffunction-sections -fdata-sections -Wl,--gc-sections -lSDL2 -lSDL2_mixer -o "$(executable)_debug"
g++ $(source) -D LUA_USE_LINUX -D DEBUG -g -Wall -Os -ffunction-sections -fdata-sections -Wl,--gc-sections -lSDL2 -o "$(executable)_debug"

346
jail_audio.cpp Normal file
View File

@@ -0,0 +1,346 @@
#ifndef JA_USESDLMIXER
#include "jail_audio.h"
#include "stb_vorbis.c"
#include <SDL2/SDL.h>
#include <stdio.h>
#define JA_MAX_SIMULTANEOUS_CHANNELS 5
struct JA_Sound_t {
Uint32 length {0};
Uint8* buffer {NULL};
};
struct JA_Channel_t {
JA_Sound_t *sound;
int pos {0};
int times {0};
JA_Channel_state state { JA_CHANNEL_FREE };
};
struct JA_Music_t {
int samples {0};
int pos {0};
int times {0};
short* output {NULL};
JA_Music_state state {JA_MUSIC_INVALID};
};
JA_Music_t *current_music{NULL};
JA_Channel_t channels[JA_MAX_SIMULTANEOUS_CHANNELS];
int JA_freq {48000};
SDL_AudioFormat JA_format {AUDIO_S16};
Uint8 JA_channels {2};
int JA_musicVolume = 128;
int JA_soundVolume = 64;
bool JA_musicEnabled = true;
bool JA_soundEnabled = true;
SDL_AudioDeviceID sdlAudioDevice = 0;
void audioCallback(void * userdata, uint8_t * stream, int len) {
SDL_memset(stream, 0, len);
if (current_music != NULL && current_music->state == JA_MUSIC_PLAYING) {
const int size = SDL_min(len, current_music->samples*2-current_music->pos);
SDL_MixAudioFormat(stream, (Uint8*)(current_music->output+current_music->pos), AUDIO_S16, size, JA_musicVolume);
current_music->pos += size/2;
if (size < len) {
if (current_music->times != 0) {
SDL_MixAudioFormat(stream+size, (Uint8*)current_music->output, AUDIO_S16, len-size, JA_musicVolume);
current_music->pos = (len-size)/2;
if (current_music->times > 0) current_music->times--;
} else {
current_music->pos = 0;
current_music->state = JA_MUSIC_STOPPED;
}
}
}
// Mixar els channels mi amol
for (int i = 0; i < JA_MAX_SIMULTANEOUS_CHANNELS; i++) {
if (channels[i].state == JA_CHANNEL_PLAYING) {
const int size = SDL_min(len, channels[i].sound->length - channels[i].pos);
SDL_MixAudioFormat(stream, channels[i].sound->buffer + channels[i].pos, AUDIO_S16, size, JA_soundVolume);
channels[i].pos += size;
if (size < len) {
if (channels[i].times != 0) {
SDL_MixAudioFormat(stream + size, channels[i].sound->buffer, AUDIO_S16, len-size, JA_soundVolume);
channels[i].pos = len-size;
if (channels[i].times > 0) channels[i].times--;
} else {
JA_StopChannel(i);
}
}
}
}
}
void JA_Init(const int freq, const SDL_AudioFormat format, const int channels) {
JA_freq = freq;
JA_format = format;
JA_channels = channels;
SDL_AudioSpec audioSpec{JA_freq, JA_format, JA_channels, 0, 1024, 0, 0, audioCallback, NULL};
if (sdlAudioDevice != 0) SDL_CloseAudioDevice(sdlAudioDevice);
sdlAudioDevice = SDL_OpenAudioDevice(NULL, 0, &audioSpec, NULL, 0);
if (sdlAudioDevice==0) printf("Failed to initialize SDL audio!\n");
SDL_PauseAudioDevice(sdlAudioDevice, 0);
}
void JA_Quit() {
SDL_PauseAudioDevice(sdlAudioDevice, 1);
if (sdlAudioDevice != 0) SDL_CloseAudioDevice(sdlAudioDevice);
sdlAudioDevice = 0;
}
JA_Music_t *JA_LoadMusic(Uint8* buffer, Uint32 length)
{
int chan, samplerate;
JA_Music_t *music = new JA_Music_t();
music->samples = stb_vorbis_decode_memory(buffer, length, &chan, &samplerate, &music->output);
// [RZC 28/08/22] Abans el descomprimiem mentre el teniem obert
// music->samples = stb_vorbis_decode_filename(filename, &chan, &samplerate, &music->output);
SDL_AudioCVT cvt;
SDL_BuildAudioCVT(&cvt, AUDIO_S16, chan, samplerate, JA_format, JA_channels, JA_freq);
if (cvt.needed) {
cvt.len = music->samples * chan * 2;
cvt.buf = (Uint8 *) SDL_malloc(cvt.len * cvt.len_mult);
SDL_memcpy(cvt.buf, music->output, cvt.len);
SDL_ConvertAudio(&cvt);
free(music->output);
music->output = (short*)cvt.buf;
}
music->pos = 0;
music->state = JA_MUSIC_STOPPED;
return music;
}
JA_Music_t *JA_LoadMusic(const char* filename)
{
// [RZC 28/08/22] Carreguem primer el arxiu en memòria i després el descomprimim. Es algo més rapid.
FILE *f = fopen(filename, "rb");
fseek(f, 0, SEEK_END);
long fsize = ftell(f);
fseek(f, 0, SEEK_SET);
Uint8 *buffer = (Uint8*)malloc(fsize + 1);
if (fread(buffer, fsize, 1, f)!=1) return NULL;
fclose(f);
JA_Music_t *music = JA_LoadMusic(buffer, fsize);
free(buffer);
return music;
}
void JA_PlayMusic(JA_Music_t *music, const int loop)
{
if (!JA_musicEnabled) return;
if (current_music != NULL) {
current_music->pos = 0;
current_music->state = JA_MUSIC_STOPPED;
}
current_music = music;
current_music->pos = 0;
current_music->state = JA_MUSIC_PLAYING;
current_music->times = loop;
}
void JA_PauseMusic()
{
if (!JA_musicEnabled) return;
if (current_music == NULL || current_music->state == JA_MUSIC_INVALID) return;
current_music->state = JA_MUSIC_PAUSED;
}
void JA_ResumeMusic()
{
if (!JA_musicEnabled) return;
if (current_music == NULL || current_music->state == JA_MUSIC_INVALID) return;
current_music->state = JA_MUSIC_PLAYING;
}
void JA_StopMusic()
{
if (!JA_musicEnabled) return;
if (current_music == NULL || current_music->state == JA_MUSIC_INVALID) return;
current_music->pos = 0;
current_music->state = JA_MUSIC_STOPPED;
}
JA_Music_state JA_GetMusicState() {
if (!JA_musicEnabled) return JA_MUSIC_DISABLED;
if (current_music == NULL) return JA_MUSIC_INVALID;
return current_music->state;
}
void JA_DeleteMusic(JA_Music_t *music) {
if (current_music == music) current_music = NULL;
free(music->output);
delete music;
}
int JA_SetMusicVolume(int volume)
{
JA_musicVolume = volume > 128 ? 128 : volume < 0 ? 0 : volume;
return JA_musicVolume;
}
void JA_EnableMusic(const bool value)
{
if (!value && current_music != NULL && current_music->state==JA_MUSIC_PLAYING) JA_StopMusic();
JA_musicEnabled = value;
}
JA_Sound_t *JA_NewSound(Uint8* buffer, Uint32 length) {
JA_Sound_t *sound = new JA_Sound_t();
sound->buffer = buffer;
sound->length = length;
return sound;
}
JA_Sound_t *JA_LoadSound(uint8_t* buffer, uint32_t size) {
JA_Sound_t *sound = new JA_Sound_t();
SDL_AudioSpec wavSpec;
SDL_LoadWAV_RW(SDL_RWFromMem(buffer, size),1, &wavSpec, &sound->buffer, &sound->length);
SDL_AudioCVT cvt;
SDL_BuildAudioCVT(&cvt, wavSpec.format, wavSpec.channels, wavSpec.freq, JA_format, JA_channels, JA_freq);
cvt.len = sound->length;
cvt.buf = (Uint8 *) SDL_malloc(cvt.len * cvt.len_mult);
SDL_memcpy(cvt.buf, sound->buffer, sound->length);
SDL_ConvertAudio(&cvt);
SDL_FreeWAV(sound->buffer);
sound->buffer = cvt.buf;
sound->length = cvt.len_cvt;
return sound;
}
JA_Sound_t *JA_LoadSound(const char* filename) {
JA_Sound_t *sound = new JA_Sound_t();
SDL_AudioSpec wavSpec;
SDL_LoadWAV(filename, &wavSpec, &sound->buffer, &sound->length);
SDL_AudioCVT cvt;
SDL_BuildAudioCVT(&cvt, wavSpec.format, wavSpec.channels, wavSpec.freq, JA_format, JA_channels, JA_freq);
cvt.len = sound->length;
cvt.buf = (Uint8 *) SDL_malloc(cvt.len * cvt.len_mult);
SDL_memcpy(cvt.buf, sound->buffer, sound->length);
SDL_ConvertAudio(&cvt);
SDL_FreeWAV(sound->buffer);
sound->buffer = cvt.buf;
sound->length = cvt.len_cvt;
return sound;
}
int JA_PlaySound(JA_Sound_t *sound, const int loop)
{
if (!JA_soundEnabled) return -1;
int channel = 0;
while (channel < JA_MAX_SIMULTANEOUS_CHANNELS && channels[channel].state != JA_CHANNEL_FREE) { channel++; }
if (channel == JA_MAX_SIMULTANEOUS_CHANNELS) channel = 0;
channels[channel].sound = sound;
channels[channel].times = loop;
channels[channel].pos = 0;
channels[channel].state = JA_CHANNEL_PLAYING;
return channel;
}
void JA_DeleteSound(JA_Sound_t *sound)
{
for (int i = 0; i < JA_MAX_SIMULTANEOUS_CHANNELS; i++) {
if (channels[i].sound == sound) JA_StopChannel(i);
}
SDL_free(sound->buffer);
delete sound;
}
void JA_PauseChannel(const int channel)
{
if (!JA_soundEnabled) return;
if (channel == -1) {
for (int i = 0; i < JA_MAX_SIMULTANEOUS_CHANNELS; i++) {
if (channels[i].state == JA_CHANNEL_PLAYING) channels[i].state = JA_CHANNEL_PAUSED;
}
} else if (channel >= 0 && channel < JA_MAX_SIMULTANEOUS_CHANNELS) {
if (channels[channel].state == JA_CHANNEL_PLAYING) channels[channel].state = JA_CHANNEL_PAUSED;
}
}
void JA_ResumeChannel(const int channel)
{
if (!JA_soundEnabled) return;
if (channel == -1) {
for (int i = 0; i < JA_MAX_SIMULTANEOUS_CHANNELS; i++) {
if (channels[i].state == JA_CHANNEL_PAUSED) channels[i].state = JA_CHANNEL_PLAYING;
}
} else if (channel >= 0 && channel < JA_MAX_SIMULTANEOUS_CHANNELS) {
if (channels[channel].state == JA_CHANNEL_PAUSED) channels[channel].state = JA_CHANNEL_PLAYING;
}
}
void JA_StopChannel(const int channel)
{
if (!JA_soundEnabled) return;
if (channel == -1) {
for (int i = 0; i < JA_MAX_SIMULTANEOUS_CHANNELS; i++) {
channels[i].state = JA_CHANNEL_FREE;
channels[i].pos = 0;
channels[i].sound = NULL;
}
} else if (channel >= 0 && channel < JA_MAX_SIMULTANEOUS_CHANNELS) {
channels[channel].state = JA_CHANNEL_FREE;
channels[channel].pos = 0;
channels[channel].sound = NULL;
}
}
JA_Channel_state JA_GetChannelState(const int channel)
{
if (!JA_soundEnabled) return JA_SOUND_DISABLED;
if (channel < 0 || channel >= JA_MAX_SIMULTANEOUS_CHANNELS) return JA_CHANNEL_INVALID;
return channels[channel].state;
}
int JA_SetSoundVolume(int volume)
{
JA_soundVolume = volume > 128 ? 128 : volume < 0 ? 0 : volume;
return JA_soundVolume;
}
void JA_EnableSound(const bool value)
{
for (int i = 0; i < JA_MAX_SIMULTANEOUS_CHANNELS; i++)
{
if (channels[i].state == JA_CHANNEL_PLAYING) JA_StopChannel(i);
}
JA_soundEnabled = value;
}
int JA_SetVolume(int volume)
{
JA_musicVolume = volume > 128 ? 128 : volume < 0 ? 0 : volume;
JA_soundVolume = JA_musicVolume/2;
return JA_musicVolume;
}
#endif

36
jail_audio.h Normal file
View File

@@ -0,0 +1,36 @@
#pragma once
#include <SDL2/SDL.h>
enum JA_Channel_state { JA_CHANNEL_INVALID, JA_CHANNEL_FREE, JA_CHANNEL_PLAYING, JA_CHANNEL_PAUSED, JA_SOUND_DISABLED };
enum JA_Music_state { JA_MUSIC_INVALID, JA_MUSIC_PLAYING, JA_MUSIC_PAUSED, JA_MUSIC_STOPPED, JA_MUSIC_DISABLED };
struct JA_Sound_t;
struct JA_Music_t;
void JA_Init(const int freq, const SDL_AudioFormat format, const int channels);
void JA_Quit();
JA_Music_t *JA_LoadMusic(const char* filename);
JA_Music_t *JA_LoadMusic(Uint8* buffer, Uint32 length);
void JA_PlayMusic(JA_Music_t *music, const int loop = -1);
void JA_PauseMusic();
void JA_ResumeMusic();
void JA_StopMusic();
JA_Music_state JA_GetMusicState();
void JA_DeleteMusic(JA_Music_t *music);
int JA_SetMusicVolume(int volume);
void JA_EnableMusic(const bool value);
JA_Sound_t *JA_NewSound(Uint8* buffer, Uint32 length);
JA_Sound_t *JA_LoadSound(Uint8* buffer, Uint32 length);
JA_Sound_t *JA_LoadSound(const char* filename);
int JA_PlaySound(JA_Sound_t *sound, const int loop = 0);
void JA_PauseChannel(const int channel);
void JA_ResumeChannel(const int channel);
void JA_StopChannel(const int channel);
JA_Channel_state JA_GetChannelState(const int channel);
void JA_DeleteSound(JA_Sound_t *sound);
int JA_SetSoundVolume(int volume);
void JA_EnableSound(const bool value);
int JA_SetVolume(int volume);

View File

@@ -3,7 +3,8 @@
#include <string.h>
#include "lua.h"
#include "gif.c"
#include "SDL2/SDL_mixer.h"
//#include "SDL2/SDL_mixer.h"
#include "jail_audio.h"
#ifdef MACOS_BUNDLE
#include <libgen.h>
@@ -98,8 +99,8 @@ SDL_GameController *gamepad = NULL;
int8_t pad_just_pressed = SDL_CONTROLLER_BUTTON_INVALID;
#define MAX_SOUNDS 50
Mix_Music *music = NULL;
Mix_Chunk *sounds[MAX_SOUNDS];
JA_Music_t *music = NULL;
JA_Sound_t *sounds[MAX_SOUNDS];
int16_t beats, num_beats = 0;
@@ -112,19 +113,21 @@ char* get_value_from_line(char* line) {
void read_ini() {
int size;
printf("Carregant 'game.ini'...");
FILE *f = file_getfilepointer("game.ini", size); // fopen("game.ini", "r");
char line[1024];
if (f == NULL) return;
if (f == NULL) { printf("FAIL!\n"); return; }
printf("OK!\n");
while (fgets(line, sizeof(line), f)) {
char *value = get_value_from_line(line);
if (value != NULL) {
value[strlen(value)-1] = '\0';
if (strcmp(line, "title") == 0) strcpy(window_title, value);
else if (strcmp(line, "config") == 0) strcpy(config_folder, value);
else if (strcmp(line, "width") == 0) screen_width = atoi(value);
else if (strcmp(line, "height") == 0) screen_height = atoi(value);
else if (strcmp(line, "zoom") == 0) screen_zoom = atoi(value);
else if (strcmp(line, "fullscreen") == 0) screen_fullscreen = atoi(value);
if (strcmp(line, "title") == 0) { strcpy(window_title, value); printf("-title=%s\n", window_title); }
else if (strcmp(line, "config") == 0) { strcpy(config_folder, value); printf("-config=%s\n", config_folder); }
else if (strcmp(line, "width") == 0) { screen_width = atoi(value); printf("-screen width=%i\n", screen_width); }
else if (strcmp(line, "height") == 0) { screen_height = atoi(value); printf("-screen height=%i\n", screen_height); }
else if (strcmp(line, "zoom") == 0) { screen_zoom = atoi(value); printf("-screen zoom=%i\n", screen_zoom); }
else if (strcmp(line, "fullscreen") == 0) { screen_fullscreen = atoi(value); printf("-screen sullscreen=%i\n", screen_fullscreen); }
//else if (strcmp(line, "files") == 0) {
//lua_files = (char*)malloc(strlen(value));
// strcpy(lua_files, value);
@@ -132,6 +135,7 @@ void read_ini() {
}
}
fclose(f);
printf("FET\n");
}
void pset_fast(int x, int y) {
@@ -149,6 +153,7 @@ void pset_pattern(int x, int y) {
}
void reinit() {
printf("REINIT\n");
do_pset = pset_fast;
ds::pen_color = 6;
ds::back_color = 0;
@@ -168,13 +173,14 @@ void reinit() {
}
void initaudio() {
Mix_OpenAudio(44100, AUDIO_S16, 1, 512);
printf("Iniciant JailAudio...");
JA_Init(44100, AUDIO_S16, 1);
for (int i=0;i<MAX_SOUNDS;++i) sounds[i] = NULL;
}
void quitaudio() {
if (music != NULL) Mix_FreeMusic(music);
for (int i=0;i<MAX_SOUNDS;++i) if (sounds[i]!=NULL) Mix_FreeChunk(sounds[i]);
Mix_CloseAudio();
if (music != NULL) JA_DeleteMusic(music);
for (int i=0;i<MAX_SOUNDS;++i) if (sounds[i]!=NULL) JA_DeleteSound(sounds[i]);
JA_Quit();
}
int scrw() {
@@ -319,7 +325,7 @@ int main(int argc,char*argv[]){
initGamePad();
Mix_Init(MIX_INIT_OGG);
//Mix_Init(MIX_INIT_OGG);
SDL_Event mini_eve;
@@ -423,7 +429,7 @@ int main(int argc,char*argv[]){
lua_quit();
quitaudio();
Mix_Quit();
//Mix_Quit();
for (int i=0;i<10;++i) freesurf(i);
dest_surface = source_surface = map_surface = NULL;
@@ -1112,32 +1118,32 @@ int rnd(int x) {
void playmusic(const char *filename, const int loop) {
int size;
char *buffer = file_getfilebuffer(filename, size);
if (music != NULL) Mix_FreeMusic(music);
music = Mix_LoadMUS_RW(SDL_RWFromMem(buffer, size), 1);
Mix_PlayMusic(music, loop);
if (music != NULL) JA_DeleteMusic(music);
music = JA_LoadMusic((Uint8*)buffer, size);
JA_PlayMusic(music, loop);
}
void pausemusic() {
Mix_PauseMusic();
JA_PauseMusic();
}
void resumemusic() {
Mix_ResumeMusic();
JA_ResumeMusic();
}
void stopmusic(const int t) {
//Mix_HaltMusic();
Mix_FadeOutMusic(t);
JA_StopMusic();
//Mix_FadeOutMusic(t);
}
void musicpos(float value)
{
Mix_SetMusicPosition(value);
//Mix_SetMusicPosition(value);
}
float musicpos()
{
return Mix_GetMusicPosition(music);
return 0; //Mix_GetMusicPosition(music);
}
int loadsound(const char *filename) {
@@ -1145,24 +1151,26 @@ int loadsound(const char *filename) {
char *buffer = file_getfilebuffer(filename, size);
int i=0;
while (i<MAX_SOUNDS && sounds[i]!=NULL) i++;
if (i==MAX_SOUNDS) { i=0; Mix_FreeChunk(sounds[i]); }
sounds[i]=Mix_LoadWAV_RW(SDL_RWFromMem(buffer, size), 1);
if (i==MAX_SOUNDS) { i=0; JA_DeleteSound(sounds[i]); }
sounds[i]=JA_LoadSound((Uint8*)buffer, size);
return i;
}
void freesound(int soundfile) {
Mix_FreeChunk(sounds[soundfile]);
JA_DeleteSound(sounds[soundfile]);
sounds[soundfile] = NULL;
}
int playsound(int soundfile, const int volume) {
const int channel = Mix_PlayChannel(-1, sounds[soundfile], 0);
Mix_Volume(channel, volume!=-1?volume:MIX_MAX_VOLUME);
const int channel = JA_PlaySound(sounds[soundfile], 0);
JA_SetSoundVolume(128);
//Mix_Volume(channel, volume!=-1?volume:MIX_MAX_VOLUME);
return channel;
}
void stopsound(int soundchannel) {
Mix_HaltChannel(soundchannel);
JA_StopChannel(soundchannel);
//Mix_HaltChannel(soundchannel);
}
int getzoom() {

5584
stb_vorbis.c Normal file

File diff suppressed because it is too large Load Diff