X-Git-Url: http://de.git.xonotic.org/?a=blobdiff_plain;f=qcsrc%2Fserver%2Fw_crylink.qc;h=bb44e827e709cd0eb84e37bdf04c361179055e45;hb=64b6c7420b3e1c307f408a9f17d9c765a268621a;hp=0b3118bb606cea52a6c5115e5bf437ea0a313b6e;hpb=74a82a7354648fcc2698c19afc0581f7bdc3b1ca;p=xonotic%2Fxonotic-data.pk3dir.git diff --git a/qcsrc/server/w_crylink.qc b/qcsrc/server/w_crylink.qc index 0b3118bb6..bb44e827e 100644 --- a/qcsrc/server/w_crylink.qc +++ b/qcsrc/server/w_crylink.qc @@ -133,6 +133,7 @@ vector W_Crylink_LinkJoin(entity e, float jspeed, float jtime) p.velocity = WarpZone_RefSys_TransformVelocity(e, p, avg_velocity); UpdateCSQCProjectile(p); } + targ_origin = avg_origin + 1000000000 * normalize(avg_velocity); // HUUUUUUGE } else { @@ -224,6 +225,28 @@ void W_Crylink_LinkJoinEffect_Think() remove(self); } +float W_Crylink_Touch_WouldHitFriendly(entity projectile, float rad) +{ + entity head = WarpZone_FindRadius((projectile.origin + (projectile.mins + projectile.maxs) * 0.5), rad + MAX_DAMAGEEXTRARADIUS, FALSE); + float hit_friendly; + float hit_enemy; + + while(head) + { + if((head.takedamage != DAMAGE_NO) && (head.deadflag == DEAD_NO)) + { + if(IsDifferentTeam(head, projectile.realowner)) + ++hit_enemy; + else + ++hit_friendly; + } + + head = head.chain; + } + + return (hit_enemy ? FALSE : hit_friendly); +} + // NO bounce protection, as bounces are limited! void W_Crylink_Touch (void) { @@ -241,7 +264,10 @@ void W_Crylink_Touch (void) f = autocvar_g_balance_crylink_primary_bouncedamagefactor; if(a) f *= a; - if (RadiusDamage (self, self.realowner, autocvar_g_balance_crylink_primary_damage * f, autocvar_g_balance_crylink_primary_edgedamage * f, autocvar_g_balance_crylink_primary_radius, world, autocvar_g_balance_crylink_primary_force * f, self.projectiledeathtype, other) && autocvar_g_balance_crylink_primary_linkexplode) + + float totaldamage = RadiusDamage(self, self.realowner, autocvar_g_balance_crylink_primary_damage * f, autocvar_g_balance_crylink_primary_edgedamage * f, autocvar_g_balance_crylink_primary_radius, world, autocvar_g_balance_crylink_primary_force * f, self.projectiledeathtype, other); + + if(totaldamage && ((autocvar_g_balance_crylink_primary_linkexplode == 2) || ((autocvar_g_balance_crylink_primary_linkexplode == 1) && !W_Crylink_Touch_WouldHitFriendly(self, autocvar_g_balance_crylink_primary_radius)))) { if(self == self.realowner.crylink_lastgroup) self.realowner.crylink_lastgroup = world; @@ -282,7 +308,10 @@ void W_Crylink_Touch2 (void) f = autocvar_g_balance_crylink_secondary_bouncedamagefactor; if(a) f *= a; - if (RadiusDamage (self, self.realowner, autocvar_g_balance_crylink_secondary_damage * f, autocvar_g_balance_crylink_secondary_edgedamage * f, autocvar_g_balance_crylink_secondary_radius, world, autocvar_g_balance_crylink_secondary_force * f, self.projectiledeathtype, other) && autocvar_g_balance_crylink_secondary_linkexplode) + + float totaldamage = RadiusDamage(self, self.realowner, autocvar_g_balance_crylink_secondary_damage * f, autocvar_g_balance_crylink_secondary_edgedamage * f, autocvar_g_balance_crylink_secondary_radius, world, autocvar_g_balance_crylink_secondary_force * f, self.projectiledeathtype, other); + + if(totaldamage && ((autocvar_g_balance_crylink_secondary_linkexplode == 2) || ((autocvar_g_balance_crylink_secondary_linkexplode == 1) && !W_Crylink_Touch_WouldHitFriendly(self, autocvar_g_balance_crylink_secondary_radius)))) { if(self == self.realowner.crylink_lastgroup) self.realowner.crylink_lastgroup = world; @@ -335,8 +364,8 @@ void W_Crylink_Attack (void) shots = autocvar_g_balance_crylink_primary_shots; pointparticles(particleeffectnum("crylink_muzzleflash"), w_shotorg, w_shotdir * 1000, shots); - proj = world; - while (counter < shots) + proj = prevproj = firstproj = world; + for(counter = 0; counter < shots; ++counter) { proj = spawn (); proj.reset = W_Crylink_Reset; @@ -408,12 +437,11 @@ void W_Crylink_Attack (void) //proj.glow_size = 20; proj.flags = FL_PROJECTILE; - + proj.missile_flags = MIF_SPLASH; + CSQCProjectile(proj, TRUE, (proj.cnt ? PROJECTILE_CRYLINK_BOUNCING : PROJECTILE_CRYLINK), TRUE); other = proj; MUTATOR_CALLHOOK(EditProjectile); - - counter = counter + 1; } if(autocvar_g_balance_crylink_primary_joinspread != 0 || autocvar_g_balance_crylink_primary_jointime != 0) { @@ -427,6 +455,8 @@ void W_Crylink_Attack2 (void) { float counter, shots; entity proj, prevproj, firstproj; + vector s; + vector forward, right, up; float maxdmg; W_DecreaseAmmo(ammo_cells, autocvar_g_balance_crylink_secondary_ammo, autocvar_g_balance_crylink_reload_ammo); @@ -437,11 +467,14 @@ void W_Crylink_Attack2 (void) maxdmg += autocvar_g_balance_crylink_secondary_joinexplode_damage; W_SetupShot (self, FALSE, 2, "weapons/crylink_fire2.wav", CH_WEAPON_A, maxdmg); + forward = v_forward; + right = v_right; + up = v_up; shots = autocvar_g_balance_crylink_secondary_shots; pointparticles(particleeffectnum("crylink_muzzleflash"), w_shotorg, w_shotdir * 1000, shots); - proj = world; - while (counter < shots) + proj = prevproj = firstproj = world; + for(counter = 0; counter < shots; ++counter) { proj = spawn (); proj.reset = W_Crylink_Reset; @@ -477,7 +510,26 @@ void W_Crylink_Attack2 (void) setorigin (proj, w_shotorg); setsize(proj, '0 0 0', '0 0 0'); - W_SetupProjectileVelocityEx(proj, (w_shotdir + (((counter + 0.5) / shots) * 2 - 1) * v_right * autocvar_g_balance_crylink_secondary_spread * g_weaponspreadfactor), v_up, autocvar_g_balance_crylink_secondary_speed, 0, 0, 0, FALSE); + if(autocvar_g_balance_crylink_secondary_spreadtype == 1) + { + s = '0 0 0'; + if (counter == 0) + s = '0 0 0'; + else + { + makevectors('0 360 0' * (0.75 + (counter - 0.5) / (shots - 1))); + s_y = v_forward_x; + s_z = v_forward_y; + } + s = s * autocvar_g_balance_crylink_secondary_spread * g_weaponspreadfactor; + s = w_shotdir + right * s_y + up * s_z; + } + else + { + s = (w_shotdir + (((counter + 0.5) / shots) * 2 - 1) * v_right * autocvar_g_balance_crylink_secondary_spread * g_weaponspreadfactor); + } + + W_SetupProjectileVelocityEx(proj, s, v_up, autocvar_g_balance_crylink_secondary_speed, 0, 0, 0, FALSE); proj.touch = W_Crylink_Touch2; proj.think = W_Crylink_Fadethink; if(counter == (shots - 1) / 2) @@ -501,12 +553,11 @@ void W_Crylink_Attack2 (void) //proj.glow_size = 20; proj.flags = FL_PROJECTILE; - + proj.missile_flags = MIF_SPLASH; + CSQCProjectile(proj, TRUE, (proj.cnt ? PROJECTILE_CRYLINK_BOUNCING : PROJECTILE_CRYLINK), TRUE); other = proj; MUTATOR_CALLHOOK(EditProjectile); - - counter = counter + 1; } if(autocvar_g_balance_crylink_secondary_joinspread != 0 || autocvar_g_balance_crylink_secondary_jointime != 0) {