]> de.git.xonotic.org Git - xonotic/darkplaces.git/blobdiff - dpvsimpledecode.c
Configure all of the CL_MeshEntities* meshes the same, the material flags decide...
[xonotic/darkplaces.git] / dpvsimpledecode.c
index bdfcf319b0dfaf96aeb592e4af9083e15fe6c634..ed89260a9f97a857617d01c55a4f8fb8c445ade1 100644 (file)
@@ -1,26 +1,16 @@
-
-#include <stdlib.h>
-#include <stdio.h>
-#include <math.h>
-#include <string.h>
+#include "quakedef.h"
 #include "dpvsimpledecode.h"
-#include "wavefile.h"
-
-#define EMBEDDEDHZREAD 1
 
-#ifndef EMBEDDEDHZREAD
-#include "hz_read.h"
-#include "hz_read.c"
-#else
 #define HZREADERROR_OK 0
 #define HZREADERROR_EOF 1
 #define HZREADERROR_MALLOCFAILED 2
 
-#define HZREADBLOCKSIZE 16000
+//#define HZREADBLOCKSIZE 16000
+#define HZREADBLOCKSIZE 1048576
 
-typedef struct
+typedef struct hz_bitstream_read_s
 {
-       FILE *file;
+       qfile_t *file;
        int endoffile;
 }
 hz_bitstream_read_t;
@@ -33,7 +23,7 @@ typedef struct hz_bitstream_readblock_s
 }
 hz_bitstream_readblock_t;
 
-typedef struct
+typedef struct hz_bitstream_readblocks_s
 {
        hz_bitstream_readblock_t *blocks;
        hz_bitstream_readblock_t *current;
@@ -43,13 +33,13 @@ typedef struct
 }
 hz_bitstream_readblocks_t;
 
-hz_bitstream_read_t *hz_bitstream_read_open(char *filename)
+static hz_bitstream_read_t *hz_bitstream_read_open(char *filename)
 {
-       FILE *file;
+       qfile_t *file;
        hz_bitstream_read_t *stream;
-       if ((file = fopen(filename, "rb")))
+       if ((file = FS_OpenVirtualFile(filename, false)))
        {
-               stream = malloc(sizeof(hz_bitstream_read_t));
+               stream = (hz_bitstream_read_t *)Z_Malloc(sizeof(hz_bitstream_read_t));
                memset(stream, 0, sizeof(*stream));
                stream->file = file;
                return stream;
@@ -58,37 +48,26 @@ hz_bitstream_read_t *hz_bitstream_read_open(char *filename)
                return NULL;
 }
 
-void hz_bitstream_read_close(hz_bitstream_read_t *stream)
+static void hz_bitstream_read_close(hz_bitstream_read_t *stream)
 {
        if (stream)
        {
-               fclose(stream->file);
-               free(stream);
+               FS_Close(stream->file);
+               Z_Free(stream);
        }
 }
 
-unsigned int hz_bitstream_read_currentbyte(hz_bitstream_read_t *stream)
-{
-       return ftell(stream->file);
-}
-
-int hz_bitstream_read_seek(hz_bitstream_read_t *stream, unsigned int position)
-{
-       stream->endoffile = 0;
-       return fseek(stream->file, position, SEEK_SET) != 0;
-}
-
-hz_bitstream_readblocks_t *hz_bitstream_read_blocks_new(void)
+static hz_bitstream_readblocks_t *hz_bitstream_read_blocks_new(void)
 {
        hz_bitstream_readblocks_t *blocks;
-       blocks = malloc(sizeof(hz_bitstream_readblocks_t));
+       blocks = (hz_bitstream_readblocks_t *)Z_Malloc(sizeof(hz_bitstream_readblocks_t));
        if (blocks == NULL)
                return NULL;
        memset(blocks, 0, sizeof(hz_bitstream_readblocks_t));
        return blocks;
 }
 
-void hz_bitstream_read_blocks_free(hz_bitstream_readblocks_t *blocks)
+static void hz_bitstream_read_blocks_free(hz_bitstream_readblocks_t *blocks)
 {
        hz_bitstream_readblock_t *b, *n;
        if (blocks == NULL)
@@ -96,18 +75,18 @@ void hz_bitstream_read_blocks_free(hz_bitstream_readblocks_t *blocks)
        for (b = blocks->blocks;b;b = n)
        {
                n = b->next;
-               free(b);
+               Z_Free(b);
        }
-       free(blocks);
+       Z_Free(blocks);
 }
 
-void hz_bitstream_read_flushbits(hz_bitstream_readblocks_t *blocks)
+static void hz_bitstream_read_flushbits(hz_bitstream_readblocks_t *blocks)
 {
        blocks->store = 0;
        blocks->count = 0;
 }
 
-int hz_bitstream_read_blocks_read(hz_bitstream_readblocks_t *blocks, hz_bitstream_read_t *stream, unsigned int size)
+static int hz_bitstream_read_blocks_read(hz_bitstream_readblocks_t *blocks, hz_bitstream_read_t *stream, unsigned int size)
 {
        int s;
        hz_bitstream_readblock_t *b, *p;
@@ -118,7 +97,7 @@ int hz_bitstream_read_blocks_read(hz_bitstream_readblocks_t *blocks, hz_bitstrea
        {
                if (b == NULL)
                {
-                       b = malloc(sizeof(hz_bitstream_readblock_t));
+                       b = (hz_bitstream_readblock_t *)Z_Malloc(sizeof(hz_bitstream_readblock_t));
                        if (b == NULL)
                                return HZREADERROR_MALLOCFAILED;
                        b->next = NULL;
@@ -133,7 +112,7 @@ int hz_bitstream_read_blocks_read(hz_bitstream_readblocks_t *blocks, hz_bitstrea
                else
                        b->size = s;
                s -= b->size;
-               if (fread(b->data, 1, b->size, stream->file) != b->size)
+               if (FS_Read(stream->file, b->data, b->size) != (fs_offset_t)b->size)
                {
                        stream->endoffile = 1;
                        break;
@@ -154,7 +133,7 @@ int hz_bitstream_read_blocks_read(hz_bitstream_readblocks_t *blocks, hz_bitstrea
        return HZREADERROR_OK;
 }
 
-unsigned int hz_bitstream_read_blocks_getbyte(hz_bitstream_readblocks_t *blocks)
+static unsigned int hz_bitstream_read_blocks_getbyte(hz_bitstream_readblocks_t *blocks)
 {
        while (blocks->current != NULL && blocks->position >= blocks->current->size)
        {
@@ -166,7 +145,7 @@ unsigned int hz_bitstream_read_blocks_getbyte(hz_bitstream_readblocks_t *blocks)
        return blocks->current->data[blocks->position++];
 }
 
-int hz_bitstream_read_bit(hz_bitstream_readblocks_t *blocks)
+static int hz_bitstream_read_bit(hz_bitstream_readblocks_t *blocks)
 {
        if (!blocks->count)
        {
@@ -178,7 +157,7 @@ int hz_bitstream_read_bit(hz_bitstream_readblocks_t *blocks)
        return (blocks->store >> blocks->count) & 1;
 }
 
-unsigned int hz_bitstream_read_bits(hz_bitstream_readblocks_t *blocks, unsigned int size)
+static unsigned int hz_bitstream_read_bits(hz_bitstream_readblocks_t *blocks, int size)
 {
        unsigned int num = 0;
        // we can only handle about 24 bits at a time safely
@@ -199,18 +178,18 @@ unsigned int hz_bitstream_read_bits(hz_bitstream_readblocks_t *blocks, unsigned
        return num;
 }
 
-unsigned int hz_bitstream_read_byte(hz_bitstream_readblocks_t *blocks)
+static unsigned int hz_bitstream_read_byte(hz_bitstream_readblocks_t *blocks)
 {
        return hz_bitstream_read_blocks_getbyte(blocks);
 }
 
-unsigned int hz_bitstream_read_short(hz_bitstream_readblocks_t *blocks)
+static unsigned int hz_bitstream_read_short(hz_bitstream_readblocks_t *blocks)
 {
        return (hz_bitstream_read_byte(blocks) << 8)
             | (hz_bitstream_read_byte(blocks));
 }
 
-unsigned int hz_bitstream_read_int(hz_bitstream_readblocks_t *blocks)
+static unsigned int hz_bitstream_read_int(hz_bitstream_readblocks_t *blocks)
 {
        return (hz_bitstream_read_byte(blocks) << 24)
             | (hz_bitstream_read_byte(blocks) << 16)
@@ -218,14 +197,13 @@ unsigned int hz_bitstream_read_int(hz_bitstream_readblocks_t *blocks)
             | (hz_bitstream_read_byte(blocks));
 }
 
-void hz_bitstream_read_bytes(hz_bitstream_readblocks_t *blocks, void *outdata, unsigned int size)
+static void hz_bitstream_read_bytes(hz_bitstream_readblocks_t *blocks, void *outdata, unsigned int size)
 {
        unsigned char *out;
-       out = outdata;
+       out = (unsigned char *)outdata;
        while (size--)
                *out++ = hz_bitstream_read_byte(blocks);
 }
-#endif
 
 #define BLOCKSIZE 8
 
@@ -252,14 +230,15 @@ typedef struct dpvsimpledecodestream_s
        unsigned int info_imageBmask;
        unsigned int info_imageBshift;
        unsigned int info_imagesize;
+       double info_aspectratio;
 
        // current video frame (needed because of delta compression)
        int videoframenum;
        // current video frame data (needed because of delta compression)
        unsigned int *videopixels;
 
-       // wav file the sound is being read from
-       wavefile_t *wavefile;
+       // channel the sound file is being played on
+       int sndchan;
 }
 dpvsimpledecodestream_t;
 
@@ -300,7 +279,6 @@ static int dpvsimpledecode_setpixelformat(dpvsimpledecodestream_t *s, unsigned i
        default:
                s->error = DPVSIMPLEDECODEERROR_UNSUPPORTEDBPP;
                return s->error;
-               break;
        }
        for (Rshift = 0;!(Rmask & 1);Rshift++, Rmask >>= 1);
        for (Gshift = 0;!(Gmask & 1);Gshift++, Gmask >>= 1);
@@ -354,38 +332,14 @@ static int dpvsimpledecode_setpixelformat(dpvsimpledecodestream_t *s, unsigned i
 
 // opening and closing streams
 
-static void StripExtension(char *in, char *out)
-{
-       char *dot, *c;
-       dot = NULL;
-       for (c = in;*c;c++)
-       {
-               if (*c == ':' || *c == '\\' || *c == '/')
-                       dot = NULL;
-               if (*c == '.')
-                       dot = c;
-       }
-       if (dot == NULL)
-       {
-               // nothing to remove
-               strcpy(out, in);
-               return;
-       }
-       else
-       {
-               memcpy(out, in, dot - in);
-               out[dot - in] = 0;
-       }
-}
-
 // opens a stream
-void *dpvsimpledecode_open(char *filename, char **errorstring)
+void *dpvsimpledecode_open(clvideo_t *video, char *filename, const char **errorstring)
 {
        dpvsimpledecodestream_t *s;
        char t[8], *wavename;
        if (errorstring != NULL)
                *errorstring = NULL;
-       s = malloc(sizeof(dpvsimpledecodestream_t));
+       s = (dpvsimpledecodestream_t *)Z_Malloc(sizeof(dpvsimpledecodestream_t));
        if (s != NULL)
        {
                s->bitstream = hz_bitstream_read_open(filename);
@@ -407,22 +361,40 @@ void *dpvsimpledecode_open(char *filename, char **errorstring)
                                                s->info_imagewidth = hz_bitstream_read_short(s->framedatablocks);
                                                s->info_imageheight = hz_bitstream_read_short(s->framedatablocks);
                                                s->info_framerate = (double) hz_bitstream_read_int(s->framedatablocks) * (1.0 / 65536.0);
+                                               s->info_aspectratio = (double)s->info_imagewidth / (double)s->info_imageheight;
 
                                                if (s->info_framerate > 0.0)
                                                {
-                                                       s->videopixels = malloc(s->info_imagewidth * s->info_imageheight * sizeof(*s->videopixels));
+                                                       s->videopixels = (unsigned int *)Z_Malloc(s->info_imagewidth * s->info_imageheight * sizeof(*s->videopixels));
                                                        if (s->videopixels != NULL)
                                                        {
-                                                               wavename = malloc(strlen(filename) + 10);
+                                                               size_t namelen;
+
+                                                               namelen = strlen(filename) + 10;
+                                                               wavename = (char *)Z_Malloc(namelen);
                                                                if (wavename)
                                                                {
-                                                                       StripExtension(filename, wavename);
-                                                                       strcat(wavename, ".wav");
-                                                                       s->wavefile = waveopen(wavename, NULL);
-                                                                       free(wavename);
+                                                                       sfx_t* sfx;
+
+                                                                       FS_StripExtension(filename, wavename, namelen);
+                                                                       strlcat(wavename, ".wav", namelen);
+                                                                       sfx = S_PrecacheSound (wavename, false, false);
+                                                                       if (sfx != NULL)
+                                                                               s->sndchan = S_StartSound (-1, 0, sfx, vec3_origin, 1.0f, 0);
+                                                                       else
+                                                                               s->sndchan = -1;
+                                                                       Z_Free(wavename);
                                                                }
                                                                // all is well...
+                                                               // set the module functions
                                                                s->videoframenum = -10000;
+                                                               video->close = dpvsimpledecode_close;
+                                                               video->getwidth = dpvsimpledecode_getwidth;
+                                                               video->getheight = dpvsimpledecode_getheight;
+                                                               video->getframerate = dpvsimpledecode_getframerate;
+                                                               video->decodeframe = dpvsimpledecode_video;
+                                                               video->getaspectratio = dpvsimpledecode_getaspectratio;
+
                                                                return s;
                                                        }
                                                        else if (errorstring != NULL)
@@ -444,7 +416,7 @@ void *dpvsimpledecode_open(char *filename, char **errorstring)
                }
                else if (errorstring != NULL)
                        *errorstring = "unable to open file";
-               free(s);
+               Z_Free(s);
        }
        else if (errorstring != NULL)
                *errorstring = "unable to allocate memory for stream info structure";
@@ -454,18 +426,18 @@ void *dpvsimpledecode_open(char *filename, char **errorstring)
 // closes a stream
 void dpvsimpledecode_close(void *stream)
 {
-       dpvsimpledecodestream_t *s = stream;
+       dpvsimpledecodestream_t *s = (dpvsimpledecodestream_t *)stream;
        if (s == NULL)
                return;
        if (s->videopixels)
-               free(s->videopixels);
-       if (s->wavefile)
-               waveclose(s->wavefile);
+               Z_Free(s->videopixels);
+       if (s->sndchan != -1)
+               S_StopChannel (s->sndchan, true, true);
        if (s->framedatablocks)
                hz_bitstream_read_blocks_free(s->framedatablocks);
        if (s->bitstream)
                hz_bitstream_read_close(s->bitstream);
-       free(s);
+       Z_Free(s);
 }
 
 // utilitarian functions
@@ -474,9 +446,9 @@ void dpvsimpledecode_close(void *stream)
 // number to DPVSIMPLEDECODEERROR_NONE
 // if the supplied string pointer variable is not NULL, it will be set to the
 // error message
-int dpvsimpledecode_error(void *stream, char **errorstring)
+int dpvsimpledecode_error(void *stream, const char **errorstring)
 {
-       dpvsimpledecodestream_t *s = stream;
+       dpvsimpledecodestream_t *s = (dpvsimpledecodestream_t *)stream;
        int e;
        e = s->error;
        s->error = 0;
@@ -525,37 +497,30 @@ int dpvsimpledecode_error(void *stream, char **errorstring)
 // returns the width of the image data
 unsigned int dpvsimpledecode_getwidth(void *stream)
 {
-       dpvsimpledecodestream_t *s = stream;
+       dpvsimpledecodestream_t *s = (dpvsimpledecodestream_t *)stream;
        return s->info_imagewidth;
 }
 
 // returns the height of the image data
 unsigned int dpvsimpledecode_getheight(void *stream)
 {
-       dpvsimpledecodestream_t *s = stream;
+       dpvsimpledecodestream_t *s = (dpvsimpledecodestream_t *)stream;
        return s->info_imageheight;
 }
 
-// returns the sound sample rate of the stream
-unsigned int dpvsimpledecode_getsoundrate(void *stream)
-{
-       dpvsimpledecodestream_t *s = stream;
-       if (s->wavefile)
-               return s->wavefile->info_rate;
-       else
-               return 0;
-}
-
 // returns the framerate of the stream
 double dpvsimpledecode_getframerate(void *stream)
 {
-       dpvsimpledecodestream_t *s = stream;
+       dpvsimpledecodestream_t *s = (dpvsimpledecodestream_t *)stream;
        return s->info_framerate;
 }
 
-
-
-
+// return aspect ratio of the stream
+double dpvsimpledecode_getaspectratio(void *stream)
+{
+       dpvsimpledecodestream_t *s = (dpvsimpledecodestream_t *)stream;
+       return s->info_aspectratio;
+}
 
 static int dpvsimpledecode_convertpixels(dpvsimpledecodestream_t *s, void *imagedata, int imagebytesperrow)
 {
@@ -582,7 +547,7 @@ static int dpvsimpledecode_convertpixels(dpvsimpledecodestream_t *s, void *image
                unsigned int *outrow;
                for (y = 0;y < height;y++)
                {
-                       outrow = (void *)((unsigned char *)imagedata + y * imagebytesperrow);
+                       outrow = (unsigned int *)((unsigned char *)imagedata + y * imagebytesperrow);
                        for (x = 0;x < width;x++)
                        {
                                a = *in++;
@@ -595,7 +560,7 @@ static int dpvsimpledecode_convertpixels(dpvsimpledecodestream_t *s, void *image
                unsigned short *outrow;
                for (y = 0;y < height;y++)
                {
-                       outrow = (void *)((unsigned char *)imagedata + y * imagebytesperrow);
+                       outrow = (unsigned short *)((unsigned char *)imagedata + y * imagebytesperrow);
                        if (Rloss == 19 && Gloss == 10 && Bloss == 3 && Rshift == 11 && Gshift == 5 && Bshift == 0)
                        {
                                // optimized
@@ -665,7 +630,7 @@ static int dpvsimpledecode_decompressimage(dpvsimpledecodestream_t *s)
 // decodes a video frame to the supplied output pixels
 int dpvsimpledecode_video(void *stream, void *imagedata, unsigned int Rmask, unsigned int Gmask, unsigned int Bmask, unsigned int bytesperpixel, int imagebytesperrow)
 {
-       dpvsimpledecodestream_t *s = stream;
+       dpvsimpledecodestream_t *s = (dpvsimpledecodestream_t *)stream;
        unsigned int framedatasize;
        char t[4];
        s->error = DPVSIMPLEDECODEERROR_NONE;
@@ -689,20 +654,3 @@ int dpvsimpledecode_video(void *stream, void *imagedata, unsigned int Rmask, uns
        dpvsimpledecode_convertpixels(s, imagedata, imagebytesperrow);
        return s->error;
 }
-
-// (note: sound is 16bit stereo native-endian, left channel first)
-int dpvsimpledecode_audio(void *stream, short *soundbuffer, int requestedlength)
-{
-       int samples;
-       dpvsimpledecodestream_t *s = stream;
-       s->error = DPVSIMPLEDECODEERROR_NONE;
-       if (requestedlength)
-       {
-               samples = 0;
-               if (s->wavefile && requestedlength)
-                       samples = waveread16stereo(s->wavefile, soundbuffer, requestedlength);
-               if (samples < requestedlength)
-                       memset(soundbuffer + samples * 2, 0, (requestedlength - samples) * sizeof(short[2]));
-       }
-       return s->error;
-}