mirror of
https://github.com/bjornbytes/lovr.git
synced 2024-07-03 21:13:42 +00:00
Basic SoundData objects;
This commit is contained in:
parent
f903b6014c
commit
764f6eb595
|
@ -56,6 +56,7 @@ extern const luaL_Reg lovrRasterizer[];
|
||||||
extern const luaL_Reg lovrShader[];
|
extern const luaL_Reg lovrShader[];
|
||||||
extern const luaL_Reg lovrShape[];
|
extern const luaL_Reg lovrShape[];
|
||||||
extern const luaL_Reg lovrSliderJoint[];
|
extern const luaL_Reg lovrSliderJoint[];
|
||||||
|
extern const luaL_Reg lovrSoundData[];
|
||||||
extern const luaL_Reg lovrSource[];
|
extern const luaL_Reg lovrSource[];
|
||||||
extern const luaL_Reg lovrSphereShape[];
|
extern const luaL_Reg lovrSphereShape[];
|
||||||
extern const luaL_Reg lovrTexture[];
|
extern const luaL_Reg lovrTexture[];
|
||||||
|
|
|
@ -2,7 +2,9 @@
|
||||||
#include "data/audioStream.h"
|
#include "data/audioStream.h"
|
||||||
#include "data/modelData.h"
|
#include "data/modelData.h"
|
||||||
#include "data/rasterizer.h"
|
#include "data/rasterizer.h"
|
||||||
|
#include "data/soundData.h"
|
||||||
#include "data/textureData.h"
|
#include "data/textureData.h"
|
||||||
|
#include "data/vertexData.h"
|
||||||
|
|
||||||
int l_lovrDataInit(lua_State* L) {
|
int l_lovrDataInit(lua_State* L) {
|
||||||
lua_newtable(L);
|
lua_newtable(L);
|
||||||
|
@ -11,6 +13,7 @@ int l_lovrDataInit(lua_State* L) {
|
||||||
luax_registertype(L, "AudioStream", lovrAudioStream);
|
luax_registertype(L, "AudioStream", lovrAudioStream);
|
||||||
luax_registertype(L, "ModelData", lovrModelData);
|
luax_registertype(L, "ModelData", lovrModelData);
|
||||||
luax_registertype(L, "Rasterizer", lovrRasterizer);
|
luax_registertype(L, "Rasterizer", lovrRasterizer);
|
||||||
|
luax_extendtype(L, "Blob", "SoundData", lovrBlob, lovrSoundData);
|
||||||
luax_extendtype(L, "Blob", "TextureData", lovrBlob, lovrTextureData);
|
luax_extendtype(L, "Blob", "TextureData", lovrBlob, lovrTextureData);
|
||||||
luax_extendtype(L, "Blob", "VertexData", lovrBlob, lovrVertexData);
|
luax_extendtype(L, "Blob", "VertexData", lovrBlob, lovrVertexData);
|
||||||
return 1;
|
return 1;
|
||||||
|
@ -41,7 +44,7 @@ int l_lovrDataNewBlob(lua_State* L) {
|
||||||
}
|
}
|
||||||
|
|
||||||
int l_lovrDataNewAudioStream(lua_State* L) {
|
int l_lovrDataNewAudioStream(lua_State* L) {
|
||||||
Blob* blob = luax_readblob(L, 1, "Sound");
|
Blob* blob = luax_readblob(L, 1, "AudioStream");
|
||||||
size_t bufferSize = luaL_optinteger(L, 2, 4096);
|
size_t bufferSize = luaL_optinteger(L, 2, 4096);
|
||||||
AudioStream* stream = lovrAudioStreamCreate(blob, bufferSize);
|
AudioStream* stream = lovrAudioStreamCreate(blob, bufferSize);
|
||||||
luax_pushtype(L, AudioStream, stream);
|
luax_pushtype(L, AudioStream, stream);
|
||||||
|
@ -77,6 +80,32 @@ int l_lovrDataNewRasterizer(lua_State* L) {
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int l_lovrDataNewSoundData(lua_State* L) {
|
||||||
|
if (lua_type(L, 1) == LUA_TNUMBER) {
|
||||||
|
int samples = luaL_checkinteger(L, 1);
|
||||||
|
int sampleRate = luaL_optinteger(L, 2, 44100);
|
||||||
|
int bitDepth = luaL_optinteger(L, 3, 16);
|
||||||
|
int channelCount = luaL_optinteger(L, 4, 2);
|
||||||
|
SoundData* soundData = lovrSoundDataCreate(samples, sampleRate, bitDepth, channelCount);
|
||||||
|
luax_pushtype(L, SoundData, soundData);
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
AudioStream** audioStream;
|
||||||
|
if ((audioStream = luax_totype(L, 1, AudioStream)) != NULL) {
|
||||||
|
SoundData* soundData = lovrSoundDataCreateFromAudioStream(*audioStream);
|
||||||
|
luax_pushtype(L, SoundData, soundData);
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
Blob* blob = luax_readblob(L, 1, "SoundData");
|
||||||
|
SoundData* soundData = lovrSoundDataCreateFromBlob(blob);
|
||||||
|
luax_pushtype(L, SoundData, soundData);
|
||||||
|
lovrRelease(blob);
|
||||||
|
lovrRelease(soundData);
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
int l_lovrDataNewTextureData(lua_State* L) {
|
int l_lovrDataNewTextureData(lua_State* L) {
|
||||||
TextureData* textureData = NULL;
|
TextureData* textureData = NULL;
|
||||||
if (lua_type(L, 1) == LUA_TNUMBER) {
|
if (lua_type(L, 1) == LUA_TNUMBER) {
|
||||||
|
@ -135,6 +164,7 @@ const luaL_Reg lovrData[] = {
|
||||||
{ "newAudioStream", l_lovrDataNewAudioStream },
|
{ "newAudioStream", l_lovrDataNewAudioStream },
|
||||||
{ "newModelData", l_lovrDataNewModelData },
|
{ "newModelData", l_lovrDataNewModelData },
|
||||||
{ "newRasterizer", l_lovrDataNewRasterizer },
|
{ "newRasterizer", l_lovrDataNewRasterizer },
|
||||||
|
{ "newSoundData", l_lovrDataNewSoundData },
|
||||||
{ "newTextureData", l_lovrDataNewTextureData },
|
{ "newTextureData", l_lovrDataNewTextureData },
|
||||||
{ "newVertexData", l_lovrDataNewVertexData },
|
{ "newVertexData", l_lovrDataNewVertexData },
|
||||||
{ NULL, NULL }
|
{ NULL, NULL }
|
||||||
|
|
41
src/api/types/soundData.c
Normal file
41
src/api/types/soundData.c
Normal file
|
@ -0,0 +1,41 @@
|
||||||
|
#include "api.h"
|
||||||
|
#include "data/soundData.h"
|
||||||
|
|
||||||
|
int l_lovrSoundDataGetBitDepth(lua_State* L) {
|
||||||
|
SoundData* soundData = luax_checktype(L, 1, SoundData);
|
||||||
|
lua_pushinteger(L, soundData->bitDepth);
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
int l_lovrSoundDataGetChannelCount(lua_State* L) {
|
||||||
|
SoundData* soundData = luax_checktype(L, 1, SoundData);
|
||||||
|
lua_pushinteger(L, soundData->channelCount);
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
int l_lovrSoundDataGetDuration(lua_State* L) {
|
||||||
|
SoundData* soundData = luax_checktype(L, 1, SoundData);
|
||||||
|
lua_pushnumber(L, soundData->samples / (float) soundData->sampleRate);
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
int l_lovrSoundDataGetSampleCount(lua_State* L) {
|
||||||
|
SoundData* soundData = luax_checktype(L, 1, SoundData);
|
||||||
|
lua_pushinteger(L, soundData->samples);
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
int l_lovrSoundDataGetSampleRate(lua_State* L) {
|
||||||
|
SoundData* soundData = luax_checktype(L, 1, SoundData);
|
||||||
|
lua_pushinteger(L, soundData->sampleRate);
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
const luaL_Reg lovrSoundData[] = {
|
||||||
|
{ "getBitDepth", l_lovrSoundDataGetBitDepth },
|
||||||
|
{ "getChannelCount", l_lovrSoundDataGetChannelCount },
|
||||||
|
{ "getDuration", l_lovrSoundDataGetDuration },
|
||||||
|
{ "getSampleCount", l_lovrSoundDataGetSampleCount },
|
||||||
|
{ "getSampleRate", l_lovrSoundDataGetSampleRate },
|
||||||
|
{ NULL, NULL }
|
||||||
|
};
|
|
@ -262,7 +262,7 @@ void lovrSourceStream(Source* source, ALuint* buffers, int count) {
|
||||||
int n = 0;
|
int n = 0;
|
||||||
|
|
||||||
// Keep decoding until there is nothing left to decode or all the buffers are filled
|
// Keep decoding until there is nothing left to decode or all the buffers are filled
|
||||||
while (n < count && (samples = lovrAudioStreamDecode(stream)) != 0) {
|
while (n < count && (samples = lovrAudioStreamDecode(stream, NULL, 0)) != 0) {
|
||||||
alBufferData(buffers[n++], format, stream->buffer, samples * sizeof(ALshort), frequency);
|
alBufferData(buffers[n++], format, stream->buffer, samples * sizeof(ALshort), frequency);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -37,11 +37,11 @@ void lovrAudioStreamDestroy(void* ref) {
|
||||||
free(stream);
|
free(stream);
|
||||||
}
|
}
|
||||||
|
|
||||||
int lovrAudioStreamDecode(AudioStream* stream) {
|
int lovrAudioStreamDecode(AudioStream* stream, short* destination, size_t size) {
|
||||||
stb_vorbis* decoder = (stb_vorbis*) stream->decoder;
|
stb_vorbis* decoder = (stb_vorbis*) stream->decoder;
|
||||||
short* buffer = (short*) stream->buffer;
|
short* buffer = destination ? destination : (short*) stream->buffer;
|
||||||
|
int capacity = destination ? size : (stream->bufferSize / sizeof(short));
|
||||||
int channelCount = stream->channelCount;
|
int channelCount = stream->channelCount;
|
||||||
int capacity = stream->bufferSize / sizeof(short);
|
|
||||||
int samples = 0;
|
int samples = 0;
|
||||||
|
|
||||||
while (samples < capacity) {
|
while (samples < capacity) {
|
||||||
|
|
|
@ -17,7 +17,7 @@ typedef struct {
|
||||||
|
|
||||||
AudioStream* lovrAudioStreamCreate(Blob* blob, size_t bufferSize);
|
AudioStream* lovrAudioStreamCreate(Blob* blob, size_t bufferSize);
|
||||||
void lovrAudioStreamDestroy(void* ref);
|
void lovrAudioStreamDestroy(void* ref);
|
||||||
int lovrAudioStreamDecode(AudioStream* stream);
|
int lovrAudioStreamDecode(AudioStream* stream, short* destination, size_t size);
|
||||||
void lovrAudioStreamRewind(AudioStream* stream);
|
void lovrAudioStreamRewind(AudioStream* stream);
|
||||||
void lovrAudioStreamSeek(AudioStream* stream, int sample);
|
void lovrAudioStreamSeek(AudioStream* stream, int sample);
|
||||||
int lovrAudioStreamTell(AudioStream* stream);
|
int lovrAudioStreamTell(AudioStream* stream);
|
||||||
|
|
52
src/data/soundData.c
Normal file
52
src/data/soundData.c
Normal file
|
@ -0,0 +1,52 @@
|
||||||
|
#include "data/soundData.h"
|
||||||
|
#include "lib/stb/stb_vorbis.h"
|
||||||
|
|
||||||
|
SoundData* lovrSoundDataCreate(int samples, int sampleRate, int bitDepth, int channelCount) {
|
||||||
|
SoundData* soundData = lovrAlloc(sizeof(SoundData), lovrSoundDataDestroy);
|
||||||
|
if (!soundData) return NULL;
|
||||||
|
|
||||||
|
soundData->samples = samples;
|
||||||
|
soundData->sampleRate = sampleRate;
|
||||||
|
soundData->bitDepth = bitDepth;
|
||||||
|
soundData->channelCount = channelCount;
|
||||||
|
soundData->blob.size = samples * channelCount * (bitDepth / 8);
|
||||||
|
soundData->blob.data = calloc(1, soundData->blob.size);
|
||||||
|
|
||||||
|
return soundData;
|
||||||
|
}
|
||||||
|
|
||||||
|
SoundData* lovrSoundDataCreateFromAudioStream(AudioStream* audioStream) {
|
||||||
|
SoundData* soundData = lovrAlloc(sizeof(SoundData), lovrSoundDataDestroy);
|
||||||
|
if (!soundData) return NULL;
|
||||||
|
|
||||||
|
soundData->samples = audioStream->samples;
|
||||||
|
soundData->sampleRate = audioStream->sampleRate;
|
||||||
|
soundData->bitDepth = audioStream->bitDepth;
|
||||||
|
soundData->channelCount = audioStream->channelCount;
|
||||||
|
soundData->blob.size = audioStream->samples * audioStream->channelCount * (audioStream->bitDepth / 8);
|
||||||
|
soundData->blob.data = calloc(1, soundData->blob.size);
|
||||||
|
|
||||||
|
int samples;
|
||||||
|
short* buffer = soundData->blob.data;
|
||||||
|
size_t offset = 0;
|
||||||
|
lovrAudioStreamRewind(audioStream);
|
||||||
|
while ((samples = lovrAudioStreamDecode(audioStream, buffer + offset, soundData->blob.size - (offset * sizeof(short)))) != 0) {
|
||||||
|
offset += samples;
|
||||||
|
}
|
||||||
|
|
||||||
|
return soundData;
|
||||||
|
}
|
||||||
|
|
||||||
|
SoundData* lovrSoundDataCreateFromBlob(Blob* blob) {
|
||||||
|
SoundData* soundData = lovrAlloc(sizeof(SoundData), lovrSoundDataDestroy);
|
||||||
|
if (!soundData) return NULL;
|
||||||
|
|
||||||
|
soundData->samples = stb_vorbis_decode_memory(blob->data, blob->size, &soundData->channelCount, &soundData->sampleRate, (short**) &soundData->blob.data);
|
||||||
|
soundData->bitDepth = 16;
|
||||||
|
|
||||||
|
return soundData;
|
||||||
|
}
|
||||||
|
|
||||||
|
void lovrSoundDataDestroy(void* ref) {
|
||||||
|
lovrBlobDestroy(ref);
|
||||||
|
}
|
17
src/data/soundData.h
Normal file
17
src/data/soundData.h
Normal file
|
@ -0,0 +1,17 @@
|
||||||
|
#include "data/blob.h"
|
||||||
|
#include "data/audioStream.h"
|
||||||
|
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
typedef struct {
|
||||||
|
Blob blob;
|
||||||
|
int channelCount;
|
||||||
|
int sampleRate;
|
||||||
|
int samples;
|
||||||
|
int bitDepth;
|
||||||
|
} SoundData;
|
||||||
|
|
||||||
|
SoundData* lovrSoundDataCreate(int samples, int sampleRate, int bitDepth, int channels);
|
||||||
|
SoundData* lovrSoundDataCreateFromAudioStream(AudioStream* audioStream);
|
||||||
|
SoundData* lovrSoundDataCreateFromBlob(Blob* blob);
|
||||||
|
void lovrSoundDataDestroy(void* ref);
|
Loading…
Reference in a new issue