⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 i_sound_sdl.c

📁 PIXIL is a small footprint operating environment, complete with PDA PIM applications, a browser and
💻 C
📖 第 1 页 / 共 2 页
字号:
// Emacs style mode select   -*- C++ -*- //-----------------------------------------------------------------------------//// $Id: i_sound_sdl.c,v 1.1 2003/09/08 19:41:53 jasonk Exp $//// Copyright (C) 1993-1996 by id Software, Inc.//// This source is available for distribution and/or modification// only under the terms of the DOOM Source Code License as// published by id Software. All rights reserved.//// The source is distributed in the hope that it will be useful,// but WITHOUT ANY WARRANTY; without even the implied warranty of// FITNESS FOR A PARTICULAR PURPOSE. See the DOOM Source Code License// for more details.//// $Log: i_sound_sdl.c,v $// Revision 1.1  2003/09/08 19:41:53  jasonk// Addition of packages directory and associated files.//// Revision 1.1  2000/12/08 21:07:53  jeffw// nxdoom initial entry -- No nxdoom/Makefile so it won't build automatically////// DESCRIPTION://	System interface for sound.////-----------------------------------------------------------------------------static const charrcsid[] = "$Id: i_sound_sdl.c,v 1.1 2003/09/08 19:41:53 jasonk Exp $";#include <math.h>#include "SDL_audio.h"#include "SDL_mutex.h"#include "SDL_byteorder.h"#include "SDL_version.h"#include "z_zone.h"#include "m_swap.h"#include "i_system.h"#include "i_sound.h"#include "m_argv.h"#include "m_misc.h"#include "w_wad.h"#include "doomdef.h"// The number of internal mixing channels,//  the samples calculated for each mixing step,//  the size of the 16bit, 2 hardware channel (stereo)//  mixing buffer, and the samplerate of the raw data.// Needed for calling the actual sound output.static int SAMPLECOUNT=		512;#define NUM_CHANNELS		8#define SAMPLERATE		11025	// Hz// The actual lengths of all sound effects.int 		lengths[NUMSFX];// The actual output device.int	audio_fd;// The channel step amount...unsigned int	channelstep[NUM_CHANNELS];// ... and a 0.16 bit remainder of last step.unsigned int	channelstepremainder[NUM_CHANNELS];// The channel data pointers, start and end.unsigned char*	channels[NUM_CHANNELS];unsigned char*	channelsend[NUM_CHANNELS];// Time/gametic that the channel started playing,//  used to determine oldest, which automatically//  has lowest priority.// In case number of active sounds exceeds//  available channels.int		channelstart[NUM_CHANNELS];// The sound in channel handles,//  determined on registration,//  might be used to unregister/stop/modify,//  currently unused.int 		channelhandles[NUM_CHANNELS];// SFX id of the playing sound effect.// Used to catch duplicates (like chainsaw).int		channelids[NUM_CHANNELS];			// Pitch to stepping lookup, unused.int		steptable[256];// Volume lookups.int		vol_lookup[128*256];// Hardware left and right channel volume lookup.int*		channelleftvol_lookup[NUM_CHANNELS];int*		channelrightvol_lookup[NUM_CHANNELS];//// This function loads the sound data from the WAD lump,//  for single sound.//void*getsfx( char*         sfxname,  int*          len ){    unsigned char*      sfx;    unsigned char*      paddedsfx;    int                 i;    int                 size;    int                 paddedsize;    char                name[20];    int                 sfxlump;        // Get the sound data from the WAD, allocate lump    //  in zone memory.    sprintf(name, "ds%s", sfxname);    // Now, there is a severe problem with the    //  sound handling, in it is not (yet/anymore)    //  gamemode aware. That means, sounds from    //  DOOM II will be requested even with DOOM    //  shareware.    // The sound list is wired into sounds.c,    //  which sets the external variable.    // I do not do runtime patches to that    //  variable. Instead, we will use a    //  default sound for replacement.    if ( W_CheckNumForName(name) == -1 )      sfxlump = W_GetNumForName("dspistol");    else      sfxlump = W_GetNumForName(name);        size = W_LumpLength( sfxlump );    // Debug.    // fprintf( stderr, "." );    //fprintf( stderr, " -loading  %s (lump %d, %d bytes)\n",    //	     sfxname, sfxlump, size );    //fflush( stderr );        sfx = (unsigned char*)W_CacheLumpNum( sfxlump, PU_STATIC );    // Pads the sound effect out to the mixing buffer size.    // The original realloc would interfere with zone memory.    paddedsize = ((size-8 + (SAMPLECOUNT-1)) / SAMPLECOUNT) * SAMPLECOUNT;    // Allocate from zone memory.    paddedsfx = (unsigned char*)Z_Malloc( paddedsize+8, PU_STATIC, 0 );    // ddt: (unsigned char *) realloc(sfx, paddedsize+8);    // This should interfere with zone memory handling,    //  which does not kick in in the soundserver.    // Now copy and pad.    memcpy(  paddedsfx, sfx, size );    for (i=size ; i<paddedsize+8 ; i++)        paddedsfx[i] = 128;    // Remove the cached lump.    Z_Free( sfx );        // Preserve padded length.    *len = paddedsize;    // Return allocated padded data.    return (void *) (paddedsfx + 8);}//// This function adds a sound to the//  list of currently active sounds,//  which is maintained as a given number//  (eight, usually) of internal channels.// Returns a handle.//intaddsfx( int		sfxid,  int		volume,  int		step,  int		seperation ){    static unsigned short	handlenums = 0;     int		i;    int		rc = -1;        int		oldest = gametic;    int		oldestnum = 0;    int		slot;    int		rightvol;    int		leftvol;    // Chainsaw troubles.    // Play these sound effects only one at a time.    if ( sfxid == sfx_sawup	 || sfxid == sfx_sawidl	 || sfxid == sfx_sawful	 || sfxid == sfx_sawhit	 || sfxid == sfx_stnmov	 || sfxid == sfx_pistol	 )    {	// Loop all channels, check.	for (i=0 ; i<NUM_CHANNELS ; i++)	{	    // Active, and using the same SFX?	    if ( (channels[i])		 && (channelids[i] == sfxid) )	    {		// Reset.		channels[i] = 0;		// We are sure that iff,		//  there will only be one.		break;	    }	}    }    // Loop all channels to find oldest SFX.    for (i=0; (i<NUM_CHANNELS) && (channels[i]); i++)    {	if (channelstart[i] < oldest)	{	    oldestnum = i;	    oldest = channelstart[i];	}    }    // Tales from the cryptic.    // If we found a channel, fine.    // If not, we simply overwrite the first one, 0.    // Probably only happens at startup.    if (i == NUM_CHANNELS)	slot = oldestnum;    else	slot = i;    // Okay, in the less recent channel,    //  we will handle the new SFX.    // Set pointer to raw data.    channels[slot] = (unsigned char *) S_sfx[sfxid].data;    // Set pointer to end of raw data.    channelsend[slot] = channels[slot] + lengths[sfxid];    // Reset current handle number, limited to 0..100.    if (!handlenums)	handlenums = 100;    // Assign current handle number.    // Preserved so sounds could be stopped (unused).    channelhandles[slot] = rc = handlenums++;    // Set stepping???    // Kinda getting the impression this is never used.    channelstep[slot] = step;    // ???    channelstepremainder[slot] = 0;    // Should be gametic, I presume.    channelstart[slot] = gametic;    // Separation, that is, orientation/stereo.    //  range is: 1 - 256    seperation += 1;    // Per left/right channel.    //  x^2 seperation,    //  adjust volume properly.    volume *= 8;    leftvol =	volume - ((volume*seperation*seperation) >> 16); ///(256*256);    seperation = seperation - 257;    rightvol =	volume - ((volume*seperation*seperation) >> 16);	    // Sanity check, clamp volume.    if (rightvol < 0 || rightvol > 127)	I_Error("rightvol out of bounds");        if (leftvol < 0 || leftvol > 127)	I_Error("leftvol out of bounds");        // Get the proper lookup table piece    //  for this volume level???    channelleftvol_lookup[slot] = &vol_lookup[leftvol*256];    channelrightvol_lookup[slot] = &vol_lookup[rightvol*256];    // Preserve sound SFX id,    //  e.g. for avoiding duplicates of chainsaw.    channelids[slot] = sfxid;    // You tell me.    return rc;}//// SFX API// Note: this was called by S_Init.// However, whatever they did in the// old DPMS based DOS version, this// were simply dummies in the Linux// version.// See soundserver initdata().//void I_SetChannels(){  // Init internal lookups (raw data, mixing buffer, channels).  // This function sets up internal lookups used during  //  the mixing process.   int		i;  int		j;      int*	steptablemid = steptable + 128;    // Okay, reset internal mixing channels to zero.  /*for (i=0; i<NUM_CHANNELS; i++)  {    channels[i] = 0;  }*/  // This table provides step widths for pitch parameters.  // I fail to see that this is currently used.  for (i=-128 ; i<128 ; i++)    steptablemid[i] = (int)(pow(2.0, (i/64.0))*65536.0);  

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -