1 #using scripts\codescripts\struct;
3 #using scripts\shared\system_shared;
5 #insert scripts\shared\shared.gsh;
6 #insert scripts\zm\_zm_utility.gsh;// for the "is_drinking" check for unitriggers.
8 #using scripts\zm\_zm_utility;
9 #using scripts\zm\_zm_zonemgr;
20 #define PLAYER_RADIUS 15.0
21 #define PLAYER_STAND_MAX_Z 70.0
22 #define UNITRIGGER_MAX_RADIUS (128 - PLAYER_RADIUS)
24 #namespace zm_unitrigger;
30 level._unitriggers = SpawnStruct();
31 level._unitriggers._deferredInitList = [];
32 level._unitriggers.trigger_pool = [];
33 level._unitriggers.trigger_stubs = [];
34 level._unitriggers.dynamic_stubs = [];
35 level._unitriggers.system_trigger_funcs = [];
36 level._unitriggers.largest_radius = 64;
38 stubs_keys =
array(
"unitrigger_radius",
"unitrigger_radius_use",
"unitrigger_box",
"unitrigger_box_use");
42 for(i = 0; i < stubs_keys.size; i ++)
44 stubs = ArrayCombine(stubs,
struct::get_array(stubs_keys[i],
"script_unitrigger_type"),
true,
false);
47 for(i = 0; i < stubs.size; i ++)
55 level._unitriggers.system_trigger_funcs[system] = trigger_func;
60 if (!isdefined(opt_on_off))
62 unitrigger_stub.trigger_per_player = opt_on_off;
67 if(
self.trigger_per_player)
69 return self.playertrigger[player GetEntityNumber()];
79 if (isdefined(
self.originFunc))
80 origin =
self [[
self.originFunc]]();
88 if(!isdefined(unitrigger_stub.script_unitrigger_type))
93 if(isdefined(trigger_func))
95 unitrigger_stub.trigger_func = trigger_func;
97 else if(isdefined(unitrigger_stub.unitrigger_system) && isdefined(level._unitriggers.system_trigger_funcs[unitrigger_stub.unitrigger_system]))
99 unitrigger_stub.trigger_func = level._unitriggers.system_trigger_funcs[unitrigger_stub.unitrigger_system];
104 switch(unitrigger_stub.script_unitrigger_type)
106 case "unitrigger_radius":
107 case "unitrigger_radius_use":
108 if(!isdefined(unitrigger_stub.radius))
110 unitrigger_stub.radius = 32;
113 if(!isdefined(unitrigger_stub.script_height))
115 unitrigger_stub.script_height = 64;
119 case "unitrigger_box":
120 case "unitrigger_box_use":
121 if(!isdefined(unitrigger_stub.script_width))
123 unitrigger_stub.script_width = 64;
126 if(!isdefined(unitrigger_stub.script_height))
128 unitrigger_stub.script_height = 64;
131 if(!isdefined(unitrigger_stub.script_length))
133 unitrigger_stub.script_length = 64;
135 box_radius = Length( (unitrigger_stub.script_width/2,unitrigger_stub.script_length/2,unitrigger_stub.script_height/2) );
136 if(!isdefined(unitrigger_stub.radius) || unitrigger_stub.radius<box_radius)
138 unitrigger_stub.radius = box_radius;
148 if ( unitrigger_stub.radius > level._unitriggers.largest_radius )
151 if ( IsDefined(level.fixed_max_player_use_radius) )
153 if ( level.fixed_max_player_use_radius > GetDVarFloat(
"player_useRadius_zm" ) )
154 SetDvar(
"player_useRadius_zm", level.fixed_max_player_use_radius );
156 else if ( level._unitriggers.largest_radius > GetDVarFloat(
"player_useRadius_zm" ) )
158 SetDvar(
"player_useRadius_zm", level._unitriggers.largest_radius );
162 level._unitriggers.trigger_stubs[level._unitriggers.trigger_stubs.size] = unitrigger_stub;
163 unitrigger_stub.registered = 1;
170 level._unitriggers.dynamic_stubs[level._unitriggers.dynamic_stubs.size] = unitrigger_stub;
181 if (!isdefined( unitrigger_stub ))
183 unitrigger_stub.registered = 0;
184 if(
IS_TRUE(unitrigger_stub.trigger_per_player))
186 if(isdefined(unitrigger_stub.playertrigger) && (unitrigger_stub.playertrigger.size > 0))
188 keys = GetArrayKeys(unitrigger_stub.playertrigger);
189 foreach( key
in keys )
191 trigger = unitrigger_stub.playertrigger[key];
192 trigger notify(
"kill_trigger");
193 if (isdefined(trigger))
196 unitrigger_stub.playertrigger = [];
201 if ( isdefined(unitrigger_stub.trigger) )
203 trigger = unitrigger_stub.trigger;
204 trigger notify(
"kill_trigger");
205 trigger.stub.trigger = undefined;
209 if (isdefined( unitrigger_stub.in_zone ))
211 ArrayRemoveValue( level.zones[unitrigger_stub.in_zone].unitrigger_stubs, unitrigger_stub );
212 unitrigger_stub.in_zone = undefined;
215 ArrayRemoveValue( level._unitriggers.trigger_stubs, unitrigger_stub );
216 ArrayRemoveValue( level._unitriggers.dynamic_stubs, unitrigger_stub );
221 self.last_used_time = 0;
227 if((GetTime() -
self.last_used_time) > 1000)
230 level._unitriggers.contact_ent = undefined;
238 if(level.zones.size == 0)
240 unitrigger_stub.trigger_func = trigger_func;
241 level._unitriggers._deferredInitList[level._unitriggers._deferredInitList.size] = unitrigger_stub;
245 if(!isdefined(level._unitriggers.contact_ent))
247 level._unitriggers.contact_ent =
spawn(
"script_origin", (0,0,0));
253 if(!isdefined(level._no_static_unitriggers))
256 level._unitriggers.contact_ent.last_used_time = GetTime();
257 level._unitriggers.contact_ent.origin = unitrigger_stub.origin;
259 if(isdefined(unitrigger_stub.in_zone) && !isdefined(recalculate_zone))
261 level.zones[unitrigger_stub.in_zone].unitrigger_stubs[level.zones[unitrigger_stub.in_zone].unitrigger_stubs.size] = unitrigger_stub;
265 keys = GetArrayKeys(level.zones);
267 for(i = 0; i < keys.size; i ++)
271 if(!isdefined(level.zones[keys[i]].unitrigger_stubs))
273 level.zones[keys[i]].unitrigger_stubs = [];
276 level.zones[keys[i]].unitrigger_stubs[level.zones[keys[i]].unitrigger_stubs.size] = unitrigger_stub;
277 unitrigger_stub.in_zone = keys[i];
283 level._unitriggers.dynamic_stubs[level._unitriggers.dynamic_stubs.size] = unitrigger_stub;
284 unitrigger_stub.registered = 1;
289 if(level.zones.size == 0)
291 unitrigger_stub.trigger_func = trigger_func;
292 level._unitriggers._deferredInitList[level._unitriggers._deferredInitList.size] = unitrigger_stub;
296 if(!isdefined(level._unitriggers.contact_ent))
298 level._unitriggers.contact_ent =
spawn(
"script_origin", (0,0,0));
304 level._unitriggers.dynamic_stubs[level._unitriggers.dynamic_stubs.size] = unitrigger_stub;
305 unitrigger_stub.registered = 1;
321 trigger notify(
"kill_trigger");
322 if(
IS_TRUE(trigger.stub.trigger_per_player))
324 trigger.stub.playerTrigger[player GetEntityNumber()] = undefined;
328 trigger.stub.trigger = undefined;
332 level._unitriggers.trigger_pool[player GetEntityNumber()] = undefined;
337 if (!isdefined(trigger) || !isdefined(stub))
339 keep_thread = default_keep;
340 if (!isdefined(stub.prompt_and_visibility_func) ||
341 trigger [[stub.prompt_and_visibility_func]]( player ) )
344 if (!
IS_TRUE(trigger.thread_running))
346 trigger.thread_running =
true;
347 if (IsDefined(trigger.reassess_time) && trigger.reassess_time <= 0.0)
348 trigger.reassess_time = undefined;
352 if (
IS_TRUE(trigger.thread_running))
354 trigger.thread_running =
false;
356 if ( IsDefined(stub.inactive_reassess_time) )
357 trigger.reassess_time = stub.inactive_reassess_time;
359 trigger.reassess_time = 1.0;
368 if(level._unitriggers._deferredInitList.size)
370 for(i = 0; i < level._unitriggers._deferredInitList.size; i ++)
375 for(i = 0; i < level._unitriggers._deferredInitList.size; i ++)
377 level._unitriggers._deferredInitList[i] = undefined;
380 level._unitriggers._deferredInitList = undefined;
384 valid_range_sq = valid_range * valid_range;
386 while( !isdefined( level.active_zone_names ) )
394 active_zone_names = level.active_zone_names;
398 for(j = 0; j < active_zone_names.size; j ++)
400 if(isdefined(level.zones[active_zone_names[j]].unitrigger_stubs))
402 candidate_list = ArrayCombine(candidate_list, level.zones[active_zone_names[j]].unitrigger_stubs,
true,
false);
406 candidate_list = ArrayCombine(candidate_list, level._unitriggers.dynamic_stubs,
true,
false);
408 players = GetPlayers();
410 for(i = 0; i < players.size; i ++)
414 if(!isdefined(player))
421 trigger = level._unitriggers.trigger_pool[player GetEntityNumber()];
423 old_trigger = undefined;
426 if(isdefined(trigger))
428 dst = valid_range_sq;
431 dst = trigger.stub.test_radius_sq;
432 time_to_ressess =
false;
433 trigger_still_valid =
false;
435 if( Distance2DSquared(player_origin, origin) < dst)
437 if (isdefined(trigger.reassess_time))
439 trigger.reassess_time -= 0.05;
440 if (trigger.reassess_time > 0.0)
442 time_to_ressess =
true;
451 trigger_still_valid =
true;
458 if ( IsDefined(trigger) && time_to_ressess && (closest.size < 2 ||
IS_TRUE(trigger.thread_running) ) )
464 if (trigger_still_valid && closest.size < 2)
477 if (trigger_still_valid)
479 old_trigger = trigger;
481 level._unitriggers.trigger_pool[player GetEntityNumber()] = undefined;
483 else if (IsDefined(trigger))
494 first_usable=undefined;
495 first_visible=undefined;
496 trigger_found =
false;
499 while (index < closest.size)
507 if(!
IS_TRUE(closest[index].registered))
515 if (isdefined(trigger))
518 trigger.parent_player = player;
529 level._unitriggers.trigger_pool[player GetEntityNumber()] = trigger;
530 trigger_found =
true;
535 if (!isdefined(first_usable))
537 first_usable = index;
541 if (!isdefined(first_visible))
543 first_visible = index;
547 if (isdefined(trigger))
550 level._unitriggers.trigger_pool[player GetEntityNumber()] = undefined;
553 last_trigger = trigger;
561 if (!IsDefined(player))
567 if (isdefined(first_usable))
568 index = first_usable;
569 else if (isdefined(first_visible))
570 index = first_visible;
573 if (isdefined(trigger))
575 trigger.parent_player = player;
576 level._unitriggers.trigger_pool[player GetEntityNumber()] = trigger;
580 if (isdefined(old_trigger))
586 if (isdefined(trigger))
601 if(!isdefined(
self.prompt_and_visibility_func))
606 if(
IS_TRUE(
self.trigger_per_player))
608 if(!isdefined(
self.playertrigger))
613 players = GetPlayers();
615 for(i = 0; i < players.size; i ++)
617 if(isdefined(
self.playertrigger[players[i] GetEntityNumber()]))
619 self.playertrigger[players[i] GetEntityNumber()] [[
self.prompt_and_visibility_func]](players[i]);
625 if(isdefined(
self.trigger))
627 self.trigger [[
self.prompt_and_visibility_func]](GetPlayers()[0]);
634 return isdefined(old_trigger) && old_trigger == trigger && trigger.parent_player == old_trigger.parent_player;
639 if (!isdefined(stub))
642 if(
IS_TRUE(stub.trigger_per_player))
644 if (!isdefined(stub.playertrigger))
645 stub.playertrigger = [];
646 if(!isdefined(stub.playertrigger[player GetEntityNumber()]))
649 level._unitriggers.trigger_pool[player GetEntityNumber()] = trigger;
652 trigger = stub.playertrigger[player GetEntityNumber()];
656 if(!isdefined(stub.trigger))
659 level._unitriggers.trigger_pool[player GetEntityNumber()] = trigger;
660 }
else trigger = stub.trigger;
667 if( isdefined( level._zm_build_trigger_from_unitrigger_stub_override ) )
669 if( stub [[ level._zm_build_trigger_from_unitrigger_stub_override ]]( player ) )
675 radius = stub.radius;
677 if(!isdefined(radius))
682 script_height = stub.script_height;
683 if(!isdefined(script_height))
688 script_width = stub.script_width;
689 if(!isdefined(script_width))
695 script_length = stub.script_length;
696 if(!isdefined(script_length))
705 switch(stub.script_unitrigger_type)
707 case "unitrigger_radius":
708 trigger =
Spawn(
"trigger_radius", origin, 0, radius, script_height);
710 case "unitrigger_radius_use":
711 trigger =
Spawn(
"trigger_radius_use", origin, 0, radius, script_height);
713 case "unitrigger_box":
714 trigger =
Spawn(
"trigger_box", origin, 0, script_width, script_length, script_height);
716 case "unitrigger_box_use":
717 trigger =
Spawn(
"trigger_box_use", origin, 0, script_width, script_length, script_height);
721 if(isdefined(trigger))
723 if(isdefined(stub.angles))
725 trigger.angles = stub.angles;
728 if (isdefined(stub.onSpawnFunc))
729 stub [[stub.onSpawnFunc]](trigger);
731 if(isdefined(stub.cursor_hint))
733 if ( stub.cursor_hint ==
"HINT_WEAPON" && IsDefined(stub.cursor_hint_weapon) )
734 trigger SetCursorHint(stub.cursor_hint,stub.cursor_hint_weapon);
736 trigger SetCursorHint(stub.cursor_hint);
738 trigger TriggerIgnoreTeam();
742 trigger UseTriggerRequireLookAt();
744 if(
IS_TRUE(stub.require_look_toward))
746 trigger UseTriggerRequireLookToward(
true);
749 if(isdefined(stub.hint_string))
751 if(isdefined(stub.hint_parm2))
753 trigger SetHintString(stub.hint_string, stub.hint_parm1, stub.hint_parm2);
755 else if(isdefined(stub.hint_parm1))
757 trigger SetHintString(stub.hint_string, stub.hint_parm1);
759 else if(isdefined(stub.cost) && !
IS_TRUE( level.weapon_cost_client_filled ))
761 trigger SetHintString(stub.hint_string, stub.cost);
765 trigger SetHintString(stub.hint_string);
774 if(
IS_TRUE(stub.trigger_per_player))
776 if(isdefined(trigger))
778 trigger setInvisibleToAll();
779 trigger setVisibleToPlayer( player );
781 if (!isdefined(stub.playertrigger))
782 stub.playertrigger = [];
783 stub.playertrigger[player GetEntityNumber()] = trigger;
786 stub.trigger = trigger;
787 trigger.thread_running =
false;
794 trig.script_noteworthy = stub.script_noteworthy;
795 trig.targetname = stub.targetname;
796 trig.target = stub.target;
800 trig.weapon = stub.weapon;
801 trig.clientFieldName = stub.clientFieldName;
804 trig.useTime = stub.useTime;
810 self endon(
"kill_trigger");
812 if(isdefined(trigger_func))
814 self [[trigger_func]]();
826 for( i = 0; i <
array.size; i++ )
828 if (!isdefined(
array[i]))
831 radius_sq =
array[ i ].test_radius_sq;
833 newdistsq = Distance2DSquared( origin, org );
834 if( newdistsq >= radius_sq )
838 if ( abs(origin[2]-org[2]) > 42 )
840 array[i].dsquared = newdistsq;
842 while(j<triggers.size && newdistsq > triggers[j].dsquared)
844 ArrayInsert(triggers,
array[i],j);
855 s_unitrigger = SpawnStruct();
856 s_unitrigger.origin =
self.origin;
857 s_unitrigger.angles =
self.angles;
858 s_unitrigger.script_unitrigger_type = s_trigger_type;
859 s_unitrigger.cursor_hint =
"HINT_NOICON";
860 s_unitrigger.hint_string = str_hint;
861 s_unitrigger.prompt_and_visibility_func = func_prompt_and_visibility;
862 s_unitrigger.related_parent =
self;
863 s_unitrigger.radius = n_radius;
864 self.s_unitrigger = s_unitrigger;
874 s_unitrigger = SpawnStruct();
875 s_unitrigger.origin =
self.origin;
876 s_unitrigger.angles =
self.angles;
877 s_unitrigger.script_unitrigger_type = s_trigger_type;
878 s_unitrigger.cursor_hint =
"HINT_NOICON";
879 s_unitrigger.hint_string = str_hint;
880 s_unitrigger.prompt_and_visibility_func = func_prompt_and_visibility;
881 s_unitrigger.related_parent =
self;
882 s_unitrigger.radius = n_radius;
883 self.s_unitrigger = s_unitrigger;
902 self endon(
"death" );
906 self waittill(
"trigger", player );
923 self.stub.related_parent notify(
"trigger_activated", player );