TORCS  1.3.9
The Open Racing Car Simulator
PlibSoundInterface.cpp
Go to the documentation of this file.
1 /***************************************************************************
2 
3  file : PlibSoundInterface.cpp
4  created : Thu Apr 7 04:21 CEST 2005
5  copyright : (C) 2005 Christos Dimitrakakis
6  email : dimitrak@idiap.ch
7  version : $Id$
8 
9 ***************************************************************************/
10 
11 /***************************************************************************
12  * *
13  * This program is free software; you can redistribute it and/or modify *
14  * it under the terms of the GNU General Public License as published by *
15  * the Free Software Foundation; either version 2 of the License, or *
16  * (at your option) any later version. *
17  * *
18  ***************************************************************************/
19 
20 #include "SoundInterface.h"
21 #include "TorcsSound.h"
22 #include "CarSoundData.h"
23 
24 
25 
26 PlibSoundInterface::PlibSoundInterface(float sampling_rate, int n_channels) : SoundInterface (sampling_rate, n_channels)
27 {
28  sched = new slScheduler ((int) sampling_rate);
29  sched->setSafetyMargin (0.128f);
30  sched->setMaxConcurrent (n_channels);
31  engpri = NULL;
32  car_src = NULL;
33  global_gain = 1.0f;
34 
35  // initialise mappings
43 
44 }
45 
47 {
48  for (unsigned int i=0; i<sound_list.size(); i++) {
49  delete sound_list[i];
50  }
51  delete [] engpri;
52  delete sched;
53 
54  if (car_src) {
55  delete [] car_src;
56  }
57 
58 }
59 
61 {
62  engpri = new SoundPri[n_cars];
63  car_src = new SoundSource[n_cars];
64 }
65 
67 {
68  return sched;
69 }
70 
71 TorcsSound* PlibSoundInterface::addSample (const char* filename, int flags, bool loop, bool static_pool)
72 {
73  PlibTorcsSound* sound = new PlibTorcsSound (sched, filename, flags, loop);
74  sound->setVolume (2.0*global_gain);
75  sound_list.push_back ((TorcsSound*) sound);
76  return sound;
77 }
78 
79 void PlibSoundInterface::update(CarSoundData** car_sound_data, int n_cars, sgVec3 p_obs, sgVec3 u_obs, sgVec3 c_obs, sgVec3 a_obs)
80 {
81  // Copy car ID basically.
82  int i;
83  for (i = 0; i<n_cars; i++) {
85  }
86 
87  for (i = 0; i<n_cars; i++) {
88  int id = engpri[i].id;
89  sgVec3 p;
90  sgVec3 u;
93  car_src[id].setSource (p, u);
94  car_src[id].setListener (p_obs, u_obs);
95  car_src[id].update();
96  engpri[id].a = car_src[id].a;
97  }
98 
99  qsort ((void*) engpri, n_cars, sizeof(SoundPri), &sortSndPriority);
100 
101  for (i = 0; i<n_cars; i++) {
102  int id = engpri[i].id;
103  TorcsSound* engine = car_sound_data[id]->getEngineSound();
104  if (i>=NB_ENGINE_SOUND) {
105  engine->setVolume (0.0f);
106  engine->pause();
107  //printf ("Pausing %d (%d)\n", id, i);
108  } else {
109  engine->resume();
110  engine->setLPFilter(car_src[id].lp*car_sound_data[id]->engine.lp);
111  engine->setPitch(car_src[id].f*car_sound_data[id]->engine.f);
112  engine->setVolume(global_gain*car_src[id].a*car_sound_data[id]->engine.a);
113  engine->update();
114  }
115  }
116 
117  float max_skid_vol[4] = {0.0f, 0.0f, 0.0f, 0.0f};
118  int max_skid_id[4] = {0,0,0,0};
119  int id;
120  for (id = 0; id<n_cars; id++) {
121  CarSoundData* sound_data = car_sound_data[id];
122  for (int j=0; j<4; j++) {
123  float skvol=sound_data->attenuation*sound_data->wheel[j].skid.a;
124  if (skvol > max_skid_vol[j]) {
125  max_skid_vol[j] = skvol;
126  max_skid_id[j] = id;
127  }
128  }
129  }
130 
131  for (i = 0; i<4; i++) {
132  int id = max_skid_id[i];
133  WheelSoundData* sound_data = car_sound_data[id]->wheel;
134  float mod_a = car_src[id].a;
135  float mod_f = car_src[id].f;
136  skid_sound[i]->setVolume (global_gain*sound_data[i].skid.a * mod_a);
137  skid_sound[i]->setPitch (sound_data[i].skid.f * mod_f);
138  skid_sound[i]->update();
139 #if 0
140  if (sound_data[i].skid.a > VOLUME_CUTOFF) {
141  skid_sound[i]->start();
142  } else {
143  skid_sound[i]->stop();
144  }
145 #endif
146  }
147 
148 
149  // other looping sounds
151  SortSingleQueue (car_sound_data, &road, n_cars);
153 
157 
161 
165 
169 
173 
174  axle.snd = axle_sound;
175  SortSingleQueue (car_sound_data, &axle, n_cars);
177 
178 
179  // One-off sounds
180  for (id = 0; id<n_cars; id++) {
181  float crash_threshold = 0.5f;
182  float gear_threshold = 0.75;
183 
184  CarSoundData* sound_data = car_sound_data[id];
185 
186  if (sound_data->crash) {
187  if (++curCrashSnd>=NB_CRASH_SOUND) {
188 
189  curCrashSnd = 0;
190  }
191  if (car_src[id].a > crash_threshold) {
193  }
194  }
195 
196  if (sound_data->bang) {
197  if (car_src[id].a > crash_threshold) {
198  bang_sound->start();
199  }
200  }
201 
202  if (sound_data->bottom_crash) {
203  if (car_src[id].a > crash_threshold) {
205  }
206  }
207 
208  if (sound_data->gear_changing) {
209  if (car_src[id].a > gear_threshold) {
211  }
212  }
213  }
214 
215 
216  sched->update();
217 }
218 
219 
220 
221 
222 
223 int sortSndPriority(const void* a, const void* b)
224 {
225  SoundPri* A = (SoundPri*) a;
226  SoundPri* B = (SoundPri*) b;
227  if (A->a > B->a) {
228  return -1;
229  } else {
230  return 1;
231  }
232 }
233 
234 
236 {
237  int id = smap->id;
238  //float max_vol = smap->max_vol;
239  QSoundChar CarSoundData::*p2schar = smap->schar;
240  QSoundChar* schar = &(car_sound_data[id]->*p2schar);
241  TorcsSound* snd = smap->snd;
242 
243  snd->setVolume (global_gain * schar->a * car_src[id].a);
244  snd->setPitch (schar->f * car_src[id].f);
245  snd->update();
246 #if 0
247  f (max_vol > VOLUME_CUTOFF) {
248  snd->start();
249  } else {
250  snd->stop();
251  }
252 #endif
253 }
virtual void setVolume(float vol)
Set the volume.
Definition: TorcsSound.cpp:117
QSoundChar road
Definition: CarSoundData.h:100
Sound source management.
Definition: TorcsSound.h:141
float a
amplitude
int id
car ID.
virtual void setLPFilter(float lp)
Set the filter.
Definition: TorcsSound.cpp:35
void update()
Calculate environmental parameters for current situation.
Definition: TorcsSound.cpp:201
QSoundChar engine_backfire
Definition: CarSoundData.h:96
QSoundChar axle
Definition: CarSoundData.h:95
static CarSoundData ** car_sound_data
Definition: grsound.cpp:38
TorcsSound * bang_sound
sounds when suspension fully compressed
QueueSoundMap axle
QueueSoundMap turbo
int curCrashSnd
holds current crash sound used - the sound cycles
TorcsSound * getEngineSound()
Definition: CarSoundData.h:107
QSoundChar turbo
Definition: CarSoundData.h:94
virtual void setPitch(float pitch)
Set the pitch.
Definition: TorcsSound.cpp:30
A queue containing mappings between sounds and sound sources.
virtual void stop()=0
TorcsSound * bottom_crash_sound
bang when crashing from a great height
float f
Definition: QSoundChar.h:7
QSoundChar CarSoundData::* schar
The calculated sound characteristic.
void setSource(sgVec3 p, sgVec3 u)
Set source position and velocity.
Definition: TorcsSound.cpp:262
virtual void resume()=0
Manages the source sound of each individual car.
Definition: CarSoundData.h:25
QSoundChar skid
Definition: CarSoundData.h:21
TorcsSound * backfire_loop_sound
exhaust backfire sound
virtual TorcsSound * addSample(const char *filename, int flags=(ACTIVE_VOLUME|ACTIVE_PITCH), bool loop=false, bool static_pool=true)
WheelSoundData wheel[4]
Definition: CarSoundData.h:84
QSoundChar grass
Definition: CarSoundData.h:99
QueueSoundMap grass_skid
SoundSource * car_src
TorcsSound * grass_skid_sound
skidding on dirt/grass
TorcsSound * turbo_sound
turbo spinning sound
QueueSoundMap grass
TorcsSound * road_ride_sound
rolling on normal road
float a
Definition: QSoundChar.h:6
void setListener(sgVec3 p, sgVec3 u)
Set listener position and velocity.
Definition: TorcsSound.cpp:272
virtual slScheduler * getScheduler()
#define NB_ENGINE_SOUND
Definition: sound_defines.h:12
PLIB-specific torcs sound.
Definition: TorcsSound.h:94
virtual void update(CarSoundData **car_sound_data, int n_cars, sgVec3 p_obs, sgVec3 u_obs, sgVec3 c_obs=NULL, sgVec3 a_obs=NULL)
QueueSoundMap backfire_loop
float f
Environmental frequency shift.
Definition: TorcsSound.h:148
float attenuation
global distance attenuation
Definition: CarSoundData.h:85
int n_channels
number of channels
bool gear_changing
Definition: CarSoundData.h:140
TorcsSound * snd
The raw sound.
float a
Environmental attenuation.
Definition: TorcsSound.h:147
virtual void setVolume(float vol)
Set the volume.
Definition: TorcsSound.cpp:25
slScheduler * sched
virtual void update()=0
static Point p[4]
Definition: Convex.cpp:54
QSoundChar drag_collision
Definition: CarSoundData.h:93
void SortSingleQueue(CarSoundData **car_sound_data, QueueSoundMap *smap, int n_cars)
Find the max amplitude sound in car_sound_data and put it in smap.
void getCarPosition(sgVec3 p)
Definition: CarSoundData.h:121
QueueSoundMap road
The following are mappings for sound prioritisation.
float sampling_rate
sampling rate
virtual void setNCars(int n_cars)
TorcsSound * gear_change_sound
sound when changing gears
#define NB_CRASH_SOUND
Definition: sound_defines.h:11
virtual void start()=0
Sound interface.
void getCarSpeed(sgVec3 u)
Definition: CarSoundData.h:127
void copyEngPri(SoundPri &epri)
Definition: CarSoundData.h:108
virtual void pause()=0
std::vector< TorcsSound * > sound_list
TorcsSound * crash_sound[NB_CRASH_SOUND]
list of crash sounds
TorcsSound * metal_skid_sound
metal skidding on metal
TorcsSound * grass_ride_sound
rolling on dirt/grass
QSoundChar grass_skid
Definition: CarSoundData.h:97
PlibSoundInterface(float sampling_rate, int n_channels)
void SetMaxSoundCar(CarSoundData **car_sound_data, QueueSoundMap *smap)
int sortSndPriority(const void *a, const void *b)
#define VOLUME_CUTOFF
QueueSoundMap metal_skid
TorcsSound * axle_sound
axle/gear spinning sound
TorcsSound * skid_sound[4]
set of skid sounds, one per tyre
A generic TORCS sound.
Definition: TorcsSound.h:53
int id
The id of the car producing the sound, used for retrieving doppler effects etc.
Sound priority, used to sort cars according to amplitude attenuation.