1 #using scripts\codescripts\struct;
3 #using scripts\shared\fx_shared;
4 #using scripts\shared\sound_shared;
5 #using scripts\shared\system_shared;
6 #using scripts\shared\trigger_shared;
7 #using scripts\shared\util_shared;
9 #insert scripts\shared\shared.gsh;
19 level._client_exploders = [];
20 level._client_exploder_ids = [];
28 ents = GetEntArray(
"script_brushmodel",
"classname" );
29 smodels = GetEntArray(
"script_model",
"classname" );
30 for ( i = 0; i < smodels.size; i++ )
32 ents[ents.size] = smodels[i];
35 for ( i = 0; i < ents.size; i++ )
37 if ( isdefined( ents[i].script_prefab_exploder ) )
39 ents[i].script_exploder = ents[i].script_prefab_exploder;
42 if ( isdefined( ents[i].script_exploder ) )
44 if ( ents[i].script_exploder < 10000 )
46 level.exploders[ents[i].script_exploder] =
true;
49 if ( ( ents[i].model ==
"fx" ) &&( ( !isdefined( ents[i].targetname ) ) || ( ents[i].targetname !=
"exploderchunk" ) ) )
53 else if ( ( isdefined( ents[i].targetname ) ) &&( ents[i].targetname ==
"exploder" ) )
58 if( isdefined( ents[i].script_disconnectpaths ) )
60 ents[i] ConnectPaths();
63 else if ( ( isdefined( ents[i].targetname ) ) &&( ents[i].targetname ==
"exploderchunk" ) )
70 ents[i] ConnectPaths();
76 script_exploders = [];
78 potentialExploders = GetEntArray(
"script_brushmodel",
"classname" );
79 for ( i = 0; i < potentialExploders.size; i++ )
81 if( isdefined( potentialExploders[i].script_prefab_exploder ) )
83 potentialExploders[i].script_exploder = potentialExploders[i].script_prefab_exploder;
86 if( isdefined( potentialExploders[i].script_exploder ) )
88 script_exploders[script_exploders.size] = potentialExploders[i];
92 /#println(
"Server : Potential exploders from brushmodels " + potentialExploders.size);#/
94 potentialExploders = GetEntArray(
"script_model",
"classname" );
95 for ( i = 0; i < potentialExploders.size; i++ )
97 if( isdefined( potentialExploders[i].script_prefab_exploder ) )
99 potentialExploders[i].script_exploder = potentialExploders[i].script_prefab_exploder;
102 if( isdefined( potentialExploders[i].script_exploder ) )
104 script_exploders[script_exploders.size] = potentialExploders[i];
108 /#println(
"Server : Potential exploders from script_model " + potentialExploders.size);#/
110 potentialExploders = GetEntArray(
"item_health",
"classname" );
111 for ( i = 0; i < potentialExploders.size; i++ )
113 if( isdefined( potentialExploders[i].script_prefab_exploder ) )
115 potentialExploders[i].script_exploder = potentialExploders[i].script_prefab_exploder;
118 if( isdefined( potentialExploders[i].script_exploder ) )
120 script_exploders[script_exploders.size] = potentialExploders[i];
124 /#println(
"Server : Potential exploders from item_health " + potentialExploders.size);#/
127 if( !isdefined( level.createFXent ) )
129 level.createFXent = [];
132 acceptableTargetnames = [];
133 acceptableTargetnames[
"exploderchunk visible"] =
true;
134 acceptableTargetnames[
"exploderchunk"] =
true;
135 acceptableTargetnames[
"exploder"] =
true;
137 for ( i = 0; i < script_exploders.size; i ++ )
144 ent.v[
"delay" ] =
exploder.script_delay;
145 ent.v[
"firefx" ] =
exploder.script_firefx;
146 ent.v[
"firefxdelay" ] =
exploder.script_firefxdelay;
147 ent.v[
"firefxsound" ] =
exploder.script_firefxsound;
148 ent.v[
"firefxtimeout" ] =
exploder.script_firefxtimeout;
149 ent.v[
"earthquake" ] =
exploder.script_earthquake;
150 ent.v[
"damage" ] =
exploder.script_damage;
151 ent.v[
"damage_radius" ] =
exploder.script_radius;
152 ent.v[
"soundalias" ] =
exploder.script_soundalias;
153 ent.v[
"repeat" ] =
exploder.script_repeat;
154 ent.v[
"delay_min" ] =
exploder.script_delay_min;
155 ent.v[
"delay_max" ] =
exploder.script_delay_max;
157 ent.v[
"ender" ] =
exploder.script_ender;
158 ent.v[
"type" ] =
"exploder";
161 if ( !isdefined(
exploder.script_fxid ) )
163 ent.v[
"fxid" ] =
"No FX";
170 ent.v[
"exploder" ] =
exploder.script_exploder;
171 assert( isdefined(
exploder.script_exploder ),
"Exploder at origin " +
exploder.origin +
" has no script_exploder" );
173 if ( !isdefined( ent.v[
"delay" ] ) )
175 ent.v[
"delay" ] = 0;
181 e_target = GetEnt( ent.v[
"target" ],
"targetname" );
188 ent.v[
"angles" ] = vectortoangles( org - ent.v[
"origin" ] );
197 ent.model.disconnect_paths =
exploder.script_disconnectpaths;
200 if ( isdefined(
exploder.targetname ) && isdefined( acceptableTargetnames[
exploder.targetname ] ) )
202 ent.v[
"exploder_type" ] =
exploder.targetname;
206 ent.v[
"exploder_type" ] =
"normal";
210 level.createFXexploders = [];
212 for (i = 0; i < level.createFXent.size;i ++ )
214 ent = level.createFXent[i];
216 if(ent.v[
"type"] !=
"exploder")
223 if (!isdefined(level.createFXexploders[ent.v[
"exploder"]]))
225 level.createFXexploders[ent.v[
"exploder"]] = [];
228 level.createFXexploders[ent.v[
"exploder"]][level.createFXexploders[ent.v[
"exploder"]].size] = ent;
232 level.radiantExploders = [];
239 if ( isdefined( trig.script_prefab_exploder ) )
241 trig.script_exploder = trig.script_prefab_exploder;
244 if ( isdefined( trig.script_exploder ) )
249 if ( isdefined( trig.script_exploder_radiant ) )
254 if ( isdefined( trig.script_stop_exploder ) )
259 if ( isdefined( trig.script_stop_exploder_radiant ) )
277 if( IsInt( exploder_id ) )
296 wait
self.script_delay;
299 self playSound(level.scr_sound[
self.script_sound]);
304 if( isdefined(
self.v[
"repeat" ] ) )
306 for( i = 0;i <
self.v[
"repeat" ];i ++ )
308 playfx( level._effect[
self.v[
"fxid" ] ],
self.v[
"origin" ],
self.v[
"forward" ],
self.v[
"up" ] );
318 if ( isdefined(
self.looper ) )
320 self.looper
delete();
323 self.looper = spawnFx(
fx::get(
self.v[
"fxid" ] ),
self.v[
"origin" ],
self.v[
"forward" ],
self.v[
"up" ] );
324 triggerFx(
self.looper );
330 forward =
self.v[
"forward" ];
335 firefxSound =
self.v[
"firefxsound" ];
336 origin =
self.v[
"origin" ];
337 firefx =
self.v[
"firefx" ];
338 ender =
self.v[
"ender" ];
339 if( !isdefined( ender ) )
341 ender =
"createfx_effectStopper";
345 if( isdefined(
self.v[
"firefxdelay" ] ) )
347 fireFxDelay =
self.v[
"firefxdelay" ];
352 if( isdefined( firefxSound ) )
357 playfx( level._effect[ firefx ],
self.v[
"origin" ], forward, up );
368 origin =
self.v[
"origin" ];
369 alias =
self.v[
"soundalias" ];
380 if( !isdefined(
self.v[
"trailfxtag"] ) )
382 self.v[
"trailfxtag"] =
"tag_origin";
385 temp_ent = undefined;
388 if(
self.v[
"trailfxtag"] ==
"tag_origin")
390 PlayFxOnTag( level._effect[
self.v[
"trailfx"]],
self.model,
self.v[
"trailfxtag"] );
394 temp_ent =
Spawn(
"script_model",
self.model.origin );
395 temp_ent SetModel(
"tag_origin" );
396 temp_ent LinkTo(
self.model,
self.v[
"trailfxtag" ] );
397 PlayFxOnTag( level._effect[
self.v[
"trailfx"]], temp_ent,
"tag_origin" );
401 if( isdefined(
self.v[
"trailfxsound"] ) )
405 if(!isdefined(temp_ent))
407 self.model PlayLoopSound(
self.v[
"trailfxsound"] );
411 temp_ent PlayLoopSound(
self.v[
"trailfxsound"] );
416 if( isdefined(
self.v[
"ender" ] ) && isdefined( temp_ent ) )
421 if( !isdefined(
self.v[
"trailfxtimeout"] ) )
426 wait(
self.v[
"trailfxtimeout"] );
429 if(isdefined(temp_ent))
437 ent endon(
"death" );
438 self waittill( ender );
444 if( !isdefined(
self.v[
"delay" ] ) )
446 self.v[
"delay" ] = 0;
449 min_delay =
self.v[
"delay" ];
450 max_delay =
self.v[
"delay" ] + 0.001;
451 if( isdefined(
self.v[
"delay_min" ] ) )
453 min_delay =
self.v[
"delay_min" ];
456 if( isdefined(
self.v[
"delay_max" ] ) )
458 max_delay =
self.v[
"delay_max" ];
463 wait( randomfloatrange( min_delay, max_delay ) );
469 if( !isdefined(
self.v[
"soundalias" ] ) ||
self.v[
"soundalias" ] ==
"nil" )
479 num =
self.v[
"exploder" ];
481 if( isdefined(
self.v[
"delay" ] ) )
483 wait(
self.v[
"delay" ] );
490 if( !isdefined(
self.model ) )
496 assert( isdefined(
self.model ) );
498 if( !isdefined(
self.v[
"fxid" ] ) ||
self.v[
"fxid" ] ==
"No FX" )
500 self.v[
"exploder" ] = undefined;
509 if( isdefined(
self.v[
"delay" ] ) )
511 wait(
self.v[
"delay" ] );
514 assert( isdefined(
self.model ) );
522 if( isdefined(
self.v[
"delay" ] ) )
524 wait(
self.v[
"delay" ] );
529 if( isdefined(
self.v[
"target" ] ) )
531 ent = getent(
self.v[
"target" ],
"targetname" );
534 if( !isdefined( ent ) )
542 startorg =
self.v[
"origin" ];
543 startang =
self.v[
"angles" ];
547 temp_vec = ( org -
self.v[
"origin" ] );
552 self.model rotateVelocity( ( x, y, z ), 12 );
554 self.model moveGravity( ( x, y, z ), 12 );
556 self.v[
"exploder" ] = undefined;
563 trigger endon(
"death" );
565 level endon(
"killexplodertridgers" + script_value );
569 if( isdefined( trigger.script_chance ) && RandomFloat( 1 ) > trigger.script_chance )
571 if ( isdefined( trigger.script_delay ) )
573 wait( trigger.script_delay );
584 level notify(
"killexplodertridgers" + script_value );
589 if(!isdefined(level._exploder_ids))
594 keys = GetArrayKeys( level._exploder_ids );
597 println(
"Server Exploder dictionary : ");
599 for( i = 0; i < keys.size; i++ )
601 println(keys[i] +
" : " + level._exploder_ids[keys[i]]);
608 if(!isdefined(level._exploder_ids))
610 level._exploder_ids = [];
611 level._exploder_id = 1;
614 if(!isdefined(level._exploder_ids[ent.v[
"exploder"]]))
616 level._exploder_ids[ent.v[
"exploder"]] = level._exploder_id;
617 level._exploder_id ++;
620 return level._exploder_ids[ent.v[
"exploder"]];
626 ent.v[
"delay" ] = 0;
627 ent.v[
"exploder" ] = 1;
628 ent.v[
"exploder_type" ] =
"normal";
636 level notify(
"exploder" + num );
640 if(IsDefined(level.createFXexploders[num]))
642 for(i = 0; i < level.createFXexploders[num].size; i ++)
644 if(client_send && IsDefined(level.createFXexploders[num][i].v[
"exploder_server"]))
653 if(level.clientScripts)
655 if(client_send ==
true)
665 level notify(
"exploder" +
string );
667 ActivateClientRadiantExploder(
string );
682 level notify(
"exploder" +
self.v[
"exploder"]);
686 if(!level.clientScripts || !isdefined(level._exploder_ids[
int(
self.v[
"exploder"])] ) || isdefined(
self.v[
"exploder_server"]))
689 println(
"Exploder " +
self.v[
"exploder"] +
" created on server.");
691 if( isdefined(
self.v[
"firefx" ] ) )
696 if( isdefined(
self.v[
"fxid" ] ) &&
self.v[
"fxid" ] !=
"No FX" )
700 else if( isdefined(
self.v[
"soundalias" ] ) )
705 if( isdefined(
self.v[
"earthquake" ] ) )
710 if( isdefined(
self.v[
"rumble" ] ) )
718 if( isdefined(
self.v[
"trailfx" ] ) )
723 if( isdefined(
self.v[
"damage" ] ) )
728 if(
self.v[
"exploder_type" ] ==
"exploder" )
732 else if( (
self.v[
"exploder_type" ] ==
"exploderchunk" ) || (
self.v[
"exploder_type" ] ==
"exploderchunk visible" ) )
745 if(!isdefined(level._exploder_ids[num]))
750 if(!isdefined(level._client_exploders[num]))
752 level._client_exploders[num] = 1;
755 if(!isdefined(level._client_exploder_ids[num]))
757 level._client_exploder_ids[num] = 1;
760 ActivateClientExploder(level._exploder_ids[num]);
765 if(level.clientScripts)
770 if(isdefined(level.createFXexploders[num]))
772 for(i = 0; i < level.createFXexploders[num].size; i ++)
775 if ( !isdefined( level.createFXexploders[num][i].looper ) )
780 level.createFXexploders[num][i].looper
delete();
788 if( IsString( exploder_id ) )
790 DeactivateClientRadiantExploder( exploder_id );
794 if(!isdefined(level._exploder_ids[exploder_id]))
799 if(!isdefined(level._client_exploders[exploder_id]))
804 level._client_exploders[exploder_id] = undefined;
806 level._client_exploder_ids[exploder_id] = undefined;
808 DeactivateClientExploder(level._exploder_ids[exploder_id]);
813 if( IsString( exploder_string ) )
815 KillClientRadiantExploder( exploder_string );
819 assertmsg(
"unhandled exploder type, only radiant exploders are handled" );
824 if( isdefined(
self.v[
"delay" ] ) )
826 delay =
self.v[
"delay" ];
833 if( isdefined(
self.v[
"damage_radius" ] ) )
835 radius =
self.v[
"damage_radius" ];
843 origin =
self.v[
"origin" ];
852 earthquake_name =
self.v[
"earthquake" ];
854 assert(isdefined(level.earthquake) && isdefined(level.earthquake[earthquake_name]),
855 "No earthquake '" + earthquake_name +
"' defined for exploder - call add_earthquake() in your level script.");
858 eq = level.earthquake[earthquake_name];
859 earthquake( eq[
"magnitude" ], eq[
"duration" ],
self.v[
"origin" ], eq[
"radius" ] );
867 a_players = GetPlayers();
869 if( isdefined(
self.v[
"damage_radius" ] ) )
871 n_rumble_threshold_squared =
self.v[
"damage_radius" ] *
self.v[
"damage_radius" ];
875 /#println(
"exploder #" +
self.v[
"exploder" ] +
" missing script_radius KVP, using default." );#/
876 n_rumble_threshold_squared = 128 * 128;
879 for( i = 0; i < a_players.size; i++ )
881 n_player_dist_squared = distancesquared( a_players[ i ].origin,
self.v[
"origin" ] );
883 if( n_player_dist_squared < n_rumble_threshold_squared )
885 a_players[ i ] PlayRumbleonentity(
self.v[
"rumble" ] );