527 lines
16 KiB
Plaintext
527 lines
16 KiB
Plaintext
/*======================================================================
|
|
SOUND functions
|
|
======================================================================*/
|
|
float SOUND_PLAYONCE = 2; // When triggered plays once
|
|
|
|
//----------------------------------------------------------------------
|
|
void() ambient_sound_setup =
|
|
{
|
|
if (self.volume > 1) self.volume = 1;
|
|
ambientsound (self.origin, self.noise, self.volume, ATTN_STATIC);
|
|
};
|
|
|
|
/*============================================================================
|
|
/*QUAKED ambient_custom_loop (0.3 0.1 0.6) (-16 -16 -8) (16 16 8) x
|
|
Custom ambient (must be looped) sound, CANNOT toggle/switch state
|
|
-------- KEYS --------
|
|
volume : volume of sound (default 1, capped at 1)
|
|
noise : custom sound to play (looped)
|
|
-------- SPAWNFLAGS --------
|
|
STARTOFF : Wait for trigger, will become static
|
|
-------- NOTES --------
|
|
Custom ambient (must be looped) sound, CANNOT toggle/switch state
|
|
============================================================================*/
|
|
void() ambient_custom_loop =
|
|
{
|
|
// Check for sound file
|
|
if (self.noise == "") {
|
|
dprint("\b[AMB_CUSTOM_LOOP]\b Missing sound file\n");
|
|
spawn_marker(self.origin, SPNMARK_YELLOW);
|
|
remove(self);
|
|
return;
|
|
}
|
|
|
|
precache_sound (self.noise);
|
|
if (self.volume <= 0) self.volume = 1;
|
|
if (self.volume > 1) self.volume = 1;
|
|
|
|
// Ambient sounds can ONLY be setup on frame 1
|
|
// The command (ambientsound) does not work delayed
|
|
ambient_sound_setup();
|
|
};
|
|
//----------------------------------------------------------------------
|
|
void() ambient_comp_hum =
|
|
{
|
|
self.noise = "ambience/comp1.wav";
|
|
precache_sound (self.noise);
|
|
self.volume = 1;
|
|
ambient_sound_setup();
|
|
};
|
|
//----------------------------------------------------------------------
|
|
void() ambient_drip =
|
|
{
|
|
self.noise = "ambience/drip1.wav";
|
|
precache_sound (self.noise);
|
|
self.volume = 0.5;
|
|
ambient_sound_setup();
|
|
};
|
|
//----------------------------------------------------------------------
|
|
void() ambient_drone =
|
|
{
|
|
self.noise = "ambience/drone6.wav";
|
|
precache_sound (self.noise);
|
|
self.volume = 0.5;
|
|
ambient_sound_setup();
|
|
};
|
|
//----------------------------------------------------------------------
|
|
void() ambient_flouro_buzz =
|
|
{
|
|
self.noise = "ambience/buzz1.wav";
|
|
precache_sound (self.noise);
|
|
self.volume = 1;
|
|
ambient_sound_setup();
|
|
};
|
|
//----------------------------------------------------------------------
|
|
void() ambient_light_buzz =
|
|
{
|
|
self.noise = "ambience/fl_hum1.wav";
|
|
precache_sound (self.noise);
|
|
self.volume = 0.5;
|
|
ambient_sound_setup();
|
|
};
|
|
//----------------------------------------------------------------------
|
|
void() ambient_suck_wind =
|
|
{
|
|
self.noise = "ambience/suck1.wav";
|
|
precache_sound (self.noise);
|
|
self.volume = 1;
|
|
ambient_sound_setup();
|
|
};
|
|
//----------------------------------------------------------------------
|
|
void() ambient_swamp1 =
|
|
{
|
|
self.noise = "ambience/swamp1.wav";
|
|
precache_sound (self.noise);
|
|
self.volume = 0.5;
|
|
ambient_sound_setup();
|
|
};
|
|
//----------------------------------------------------------------------
|
|
void() ambient_swamp2 =
|
|
{
|
|
self.noise = "ambience/swamp2.wav";
|
|
precache_sound (self.noise);
|
|
self.volume = 0.5;
|
|
ambient_sound_setup();
|
|
};
|
|
//----------------------------------------------------------------------
|
|
void() ambient_thunder =
|
|
{
|
|
self.noise = "ambience/thunder1.wav";
|
|
precache_sound (self.noise);
|
|
self.volume = 0.5;
|
|
ambient_sound_setup();
|
|
};
|
|
|
|
//======================================================================
|
|
/*QUAKED ambient_custom_sound (0.5 0.1 0.8) (-16 -16 -8) (16 16 8) x PLAYONCE x x x x STARTOFF x
|
|
Play a sound on a periodic basis
|
|
-------- KEYS --------
|
|
targetname : trigger entity (works with entity state system)
|
|
target : targets to trigger each time sound is played
|
|
volume : volume of sound (default 1, capped at 1)
|
|
noise : primary sound (ambience/windgust1a.wav)
|
|
noise1 : stop sound (anbience/switch_6off.wav)
|
|
noise2 : random sound (ambience/windgust1b.wav)
|
|
wait : random time between sounds (default 20, =-1 no random element)
|
|
delay : minimum time between sounds (default 2)
|
|
waitmin : Starting time (waitmin + random() x waitmin, =-1 no delay)
|
|
waitmin2: 1 = Will not silence any playing sound if switching off
|
|
impulse : channel on which to play sound (0-7) (0 automatic is default)
|
|
speed : attenuation -1=no attenuation, 1=normal (default), 2=idle, 3=static, 4=quiet
|
|
-------- SPAWNFLAGS --------
|
|
PLAYONCE : When triggered plays once
|
|
STARTOFF : Starts off and waits for trigger
|
|
-------- NOTES --------
|
|
Play a sound on a periodic basis
|
|
*/
|
|
//======================================================================
|
|
void() ambient_custom_stop =
|
|
{
|
|
// Cannot block via entity state because there is an 'off sound'
|
|
// Need to check against entity internal state for off state
|
|
if (self.state == STATE_OFF) return;
|
|
|
|
// Switch off sound emitter, clear next think
|
|
self.state = STATE_OFF;
|
|
self.think = SUB_Null;
|
|
self.nextthink = time + 0.1;
|
|
|
|
// Catch play once/disable setting separate
|
|
if (self.estate & ESTATE_DISABLE) return;
|
|
|
|
// Check for OFF sound, else play silence to clear sound
|
|
if (self.noise1 != "")
|
|
sound (self, self.impulse, self.noise1, self.volume, self.speed);
|
|
else {
|
|
// If aflag is defined, do not cut off sound
|
|
if (!self.waitmin2) sound (self, self.impulse, SOUND_EMPTY, self.volume, self.speed);
|
|
}
|
|
};
|
|
|
|
//----------------------------------------------------------------------
|
|
void() ambient_custom_play =
|
|
{
|
|
// Block everything except ON entity state
|
|
if (self.estate & ESTATE_BLOCK) return;
|
|
|
|
// Internal state used for switch off sound
|
|
self.state = STATE_ON;
|
|
|
|
// Check for random volume changes
|
|
if (self.t_width > 0) {
|
|
self.volume = self.t_width + (random() * self.t_length);
|
|
if (self.volume > 1) self.volume = 1;
|
|
}
|
|
|
|
// Check for weather system?
|
|
if (self.check_weather == TRUE) {
|
|
// Check if weather system still active?
|
|
if (!query_configflag(SVR_WEATHER)) {
|
|
// never has multiple sounds
|
|
sound (self, self.impulse, self.noise, self.volume, self.speed);
|
|
}
|
|
}
|
|
else {
|
|
// Check for multiple random sounds
|
|
if (self.noise2 != "" && random() < 0.5)
|
|
sound (self, self.impulse, self.noise2, self.volume, self.speed);
|
|
else sound (self, self.impulse, self.noise, self.volume, self.speed);
|
|
|
|
// If any targets defined, trigger them
|
|
if (self.target != "") trigger_strs(self.target, self);
|
|
}
|
|
|
|
// Keep playing sound?
|
|
// If sound is setup to play once, don't turn off sound before finished
|
|
// Let the sound play out and switch off ambient sound entity
|
|
if (self.spawnflags & SOUND_PLAYONCE) self.estate = ESTATE_DISABLE;
|
|
else {
|
|
// Check for any random time element
|
|
if (self.wait == 0) self.nextthink = time + self.delay;
|
|
else self.nextthink = time + self.delay + random()*self.wait;
|
|
self.think = ambient_custom_play;
|
|
}
|
|
};
|
|
|
|
//----------------------------------------------------------------------
|
|
void() ambient_custom_use =
|
|
{
|
|
// Deal with STARTOFF functionality first
|
|
if (self.spawnflags & ENT_STARTOFF) {
|
|
// Remove spawnflag and switch ON entity
|
|
self.spawnflags = self.spawnflags - ENT_STARTOFF;
|
|
self.estate_on();
|
|
}
|
|
else {
|
|
// Block USE functionality if state wrong
|
|
if (self.estate & ESTATE_BLOCK) return;
|
|
|
|
// Toggle state of ambient sound to start/stop
|
|
if (self.state == STATE_OFF) self.estate_on();
|
|
else self.estate_off();
|
|
}
|
|
};
|
|
|
|
//----------------------------------------------------------------------
|
|
void() ambient_custom_on =
|
|
{
|
|
self.estate = ESTATE_ON;
|
|
ambient_custom_play();
|
|
};
|
|
|
|
//----------------------------------------------------------------------
|
|
void() ambient_custom_off =
|
|
{
|
|
self.estate = ESTATE_OFF;
|
|
ambient_custom_stop();
|
|
};
|
|
|
|
//----------------------------------------------------------------------
|
|
void() ambient_custom_disable =
|
|
{
|
|
self.state = STATE_OFF;
|
|
sound (self, self.impulse, SOUND_EMPTY, self.volume, self.speed);
|
|
};
|
|
|
|
//----------------------------------------------------------------------
|
|
void() ambient_custom_sound =
|
|
{
|
|
// Check for sound file
|
|
if (self.noise == "") {
|
|
dprint("\b[AMBIENT_SOUND]\b Missing sound file at ");
|
|
dprint(vtos(self.origin)); dprint("\n");
|
|
spawn_marker(self.origin, SPNMARK_YELLOW);
|
|
remove(self);
|
|
return;
|
|
}
|
|
precache_sound (self.noise);
|
|
|
|
// Is there an OFF sound defined (used for toggle sounds)
|
|
if (self.noise1 != "") precache_sound (self.noise1);
|
|
|
|
// Is there any random alternative sounds
|
|
if (self.noise2 != "") precache_sound (self.noise2);
|
|
|
|
self.classtype = CT_SOUNDEMITTER;
|
|
if (self.volume <= 0 || self.volume > 1) self.volume = 1;
|
|
|
|
// Setup defaults for sound waits (-1=no random element)
|
|
if (self.wait == 0) self.wait = 20;
|
|
if (self.wait < 0) self.wait = 0;
|
|
|
|
if (self.delay <= 0) self.delay = 2;
|
|
if (self.waitmin == 0) self.waitmin = 4;
|
|
if (self.impulse <= 0) self.impulse = 1;
|
|
|
|
// attenuation -1=no attenuation, 1=normal (default), 2=idle, 3=static, 4=quiet
|
|
if (self.speed < 0) self.speed = ATTN_NONE;
|
|
else if (self.speed == 2) self.speed = ATTN_IDLE;
|
|
else if (self.speed == 3) self.speed = ATTN_STATIC;
|
|
else if (self.speed == 4) self.speed = ATTN_QUIET;
|
|
else self.speed = ATTN_NORM;
|
|
|
|
// Setup Entity State functionality
|
|
if (self.targetname != "") self.use = entity_state_use;
|
|
self.estate_on = ambient_custom_on;
|
|
self.estate_off = ambient_custom_off;
|
|
self.estate_use = ambient_custom_use;
|
|
self.estate_disable = ambient_custom_disable;
|
|
if (self.spawnflags & ENT_STARTOFF) self.estate_off();
|
|
else {
|
|
if (self.waitmin > 0) {
|
|
self.nextthink = time + self.waitmin + random()*self.waitmin;
|
|
self.think = self.estate_on;
|
|
}
|
|
else self.estate_on();
|
|
}
|
|
};
|
|
|
|
//----------------------------------------------------------------------
|
|
void() ambient_custom_water =
|
|
{
|
|
if (self.noise == "") self.noise = "ambience/water1.wav";
|
|
if (!self.volume) self.volume = 0.75;
|
|
ambient_custom_loop();
|
|
};
|
|
|
|
//----------------------------------------------------------------------
|
|
void() ambient_custom_rain =
|
|
{
|
|
if (self.count == 1) {
|
|
// Long dripping water sound
|
|
self.noise = "ambience/rain1_nl.wav";
|
|
if (!self.speed) self.speed = 2;
|
|
if (!self.volume) self.volume = 0.4;
|
|
// Sound is 7s long, 0.1s for overlap
|
|
self.delay = 6.9;
|
|
}
|
|
else {
|
|
// Very short intense rain sound
|
|
self.noise = "ambience/rain2_nl.wav";
|
|
if (!self.speed) self.speed = 1;
|
|
if (!self.volume) self.volume = 0.5;
|
|
// Sound is 3s long, 0.1s for overlap
|
|
self.delay = 2.9;
|
|
}
|
|
|
|
self.wait = -1; // pretend loop, no pause
|
|
self.waitmin = -1; // No start delay
|
|
self.check_weather = TRUE; // Keep checking weather system
|
|
|
|
// Always start off, must be triggered
|
|
self.spawnflags = self.spawnflags | ENT_STARTOFF;
|
|
|
|
// Back into main function
|
|
ambient_custom_sound();
|
|
};
|
|
|
|
//----------------------------------------------------------------------
|
|
void() ambient_custom_rumble =
|
|
{
|
|
// Always precache all sounds and then randomly pick one
|
|
// load/save games will always generate new random selection
|
|
// and that will produce cache errors everytime
|
|
precache_sound ("ambience/rumble1.wav");
|
|
precache_sound ("ambience/rumble2.wav");
|
|
precache_sound ("ambience/rumble3.wav");
|
|
|
|
// Pick a random sound to start with
|
|
if (self.count < 0) self.count = random()*3;
|
|
|
|
// Setup sound wav names
|
|
if (self.count <= 1) {
|
|
self.noise = "ambience/rumble1.wav";
|
|
// Pick an alternative random sound
|
|
if (self.lefty) {
|
|
if (random() < 0.5) self.noise2 = "ambience/rumble2.wav";
|
|
else self.noise2 = "ambience/rumble3.wav";
|
|
}
|
|
}
|
|
else if (self.count <= 2) {
|
|
self.noise = "ambience/rumble2.wav";
|
|
if (self.lefty) {
|
|
if (random() < 0.5) self.noise2 = "ambience/rumble1.wav";
|
|
else self.noise2 = "ambience/rumble3.wav";
|
|
}
|
|
}
|
|
else {
|
|
self.noise = "ambience/rumble3.wav";
|
|
if (self.lefty) {
|
|
if (random() < 0.5) self.noise2 = "ambience/rumble1.wav";
|
|
else self.noise2 = "ambience/rumble2.wav";
|
|
}
|
|
}
|
|
|
|
// Default values for rumble
|
|
if (!self.volume) { self.t_width = 0.5; self.t_length = 0.5; }
|
|
if (!self.speed) self.speed = 1;
|
|
if (!self.delay) self.delay = 20;
|
|
if (!self.wait) self.wait = 20;
|
|
if (!self.waitmin) self.waitmin = 6 + random()*6;
|
|
|
|
// Back into main function
|
|
ambient_custom_sound();
|
|
};
|
|
|
|
//----------------------------------------------------------------------
|
|
void() ambient_custom_wind =
|
|
{
|
|
// Always precache all sounds and then randomly pick one
|
|
// load/save games will always generate new random selection
|
|
// and that will produce cache errors everytime
|
|
precache_sound ("ambience/windgust1.wav");
|
|
precache_sound ("ambience/windgust2.wav");
|
|
precache_sound ("ambience/windgust3.wav");
|
|
precache_sound ("ambience/windgust4.wav");
|
|
precache_sound ("ambience/windgust5.wav");
|
|
precache_sound ("ambience/windgust6.wav");
|
|
|
|
// Pick a random sound to start with
|
|
if (self.count < 0) self.count = random()*6;
|
|
|
|
// Setup sound wav names
|
|
if (self.count <= 1) {
|
|
self.noise = "ambience/windgust1.wav";
|
|
// Pick an alternative random sound
|
|
if (self.lefty) {
|
|
if (random() < 0.5) self.noise2 = "ambience/windgust2.wav";
|
|
else self.noise2 = "ambience/windgust3.wav";
|
|
}
|
|
}
|
|
else if (self.count <= 2) {
|
|
self.noise = "ambience/windgust2.wav";
|
|
if (self.lefty) {
|
|
if (random() < 0.5) self.noise2 = "ambience/windgust1.wav";
|
|
else self.noise2 = "ambience/windgust3.wav";
|
|
}
|
|
}
|
|
else if (self.count <= 3) {
|
|
self.noise = "ambience/windgust3.wav";
|
|
if (self.lefty) {
|
|
if (random() < 0.5) self.noise2 = "ambience/windgust1.wav";
|
|
else self.noise2 = "ambience/windgust2.wav";
|
|
}
|
|
}
|
|
else if (self.count <= 4) {
|
|
self.noise = "ambience/windgust4.wav";
|
|
if (self.lefty) {
|
|
if (random() < 0.5) self.noise2 = "ambience/windgust5.wav";
|
|
else self.noise2 = "ambience/windgust6.wav";
|
|
}
|
|
}
|
|
else if (self.count <= 5) {
|
|
self.noise = "ambience/windgust5.wav";
|
|
if (self.lefty) {
|
|
if (random() < 0.5) self.noise2 = "ambience/windgust4.wav";
|
|
else self.noise2 = "ambience/windgust6.wav";
|
|
}
|
|
}
|
|
else {
|
|
self.noise = "ambience/windgust6.wav";
|
|
if (self.lefty) {
|
|
if (random() < 0.5) self.noise2 = "ambience/windgust4.wav";
|
|
else self.noise2 = "ambience/windgust5.wav";
|
|
}
|
|
}
|
|
|
|
// Default values for wind
|
|
if (!self.volume) self.volume = 1;
|
|
if (!self.speed) self.speed = 1;
|
|
if (!self.delay) self.delay = 10;
|
|
if (!self.wait) self.wait = 10;
|
|
if (!self.waitmin) self.waitmin = 4 + random()*4;
|
|
|
|
// Back into main function
|
|
ambient_custom_sound();
|
|
};
|
|
|
|
//----------------------------------------------------------------------
|
|
void() ambient_custom_wood =
|
|
{
|
|
// Always precache all sounds and then randomly pick one
|
|
// load/save games will always generate new random selection
|
|
// and that will produce cache errors everytime
|
|
precache_sound ("ambience/woodcreak2a.wav");
|
|
precache_sound ("ambience/woodcreak2b.wav");
|
|
precache_sound ("ambience/woodcreak2c.wav");
|
|
precache_sound ("ambience/woodcreak2d.wav");
|
|
|
|
// Pick a random sound to start with
|
|
if (self.count < 0) self.count = random()*4;
|
|
|
|
if (self.count <= 1) {
|
|
self.noise = "ambience/woodcreak2a.wav";
|
|
// Pick an alternative random sound
|
|
if (self.lefty) {
|
|
if (random() < 0.5) self.noise2 = "ambience/woodcreak2b.wav";
|
|
else self.noise2 = "ambience/woodcreak2c.wav";
|
|
}
|
|
}
|
|
else if (self.count <= 2) {
|
|
self.noise = "ambience/woodcreak2b.wav";
|
|
if (self.lefty) {
|
|
if (random() < 0.5) self.noise2 = "ambience/woodcreak2c.wav";
|
|
else self.noise2 = "ambience/woodcreak2d.wav";
|
|
}
|
|
}
|
|
else if (self.count <= 3) {
|
|
self.noise = "ambience/woodcreak2c.wav";
|
|
if (self.lefty) {
|
|
if (random() < 0.5) self.noise2 = "ambience/woodcreak2a.wav";
|
|
else self.noise2 = "ambience/woodcreak2d.wav";
|
|
}
|
|
}
|
|
else {
|
|
self.noise = "ambience/woodcreak2d.wav";
|
|
if (self.lefty) {
|
|
if (random() < 0.5) self.noise2 = "ambience/woodcreak2a.wav";
|
|
else self.noise2 = "ambience/woodcreak2b.wav";
|
|
}
|
|
}
|
|
|
|
// Default values for wood
|
|
if (!self.volume) self.volume = 1;
|
|
if (!self.speed) self.speed = 2;
|
|
if (!self.delay) self.delay = 15;
|
|
if (!self.wait) self.wait = 30;
|
|
if (!self.waitmin) self.waitmin = 8 + random()*8;
|
|
|
|
// Back into main function
|
|
ambient_custom_sound();
|
|
};
|
|
|
|
//----------------------------------------------------------------------
|
|
void() ambient_custom_chime =
|
|
{
|
|
if (self.noise == "") self.noise = "ambience/chimes.wav";
|
|
if (!self.speed) self.speed = 2;
|
|
if (!self.volume) self.volume = 1;
|
|
if (!self.wait) self.wait = 10;
|
|
if (!self.delay) self.delay = 10;
|
|
if (!self.waitmin) self.waitmin = 10 + random()*10;
|
|
if (!self.waitmin2) self.waitmin2 = -1;
|
|
|
|
// Back into main function
|
|
ambient_custom_sound();
|
|
};
|