00001 #include "sound.h"
00002 #include "tll.h"
00003 #include "camera.h"
00004 #include "resource.rh"
00005 #include "mmgr.h"
00006
00007 extern int device;
00008 extern BOOL lowqual;
00009 extern int SphereSector;
00010 extern VECTOR SpherePosition;
00011 extern int numSamples;
00012 extern int numChannels;
00013 extern LinkedList<SOUND_SAMPLE> SampleList;
00014 extern LinkedList<SOUND_CHANNEL> ChannelList;
00015 extern HWND hWnd;
00016 extern CAMERA* camera;
00017 extern CAMERA LastCam;
00018 extern int currentCamera;
00019
00020 int SOUND_SAMPLE::Compare(const SOUND_SAMPLE& Sample)
00021 {
00022 if (linkPosition < Sample.linkPosition)
00023 return smaller;
00024 if (linkPosition > Sample.linkPosition)
00025 return bigger;
00026 else
00027 return same;
00028 }
00029
00030 int SOUND_CHANNEL::Compare(const SOUND_CHANNEL& Channel)
00031 {
00032 if (linkPosition < Channel.linkPosition)
00033 return smaller;
00034 if (linkPosition > Channel.linkPosition)
00035 return bigger;
00036 else
00037 return same;
00038 }
00039
00040 void InitializeBASS()
00041 {
00042
00043 if (BASS_GetVersion() != MAKELONG(1, 4))
00044 MessageBox(0, "BASS version 1.4 was not loaded", "Incorrect BASS.DLL", 0);
00045
00046
00047 if (!BASS_Init(device, lowqual?22050:44100, BASS_DEVICE_3D, hWnd))
00048 MessageBox(0, "Could not initialize output device", "Error", 0);
00049
00050
00051 BASS_Set3DFactors(1.0, 1.0, 1.0);
00052
00053
00054 BASS_SetEAXParameters(-1, 0.0, -1.0, -1.0);
00055
00056 BASS_Start();
00057 }
00058
00059
00060 void LoadSample(SOUND_SAMPLE* Sample)
00061 {
00062
00063 Sample->hSample = BASS_SampleLoad(FALSE, Sample->name, 0, 0, Sample->max, Sample->flags);
00064 if (Sample->hSample)
00065 {
00066 BASS_SAMPLE sampleInfo;
00067 BASS_SampleGetInfo(Sample->hSample, &sampleInfo);
00068
00069 sampleInfo.volume = Sample->volume;
00070 sampleInfo.mindist = Sample->mindist;
00071 sampleInfo.maxdist = Sample->maxdist;
00072 BASS_SampleSetInfo(Sample->hSample, &sampleInfo);
00073
00074 Sample->linkPosition = ++numSamples;
00075 SampleList.Insert(Sample);
00076 }
00077 else
00078 MessageBox(NULL,"Could not load sound sample","Error",MB_OK|MB_ICONERROR);
00079 }
00080
00081 void CreateChannel(int SampleNumber)
00082 {
00083 SOUND_SAMPLE* Sample = SampleList.Get(SampleNumber);
00084 SOUND_CHANNEL* Channel = new SOUND_CHANNEL;
00085 Channel->hSample = Sample->hSample;
00086 Channel->linkPosition = ++numChannels;
00087 ChannelList.Insert(Channel);
00088 }
00089
00090 void UpdateListener()
00091 {
00092 BASS_3DVECTOR Player;
00093 BASS_3DVECTOR Bass_Front;
00094 BASS_3DVECTOR Bass_Top;
00095 BASS_3DVECTOR Bass_Velocity;
00096
00097 Player.x = camera[currentCamera].Position.x;
00098 Player.y = camera[currentCamera].Position.y;
00099 Player.z = camera[currentCamera].Position.z;
00100 VECTOR Front = camera[currentCamera].GetZUnit();
00101 VECTOR Top = camera[currentCamera].GetYUnit();
00102 Bass_Front.x = -Front.x;
00103 Bass_Front.y = -Front.y;
00104 Bass_Front.z = -Front.z;
00105 Bass_Top.x = Top.x;
00106 Bass_Top.y = Top.y;
00107 Bass_Top.z = Top.z;
00108 Bass_Velocity.x = camera[currentCamera].Position.x - LastCam.Position.x;
00109 Bass_Velocity.y = camera[currentCamera].Position.y - LastCam.Position.y;
00110 Bass_Velocity.z = camera[currentCamera].Position.z - LastCam.Position.z;
00111
00112 BASS_Set3DPosition(&Player, &Bass_Velocity, &Bass_Front, &Bass_Top);
00113
00114
00115 BASS_Apply3D();
00116 }
00117
00118 void UpdateChannel(int ChannelNumber, VECTOR* Position, VECTOR* Orientation, VECTOR* Velocity)
00119 {
00120 SOUND_CHANNEL* Channel = ChannelList.Get(ChannelNumber);
00121
00122 if (Position)
00123 {
00124 Channel->position.x = Position->x;
00125 Channel->position.y = Position->y;
00126 Channel->position.z = Position->z;
00127 }
00128 if (Orientation)
00129 {
00130 Channel->orientation.x = Orientation->x;
00131 Channel->orientation.y = Orientation->y;
00132 Channel->orientation.z = Orientation->z;
00133 }
00134 if (Velocity)
00135 {
00136 Channel->velocity.x = Velocity->x;
00137 Channel->velocity.y = Velocity->y;
00138 Channel->velocity.z = Velocity->z;
00139 }
00140
00141
00142 if (BASS_ChannelIsActive(Channel->hChannel))
00143 BASS_ChannelSet3DPosition(Channel->hChannel, &Channel->position, NULL, &Channel->velocity);
00144
00145
00146 BASS_Apply3D();
00147 }
00148
00149 void PlayChannel(int ChannelNumber)
00150 {
00151 SOUND_CHANNEL* Channel = ChannelList.Get(ChannelNumber);
00152 Channel->hChannel = BASS_SamplePlay3D(Channel->hSample, &Channel->position, NULL, &Channel->velocity);
00153
00154 char temp[256];
00155 int result = BASS_ErrorGetCode();
00156 if (result)
00157 {
00158 sprintf(temp, "BASS error code No. %d", result);
00159 MessageBox(NULL, temp, "Error", MB_OK|MB_ICONERROR);
00160 }
00161 }
00162
00163 VOID CALLBACK SoundTimerProc(HWND hWnd, UINT uMsg, UINT idEvent, DWORD dwTime)
00164 {
00165 SOUND_CHANNEL* Channel = ChannelList.Get((int)idEvent);
00166 PlayChannel((int)idEvent);
00167 if ((Channel->looped && !Channel->intermittent) || !Channel->looped)
00168 KillTimer(hWnd, idEvent);
00169 if (Channel->looped && Channel->intermittent && Channel->random)
00170 {
00171 int randomtime = (rand()%(Channel->upperrand - Channel->lowerrand)) + Channel->lowerrand;
00172 SetTimer(hWnd, idEvent, randomtime, (TIMERPROC)SoundTimerProc);
00173 }
00174 }
00175
00176 void CreateSounds()
00177 {
00178 SOUND_SAMPLE* Sample;
00179 VECTOR Position;
00180
00181
00182 Sample = new SOUND_SAMPLE;
00183 sprintf(Sample->name, "%s", "gunshot.wav");
00184 Sample->max = 10;
00185 Sample->volume = 100;
00186 Sample->mindist = 10.0;
00187 Sample->maxdist = 1000.0;
00188 Sample->flags = BASS_SAMPLE_OVER_DIST | BASS_SAMPLE_3D | BASS_SAMPLE_VAM;
00189 LoadSample(Sample);
00190
00191 CreateChannel(sample_gunshot);
00192 }
00193
00194
00195
00196 BOOL CALLBACK devicedialogproc(HWND h,UINT m,WPARAM w,LPARAM l)
00197 {
00198 switch (m) {
00199 case WM_COMMAND:
00200 switch (LOWORD(w)) {
00201 case ID_DEVLIST:
00202 if (HIWORD(w)==LBN_SELCHANGE)
00203 device=SendMessage((HWND)l,LB_GETCURSEL,0,0);
00204 else if (HIWORD(w)==LBN_DBLCLK)
00205 EndDialog(h,0);
00206 break;
00207 case ID_LOWQUAL:
00208 lowqual=SendDlgItemMessage(h,ID_LOWQUAL,BM_GETCHECK,0,0);
00209 break;
00210 case IDOK:
00211 EndDialog(h,0);
00212 return 1;
00213 }
00214 break;
00215
00216 case WM_INITDIALOG:
00217 {
00218 char text[100],*d;
00219 int c;
00220 for (c=0;BASS_GetDeviceDescription(c,&d);c++) {
00221 strcpy(text,d);
00222
00223 if (!BASS_Init(c,44100,BASS_DEVICE_3D|BASS_DEVICE_NOSYNC|BASS_DEVICE_NOTHREAD,h))
00224 continue;
00225 if (BASS_GetEAXParameters(NULL,NULL,NULL,NULL))
00226 strcat(text," [EAX]");
00227 BASS_Free();
00228 SendDlgItemMessage(h,ID_DEVLIST,LB_ADDSTRING,0,(LONG)text);
00229 }
00230 SendDlgItemMessage(h,ID_DEVLIST,LB_SETCURSEL,0,0);
00231 }
00232 device=lowqual=0;
00233 return 1;
00234 }
00235 return 0;
00236 }
00237