Sound decoders refactoring;

The decoders are now virtualized, the high-level decoding code is unified
and any format is theoretically streamable.


git-svn-id: svn://svn.code.sf.net/p/sc2/code/trunk@1266 8092fc87-c524-0410-9efc-e669fe64eaf9
This commit is contained in:
avolkov
2003-10-08 10:41:10 +00:00
parent 37683f849f
commit 7e8040a0dd
14 changed files with 1824 additions and 1076 deletions
+1 -1
View File
@@ -1,2 +1,2 @@
uqm_SUBDIRS="mikmod"
uqm_CFILES="decoder.c wav.c dukaud.c"
uqm_CFILES="decoder.c wav.c dukaud.c modaud.c oggaud.c"
File diff suppressed because it is too large Load Diff
+45 -23
View File
@@ -39,28 +39,61 @@ typedef struct tfb_decoderformats
uint32 stereo16;
} TFB_DecoderFormats;
typedef struct tfb_sounddecoder
// forward-declare
typedef struct tfb_sounddecoder TFB_SoundDecoder;
#define THIS_PTR TFB_SoundDecoder*
typedef struct tfb_sounddecoderfunc
{
// public
void *buffer;
uint32 buffer_size;
const char* (* GetName) (void);
bool (* InitModule) (int flags);
void (* TermModule) ();
uint32 (* GetStructSize) (void);
int (* GetError) (THIS_PTR);
bool (* Init) (THIS_PTR);
void (* Term) (THIS_PTR);
bool (* Open) (THIS_PTR, uio_DirHandle *dir, const char *filename);
void (* Close) (THIS_PTR);
int (* Decode) (THIS_PTR, void* buf, sint32 bufsize);
// returns <0 on error, ==0 when no more data, >0 bytes returned
uint32 (* Seek) (THIS_PTR, uint32 pcm_pos);
// returns the pcm position set
uint32 (* GetFrame) (THIS_PTR);
} TFB_SoundDecoderFuncs;
#undef THIS_PTR
struct tfb_sounddecoder
{
// decoder virtual funcs - R/O
const TFB_SoundDecoderFuncs *funcs;
// public R/O, set by decoder
uint32 format;
uint32 frequency;
bool looping;
sint32 error;
float length; // total length in seconds
char *decoder_info;
bool is_null;
bool need_swap;
// public R/O, set by wrapper
void *buffer;
uint32 buffer_size;
sint32 error;
uint32 bytes_per_samp;
// public R/W
bool looping;
// semi-private
sint32 type;
uio_DirHandle *dir;
char *filename;
void *data;
uint32 pos;
uint32 start_sample;
uint32 end_sample;
} TFB_SoundDecoder;
};
// return values
enum
@@ -70,18 +103,6 @@ enum
SOUNDDECODER_EOF,
};
// types
enum
{
SOUNDDECODER_NONE,
SOUNDDECODER_WAV,
SOUNDDECODER_MOD,
SOUNDDECODER_OGG,
SOUNDDECODER_NULL,
SOUNDDECODER_BUF,
SOUNDDECODER_DUK,
};
extern TFB_DecoderFormats decoder_formats;
void SoundDecoder_SwapWords (uint16* data, uint32 size);
sint32 SoundDecoder_Init (int flags, TFB_DecoderFormats* formats);
@@ -92,8 +113,9 @@ uint32 SoundDecoder_Decode (TFB_SoundDecoder *decoder);
uint32 SoundDecoder_DecodeAll (TFB_SoundDecoder *decoder);
float SoundDecoder_GetTime (TFB_SoundDecoder *decoder);
uint32 SoundDecoder_GetFrame (TFB_SoundDecoder *decoder);
void SoundDecoder_Seek (TFB_SoundDecoder *decoder, uint32 pcm_pos);
void SoundDecoder_Seek (TFB_SoundDecoder *decoder, uint32 msecs);
void SoundDecoder_Rewind (TFB_SoundDecoder *decoder);
void SoundDecoder_Free (TFB_SoundDecoder *decoder);
const char* SoundDecoder_GetName (TFB_SoundDecoder *decoder);
#endif
+275 -159
View File
@@ -21,6 +21,9 @@
#include <string.h>
#include <errno.h>
#include "libs/misc.h"
#include "port.h"
#include "types.h"
#include "uio.h"
#include "dukaud.h"
#include "decoder.h"
#include "endian_uqm.h"
@@ -28,7 +31,63 @@
#define DATA_BUF_SIZE 0x8000
#define DUCK_GENERAL_FPS 14.622f
static sint32 duka_error = 0;
#define THIS_PTR TFB_SoundDecoder* This
static const char* duka_GetName (void);
static bool duka_InitModule (int flags);
static void duka_TermModule ();
static uint32 duka_GetStructSize (void);
static int duka_GetError (THIS_PTR);
static bool duka_Init (THIS_PTR);
static void duka_Term (THIS_PTR);
static bool duka_Open (THIS_PTR, uio_DirHandle *dir, const char *filename);
static void duka_Close (THIS_PTR);
static int duka_Decode (THIS_PTR, void* buf, sint32 bufsize);
static uint32 duka_Seek (THIS_PTR, uint32 pcm_pos);
static uint32 duka_GetFrame (THIS_PTR);
TFB_SoundDecoderFuncs duka_DecoderVtbl =
{
duka_GetName,
duka_InitModule,
duka_TermModule,
duka_GetStructSize,
duka_GetError,
duka_Init,
duka_Term,
duka_Open,
duka_Close,
duka_Decode,
duka_Seek,
duka_GetFrame,
};
typedef struct tfb_ducksounddecoder
{
// always the first member
TFB_SoundDecoder decoder;
// public read-only
uint32 iframe; // current frame index
uint32 cframes; // total count of frames
uint32 channels; // number of channels
uint32 pcm_frame; // samples per frame
// private
sint32 last_error;
uio_Stream* duk;
uint32* frames;
// buffer
void* data;
uint32 maxdata;
uint32 cbdata;
uint32 dataofs;
// decoder stuff
sint32 predictors[2];
} TFB_DuckSoundDecoder;
typedef struct
{
@@ -45,36 +104,28 @@ typedef struct
} DukAud_AudSubframe;
sint32
duka_getError ()
{
sint32 ret = duka_error;
duka_error = dukae_None;
return ret;
}
sint32
duka_readAudFrameHeader (DukAud_Track* track, uint32 iframe,
duka_readAudFrameHeader (TFB_DuckSoundDecoder* duka, uint32 iframe,
DukAud_AudSubframe* aud)
{
DukAud_FrameHeader hdr;
uio_fseek (track->duk, track->frames[iframe], SEEK_SET);
if (uio_fread (&hdr, sizeof(hdr), 1, track->duk) != 1)
uio_fseek (duka->duk, duka->frames[iframe], SEEK_SET);
if (uio_fread (&hdr, sizeof(hdr), 1, duka->duk) != 1)
{
duka_error = errno;
duka->last_error = errno;
return dukae_BadFile;
}
hdr.audsize = UQM_SwapBE32 (hdr.audsize);
if (uio_fread (aud, sizeof(*aud), 1, track->duk) != 1)
if (uio_fread (aud, sizeof(*aud), 1, duka->duk) != 1)
{
duka_error = errno;
duka->last_error = errno;
return dukae_BadFile;
}
aud->magic = UQM_SwapBE16 (aud->magic);
if (aud->magic != 0xf77f)
return duka_error = dukae_BadFile;
return duka->last_error = dukae_BadFile;
aud->numsamples = UQM_SwapBE16 (aud->numsamples);
aud->tag = UQM_SwapBE16 (aud->tag);
@@ -84,112 +135,6 @@ duka_readAudFrameHeader (DukAud_Track* track, uint32 iframe,
return 0;
}
DukAud_Track*
duka_openTrack (uio_DirHandle *dir, const char *file)
{
DukAud_Track* track;
uio_Stream* duk;
uio_Stream* frm;
DukAud_AudSubframe aud;
char filename[256];
uint32 filelen;
size_t cread;
uint32 i;
filelen = strlen (file);
if (filelen > sizeof (filename) - 1)
return NULL;
strcpy (filename, file);
duk = uio_fopen (dir, filename, "rb");
if (!duk)
{
duka_error = errno;
return NULL;
}
strcpy (filename + filelen - 3, "frm");
frm = uio_fopen (dir, filename, "rb");
if (!frm)
{
duka_error = errno;
uio_fclose (duk);
return NULL;
}
track = (DukAud_Track *) HCalloc (sizeof (DukAud_Track));
track->duk = duk;
uio_fseek (frm, 0, SEEK_END);
track->cframes = uio_ftell (frm) / sizeof (uint32);
uio_fseek (frm, 0, SEEK_SET);
if (!track->cframes)
{
duka_error = dukae_BadFile;
uio_fclose (frm);
duka_closeTrack (track);
return NULL;
}
track->frames = (uint32*) HMalloc (track->cframes * sizeof (uint32));
cread = uio_fread (track->frames, sizeof (uint32), track->cframes, frm);
uio_fclose (frm);
if (cread != track->cframes)
{
duka_error = dukae_BadFile;
duka_closeTrack (track);
return NULL;
}
for (i = 0; i < track->cframes; ++i)
track->frames[i] = UQM_SwapBE32 (track->frames[i]);
if (duka_readAudFrameHeader (track, 0, &aud) < 0)
{
duka_closeTrack (track);
return NULL;
}
track->rate = 22050;
track->channels = 2;
track->pcm_frame = aud.numsamples;
track->data = HMalloc (DATA_BUF_SIZE);
track->maxdata = DATA_BUF_SIZE;
// estimate
track->length = (float) track->cframes / DUCK_GENERAL_FPS;
duka_error = 0;
return track;
}
void
duka_closeTrack (DukAud_Track* track)
{
if (track->data)
HFree (track->data);
if (track->duk)
uio_fclose (track->duk);
HFree (track);
duka_error = 0;
}
bool
duka_seekTrack (DukAud_Track* track, float pos /* in seconds */)
{
if (pos < 0 || pos > track->length)
return false;
track->iframe = (uint32) (pos * DUCK_GENERAL_FPS);
track->cbdata = 0;
track->dataofs = 0;
track->predictors[0] = 0;
track->predictors[1] = 0;
return true;
}
// This table is from one of the files that came with the original 3do source
// It's slightly different from the data used by MPlayer.
static int adpcm_step[89] = {
@@ -300,7 +245,7 @@ decode_nibbles (sint16 *output, sint32 output_size, sint32 channels,
// *** END part copied from MPlayer ***
sint32
duka_decodeFrame (DukAud_Track* track, DukAud_AudSubframe* header,
duka_decodeFrame (TFB_DuckSoundDecoder* duka, DukAud_AudSubframe* header,
uint8* input)
{
uint8* inend;
@@ -309,7 +254,7 @@ duka_decodeFrame (DukAud_Track* track, DukAud_AudSubframe* header,
sint32 outputsize;
outputsize = header->numsamples * 2 * sizeof (sint16);
outptr = output = (sint16*) ((uint8*)track->data + track->cbdata);
outptr = output = (sint16*) ((uint8*)duka->data + duka->cbdata);
for (inend = input + header->numsamples; input < inend; ++input)
{
@@ -317,35 +262,35 @@ duka_decodeFrame (DukAud_Track* track, DukAud_AudSubframe* header,
*(outptr++) = *input & 0x0f;
}
decode_nibbles (output, header->numsamples * 2, track->channels,
track->predictors, header->indices);
decode_nibbles (output, header->numsamples * 2, duka->channels,
duka->predictors, header->indices);
track->cbdata += outputsize;
duka->cbdata += outputsize;
return outputsize;
}
sint32
duka_readNextFrame (DukAud_Track* track)
duka_readNextFrame (TFB_DuckSoundDecoder* duka)
{
DukAud_FrameHeader hdr;
DukAud_AudSubframe* aud;
uint8* p;
uio_fseek (track->duk, track->frames[track->iframe], SEEK_SET);
if (uio_fread (&hdr, sizeof(hdr), 1, track->duk) != 1)
uio_fseek (duka->duk, duka->frames[duka->iframe], SEEK_SET);
if (uio_fread (&hdr, sizeof(hdr), 1, duka->duk) != 1)
{
duka_error = errno;
duka->last_error = errno;
return dukae_BadFile;
}
hdr.audsize = UQM_SwapBE32 (hdr.audsize);
// dump encoded data at the end of the buffer aligned on 8-byte
p = ((uint8*)track->data + track->maxdata - ((hdr.audsize + 7) & (-8)));
if (uio_fread (p, 1, hdr.audsize, track->duk) != hdr.audsize)
p = ((uint8*)duka->data + duka->maxdata - ((hdr.audsize + 7) & (-8)));
if (uio_fread (p, 1, hdr.audsize, duka->duk) != hdr.audsize)
{
duka_error = errno;
duka->last_error = errno;
return dukae_BadFile;
}
aud = (DukAud_AudSubframe*) p;
@@ -353,76 +298,247 @@ duka_readNextFrame (DukAud_Track* track)
aud->magic = UQM_SwapBE16 (aud->magic);
if (aud->magic != 0xf77f)
return duka_error = dukae_BadFile;
return duka->last_error = dukae_BadFile;
aud->numsamples = UQM_SwapBE16 (aud->numsamples);
aud->tag = UQM_SwapBE16 (aud->tag);
aud->indices[0] = UQM_SwapBE16 (aud->indices[0]);
aud->indices[1] = UQM_SwapBE16 (aud->indices[1]);
track->iframe++;
duka->iframe++;
return duka_decodeFrame (track, aud, p);
return duka_decodeFrame (duka, aud, p);
}
static sint32
duka_stuffBuffer (DukAud_Track* track, void* buf, sint32 bufsize)
duka_stuffBuffer (TFB_DuckSoundDecoder* duka, void* buf, sint32 bufsize)
{
sint32 dataleft;
dataleft = track->cbdata - track->dataofs;
dataleft = duka->cbdata - duka->dataofs;
if (dataleft > 0)
{
if (dataleft > bufsize)
dataleft = bufsize & (-4);
memcpy (buf, (uint8*)track->data + track->dataofs, dataleft);
track->dataofs += dataleft;
memcpy (buf, (uint8*)duka->data + duka->dataofs, dataleft);
duka->dataofs += dataleft;
}
if (track->cbdata > 0 && track->dataofs >= track->cbdata)
track->cbdata = track->dataofs = 0; // reset for new data
if (duka->cbdata > 0 && duka->dataofs >= duka->cbdata)
duka->cbdata = duka->dataofs = 0; // reset for new data
return dataleft;
}
sint32
duka_readData (DukAud_Track* track, void* buf, sint32 bufsize)
static const char*
duka_GetName (void)
{
return "DukAud";
}
static bool
duka_InitModule (int flags)
{
// no specific module init
return true;
(void)flags; // laugh at compiler warning
}
static void
duka_TermModule ()
{
// no specific module term
}
static uint32
duka_GetStructSize (void)
{
return sizeof (TFB_DuckSoundDecoder);
}
static int
duka_GetError (THIS_PTR)
{
TFB_DuckSoundDecoder* duka = (TFB_DuckSoundDecoder*) This;
int ret = duka->last_error;
duka->last_error = dukae_None;
return ret;
}
static bool
duka_Init (THIS_PTR)
{
//TFB_DuckSoundDecoder* duka = (TFB_DuckSoundDecoder*) This;
This->need_swap =
decoder_formats.big_endian != decoder_formats.want_big_endian;
return true;
}
static void
duka_Term (THIS_PTR)
{
//TFB_DuckSoundDecoder* duka = (TFB_DuckSoundDecoder*) This;
duka_Close (This); // ensure cleanup
}
static bool
duka_Open (THIS_PTR, uio_DirHandle *dir, const char *file)
{
TFB_DuckSoundDecoder* duka = (TFB_DuckSoundDecoder*) This;
uio_Stream* duk;
uio_Stream* frm;
DukAud_AudSubframe aud;
char filename[256];
uint32 filelen;
size_t cread;
uint32 i;
filelen = strlen (file);
if (filelen > sizeof (filename) - 1)
return false;
strcpy (filename, file);
duk = uio_fopen (dir, filename, "rb");
if (!duk)
{
duka->last_error = errno;
return false;
}
strcpy (filename + filelen - 3, "frm");
frm = uio_fopen (dir, filename, "rb");
if (!frm)
{
duka->last_error = errno;
uio_fclose (duk);
return false;
}
duka->duk = duk;
uio_fseek (frm, 0, SEEK_END);
duka->cframes = uio_ftell (frm) / sizeof (uint32);
uio_fseek (frm, 0, SEEK_SET);
if (!duka->cframes)
{
duka->last_error = dukae_BadFile;
uio_fclose (frm);
duka_Close (This);
return false;
}
duka->frames = (uint32*) HMalloc (duka->cframes * sizeof (uint32));
cread = uio_fread (duka->frames, sizeof (uint32), duka->cframes, frm);
uio_fclose (frm);
if (cread != duka->cframes)
{
duka->last_error = dukae_BadFile;
duka_Close (This);
return false;
}
for (i = 0; i < duka->cframes; ++i)
duka->frames[i] = UQM_SwapBE32 (duka->frames[i]);
if (duka_readAudFrameHeader (duka, 0, &aud) < 0)
{
duka_Close (This);
return false;
}
This->frequency = 22050;
This->format = decoder_formats.stereo16;
duka->channels = 2;
duka->pcm_frame = aud.numsamples;
duka->data = HMalloc (DATA_BUF_SIZE);
duka->maxdata = DATA_BUF_SIZE;
// estimate
This->length = (float) duka->cframes / DUCK_GENERAL_FPS;
duka->last_error = 0;
return true;
}
static void
duka_Close (THIS_PTR)
{
TFB_DuckSoundDecoder* duka = (TFB_DuckSoundDecoder*) This;
if (duka->data)
{
HFree (duka->data);
duka->data = NULL;
}
if (duka->frames)
{
HFree (duka->frames);
duka->frames = NULL;
}
if (duka->duk)
{
uio_fclose (duka->duk);
duka->duk = NULL;
}
duka->last_error = 0;
}
static int
duka_Decode (THIS_PTR, void* buf, sint32 bufsize)
{
TFB_DuckSoundDecoder* duka = (TFB_DuckSoundDecoder*) This;
sint32 stuffed;
sint32 total = 0;
if (bufsize <= 0)
return duka_error = dukae_BadArg;
return duka->last_error = dukae_BadArg;
do
{
stuffed = duka_stuffBuffer (track, buf, bufsize);
stuffed = duka_stuffBuffer (duka, buf, bufsize);
((uint8*)buf) += stuffed;
bufsize -= stuffed;
total += stuffed;
if (bufsize > 0 && track->iframe < track->cframes)
if (bufsize > 0 && duka->iframe < duka->cframes)
{
stuffed = duka_readNextFrame (track);
stuffed = duka_readNextFrame (duka);
if (stuffed <= 0)
return stuffed;
}
} while (bufsize > 0 && track->iframe < track->cframes);
} while (bufsize > 0 && duka->iframe < duka->cframes);
return total;
}
uint32
duka_getFrame (DukAud_Track* track)
static uint32
duka_Seek (THIS_PTR, uint32 pcm_pos)
{
// if there is nothing buffered return the actual current frame
// otherwise return previous
return track->dataofs == track->cbdata ?
track->iframe : track->iframe - 1;
TFB_DuckSoundDecoder* duka = (TFB_DuckSoundDecoder*) This;
uint32 iframe;
iframe = pcm_pos / duka->pcm_frame;
if (iframe < duka->cframes)
{
duka->iframe = iframe;
duka->cbdata = 0;
duka->dataofs = 0;
duka->predictors[0] = 0;
duka->predictors[1] = 0;
}
return duka->iframe * duka->pcm_frame;
}
uint32
duka_getFrameSize (DukAud_Track* track)
static uint32
duka_GetFrame (THIS_PTR)
{
return track->pcm_frame * track->channels * sizeof (uint16);
TFB_DuckSoundDecoder* duka = (TFB_DuckSoundDecoder*) This;
// if there is nothing buffered return the actual current frame
// otherwise return previous
return duka->dataofs == duka->cbdata ?
duka->iframe : duka->iframe - 1;
}
+2 -33
View File
@@ -19,32 +19,9 @@
#ifndef DUKAUD_H
#define DUKAUD_H
#include "port.h"
#include "types.h"
#include "uio.h"
#include "decoder.h"
typedef struct
{
// public read-only
uint32 iframe; // current frame index
uint32 cframes; // total count of frames
uint32 rate; // frequency
uint32 channels; // number of channels
uint32 pcm_frame; // samples per frame
float length; // length in seconds (estimated)
// private
uio_Stream* duk;
uint32* frames;
// buffer
void* data;
uint32 maxdata;
uint32 cbdata;
uint32 dataofs;
// decoder stuff
sint32 predictors[2];
} DukAud_Track;
extern TFB_SoundDecoderFuncs duka_DecoderVtbl;
typedef enum
{
@@ -56,12 +33,4 @@ typedef enum
dukae_Other = -1000,
} DukAud_Error;
sint32 duka_getError ();
DukAud_Track* duka_openTrack (uio_DirHandle *dir, const char *file);
void duka_closeTrack (DukAud_Track* track);
bool duka_seekTrack (DukAud_Track* track, float pos /* in seconds */);
sint32 duka_readData (DukAud_Track* track, void* buf, sint32 bufsize);
uint32 duka_getFrame (DukAud_Track* track);
uint32 duka_getFrameSize (DukAud_Track* track);
#endif // DUKAUD_H
@@ -0,0 +1,228 @@
/*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
/* MikMod decoder (.mod adapter)
*/
#include <stdio.h>
#include <string.h>
#include <errno.h>
#include "libs/misc.h"
#include "port.h"
#include "types.h"
#include "uio.h"
#include "decoder.h"
#include "mikmod/mikmod.h"
#include "libs/sound/sound_common.h"
#include "modaud.h"
#define THIS_PTR TFB_SoundDecoder* This
static const char* moda_GetName (void);
static bool moda_InitModule (int flags);
static void moda_TermModule ();
static uint32 moda_GetStructSize (void);
static int moda_GetError (THIS_PTR);
static bool moda_Init (THIS_PTR);
static void moda_Term (THIS_PTR);
static bool moda_Open (THIS_PTR, uio_DirHandle *dir, const char *filename);
static void moda_Close (THIS_PTR);
static int moda_Decode (THIS_PTR, void* buf, sint32 bufsize);
static uint32 moda_Seek (THIS_PTR, uint32 pcm_pos);
static uint32 moda_GetFrame (THIS_PTR);
TFB_SoundDecoderFuncs moda_DecoderVtbl =
{
moda_GetName,
moda_InitModule,
moda_TermModule,
moda_GetStructSize,
moda_GetError,
moda_Init,
moda_Term,
moda_Open,
moda_Close,
moda_Decode,
moda_Seek,
moda_GetFrame,
};
typedef struct tfb_modsounddecoder
{
// always the first member
TFB_SoundDecoder decoder;
// private
sint32 last_error;
MODULE* module;
} TFB_ModSoundDecoder;
MIKMODAPI extern struct MDRIVER drv_openal;
static const char*
moda_GetName (void)
{
return "MikMod";
}
static bool
moda_InitModule (int flags)
{
MikMod_RegisterDriver (&drv_openal);
MikMod_RegisterAllLoaders ();
if (flags & TFB_SOUNDFLAGS_HQAUDIO)
{
md_mode = DMODE_HQMIXER|DMODE_STEREO|DMODE_16BITS|DMODE_INTERP|DMODE_SURROUND;
md_mixfreq = 44100;
md_reverb = 1;
}
else if (flags & TFB_SOUNDFLAGS_LQAUDIO)
{
md_mode = DMODE_SOFT_MUSIC|DMODE_STEREO|DMODE_16BITS;
md_mixfreq = 22050;
md_reverb = 0;
}
else
{
md_mode = DMODE_SOFT_MUSIC|DMODE_STEREO|DMODE_16BITS|DMODE_INTERP;
md_mixfreq = 44100;
md_reverb = 0;
}
md_pansep = 64;
if (MikMod_Init (""))
{
fprintf (stderr, "MikMod_Init() failed, %s\n",
MikMod_strerror (MikMod_errno));
return false;
}
return true;
}
static void
moda_TermModule ()
{
MikMod_Exit ();
}
static uint32
moda_GetStructSize (void)
{
return sizeof (TFB_ModSoundDecoder);
}
static int
moda_GetError (THIS_PTR)
{
TFB_ModSoundDecoder* moda = (TFB_ModSoundDecoder*) This;
int ret = moda->last_error;
moda->last_error = 0;
return ret;
}
static bool
moda_Init (THIS_PTR)
{
//TFB_ModSoundDecoder* moda = (TFB_ModSoundDecoder*) This;
This->need_swap =
decoder_formats.big_endian != decoder_formats.want_big_endian;
return true;
}
static void
moda_Term (THIS_PTR)
{
//TFB_ModSoundDecoder* moda = (TFB_ModSoundDecoder*) This;
moda_Close (This); // ensure cleanup
}
static bool
moda_Open (THIS_PTR, uio_DirHandle *dir, const char *filename)
{
TFB_ModSoundDecoder* moda = (TFB_ModSoundDecoder*) This;
MODULE* mod;
mod = Player_Load (dir, (char*) filename, 4, 0);
if (!mod)
{
fprintf (stderr, "moda_Open(): could not load %s\n", filename);
return false;
}
moda->module = mod;
mod->extspd = 1;
mod->panflag = 1;
mod->wrap = 0;
mod->loop = 1;
This->format = decoder_formats.stereo16;
This->frequency = md_mixfreq;
This->length = 0; // FIXME way to obtain this from mikmod?
moda->last_error = 0;
return true;
}
static void
moda_Close (THIS_PTR)
{
TFB_ModSoundDecoder* moda = (TFB_ModSoundDecoder*) This;
if (moda->module)
{
Player_Free (moda->module);
moda->module = NULL;
}
}
static int
moda_Decode (THIS_PTR, void* buf, sint32 bufsize)
{
TFB_ModSoundDecoder* moda = (TFB_ModSoundDecoder*) This;
Player_Start (moda->module);
if (!Player_Active())
return 0;
return VC_WriteBytes (buf, bufsize);
}
static uint32
moda_Seek (THIS_PTR, uint32 pcm_pos)
{
TFB_ModSoundDecoder* moda = (TFB_ModSoundDecoder*) This;
Player_Start (moda->module);
if (pcm_pos)
fprintf (stderr, "moda_Seek(): "
"non-zero seek positions not supported for mod\n");
Player_SetPosition (0);
return 0;
}
static uint32
moda_GetFrame (THIS_PTR)
{
TFB_ModSoundDecoder* moda = (TFB_ModSoundDecoder*) This;
return moda->module->sngpos;
}
@@ -0,0 +1,26 @@
/*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
/* MikMod adapter */
#ifndef MODAUD_H
#define MODAUD_H
#include "decoder.h"
extern TFB_SoundDecoderFuncs moda_DecoderVtbl;
#endif // MODAUD_H
@@ -0,0 +1,256 @@
/*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
/* Ogg Vorbis decoder (.ogg adapter)
*/
#include <stdio.h>
#include <string.h>
#include <errno.h>
#include "libs/misc.h"
#include "port.h"
#include "types.h"
#include "uio.h"
#include "decoder.h"
#include <vorbis/codec.h>
#include <vorbis/vorbisfile.h>
#include "oggaud.h"
#define THIS_PTR TFB_SoundDecoder* This
static const char* ova_GetName (void);
static bool ova_InitModule (int flags);
static void ova_TermModule ();
static uint32 ova_GetStructSize (void);
static int ova_GetError (THIS_PTR);
static bool ova_Init (THIS_PTR);
static void ova_Term (THIS_PTR);
static bool ova_Open (THIS_PTR, uio_DirHandle *dir, const char *filename);
static void ova_Close (THIS_PTR);
static int ova_Decode (THIS_PTR, void* buf, sint32 bufsize);
static uint32 ova_Seek (THIS_PTR, uint32 pcm_pos);
static uint32 ova_GetFrame (THIS_PTR);
TFB_SoundDecoderFuncs ova_DecoderVtbl =
{
ova_GetName,
ova_InitModule,
ova_TermModule,
ova_GetStructSize,
ova_GetError,
ova_Init,
ova_Term,
ova_Open,
ova_Close,
ova_Decode,
ova_Seek,
ova_GetFrame,
};
typedef struct tfb_oggsounddecoder
{
// always the first member
TFB_SoundDecoder decoder;
// private
sint32 last_error;
OggVorbis_File vf;
} TFB_OggSoundDecoder;
static size_t
ogg_read (void *ptr, size_t size, size_t nmemb, void *datasource)
{
return uio_fread (ptr, size, nmemb, (uio_Stream *) datasource);
}
static int
ogg_seek (void *datasource, ogg_int64_t offset, int whence)
{
long off = (long) offset;
return uio_fseek ((uio_Stream *) datasource, off, whence);
}
static int
ogg_close (void *datasource)
{
return uio_fclose ((uio_Stream *) datasource);
}
static long
ogg_tell (void *datasource)
{
return uio_ftell ((uio_Stream *) datasource);
}
static const ov_callbacks ogg_callbacks =
{
ogg_read,
ogg_seek,
ogg_close,
ogg_tell,
};
static const char*
ova_GetName (void)
{
return "Ogg Vorbis";
}
static bool
ova_InitModule (int flags)
{
// no specific module init
return true;
(void)flags; // laugh at compiler warning
}
static void
ova_TermModule ()
{
// no specific module term
}
static uint32
ova_GetStructSize (void)
{
return sizeof (TFB_OggSoundDecoder);
}
static int
ova_GetError (THIS_PTR)
{
TFB_OggSoundDecoder* ova = (TFB_OggSoundDecoder*) This;
int ret = ova->last_error;
ova->last_error = 0;
return ret;
}
static bool
ova_Init (THIS_PTR)
{
//TFB_OggSoundDecoder* ova = (TFB_OggSoundDecoder*) This;
This->need_swap = false;
return true;
}
static void
ova_Term (THIS_PTR)
{
//TFB_OggSoundDecoder* ova = (TFB_OggSoundDecoder*) This;
ova_Close (This); // ensure cleanup
}
static bool
ova_Open (THIS_PTR, uio_DirHandle *dir, const char *filename)
{
TFB_OggSoundDecoder* ova = (TFB_OggSoundDecoder*) This;
int rc;
uio_Stream *fp;
vorbis_info *vinfo;
fp = uio_fopen (dir, filename, "rb");
if (fp == NULL)
{
fprintf (stderr, "ova_Open(): could not open %s\n", filename);
return false;
}
rc = ov_open_callbacks (fp, &ova->vf, NULL, 0, ogg_callbacks);
if (rc != 0)
{
fprintf (stderr, "ova_Open(): "
"ov_open_callbacks failed for %s, error code %d\n",
filename, rc);
uio_fclose (fp);
return false;
}
vinfo = ov_info (&ova->vf, -1);
if (!vinfo)
{
fprintf (stderr, "ova_Open(): "
"failed to retrieve ogg bitstream info for %s\n",
filename);
ov_clear (&ova->vf);
return false;
}
This->frequency = vinfo->rate;
This->length = (float) ov_time_total (&ova->vf, -1);
if (vinfo->channels == 1)
This->format = decoder_formats.mono16;
else
This->format = decoder_formats.stereo16;
ova->last_error = 0;
return true;
}
static void
ova_Close (THIS_PTR)
{
TFB_OggSoundDecoder* ova = (TFB_OggSoundDecoder*) This;
ov_clear (&ova->vf);
}
static int
ova_Decode (THIS_PTR, void* buf, sint32 bufsize)
{
TFB_OggSoundDecoder* ova = (TFB_OggSoundDecoder*) This;
long rc;
int bitstream;
rc = ov_read (&ova->vf, buf, bufsize, decoder_formats.want_big_endian,
2, 1, &bitstream);
if (rc < 0)
ova->last_error = rc;
else
ova->last_error = 0;
return rc;
}
static uint32
ova_Seek (THIS_PTR, uint32 pcm_pos)
{
TFB_OggSoundDecoder* ova = (TFB_OggSoundDecoder*) This;
int ret;
ret = ov_pcm_seek (&ova->vf, pcm_pos);
if (ret != 0)
{
ova->last_error = ret;
return (uint32) ov_pcm_tell (&ova->vf);
}
else
return pcm_pos;
}
static uint32
ova_GetFrame (THIS_PTR)
{
TFB_OggSoundDecoder* ova = (TFB_OggSoundDecoder*) This;
// this is the closest to a frame there is in ogg vorbis stream
// doesn't seem to be a func to retrive it
return ova->vf.os.pageno;
}
@@ -0,0 +1,26 @@
/*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
/* Ogg Vorbis adapter */
#ifndef OGGAUD_H
#define OGGAUD_H
#include "decoder.h"
extern TFB_SoundDecoderFuncs ova_DecoderVtbl;
#endif // OGGAUD_H
+302 -93
View File
@@ -14,17 +14,22 @@
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
/* Loader for .wav files
/* Wave decoder (.wav adapter)
* Code is based on Creative's Win32 OpenAL implementation.
*/
#include <stdio.h>
#include <errno.h>
#include <memory.h>
#include "port.h"
#include "types.h"
#include "uio.h"
#include "endian_uqm.h"
#include "libs/misc.h"
#include "wav.h"
#include "decoder.h"
#include "endian_uqm.h"
#define RIFF 0x46464952 /* "RIFF" */
#define WAVE 0x45564157 /* "WAVE" */
#define FMT 0x20746D66 /* "fmt " */
#define DATA 0x61746164 /* "data" */
@@ -52,100 +57,304 @@ typedef struct
} WAVChunkHdr_Struct;
void
LoadWAVFile (uio_DirHandle *dir, const char *file, uint32 *format,
void **data, uint32 *size, uint32 *freq, bool want_big_endian)
#define THIS_PTR TFB_SoundDecoder* This
static const char* wava_GetName (void);
static bool wava_InitModule (int flags);
static void wava_TermModule ();
static uint32 wava_GetStructSize (void);
static int wava_GetError (THIS_PTR);
static bool wava_Init (THIS_PTR);
static void wava_Term (THIS_PTR);
static bool wava_Open (THIS_PTR, uio_DirHandle *dir, const char *filename);
static void wava_Close (THIS_PTR);
static int wava_Decode (THIS_PTR, void* buf, sint32 bufsize);
static uint32 wava_Seek (THIS_PTR, uint32 pcm_pos);
static uint32 wava_GetFrame (THIS_PTR);
TFB_SoundDecoderFuncs wava_DecoderVtbl =
{
WAVChunkHdr_Struct ChunkHdr;
WAVFileHdr_Struct FileHdr;
WAVFmtHdr_Struct FmtHdr;
wava_GetName,
wava_InitModule,
wava_TermModule,
wava_GetStructSize,
wava_GetError,
wava_Init,
wava_Term,
wava_Open,
wava_Close,
wava_Decode,
wava_Seek,
wava_GetFrame,
};
typedef struct tfb_wavesounddecoder
{
// always the first member
TFB_SoundDecoder decoder;
// private
sint32 last_error;
uio_Stream *fp;
*format = decoder_formats.mono16;
*data = NULL;
*size = 0;
*freq = 22050;
fp = uio_fopen (dir, file, "rb");
if (fp)
{
uio_fread(&FileHdr.Id, 4, 1, fp);
FileHdr.Id = UQM_SwapLE32 (FileHdr.Id);
uio_fread(&FileHdr.Size, 4, 1, fp);
FileHdr.Size = UQM_SwapLE32 (FileHdr.Size);
uio_fread(&FileHdr.Type, 4, 1, fp);
FileHdr.Type = UQM_SwapLE32 (FileHdr.Type);
WAVFmtHdr_Struct FmtHdr;
uint32 data_ofs;
uint32 data_size;
uint32 max_pcm;
uint32 cur_pcm;
FileHdr.Size = ((FileHdr.Size + 1) & ~1) - 4;
while (FileHdr.Size != 0)
{
if (!uio_fread (&ChunkHdr.Id, 4, 1, fp))
break;
ChunkHdr.Id = UQM_SwapLE32 (ChunkHdr.Id);
if (!uio_fread (&ChunkHdr.Size, 4, 1, fp))
break;
ChunkHdr.Size = UQM_SwapLE32 (ChunkHdr.Size);
} TFB_WaveSoundDecoder;
if (ChunkHdr.Id == FMT)
{
uio_fread (&FmtHdr.Format, 2, 1, fp);
FmtHdr.Format = UQM_SwapLE16 (FmtHdr.Format);
uio_fread (&FmtHdr.Channels, 2, 1, fp);
FmtHdr.Channels = UQM_SwapLE16 (FmtHdr.Channels);
uio_fread (&FmtHdr.SamplesPerSec, 4, 1, fp);
FmtHdr.SamplesPerSec = UQM_SwapLE32 (FmtHdr.SamplesPerSec);
uio_fread (&FmtHdr.BytesPerSec, 4, 1, fp);
FmtHdr.BytesPerSec = UQM_SwapLE32 (FmtHdr.BytesPerSec);
uio_fread (&FmtHdr.BlockAlign, 2, 1, fp);
FmtHdr.BlockAlign = UQM_SwapLE16 (FmtHdr.BlockAlign);
uio_fread (&FmtHdr.BitsPerSample, 2, 1, fp);
FmtHdr.BitsPerSample = UQM_SwapLE16 (FmtHdr.BitsPerSample);
if (FmtHdr.Format == 0x0001)
{
*format=(FmtHdr.Channels == 1 ?
(FmtHdr.BitsPerSample == 8 ?
decoder_formats.mono8
: decoder_formats.mono16)
: (FmtHdr.BitsPerSample == 8 ?
decoder_formats.stereo8
: decoder_formats.stereo16)
);
*freq = FmtHdr.SamplesPerSec;
uio_fseek (fp, ChunkHdr.Size - 16, SEEK_CUR);
}
else
{
fprintf (stderr, "LoadWAVFile(): unsupported format %x\n", FmtHdr.Format);
uio_fclose (fp);
return;
}
}
else if (ChunkHdr.Id == DATA)
{
*size = ChunkHdr.Size;
if ((*data = HMalloc (ChunkHdr.Size + 31)))
uio_fread (*data, FmtHdr.BlockAlign, ChunkHdr.Size / FmtHdr.BlockAlign, fp);
memset(((char *)*data) + ChunkHdr.Size, 0, 31);
}
else
{
uio_fseek(fp, ChunkHdr.Size, SEEK_CUR);
}
uio_fseek (fp, ChunkHdr.Size & 1, SEEK_CUR);
FileHdr.Size -= (((ChunkHdr.Size + 1) & ~1) + 8);
}
uio_fclose(fp);
}
if (want_big_endian &&
(*format == decoder_formats.stereo16 || *format == decoder_formats.mono16))
{
SoundDecoder_SwapWords (*data, *size);
}
if (*size == 0)
fprintf (stderr, "LoadWAVFile(): loading %s failed!\n", file);
static const char*
wava_GetName (void)
{
return "Wave";
}
static bool
wava_InitModule (int flags)
{
// no specific module init
return true;
(void)flags; // laugh at compiler warning
}
static void
wava_TermModule ()
{
// no specific module term
}
static uint32
wava_GetStructSize (void)
{
return sizeof (TFB_WaveSoundDecoder);
}
static int
wava_GetError (THIS_PTR)
{
TFB_WaveSoundDecoder* wava = (TFB_WaveSoundDecoder*) This;
int ret = wava->last_error;
wava->last_error = 0;
return ret;
}
static bool
wava_Init (THIS_PTR)
{
//TFB_WaveSoundDecoder* wava = (TFB_WaveSoundDecoder*) This;
This->need_swap = decoder_formats.want_big_endian;
return true;
}
static void
wava_Term (THIS_PTR)
{
//TFB_WaveSoundDecoder* wava = (TFB_WaveSoundDecoder*) This;
wava_Close (This); // ensure cleanup
}
static bool
wava_readFileHeader (TFB_WaveSoundDecoder* wava, WAVFileHdr_Struct* hdr)
{
if (!uio_fread (&hdr->Id, 4, 1, wava->fp) ||
!uio_fread (&hdr->Size, 4, 1, wava->fp) ||
!uio_fread (&hdr->Type, 4, 1, wava->fp))
{
wava->last_error = errno;
return false;
}
hdr->Id = UQM_SwapLE32 (hdr->Id);
hdr->Size = UQM_SwapLE32 (hdr->Size);
hdr->Type = UQM_SwapLE32 (hdr->Type);
return true;
}
static bool
wava_readChunkHeader (TFB_WaveSoundDecoder* wava, WAVChunkHdr_Struct* chunk)
{
if (!uio_fread (&chunk->Id, 4, 1, wava->fp) ||
!uio_fread (&chunk->Size, 4, 1, wava->fp))
return false;
chunk->Id = UQM_SwapLE32 (chunk->Id);
chunk->Size = UQM_SwapLE32 (chunk->Size);
return true;
}
static bool
wava_readFormatHeader (TFB_WaveSoundDecoder* wava, WAVFmtHdr_Struct* fmt)
{
if (!uio_fread (&fmt->Format, 2, 1, wava->fp) ||
!uio_fread (&fmt->Channels, 2, 1, wava->fp) ||
!uio_fread (&fmt->SamplesPerSec, 4, 1, wava->fp) ||
!uio_fread (&fmt->BytesPerSec, 4, 1, wava->fp) ||
!uio_fread (&fmt->BlockAlign, 2, 1, wava->fp) ||
!uio_fread (&fmt->BitsPerSample, 2, 1, wava->fp))
return false;
fmt->Format = UQM_SwapLE16 (fmt->Format);
fmt->Channels = UQM_SwapLE16 (fmt->Channels);
fmt->SamplesPerSec = UQM_SwapLE32 (fmt->SamplesPerSec);
fmt->BytesPerSec = UQM_SwapLE32 (fmt->BytesPerSec);
fmt->BlockAlign = UQM_SwapLE16 (fmt->BlockAlign);
fmt->BitsPerSample = UQM_SwapLE16 (fmt->BitsPerSample);
return true;
}
static bool
wava_Open (THIS_PTR, uio_DirHandle *dir, const char *filename)
{
TFB_WaveSoundDecoder* wava = (TFB_WaveSoundDecoder*) This;
WAVFileHdr_Struct FileHdr;
WAVChunkHdr_Struct ChunkHdr;
wava->fp = uio_fopen (dir, filename, "rb");
if (!wava->fp)
{
wava->last_error = errno;
return false;
}
wava->data_size = 0;
wava->data_ofs = 0;
// read wave header
if (!wava_readFileHeader (wava, &FileHdr))
{
wava->last_error = errno;
wava_Close (This);
return false;
}
if (FileHdr.Id != RIFF || FileHdr.Type != WAVE)
{
fprintf (stderr, "wava_Open(): "
"not a wave file, ID 0x%08x, Type 0x%08x\n",
FileHdr.Id, FileHdr.Type);
wava_Close (This);
return false;
}
for (FileHdr.Size = ((FileHdr.Size + 1) & ~1) - 4; FileHdr.Size != 0;
FileHdr.Size -= (((ChunkHdr.Size + 1) & ~1) + 8))
{
if (!wava_readChunkHeader (wava, &ChunkHdr))
{
wava->last_error = errno;
wava_Close (This);
return false;
}
if (ChunkHdr.Id == FMT)
{
if (!wava_readFormatHeader (wava, &wava->FmtHdr))
{
wava->last_error = errno;
wava_Close (This);
return false;
}
uio_fseek (wava->fp, ChunkHdr.Size - 16, SEEK_CUR);
}
else
{
if (ChunkHdr.Id == DATA)
{
wava->data_size = ChunkHdr.Size;
wava->data_ofs = uio_ftell (wava->fp);
}
uio_fseek (wava->fp, ChunkHdr.Size, SEEK_CUR);
}
uio_fseek (wava->fp, ChunkHdr.Size & 1, SEEK_CUR);
}
if (!wava->data_size || !wava->data_ofs)
{
fprintf (stderr, "wava_Open(): bad wave file, no DATA chunk found\n");
wava_Close (This);
return false;
}
if (wava->FmtHdr.Format == 0x0001)
{
This->format = (wava->FmtHdr.Channels == 1 ?
(wava->FmtHdr.BitsPerSample == 8 ?
decoder_formats.mono8 : decoder_formats.mono16)
:
(wava->FmtHdr.BitsPerSample == 8 ?
decoder_formats.stereo8 : decoder_formats.stereo16)
);
This->frequency = wava->FmtHdr.SamplesPerSec;
}
else
{
fprintf (stderr, "wava_Open(): unsupported format %x\n", wava->FmtHdr.Format);
wava_Close (This);
return false;
}
uio_fseek (wava->fp, wava->data_ofs, SEEK_SET);
wava->max_pcm = wava->data_size / wava->FmtHdr.BlockAlign;
wava->cur_pcm = 0;
This->length = (float) wava->max_pcm / wava->FmtHdr.SamplesPerSec;
wava->last_error = 0;
return true;
}
static void
wava_Close (THIS_PTR)
{
TFB_WaveSoundDecoder* wava = (TFB_WaveSoundDecoder*) This;
if (wava->fp)
{
uio_fclose (wava->fp);
wava->fp = NULL;
}
}
static int
wava_Decode (THIS_PTR, void* buf, sint32 bufsize)
{
TFB_WaveSoundDecoder* wava = (TFB_WaveSoundDecoder*) This;
uint32 dec_pcm;
dec_pcm = bufsize / wava->FmtHdr.BlockAlign;
if (dec_pcm > wava->max_pcm - wava->cur_pcm)
dec_pcm = wava->max_pcm - wava->cur_pcm;
dec_pcm = uio_fread (buf, wava->FmtHdr.BlockAlign, dec_pcm, wava->fp);
wava->cur_pcm += dec_pcm;
return dec_pcm * wava->FmtHdr.BlockAlign;
}
static uint32
wava_Seek (THIS_PTR, uint32 pcm_pos)
{
TFB_WaveSoundDecoder* wava = (TFB_WaveSoundDecoder*) This;
if (pcm_pos > wava->max_pcm)
pcm_pos = wava->max_pcm;
wava->cur_pcm = pcm_pos;
uio_fseek (wava->fp,
wava->data_ofs + pcm_pos * wava->FmtHdr.BlockAlign,
SEEK_SET);
return pcm_pos;
}
static uint32
wava_GetFrame (THIS_PTR)
{
//TFB_WaveSoundDecoder* wava = (TFB_WaveSoundDecoder*) This;
return 0; // only 1 frame for now
(void)This; // laugh at compiler warning
}
+3 -6
View File
@@ -14,16 +14,13 @@
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
/* Loader for .wav files */
/* Wave decoder */
#ifndef WAV_H
#define WAV_H
#include "port.h"
#include "types.h"
#include "uio.h"
#include "decoder.h"
void LoadWAVFile (uio_DirHandle *dir, const char *file, uint32 *format,
void **data, uint32 *size, uint32 *freq, bool want_big_endian);
extern TFB_SoundDecoderFuncs wava_DecoderVtbl;
#endif
+2 -1
View File
@@ -164,7 +164,8 @@ _GetMusicData (uio_Stream *fp, DWORD length)
}
else
{
fprintf (stderr, " decoder: %s, rate %d format %x\n", (*pmus)->decoder->decoder_info,
fprintf (stderr, " decoder: %s, rate %d format %x\n",
SoundDecoder_GetName ((*pmus)->decoder),
(*pmus)->decoder->frequency, (*pmus)->decoder->format);
(*pmus)->num_buffers = 64;
@@ -21,7 +21,7 @@
ALCcontext *alcContext = NULL;
ALCdevice *alcDevice = NULL;
ALfloat listenerPos[] = {0.0f, 0.0f, 0.0f};
ALfloat listenerPos[] = {0.0f, 0.0f, 0.2f};
ALfloat listenerVel[] = {0.0f, 0.0f, 0.0f};
ALfloat listenerOri[] = {0.0f, 0.0f, -1.0f, 0.0f, 1.0f, 0.0f};
static Task StreamDecoderTask;
+2 -2
View File
@@ -436,7 +436,7 @@ SpliceMultiTrack (UNICODE *TrackNames[], UNICODE *TrackText)
{
fprintf (stderr, " track: %s, decoder: %s, rate %d format %x\n",
*TrackNames,
track_decs[tracks]->decoder_info,
SoundDecoder_GetName (track_decs[tracks]),
track_decs[tracks]->frequency,
track_decs[tracks]->format);
SoundDecoder_DecodeAll (track_decs[tracks]);
@@ -614,7 +614,7 @@ SpliceTrack (UNICODE *TrackName, UNICODE *TrackText, UNICODE *TimeStamp, TFB_Tra
if (last_chain->decoder)
{
static float old_volume = 0.0f;
if (last_chain->decoder->type == SOUNDDECODER_NULL)
if (last_chain->decoder->is_null)
{
if (speechVolumeScale != 0.0f)
{