]> de.git.xonotic.org Git - xonotic/xonotic-data.pk3dir.git/commitdiff
Attempt (once again) to implement constant player damage effects. eg: If the player...
authorMircea Kitsune <sonichedgehog_hyperblast00@yahoo.com>
Sat, 2 Apr 2011 15:07:26 +0000 (18:07 +0300)
committerMircea Kitsune <sonichedgehog_hyperblast00@yahoo.com>
Sat, 2 Apr 2011 15:07:26 +0000 (18:07 +0300)
How it works: It uses the same system as blood and gibs. When the player is damaged, the server creates an entity that will constantly send a client entity with info (such as origin and damage weapon). The client then receives it, and spawns particles at the player's origin each time the entity is sent. Once the lifetime of the server-side sender expires, the effect stops. The reason the repeater can't be client side is because we can't track an individual player's origin there (or at least not that I know of).

qcsrc/client/Main.qc
qcsrc/client/gibs.qc
qcsrc/common/constants.qh
qcsrc/server/g_damage.qc
qcsrc/server/g_violence.qc

index 91ce464793bcbc0f33879a90222c2934165fdb3a..325cc409d3e7ab772ef05bb5f5618fbdfab76846 100644 (file)
@@ -967,6 +967,7 @@ void(float bIsNewEntity) CSQC_Ent_Update =
                case ENT_CLIENT_LGBEAM: Ent_ReadHook(bIsNewEntity, ENT_CLIENT_LGBEAM); break;
                case ENT_CLIENT_GAUNTLET: Ent_ReadHook(bIsNewEntity, ENT_CLIENT_GAUNTLET); break;
                case ENT_CLIENT_ACCURACY: Ent_ReadAccuracy(); break;
+               case ENT_CLIENT_WEAPONDAMAGE: Ent_WeaponDamage(); break;
                default:
                        error(strcat(_("unknown entity type in CSQC_Ent_Update: %d\n"), self.enttype));
                        break;
index 1f8af46ca16c4178284485bfa93626b416506968..a6520d53d80e0bfb86946689a5f8488afa3bde2b 100644 (file)
@@ -274,3 +274,19 @@ void GibSplash_Precache()
     precache_sound ("misc/gib_splat03.wav");
     precache_sound ("misc/gib_splat04.wav");
 }
+
+void Ent_WeaponDamage()
+{
+       float type, specnum1, specnum2;
+       vector org;
+       string specstr;
+
+       type = ReadByte(); // damage weapon
+       specnum1 = ReadByte(); // player species
+       org_x = ReadCoord();
+       org_y = ReadCoord();
+       org_z = ReadCoord();
+
+       specnum2 = (specnum1 & 0x78) / 8; // blood type: using four bits (0..7, bit indexes 3,4,5)
+       specstr = species_prefix(specnum2);
+}
index 419ab73e8fa1b8e14d21f44afca79f7775e0936b..141ff000be26eea4fdcdcaa38c76193522ea6471 100644 (file)
@@ -113,6 +113,7 @@ const float ENT_CLIENT_HOOK = 27;
 const float ENT_CLIENT_LGBEAM = 28;
 const float ENT_CLIENT_GAUNTLET = 29;
 const float ENT_CLIENT_ACCURACY = 30;
+const float ENT_CLIENT_WEAPONDAMAGE = 31;
 
 const float ENT_CLIENT_TURRET = 40;
 
index 29fc297d5ef8c92e6dbfe822d6fb4aa37f280102..b062ec32a7741231f210bed59393a2d0c71dc59a 100644 (file)
@@ -497,6 +497,8 @@ entity damage_attacker;
 
 void Damage (entity targ, entity inflictor, entity attacker, float damage, float deathtype, vector hitloc, vector force)
 {
+       dprint(strcat(ftos(DEATH_WEAPONOF(deathtype)), "--\n"));
+
        float mirrordamage;
        float mirrorforce;
        float teamdamage0;
index f5def6a7dd68e4dd9660d62f4a1d7811372509bc..ba1ae0d9c8df844a3978477532dda49b0a0da779 100644 (file)
@@ -37,3 +37,59 @@ void Violence_GibSplash(entity source, float type, float amount, entity attacker
 {
        Violence_GibSplash_At(source.origin + source.view_ofs, source.velocity, type, amount, source, attacker);
 }
+
+float Violence_WeaponDamage_SendEntity(entity to, float sf)
+{
+       WriteByte(MSG_ENTITY, ENT_CLIENT_WEAPONDAMAGE);
+       WriteByte(MSG_ENTITY, self.cnt); // the damage weapon
+       WriteByte(MSG_ENTITY, self.state); // species
+       WriteCoord(MSG_ENTITY, floor(self.origin_x));
+       WriteCoord(MSG_ENTITY, floor(self.origin_y));
+       WriteCoord(MSG_ENTITY, floor(self.origin_z));
+       return TRUE;
+}
+
+void Violence_WeaponDamage(entity pl, float type)
+{
+       entity e;
+
+       e = spawn();
+       e.classname = "weapondamage";
+       e.cnt = type;
+       e.state |= 8 * pl.species; // gib type, ranges from 0 to 15
+       setorigin(e, pl.origin);
+
+       Net_LinkEntity(e, FALSE, 0.2, Violence_WeaponDamage_SendEntity);
+}
+
+.float lifetime;
+.float weapondamage_counter;
+
+void Violence_WeaponDamage_DoRepeat()
+{
+       if(time > self.lifetime)
+       {
+               self.nextthink = 0;
+               remove(self);
+               return;
+       }
+
+       if(time > self.weapondamage_counter)
+       {
+               Violence_WeaponDamage(self.owner, self.cnt);
+               self.weapondamage_counter = time + 0.5; // TO BE CVARED
+       }
+}
+
+void Violence_WeaponDamage_SetRepeat(entity pl, float type)
+{
+       entity repeater;
+       repeater = spawn();
+       repeater.classname = "weapondamage_repeater";
+       repeater.owner = pl;
+       repeater.origin = pl.origin;
+       repeater.cnt = type;
+       repeater.lifetime = time + 3; // TO BE CVARED
+       repeater.think = Violence_WeaponDamage_DoRepeat;
+       repeater.nextthink = time;
+}