home *** CD-ROM | disk | FTP | other *** search
/ Learn 3D Graphics Programming on the PC / Learn_3D_Graphics_Programming_on_the_PC_Ferraro.iso / rwwin / winsound.c_ / winsound.bin
Text File  |  1995-11-14  |  11KB  |  420 lines

  1. /**********************************************************************
  2.  *
  3.  * File :     winsound.c
  4.  *
  5.  * Abstract : 
  6.  **********************************************************************
  7.  *
  8.  * This file is a product of Criterion Software Ltd.
  9.  *
  10.  * This file is provided as is with no warranties of any kind and is
  11.  * provided without any obligation on Criterion Software Ltd. or
  12.  * Canon Inc. to assist in its use or modification.
  13.  *
  14.  * Criterion Software Ltd. will not, under any
  15.  * circumstances, be liable for any lost revenue or other damages arising
  16.  * from the use of this file.
  17.  *
  18.  * Copyright (c) 1995 Criterion Software Ltd.
  19.  * All Rights Reserved.
  20.  *
  21.  * RenderWare is a trademark of Canon Inc.
  22.  *
  23.  ************************************************************************/
  24.  
  25. /*--- Include files ---*/
  26.  
  27. #define INCLUDE_SHELLAPI_H
  28.  
  29. #include <windows.h>
  30.  
  31. #include "global.h"
  32.  
  33. #ifdef __WINDOWS_386__
  34. #include "wmwatcom.h"
  35. #else
  36. #include "wavemix.h"
  37. #endif
  38.  
  39. #include "rwwin.h"
  40. #include "resource.h"
  41.  
  42. /*--- Macro and Magic Number Definitions ---*/
  43.  
  44. /*
  45.  * This is the GetWinFlags() flag that indicates we are running a
  46.  * Windows 3.1 app under WOW. This is defined under WOW but not in
  47.  * the standard Windows include files so we have to define it
  48.  * manually.
  49.  */
  50. #if       !defined(WIN32)
  51. #if       !defined(WF_WINNT)
  52. #define   WF_WINNT 0x4000
  53. #endif /* !defined(WF_WINNT) */
  54. #endif /* !defined(WIN32) */
  55.  
  56. #define MAX_SOUND_NAME      16  /* The maximum lenght of a sound name */
  57. #define WAVEMIX_CHANNELS    4   /* The number of Wavemix channels */
  58.  
  59. /*--- Structure Definitions ---*/
  60.  
  61. /* Sound: This structure defines a single instance of a .wav file.
  62.  */
  63.  
  64. typedef struct
  65. {
  66.     char sName[MAX_SOUND_NAME];     /* The name of the sound */
  67.     LPMIXWAVE wSound;               /* The WaveMix data */
  68.     int nDefaultChannel;            /* The default channel that the sound will be
  69.                                        played on */
  70. } Sound;
  71.  
  72. /* AllSounds: A single global variable of this type is declared and used to hold
  73.  * all of the global sound data.
  74.  */
  75.  
  76. typedef struct 
  77. {
  78.     int nAmoSounds;     /* Number of sounds currently defined */
  79.     int nSetup;         /* Sound status flag,  0 = Cant play Sounds */
  80.     Sound *spSounds;    /* Array of loaded sounds */
  81.     HANDLE hSession;    /* Wavemix session information */
  82. } AllSounds;
  83.  
  84. AllSounds asGSounds;
  85.  
  86.  
  87. /* WinVer: Enumerated type which is used in determining the version of windows
  88.  * that we are currently running under
  89.  */
  90.  
  91. typedef enum
  92. {
  93.     rwNAWINVER,     /* Error code                            */
  94.     rwWINDOWSNT,    /* Windows NT                            */
  95.     rwWINDOWS95,    /* Windows 95                            */
  96.     rwWINDOWS31     /* For a WIN32 library this means Win32s */
  97. } WinVer;
  98.  
  99. /************************************************************************
  100.  *
  101.  *      Function:       WindowsVersion()
  102.  *                      
  103.  *      Description:    Determine the version of Windows that we are running on.
  104.  *
  105.  *      Return Value:   One of the versions of Windows defined in the WinVer
  106.  *                      enumerated type
  107.  *
  108.  ************************************************************************/
  109. static WinVer
  110. WindowsVersion(void)
  111. {
  112.     DWORD version;
  113.     int majorVersion;
  114.     int minorVersion;
  115.  
  116.     /*
  117.      * NOTE: In all this version checking we assume that the major
  118.      * Windows version number is three or more as we could not have
  119.      * got this far if we were running under Windows 2.0 or less.
  120.      */
  121.  
  122.     version = GetVersion();
  123.     majorVersion = LOBYTE(LOWORD(version));
  124.     minorVersion = HIBYTE(LOWORD(version));
  125.  
  126.     /*
  127.      * Note: Windows 95 is not Windows v4.0 but v3.95 so this is what
  128.      * we check for. Also, we assume that anything at all after
  129.      * Windows 95 is compatible with Windows 95.
  130.      */
  131.     if ((majorVersion == 3) && (minorVersion < 95))
  132.     {
  133.     /*
  134.      * This could be either Windows 3.1 or Windows NT - you
  135.      * can't tell from the version number. To find out we
  136.      * need to look at GetWinFlags() which returns the
  137.      * value WF_WINNT under Windows NT. The value WF_WINNT
  138.      * is not defined in the standard Windows 3.1 include
  139.      * files so we have defined it ourselved at the top
  140.      * of this file.
  141.      */
  142.     if ((GetWinFlags() & WF_WINNT) == WF_WINNT)
  143.     {
  144.         /*
  145.          * This is Windows NT of some form. As RenderWare is only
  146.          * supported on NT 3.5 we have to check the version number
  147.          * to ensure this is not NT 3.1.
  148.          */
  149.         if ((majorVersion == 3) && (minorVersion < 5))
  150.         {
  151.         /*
  152.          * This is NT 3.1 which we do not support, return an error.
  153.          */
  154.         return rwNAWINVER;
  155.         }
  156.         else
  157.         {
  158.         /*
  159.          * Windows NT 3.5.
  160.          */
  161.         return rwWINDOWSNT;
  162.         }
  163.     }
  164.     else
  165.     {
  166.         /*
  167.          * Windows 3.1.
  168.          */
  169.         return rwWINDOWS31;
  170.     }
  171.     }
  172.     else
  173.     {
  174.     /*
  175.      * Windows 95.
  176.      */
  177.     return rwWINDOWS95;
  178.     }
  179.  
  180. }
  181. /************************************************************************
  182.  *
  183.  *      Function:       AllSoundsSetup()
  184.  *                      
  185.  *      Description:    Initialise the global AllSounds data structure
  186.  *
  187.  *      Return Value:   TRUE on success, FALSE on failure
  188.  *
  189.  ************************************************************************/
  190. int AllSoundsSetup(void)
  191. {
  192.     int nCount;
  193.     MIXCONFIG cConfig;
  194.  
  195.     asGSounds.nSetup = 0;           /* Not initialized */
  196.  
  197.     if (WindowsVersion() != rwWINDOWS31) 
  198.     {
  199.         /* If you are not running 3.1 the wave mix stuff doesn't work
  200.             correctly */
  201.         return FALSE;
  202.     }
  203.  
  204.     /* No sounds loaded yet */
  205.     asGSounds.spSounds = NULL;
  206.     asGSounds.nAmoSounds = 0;
  207.  
  208. #if defined(__WINDOWS_386__)
  209.      /* Open the wavemix library. Only necessary if we are using
  210.         Watcom. Visual C++ and Borland C++ use an import library */
  211.     if (!WaveMixOpen())
  212.     {
  213.         return FALSE;
  214.     }
  215. #endif
  216.  
  217.     cConfig.wSize = sizeof(MIXCONFIG);
  218.     cConfig.dwFlags = WMIX_CONFIG_CHANNELS|WMIX_CONFIG_SAMPLINGRATE;
  219.     cConfig.wChannels = 1;
  220.     cConfig.wSamplingRate =11;
  221.  
  222.     if ((asGSounds.hSession = WaveMixConfigureInit(&cConfig))==NULL) 
  223.     {
  224. #if defined(__WINDOWS_386__)
  225.         WaveMixClose();
  226. #endif
  227.         return FALSE;
  228.     }
  229.  
  230.     for (nCount=0; nCount < WAVEMIX_CHANNELS; nCount++) 
  231.     {
  232.         if (WaveMixOpenChannel(asGSounds.hSession, nCount, WMIX_ALL)) 
  233.         {
  234.             break;
  235.         }
  236.     }
  237.  
  238.     if (nCount < WAVEMIX_CHANNELS) 
  239.     {
  240.         /* Cant open 4 channels */
  241.  
  242.         for (; nCount-1 >= 0; nCount--) 
  243.         {
  244.             WaveMixCloseChannel(asGSounds.hSession, nCount, 0UL);
  245.         }
  246.  
  247.         WaveMixCloseSession(asGSounds.hSession);
  248. #if defined(__WINDOWS_386__)
  249.         WaveMixClose();
  250. #endif
  251.         return FALSE;
  252.     }
  253.  
  254.     WaveMixActivate(asGSounds.hSession, TRUE);
  255.  
  256.     /* Mark as ready to play sounds */
  257.  
  258.     asGSounds.nSetup = 1;           /* Can play sounds */
  259.  
  260.     return TRUE;
  261. }
  262.  
  263. /************************************************************************
  264.  *
  265.  *      Function:       AllSoundsDestroy()
  266.  *                      
  267.  *      Description:    Destroy the global AllSounds data structure
  268.  *
  269.  *      Return Value:   None
  270.  *
  271.  ************************************************************************/
  272. void AllSoundsDestroy(void)
  273. {
  274.     int nCount;
  275.  
  276.     if (!asGSounds.nSetup) 
  277.     {
  278.         /* Sounds weren't set up so we don't need to do anything */
  279.         return;
  280.     }
  281.  
  282.     WaveMixActivate(asGSounds.hSession, FALSE);
  283.  
  284.     if (asGSounds.spSounds) 
  285.     {
  286.         /* Sounds loaded - free them up */
  287.  
  288.         for (nCount = 0; nCount < asGSounds.nAmoSounds; nCount++) 
  289.         {
  290.             WaveMixFreeWave(asGSounds.hSession, asGSounds.spSounds[nCount].wSound);
  291.         }
  292.         free(asGSounds.spSounds);
  293.     }
  294.  
  295.   /* Take out the sound handler */
  296.  
  297.   for (nCount = 0; nCount < WAVEMIX_CHANNELS; nCount++) 
  298.   {
  299.         WaveMixCloseChannel(asGSounds.hSession, nCount, 0UL);
  300.   }
  301.  
  302.   WaveMixCloseSession(asGSounds.hSession);
  303. #if defined(__WINDOWS_386__)
  304.   WaveMixClose();
  305. #endif
  306. }
  307.  
  308. /************************************************************************
  309.  *
  310.  *      Function:       AllSoundsAddSound()
  311.  *                      
  312.  *      Description:    Add another sounds to our sound library
  313.  *
  314.  *      Parameters:     cpFilename - the name of the .wav file to load
  315.  *                      nChannel - the default channel (0 -3 ) for this sound
  316.  *
  317.  *      Return Value:   None
  318.  *
  319.  ************************************************************************/
  320. int AllSoundsAddSound(char *cpFilename, int nChannel)
  321. {
  322.     LPMIXWAVE wWave;
  323.     Sound *spSound;
  324.     char *cpTmp;
  325.  
  326.     if (!asGSounds.nSetup) 
  327.     {
  328.         /* We're not using sounds so don't do anything */
  329.         return FALSE;
  330.     }
  331.  
  332.     wWave = WaveMixOpenWave(asGSounds.hSession, cpFilename, NULL, WMIX_FILE);
  333.     if (wWave == NULL) 
  334.     {
  335.         return FALSE;
  336.     }
  337.  
  338.     if (asGSounds.nAmoSounds) 
  339.     {
  340.         /* This isn't the first so so we need to realloc */
  341.         asGSounds.spSounds =
  342.         realloc(asGSounds.spSounds, sizeof(Sound) * (asGSounds.nAmoSounds+1));
  343.     } 
  344.     else 
  345.     {
  346.         asGSounds.spSounds = malloc(sizeof(Sound));
  347.     }
  348.  
  349.     spSound = &asGSounds.spSounds[asGSounds.nAmoSounds];
  350.     asGSounds.nAmoSounds++;
  351.  
  352.     spSound->wSound = wWave;
  353.  
  354.     strcpy(spSound->sName,cpFilename);
  355.  
  356.     /* Remove filename extension */
  357.  
  358.     for (cpTmp = spSound->sName; ((*cpTmp) && ((*cpTmp)!='.')); cpTmp++)
  359.         ;
  360.     if (*cpTmp=='.') 
  361.     {
  362.         *cpTmp = '\0';
  363.     }
  364.  
  365.     /* Save the other characteristics */
  366.  
  367.     spSound->nDefaultChannel = nChannel;
  368.  
  369.     return TRUE;
  370. }
  371.  
  372. /************************************************************************
  373.  *
  374.  *      Function:       AllSoundsPlaySound()
  375.  *                      
  376.  *      Description:    Play the sound
  377.  *
  378.  *      Parameters:     cpFilename - the name of the sound to play
  379.  *
  380.  *      Return Value:   TRUE if the sound played, FALSE otherwise
  381.  *
  382.  ************************************************************************/
  383. int AllSoundsPlaySound(char *cpFilename)
  384. {
  385.     int nCount;
  386.     Sound *spSound;
  387.     MIXPLAYPARAMS pParams;
  388.  
  389.     if (!asGSounds.nSetup) 
  390.     {
  391.         /* Not using sound so don't play a sound */
  392.         return FALSE;
  393.     };
  394.  
  395.     spSound = asGSounds.spSounds;
  396.  
  397.     for (nCount=0; nCount < asGSounds.nAmoSounds; nCount++) 
  398.     {
  399.         if (!strcmp(spSound->sName, cpFilename)) 
  400.         {
  401.             /* Found the little sucker. Play it */
  402.  
  403.             pParams.wSize       = sizeof(MIXPLAYPARAMS);
  404.             pParams.hMixSession = asGSounds.hSession;
  405.             pParams.iChannel    = spSound->nDefaultChannel;
  406.             pParams.lpMixWave   = spSound->wSound;
  407.             pParams.hWndNotify  = NULL;
  408.             pParams.dwFlags     = WMIX_CLEARQUEUE|WMIX_HIPRIORITY;
  409.             pParams.wLoops      = 0;
  410.             WaveMixPlay(&pParams);
  411.  
  412.             return TRUE;
  413.         }
  414.         spSound++;
  415.     }
  416.  
  417.     return FALSE;
  418. }
  419.  
  420.