home *** CD-ROM | disk | FTP | other *** search
/ PC Online 1999 February / PCO_0299.ISO / filesbbs / linux / mikmod-3.000 / mikmod-3 / mikmod-3.1.2 / playercode / mwav.c < prev    next >
Encoding:
C/C++ Source or Header  |  1998-12-07  |  3.2 KB  |  146 lines

  1. /*    MikMod sound library
  2.     (c) 1998 Miodrag Vallat and others - see file AUTHORS for complete list
  3.  
  4.     This library is free software; you can redistribute it and/or modify
  5.     it under the terms of the GNU Library General Public License as
  6.     published by the Free Software Foundation; either version 2 of
  7.     the License, or (at your option) any later version.
  8.  
  9.     This program is distributed in the hope that it will be useful,
  10.     but WITHOUT ANY WARRANTY; without even the implied warranty of
  11.     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  12.     GNU Library General Public License for more details.
  13.  
  14.     You should have received a copy of the GNU Library General Public
  15.     License along with this library; if not, write to the Free Software
  16.     Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  17. */
  18.  
  19. /*==============================================================================
  20.  
  21.   $Id: mwav.c,v 1.15 1998/12/07 06:00:48 miod Exp $
  22.  
  23.  WAV sample loader
  24.  
  25. ==============================================================================*/
  26.  
  27. /*
  28.    FIXME: Stereo .WAV files are not yet supported as samples.
  29. */
  30.  
  31. #ifdef HAVE_CONFIG_H
  32. #include "config.h"
  33. #endif
  34.  
  35. #include <string.h>
  36.  
  37. #include <mikmod_internals.h>
  38.  
  39. typedef struct WAV {
  40.     CHAR  rID[4];
  41.     ULONG rLen;
  42.     CHAR  wID[4];
  43.     CHAR  fID[4];
  44.     ULONG fLen;
  45.     UWORD wFormatTag;
  46.     UWORD nChannels;
  47.     ULONG nSamplesPerSec;
  48.     ULONG nAvgBytesPerSec;
  49.     UWORD nBlockAlign;
  50.     UWORD nFormatSpecific;
  51. } WAV;
  52.  
  53. SAMPLE* Sample_LoadFP(FILE* fp)
  54. {
  55.     SAMPLE *si;
  56.     WAV wh;
  57.     CHAR dID[4];
  58.  
  59.     /* read wav header */
  60.     _mm_read_string(wh.rID,4,fp);
  61.     wh.rLen = _mm_read_I_ULONG(fp);
  62.     _mm_read_string(wh.wID,4,fp);
  63.  
  64.     while(1) {
  65.         _mm_read_string(wh.fID,4,fp);
  66.         wh.fLen = _mm_read_I_ULONG(fp);
  67.         if(!(memcmp(wh.fID,"fmt ",4))) break;
  68.         _mm_fseek(fp,wh.fLen,SEEK_CUR);
  69.     }
  70.  
  71.     if(feof(fp)|| memcmp(wh.rID,"RIFF",4) || memcmp(wh.wID,"WAVE",4)) {
  72.         _mm_errno = MMERR_UNKNOWN_WAVE_TYPE;
  73.         return NULL;
  74.     }
  75.  
  76.     wh.wFormatTag      = _mm_read_I_UWORD(fp);
  77.     wh.nChannels       = _mm_read_I_UWORD(fp);
  78.     wh.nSamplesPerSec  = _mm_read_I_ULONG(fp);
  79.     wh.nAvgBytesPerSec = _mm_read_I_ULONG(fp);
  80.     wh.nBlockAlign     = _mm_read_I_UWORD(fp);
  81.     wh.nFormatSpecific = _mm_read_I_UWORD(fp);
  82.  
  83.     if(feof(fp)) {
  84.         _mm_errno = MMERR_UNKNOWN_WAVE_TYPE;
  85.         return NULL;
  86.     }
  87.  
  88.     /* skip other crap */
  89.     _mm_fseek(fp,wh.fLen-16,SEEK_CUR);
  90.     _mm_read_string(dID,4,fp);
  91.  
  92.     if(memcmp(dID,"data",4)) {
  93.         _mm_errno = MMERR_UNKNOWN_WAVE_TYPE;
  94.         return NULL;
  95.     }
  96.  
  97.     if(wh.nChannels>1) {
  98.         _mm_errno = MMERR_UNKNOWN_WAVE_TYPE;
  99.         return NULL;
  100.     }
  101.  
  102. #ifdef MIKMOD_DEBUG
  103.     fprintf(stderr,"\rwavloader : wFormatTag=%04x blockalign=%04x nFormatSpc=%04x\n",
  104.             wh.wFormatTag,wh.nBlockAlign,wh.nFormatSpecific);
  105. #endif
  106.  
  107.     if(!(si=(SAMPLE*)_mm_malloc(sizeof(SAMPLE)))) return NULL;
  108.  
  109.     si->speed  = wh.nSamplesPerSec/wh.nChannels;
  110.     si->volume = 64;
  111.     si->length = _mm_read_I_ULONG(fp);
  112.  
  113.     if(wh.nBlockAlign == 2) {
  114.         si->flags    = SF_16BITS | SF_SIGNED;
  115.         si->length >>= 1;
  116.     }
  117.  
  118.     SL_RegisterSample(si,MD_SNDFX,fp);
  119.     SL_LoadSamples();
  120.  
  121.     return si;
  122. }
  123.  
  124. SAMPLE* Sample_Load(CHAR* filename)
  125. {
  126.     FILE *fp;
  127.     SAMPLE *si;
  128.  
  129.     if(!(md_mode & DMODE_SOFT_SNDFX)) return NULL;
  130.     if(!(fp=_mm_fopen(filename,"rb"))) return NULL;
  131.  
  132.     si = Sample_LoadFP(fp);
  133.     fclose(fp);
  134.  
  135.     return si;
  136. }
  137.  
  138. void Sample_Free(SAMPLE* si)
  139. {
  140.     if(si) {
  141.         MD_SampleUnload(si->handle);
  142.         free(si);
  143.     }
  144. }
  145.  
  146.