QuakeWiki
January 7, 2011

Hit Location System

This is the source code to MauveBib’s hit location system. When used, this code makes weapons do more or less damage to the victims depending on where on the body they hit.

[c]/*
—————————————————————————

HIT LOCATION SYSTEM

Author:                 MauveBib

Email:                  skinski@email.com

Website:                http://www.planetquake.com/elf

Version:                2.0
23.5.99

I n s t r u c t i o n s

This is the source code to my hit location system.
When used, this code makes weapons do more or less
damage to the victims depending on where on the body
they hit. The damage factors are listed below :-

Chest –          Normal damage
Front of legs –  25% of normal damage
Face –           200% of normal damage
Back –           150% of normal damage
Back of legs –   37% of normal damage
Back of head –   300% of normal damage

To add and use this code in a mod, follow the following
instructions :-

1. Open up the PROGS.SRC file, and insert the words "hitloc.qc"
without quotes after the words "subs.qc"

2. Open up WEAPONS.QC and scroll down to one of the weapon
damage routines. This only works with weapons that use
T_Damage, not T_RadiusDamage. Just before the
T_Damage line, add one of the following lines:

hit_loc = HitLocation(trace_ent, trace_endpos);

hit_loc = HitLocation(other, self.origin);

Use the first line if the weapon is a direct trace weapon, e.g.
axe, shotgun, lightning. If the weapon is a projectile
one, e.g. nailgun, rocket launcher, then use the second
line.

Then, edit the T_Damage line in the following way. Just before
the final bracket, add " * hit_loc" excluding the speech
marks. Here is an example for a nailgun:-

hit_loc = HitLocation(other, self.origin);
T_Damage (other, self, self.owner, 9 * hit_loc);

3. Compile as you normally would and enjoy.

This code is totally public domain. Do with it as you will.

—————————————————————————
*/

float(entity bloke) backshot =
{

//  You won’t need to edit this routine. It checks whether or not the
//  target was hit on the front or the back. It returns TRUE if the
//  target was hit on the back.

local float result;
local vector veca, vecb;

if (bloke.classname == "player")
makevectors(bloke.v_angle);
else
makevectors(bloke.angles);
veca = v_right;
if (self.classname == "player")
makevectors(self.v_angle);
else
makevectors(self.angles);
vecb = v_forward;
result = (veca_x * vecb_y) – (vecb_x * veca_y);
if (result > 0)
return TRUE;
};

float (entity poorguy, vector org) HitLocation =
{

// This is the main hit location routine

local vector f, g, h;
local float x, zdif, pain;
if (
// Doesn’t (yet?) work on these creatures properly
// Insert in here any other non-humanoid shaped monsters
// in your mod, so it will understand not to use the
// hit location code on them.

(poorguy.classname != "monster_fish") &&
(poorguy.classname != "monster_demon1") &&
(poorguy.classname != "monster_shalrath") &&
(poorguy.classname != "monster_tarbaby") &&
(poorguy.classname != "monster_oldone") &&
(poorguy.classname != "monster_dog") &&

// And, of course, not on secret doors and shootable triggers

( (poorguy.flags & FL_MONSTER) ||
(poorguy.classname == "player") ||
(poorguy.flags & FL_CLIENT) ||

// But it does work on crucified zombies (don’t count as monsters)

(poorguy.classname == "monster_zombie") )
)
{

//  This is the main hit location code. I’m not sure if some of
//  it is redundant. If I get round to testing it, I’ll release
//  a more efficient version.

g = org;
g_z = 0;
h = poorguy.origin;
h_z = 0;
x = vlen ((g – h));
f = ((normalize (f) * x) + org);
zdif = (f_z – poorguy.origin_z);
if ( (zdif < 0) &&

//  A wizard obviously can’t be shot in the leg. Change this if it
//  conflicts with your mod.

(poorguy.classname != "monster_wizard") )
{
//            sprint(self.owner, "Leg shot!\n");
// leg = 25%
pain = 0.25;                 // Leg
}
else if ( (zdif > 20) &&

//  Shamblers are taller than most people. Again, change if you
//  need to.

(poorguy.classname != "monster_shambler") )
{
//            sprint(self.owner, "Head shot!\n");
// head = 200%
pain = 2;                 // Head
}
else if ( (zdif > 35) &&
(poorguy.classname == "monster_shambler") )
{
//            sprint(self.owner, "Head shot!\n");
// smambler head = 200%
pain = 2;                 // Shambler head
}
}
if (!pain)
// chest = 100%
pain = 1;

if (backshot(poorguy))
// All back hits do an extra 50% on top.
pain = pain * 1.5;

return pain;
};[/c]

Post a Comment

1 Comment

  1. […] detection" Surely you heard about this. I remembered this very complex QC code from MauveBib: click me He brought the "hit location system" to Quake. I meant this code, as I replied to gdiddy […]

    comment-bottom

Sorry, the comment form is closed at this time.