aboutsummaryrefslogtreecommitdiff
path: root/src/libjin/audio/sdl/source.cpp
diff options
context:
space:
mode:
authorchai <chaifix@163.com>2018-07-28 00:50:12 +0800
committerchai <chaifix@163.com>2018-07-28 00:50:12 +0800
commit92dab582ccac31be7fa410e7f4fb3789e88a0629 (patch)
tree008bbecc76a73aae38d77d1851f4230756356a33 /src/libjin/audio/sdl/source.cpp
parentb855ebb91ad8d97617ec1aa418b4add84670a07d (diff)
*update
Diffstat (limited to 'src/libjin/audio/sdl/source.cpp')
-rw-r--r--src/libjin/audio/sdl/source.cpp399
1 files changed, 0 insertions, 399 deletions
diff --git a/src/libjin/audio/sdl/source.cpp b/src/libjin/audio/sdl/source.cpp
deleted file mode 100644
index 0eedbba..0000000
--- a/src/libjin/audio/sdl/source.cpp
+++ /dev/null
@@ -1,399 +0,0 @@
-#include "../../modules.h"
-#if JIN_MODULES_AUDIO && JIN_AUDIO_SDLAUDIO
-
-#include <exception>
-#include <fstream>
-
-#include "../../math/math.h"
-#include "../../utils/macros.h"
-#include "source.h"
-#include "3rdparty/wav/wav.h"
-#define STB_VORBIS_HEADER_ONLY
-#include "3rdparty/stb/stb_vorbis.c"
-
-#include "audio.h"
-
-namespace jin
-{
-namespace audio
-{
-
-#define BITS 8
-
- typedef struct SDLSourceCommand
- {
- typedef enum Action
- {
- Nothing = 0,
- Play,
- Stop,
- Pause,
- Resume,
- Rewind,
- SetVolume,
- SetLoop,
- SetRate,
- };
- Action action;
- union {
- int _integer;
- float _float;
- bool _boolean;
- const char* _string;
- } parameter;
-
- SDLSource* source;
- };
-
- typedef enum CHANNEL
- {
- MONO = 1, //
- STEREO = 2, //
- };
-
- typedef MASK enum STATUS
- {
- PLAYING = 1,
- PAUSED = 2,
- STOPPED = 4
- };
-
-#define Command SDLSourceCommand
-#define Action Command::Action
-#define Manager SDLSourceManager
-
- shared std::queue<Command*> Manager::commands;
- shared std::stack<Command*> Manager::commandsPool;
- shared std::vector<SDLSource*> Manager::sources;
- shared Manager* Manager::manager = nullptr;
-
- SDLSource* SDLSource::createSource(const char* file)
- {
- std::ifstream fs;
- fs.open(file, std::ios::binary);
- if (!fs.is_open())
- {
- fs.close();
- return nullptr;
- }
- fs.seekg(0,std::ios::end);
- int size = fs.tellg();
- fs.seekg(0, std::ios::beg);
- char* buffer = (char*)malloc(size);
- memset(buffer, 0, size);
- fs.read(buffer, size);
- fs.close();
- SDLSource* source = createSource(buffer, size);
- free(buffer);
- return source;
- }
-
- SDLSource* SDLSource::createSource(void* mem, size_t size)
- {
- if (mem == nullptr)
- return nullptr;
- SDLSource* source = new SDLSource();
- try
- {
- SourceType format = getType(mem, size);
- switch (format)
- {
- case OGG: source->decode_ogg(mem, size); break;
- case WAV: source->decode_wav(mem, size); break;
- }
- }
- catch (SourceException& exp)
- {
- delete source;
- return nullptr;
- };
- return source;
- }
-
- SDLSource::SDLSource()
- {
- memset(&status, 0, sizeof(status));
- memset(&raw, 0, sizeof(raw));
- }
-
- SDLSource::~SDLSource()
- {
- delete raw.data;
- raw.end = 0;
- raw.data = 0;
- }
-
- void SDLSource::decode_wav(void* mem, int size)
- {
- wav_t wav;
- if (wav_read(&wav, mem, size) == 0)
- {
- raw.data = wav.data;
- raw.length = wav.length * wav.bitdepth / 8;
- raw.end = (char*)raw.data + raw.length;
- raw.samplerate = wav.samplerate;
- raw.bitdepth = wav.bitdepth;
- raw.samples = raw.length / (wav.bitdepth / 8.f) / wav.channels;
- raw.channels = clamp(wav.channels, CHANNEL::MONO, CHANNEL::STEREO);
- }
- else
- throw SourceException();
- }
-
- void SDLSource::decode_ogg(void* _mem, int size)
- {
- unsigned char* mem = (unsigned char*)_mem;
- int channels;
- int samplerate;
- short* data = (short*)raw.data;
- int samples = stb_vorbis_decode_memory(
- mem,
- size,
- &channels,
- &samplerate,
- &data
- );
- const int bitdepth = sizeof(short) * BITS;
- raw.channels = channels;
- raw.samplerate = samplerate;
- raw.data = data;
- raw.samples = samples;
- raw.length = samples * channels * sizeof(short);
- raw.bitdepth = bitdepth;
- raw.end = (char*)data + raw.length;
- }
-
-#define ActionNone(T)\
-do{\
-Command* cmd = Manager::get()->getCommand();\
-cmd->action = Action::T; \
-cmd->source = this; \
-Manager::get()->pushCommand(cmd); \
-} while (0)
-
-#define ActionArg(T, ARGT, ARG)\
-do{\
-Command* cmd = Manager::get()->getCommand();\
-cmd->action = Action::T; \
-cmd->parameter.ARGT = ARG; \
-cmd->source = this; \
-Manager::get()->pushCommand(cmd); \
-}while(0)
-
-#define ActionInt(T, INT) ActionArg(T, _integer, INT)
-#define ActionFloat(T, FLT) ActionArg(T, _float, FLT)
-#define ActionString(T, STR) ActionArg(T, _string, STR)
-#define ActionBool(T, BOL) ActionArg(T, _boolean, BOL)
-
- void SDLSource::play()
- {
- ActionNone(Play);
- }
-
- void SDLSource::stop()
- {
- ActionNone(Stop);
- }
-
- void SDLSource::pause()
- {
- ActionNone(Pause);
- }
-
- void SDLSource::resume()
- {
- ActionNone(Resume);
- }
-
- void SDLSource::rewind()
- {
- ActionNone(Rewind);
- }
-
- inline bool SDLSource::isStopped() const
- {
- return is(STOPPED);
- }
-
- bool SDLSource::isPaused() const
- {
- return is(PAUSED);
- }
-
- void SDLSource::setPitch(float pitch)
- {
- }
-
- void SDLSource::setVolume(float volume)
- {
- ActionFloat(SetVolume, volume);
- }
-
- bool SDLSource::setLoop(bool loop)
- {
- ActionBool(SetLoop, loop);
- return false;
- }
-
- void SDLSource::setRate(float rate)
- {
- ActionFloat(SetRate, rate);
- }
-
- inline void SDLSource::handle(
- SDLSourceManager* manager,
- SDLSourceCommand* cmd
- )
- {
- switch (cmd->action)
- {
- case Command::Action::Play:
- manager->removeSource(this);
- manager->pushSource(this);
- status.state = PLAYING;
- status.pos = 0; // rewind
- break;
- case Command::Action::Stop:
- manager->removeSource(this);
- status.state = STOPPED;
- status.pos = 0; // rewind
- break;
- case Command::Action::Pause:
- manager->removeSource(this);
- status.state = PAUSED;
- break;
- case Command::Action::Resume:
- manager->removeSource(this);
- manager->pushSource(this);
- status.state = PLAYING;
- break;
- case Command::Action::Rewind:
- status.state = PLAYING;
- status.pos = 0;
- break;
- case Command::Action::SetVolume:
- //float cmd->parameter._float;
- break;
- case Command::Action::SetLoop:
- status.loop = cmd->parameter._boolean;
- break;
- }
- }
-
- inline void SDLSource::process(void* buf, size_t size)
- {
- short* buffer = (short*)buf; // AUDIO_S16SYS
- unsigned int samples = size / SDLAUDIO_BYTEDEPTH;
- short* sample;
- short origin;
-
- const char bitdepth = raw.bitdepth;
- const char channles = raw.channels;
-
- int pos = status.pos;
- int pitch = status.pitch;
- int state = status.state;
- bool loop = status.loop;
- int volume = status.volume;
- short* clip16 = nullptr;
- char* clip8 = nullptr;
- int clip = 0;
-
- if (bitdepth == 8)
- clip8 = (char*)raw.data;
- else if (bitdepth == 16)
- clip16 = (short*)raw.data;
-
- for (int i = 0; i < samples; i+=2 /*˫*/)
- {
- /* Ƶļsampleᱻ */
- sample = buffer + i * SDLAUDIO_BYTEDEPTH;
- origin = *sample;
- if (bitdepth == 8)
- {
- clip = *clip8;
- }
- else if (bitdepth == 16)
- clip = *clip16;
-
- }
- }
-
- Manager* Manager::get()
- {
- return (manager == nullptr ? manager = new Manager() : manager);
- }
-
- shared void Manager::processCommands()
- {
- Command* cmd = nullptr;
- SDLSource* source = nullptr;
- while (!commands.empty())
- {
- cmd = commands.front();
- if (cmd != nullptr)
- {
- source = cmd->source;
- if (source != nullptr)
- source->handle(manager, cmd);
- }
- commands.pop();
- }
- }
-
- /* AUDIO_S16SYS[size>>1] buffer */
- shared void Manager::processSources(void* buf, size_t size)
- {
- /* clear render buffer */
- memset(buf, 0, size);
- SDLSource* src = nullptr;
- std::vector<SDLSource*>::iterator it = sources.begin();
- for (; it != sources.end();)
- {
- src = *it;
- if (src != nullptr)
- src->process(buf, size);
- ++it;
- }
- }
-
- shared void Manager::removeSource(SDLSource* source)
- {
- std::vector<SDLSource*>::iterator it = sources.begin();
- for (it = sources.begin(); it != sources.end(); )
- {
- if (*it == source)
- {
- it = sources.erase(it);
- return;
- }
- ++it;
- }
- }
-
- shared void Manager::pushSource(SDLSource* source)
- {
- if(source != nullptr)
- sources.push_back(source);
- }
-
- shared void Manager::pushCommand(SDLSourceCommand* cmd)
- {
- commands.push(cmd);
- }
-
- shared Command* Manager::getCommand()
- {
- if (!commandsPool.empty())
- {
- Command* cmd = commandsPool.top();
- commandsPool.pop();
- return cmd;
- }
- return new Command();
- }
-
-}
-}
-
-#endif // JIN_MODULES_AUDIO && JIN_AUDIO_SDLAUDIO \ No newline at end of file