1 // Comment out below to skip turrets
2 #define TTURRETS_ENABLED
3 //#define TTURRETS_CSQC
5 #ifdef TTURRETS_ENABLED
7 //#message "with tZork turrets"
11 vector real_origin(entity ent);
13 /// Map time control over pain inflicted
14 .float turret_scale_damage;
15 /// Map time control targetting range
16 .float turret_scale_range;
17 /// Map time control refire
18 .float turret_scale_refire;
19 /// Map time control ammo held and recharged
20 .float turret_scale_ammo;
21 /// Map time control aim speed
22 .float turret_scale_aim;
23 /// Map time control health
24 .float turret_scale_health;
25 /// Map time control respawn time
26 .float turret_scale_respawn;
28 /// Used for cvar reloading
29 .string cvar_basename;
32 #define TSF_SUSPENDED 1
33 /// Spawn a pillar model under the turret to make it look ok on uneven ground surfaces
34 #define TSF_TERRAINBASE 2
35 /// Disable builtin ammo regeneration
36 #define TSF_NO_AMMO_REGEN 4
37 /// Dont break path to chase enemys. will still fire at them if possible.
38 #define TSF_NO_PATHBREAK 8
40 #define TSL_NO_RESPAWN 16
42 /// target selection flags
43 .float target_select_flags;
44 /// target validatoin flags
45 .float target_validate_flags;
46 /// Dont select a target on its own.
47 #define TFL_TARGETSELECT_NO 2
48 /// Need line of sight
49 #define TFL_TARGETSELECT_LOS 4
50 /// Players are valid targets
51 #define TFL_TARGETSELECT_PLAYERS 8
52 /// Missiles are valid targets
53 #define TFL_TARGETSELECT_MISSILES 16
54 /// Responds to turret_trigger_target events
55 #define TFL_TARGETSELECT_TRIGGERTARGET 32
56 /// Angular limitations of turret head limits target selection
57 #define TFL_TARGETSELECT_ANGLELIMITS 64
58 /// Range limits apply in targetselection
59 #define TFL_TARGETSELECT_RANGELIMTS 128
60 /// DOnt select targets with a .team matching its own
61 #define TFL_TARGETSELECT_TEAMCHECK 256
62 /// Cant select targets on its own. needs to be triggerd or slaved.
63 #define TFL_TARGETSELECT_NOBUILTIN 512
64 /// TFL_TARGETSELECT_TEAMCHECK is inverted (selects only mebers of own .team)
65 #define TFL_TARGETSELECT_OWNTEAM 1024
66 /// Turrets aren't valid targets
67 #define TFL_TARGETSELECT_NOTURRETS 2048
69 #define TFL_TARGETSELECT_FOV 4096
71 #define TFL_TARGETSELECT_MISSILESONLY 8192
77 /// Go for ground, not direct hit
78 //#define TFL_AIM_GROUND 2
79 /// Go for ground, not direct hit, but only if target is on ground.
80 #define TFL_AIM_GROUND2 4
81 /// Use balistic aim. FIXME: not implemented
82 #define TFL_AIM_BALISTIC 8
83 /// Try to predict target movement (does not account for gravity)
84 #define TFL_AIM_LEAD 16
85 /// Compensate for shot traveltime when lead
86 #define TFL_AIM_SHOTTIMECOMPENSATE 32
87 /// Aim slightly in front of target
88 #define TFL_AIM_INFRONT 64
89 /// Aim slightly behind target
90 #define TFL_AIM_BEHIND 128
91 /// blend real and predicted z positions. (fake bounce prediction)
92 // #define TFL_AIM_ZEASE 256
93 /// Try to do real prediction of targets z pos at impact.
94 #define TFL_AIM_ZPREDICT 512
95 /// Simply aim at target's current location
96 #define TFL_AIM_SIMPLE 1024
98 /// track (turn and pitch head) flags
101 #define TFL_TRACK_NO 2
103 #define TFL_TRACK_PITCH 4
105 #define TFL_TRACK_ROT 8
107 /// How tracking is preformed
109 /// Hard angle increments. Ugly for fast turning, best accuracy.
110 #define TFL_TRACKTYPE_STEPMOTOR 1
111 /// Smoth absolute movement. Looks ok, fair accuracy.
112 #define TFL_TRACKTYPE_FLUIDPRECISE 2
113 /// Simulated inertia. "Wobbly mode" Looks kool, can mean really bad accuracy depending on how the feilds below are set
114 #define TFL_TRACKTYPE_FLUIDINERTIA 3
115 /// TFL_TRACKTYPE_FLUIDINERTIA: pitch multiplier
116 .float track_accel_pitch;
117 /// TFL_TRACKTYPE_FLUIDINERTIA: rotation multiplier
118 .float track_accel_rot;
119 /// TFL_TRACKTYPE_FLUIDINERTIA: Blendrate with old rotation (inertia simulation) 1 = only old, 0 = only new
120 .float track_blendrate;
122 /// How prefire check is preformed
123 .float firecheck_flags;
124 /// Dont kill the world
125 #define TFL_FIRECHECK_WORLD 2
126 /// Dont kill the dead
127 #define TFL_FIRECHECK_DEAD 4
128 /// Range limits apply
129 #define TFL_FIRECHECK_DISTANCES 8
130 /// Line Of Sight needs to be clear
131 #define TFL_FIRECHECK_LOS 16
132 /// Consider distance inpactpoint<->aimspot
133 #define TFL_FIRECHECK_AIMDIST 32
134 /// Consider enemy origin<->impactpoint
135 #define TFL_FIRECHECK_REALDIST 64
136 /// Consider angular diff head<->aimspot
137 #define TFL_FIRECHECK_ANGLEDIST 128
138 /// (re)consider target.team<->self.team
139 #define TFL_FIRECHECK_TEAMCECK 256
140 /// Try to avoid friendly fire
141 #define TFL_FIRECHECK_AFF 512
142 /// Own .ammo needs to be >= then own .shot_dmg
143 #define TFL_FIRECHECK_OWM_AMMO 1024
144 /// Others ammo need to be < others .ammo_max
145 #define TFL_FIRECHECK_OTHER_AMMO 2048
146 /// Check own .attack_finished_single vs time
147 #define TFL_FIRECHECK_REFIRE 4096
148 /// Move the acctual target to aimspot before tracing impact (and back after)
149 #define TFL_FIRECHECK_VERIFIED 8192
150 /// Dont do any chekcs
151 #define TFL_FIRECHECK_NO 16384
153 /// How shooting is done
156 #define TFL_SHOOT_NO 64
157 /// Fire in vollys (partial implementation through .shot_volly)
158 #define TFL_SHOOT_VOLLY 2
159 /// Always do a full volly, even if target is lost or dead. (not implemented)
160 #define TFL_SHOOT_VOLLYALWAYS 4
161 /// Loop though all valid tarters, and hit them.
162 #define TFL_SHOOT_HITALLVALID 8
163 /// Fiering makes unit loose target (after volly is done, if in volly mode)
164 #define TFL_SHOOT_CLEARTARGET 16
166 #define TFL_SHOOT_CUSTOM 32
168 /// Information aboute the units capabilities
169 .float turrcaps_flags;
170 /// No kown capabilities
171 #define TFL_TURRCAPS_NONE 0
172 /// Capable of sniping
173 #define TFL_TURRCAPS_SNIPER 2
174 /// Capable of splasdamage
175 #define TFL_TURRCAPS_RADIUSDMG 4
176 /// Has one or more cannons with zero shot traveltime
177 #define TFL_TURRCAPS_HITSCAN 8
178 /// More then one (type of) gun
179 #define TFL_TURRCAPS_MULTIGUN 16
180 /// Carries at least one guided weapon
181 #define TFL_TURRCAPS_GUIDED 32
182 /// At least one gun fiers slow projectiles
183 #define TFL_TURRCAPS_SLOWPROJ 64
184 /// At least one gun fiers medium speed projectiles
185 #define TFL_TURRCAPS_MEDPROJ 128
186 /// At least one gun fiers fast projectiles
187 #define TFL_TURRCAPS_FASTPROJ 256
188 /// At least one gun capable of damaging players
189 #define TFL_TURRCAPS_PLAYERKILL 512
190 /// At least one gun that can shoot town missiles
191 #define TFL_TURRCAPS_MISSILEKILL 1024
192 /// Has support capabilities. powerplants and sutch.
193 #define TFL_TURRCAPS_SUPPORT 2048
194 /// Proveides at least one type of ammmo
195 #define TFL_TURRCAPS_AMMOSOURCE 4096
196 /// Can recive targets from external sources
197 #define TFL_TURRCAPS_RECIVETARGETS 8192
198 /// Capable of self-transport
199 #define TFL_TURRCAPS_MOVE 16384
200 /// Will roam arround even if not chasing anyting
201 #define TFL_TURRCAPS_ROAM 32768
202 #define TFL_TURRCAPS_ISTURRET 65536
204 /// Ammo types needed and/or provided
206 /// Has and needs no ammo
207 #define TFL_AMMO_NONE 64
209 #define TFL_AMMO_ENERGY 2
211 #define TFL_AMMO_BULLETS 4
213 #define TFL_AMMO_ROCKETS 8
214 /// Regenerates ammo on its own
215 #define TFL_AMMO_RECHARGE 16
216 /// Can recive ammo from others
217 #define TFL_AMMO_RECIVE 32
219 /// How incomming damage is handeld
222 #define TFL_DMG_NO 256
224 #define TFL_DMG_YES 2
225 /// Can be damaged by teammates
226 #define TFL_DMG_TAKEFROMTEAM 4
228 #define TFL_DMG_RETALIATE 8
229 /// Target attackers, even is on own team
230 #define TFL_DMG_RETALIATEONTEAM 16
231 /// Loses target when damaged
232 #define TFL_DMG_TARGETLOSS 32
233 /// Reciving damage trows off aim (pointless atm, aim gets recalculated to fast). not implemented.
234 #define TFL_DMG_AIMSHAKE 64
235 /// Reciving damage slaps the head arround
236 #define TFL_DMG_HEADSHAKE 128
237 /// Die and stay dead.
238 #define TFL_DMG_DEATH_NORESPAWN 256
239 /// Supress std turret gibs on death
240 #define TFL_DMG_DEATH_NOGIBS 512
243 /// Spawn in teambased modes
244 #define TFL_SPAWN_TEAM 2
245 /// Spawn in FFA modes
246 #define TFL_SPAWN_FFA 4
250 * Fields used by turrets
252 /// Turrets internal ai speed
255 /// Where to point the when no target
258 /// Top part of turret
261 /// Start/respawn health
264 /// Defend this entity (or ratehr this entitys position)
270 /// and shoot from here. (can be non constant, think MLRS)
276 /// Predicted time the round will impact
277 .float tur_impacttime;
279 // Predicted place the round will impact
280 //.vector tur_impactpoint; // unused
282 /// What entity the aimtrace hit, if any.
283 .entity tur_impactent;
285 /// Distance to enemy
286 .float tur_dist_enemy;
288 /// Distance to aimspot
289 .float tur_dist_aimpos;
291 /// Distance impact<->aim
292 .float tur_dist_impact_to_aimpos;
294 /// Decresment counter form .shot_volly to 0.
295 .float volly_counter;
298 * Projectile/missile. its up to the individual turret implementation to
299 ** deal the damage, blow upp the missile or whatever.
301 /// Track then refireing is possible
302 //.float attack_finished; = attack_finished_single
305 /// Shots travel this fast, when appliable
309 /// Estimated (core) damage of projectiles. also reduce on ammo with this amount when fiering
311 /// If radius dmg, this is how big that radius is.
313 /// Max force exserted by round impact
315 /// < 1 = shoot # times at target (if possible)
317 /// Refire after a compleated volly.
318 .float shot_volly_refire;
320 /// Consider targets within this range
322 /// Dont consider targets closer then
323 .float target_range_min;
324 /// Targets closer to this are prefered
325 .float target_range_optimal;
328 * The standard targetselection tries to select a target based on
329 * range, angle offset, target type, "is old target"
330 * Thise biases will allow score scaling to (dis)favor diffrent targets
332 /// (dis)Favor best range this mutch
333 .float target_select_rangebias;
334 /// (dis)Favor targeting my old enemy this mutch
335 .float target_select_samebias;
336 /// (dis)Favor targeting the enemy closest to my guns current angle this mutch
337 .float target_select_anglebias;
338 /// (dis)Favor Missiles? (-1 to diable targeting compleatly)
339 .float target_select_missilebias;
340 /// (dis)Favot living players (-1 to diable targeting compleatly)
341 .float target_select_playerbias;
343 //.float target_select_fov;
344 /// Last timestamp this turret aquierd a valid target
345 .float target_select_time;
348 * Aim refers to real aiming, not gun pos (thats done by track)
350 /// Maximum offset between impact and aim spot to fire
351 .float aim_firetolerance_dist;
352 /// How fast can i rotate/pitch (per second in stepmotor mode, base force in smooth modes)
354 /// cant aim higher/lower then this
356 /// I cant rotate more then this
359 // Ammo/power. keeping dmg and ammo on a one to one ratio is preferable (for rating)
360 /// Staring & current ammo
362 /// Regenerate this mutch ammo (per second)
363 .float ammo_recharge;
364 /// Max amount of ammo i can hold
368 // Uncomment below to enable various debug output.
369 //#define TURRET_DEBUG
370 //#define TURRET_DEBUG_TARGETVALIDATE
371 //#define TURRET_DEBUG_TARGETSELECT
374 .float tur_dbg_dmg_t_h; // Total dmg that hit something (can be more then tur_dbg_dmg_t_f since it should count radius dmg.
375 .float tur_dbg_dmg_t_f; // Total damage spent
376 .float tur_dbg_start; // When did i go online?
377 .float tur_dbg_tmr1; // timer for random use
378 .float tur_dbg_tmr2; // timer for random use
379 .float tur_dbg_tmr3; // timer for random use
380 .vector tur_dbg_rvec; // Random vector, mainly for coloruing stuff'
386 /// Prefire checks and sutch
390 /// implements the actual fiering
391 .void() turret_firefunc;
392 /// prefire checks go here. return 1 to go bang, 0 not to.
393 .float() turret_firecheckfunc;
394 /// Execure AFTER main AI loop
395 .void() turret_postthink;
398 .float(entity e_target,entity e_sender) turret_addtarget;
400 .void() turret_diehook;
401 .void() turret_respawnhook;
404 * Target selection, preferably but not nessesarely
405 * return a normalized result.
407 /// Function to use for target evaluation. usualy turret_stdproc_targetscore_generic
408 .float(entity _turret, entity _target) turret_score_target;
413 /// Generic, fairly smart, bias-aware target selection.
414 float turret_stdproc_targetscore_generic(entity _turret, entity _target);
415 /// Experimental supportunits targetselector
416 float turret_stdproc_targetscore_support(entity _turret,entity _target);
421 /// Generic aimer guided by self.aim_flags
422 vector turret_stdproc_aim_generic();
425 * Turret turning & pitch
427 /// Tries to line up the turret head with the aimpos
428 void turret_stdproc_track();
430 /// Generic damage handeling. blows up the turret when health <= 0
431 void turret_stdproc_damage (entity inflictor, entity attacker, float damage, float deathtype, vector hitloc, vector vforce);
432 /// Spawns a explotion, does some damage & trows bits arround.
433 void turret_stdproc_die();
434 /// reassembles the turret.
435 void turret_stdproc_respawn();
437 /// Evaluate target validity
438 float turret_validate_target(entity e_turret,entity e_target,float validate_flags);
439 /// Turret Head Angle Diff Vector. updated by a sucsessfull call to turret_validate_target
441 /// Turret Angle Diff Vector. updated by a sucsessfull call to turret_validate_target
443 /// Turret Head Angle Diff Float. updated by a sucsessfull call to turret_validate_target
445 /// Turret Angle Diff Float. updated by a sucsessfull call to turret_validate_target
447 /// Distance. updated by a sucsessfull call to turret_validate_target
450 /// updates aim org, shot org, shot dir and enemy org for selected turret
451 void turret_do_updates(entity e_turret);
452 .vector tur_shotdir_updated;
454 void turrets_precash();
459 float TID_EWHEEL = 1;
461 float TID_FUSION = 3;
462 float TID_HELLION = 4;
464 float TID_MACHINEGUN = 6;
466 float TID_PHASER = 8;
467 float TID_PLASMA = 9;
468 float TID_PLASMA_DUAL = 10;
469 float TID_TESLA = 11;
470 float TID_WALKER = 12;
473 float TNSF_UPDATE = 2;
474 float TNSF_STATUS = 4;
475 float TNSF_SETUP = 8;
477 float TNSF_AVEL = 32;
478 float TNSF_FULL_UPDATE = 16777215;
480 #endif // TTURRETS_ENABLED