Compare commits

..

49 Commits
dev ... master

Author SHA1 Message Date
54e83e826a Merge pull request 'update16' (#35) from update16 into master
Reviewed-on: https://insultplayers.ru/git/dkanus/NicePack/pulls/35
2024-11-27 20:00:56 +03:00
0333cfc171 Add first draft of new syringe 2024-11-27 23:01:43 +07:00
430debb99e Buff explosive damage by 50% against frozen targets 2024-11-27 04:03:56 +07:00
f54f0d40db Change Enforcer's finisher rounds skill to safeguard skill 2024-11-27 03:58:26 +07:00
ff720a6b7e Nerf SPAS12
Alt fire now consists of 8 pellets instead of 12
2024-11-27 03:39:00 +07:00
64e40d58c9 Buff M41A's stun capabilities 2024-11-27 03:28:32 +07:00
d9dce6a29d Change Enforcer's Bombard's description 2024-11-27 03:15:36 +07:00
d44a1a3555 Change SA80LSW's magazine size to 60 2024-11-27 03:12:15 +07:00
e1769e8048 Change enforcer's heavy rifles' balance via burst fire parameters
This patch dramatically reduces recoil on all guns and lets XMV850
accumulate way more damage that previously possible.
2024-11-27 03:06:31 +07:00
b3b107c8ec Buff boomstick 2024-11-27 02:17:05 +07:00
a3f4baabc6 Add limit to the damage from quad damage skill 2024-11-26 03:33:21 +07:00
4924e41e84 Merge pull request 'update15' (#34) from update15 into master
Reviewed-on: https://insultplayers.ru/git/dkanus/NicePack/pulls/34
2024-11-25 22:10:57 +03:00
3716813a7b Change cooldowns to only decrease on kills 2024-11-26 02:10:50 +07:00
501662a7d7 Fix harpoon badly attaching to some static meshes
Just needed to add proper computation of relative location, that takes
into account mesh's own rotation.
2024-10-30 03:21:47 +07:00
618229b8d3 Add distance to target limit for mean husks' spam
Husks now only spam fireballs in a rage when within 30 units of
their target. They’ll still keep track of the number of shots and
enter this enraged state regardless of distance, but close
proximity is required for rapid-fire.
2024-10-29 04:15:16 +07:00
324e644db4 Add mechanic that buffs clots from the siren's scream
Increase their speed by 50% and tankiness by not receving any body
damage upon decapitation while under the effects.
2024-10-29 03:57:46 +07:00
a003061d6d Add zeds changing moveTarget when in-fighting starts 2024-10-29 03:36:40 +07:00
8f5511e899 Add attack delay to Shivers right after teleport
Now shivers cannot attack for 0.5 seconds after teleporting, which
should help with them getting cheap shots on players.
2024-10-29 03:17:30 +07:00
8dc8f35b08 Remove Claw3 animation from Shiver 2024-10-29 03:00:45 +07:00
2384dc34d1 Remove Shivers' collision removal on teleport
This should hopefully remove any issues with them not taking any damage during teleport
2024-10-29 02:52:55 +07:00
0d87e12977 Changed brute textures to his old ones 2024-09-01 20:50:38 +07:00
3d0315b28b Change heat and fire damage calculations 2024-09-01 20:06:55 +07:00
da810d50f1 Fix unintended fire damage buffs 2024-09-01 18:10:17 +07:00
b4b3111440 Replace flat damage bonus to burning zeds with scorchmark mechanic 2024-09-01 17:59:26 +07:00
6eb879f0d1 Remove strict difference between mostly fire and non-fire damage sources 2024-09-01 17:27:29 +07:00
db84dad047 Merge pull request 'update12 + 13' (#32) from update12 into master
Reviewed-on: https://insultplayers.ru/git/dkanus/NicePack/pulls/32
2024-08-04 07:03:15 +03:00
99aac40182 Add update 13 to this branch 2024-08-04 10:56:50 +07:00
e79d49ce0d Change explosives mechanics 2024-04-23 23:24:56 +07:00
08c7d99de9 Merge pull request 'update11' (#31) from update11 into master
Reviewed-on: https://insultplayers.ru/git/dkanus/NicePack/pulls/31
2024-03-24 20:25:18 +03:00
0951574451 Add stopping power mechanic 2024-03-22 20:02:15 +07:00
1bc35cc348 Balance adjustments 2024-03-20 20:27:31 +07:00
87f60c9c60 Add visual counter for health regen from healing 2024-03-19 14:34:24 +07:00
2bf5f3dbe1 Fix healing messages not showing up when healed with medic dart 2024-03-19 13:51:38 +07:00
2ddd4a34f0 Merge pull request 'update10' (#30) from update10 into master
Reviewed-on: https://insultplayers.ru/git/dkanus/NicePack/pulls/30
2024-03-16 15:57:38 +03:00
8f1f36972b Add some variables for zeds' speed modifications 2024-03-16 16:15:56 +07:00
bc5774f3d6 Fix hunting rifle ammo cost 2024-03-16 16:15:30 +07:00
8ae4dac528 Buff nailgun 2024-03-16 16:15:13 +07:00
8fb84b9695 Fix Kriss' headshot damage multiplier 2024-03-16 16:14:50 +07:00
0e825e2111 Fix SMGs cost and amount values 2024-03-16 16:14:29 +07:00
bb8a283378 Decrease M41A grenade cost 2024-03-16 16:13:21 +07:00
4d50763bc3 Fix some of the commando ammo cost discrepancies 2024-03-16 16:12:23 +07:00
879dedcd7d Add dynamic spread to SMGs 2024-03-16 16:11:49 +07:00
ed4d67dc1c Move medic SMGs to demolitionist perk 2024-03-16 16:10:59 +07:00
796b699825 Add dynamic spread mechanic 2024-03-16 16:07:57 +07:00
f8cf67e117 Merge pull request 'Fix formatting #1' (#27) from harpoon into master
Reviewed-on: https://insultplayers.ru/git/dkanus/NicePack/pulls/27
2023-05-23 12:17:15 +03:00
bf53b53b31 Apply new formatting for NiceProjectileSpawner 2023-04-09 15:15:00 +04:00
78ca66acdd Apply new formatting for NiceBulletAdapter 2023-04-09 14:52:39 +04:00
3b5f46c2b5 Optimize code flow 2023-04-09 14:30:28 +04:00
2f3385583c Apply new formatting for NiceBullet 2023-04-09 01:35:25 +04:00
103 changed files with 2711 additions and 2121 deletions

View File

@ -107,6 +107,10 @@ function PostRender(Canvas C)
local int x, y, center, barWidth, offset; local int x, y, center, barWidth, offset;
local int missesWidth, missesHeight, missesSpace; local int missesWidth, missesHeight, missesSpace;
local int missesX, missesY; local int missesX, missesY;
local TeamInfo team;
local int healthToGive, totalExpectedHealth;
local float textWidth, textHeight;
local string textToDraw;
// local Vector CamPos, ViewDir; // local Vector CamPos, ViewDir;
// local Rotator CamRot; // local Rotator CamRot;
// local float OffsetX, BarLength, BarHeight, XL, YL, posY; // local float OffsetX, BarLength, BarHeight, XL, YL, posY;
@ -256,6 +260,47 @@ function PostRender(Canvas C)
} }
} }
//// Draw quad damage bar
if (nicePawn != none && nicePawn.quadDamageRemaining > 0.0)
{
C.SetDrawColor(255, 255, 255);
barTexture = redBar;
center = C.ClipX * 0.5;
y = C.ClipY * 0.45;
barWidth = C.ClipX * 0.2;
barWidth *= nicePawn.quadDamageRemaining / class'NiceSkillEnforcerBruteA'.default.maximumDamageAdded;
x = center - (barWidth / 2);
C.SetPos(x, y);
Log("DRAWING" @ x @ y @ barWidth);
C.DrawTile(barTexture, barWidth, 32, 0, 0, barTexture.MaterialUSize(), barTexture.MaterialVSize());
}//native(466) final function DrawTile( material Mat, float XL, float YL, float U, float V, float UL, float VL );
team = C.ViewPort.Actor.Pawn.PlayerReplicationInfo.Team;
//// Draw health still in regen timer
healthToGive = ScrnHumanPawn(C.ViewPort.Actor.Pawn).clientHealthToGive;
if (healthToGive > 0) {
totalExpectedHealth = healthToGive + C.ViewPort.Actor.Pawn.health;;
C.Font = class'ROHUD'.Static.LoadSmallFontStatic(3);
if (totalExpectedHealth >= C.ViewPort.Actor.Pawn.healthMax) {
if(team.teamIndex == 0) {
C.SetDrawColor(255, 64, 64);
}
else {
C.SetDrawColor(
team.teamColor.R,
team.teamColor.G,
team.teamColor.B);
}
}
else {
C.SetDrawColor(128, 128, 128);
}
textToDraw = "+" $ healthToGive;
C.TextSize(textToDraw, textWidth, textHeight);
C.SetPos(C.ClipX * 0.05, C.ClipY * 0.9);
C.DrawText(textToDraw);
}
//// Draw cooldowns //// Draw cooldowns
if (nicePlayer.abilityManager == none) if (nicePlayer.abilityManager == none)
return; return;
@ -273,7 +318,7 @@ function PostRender(Canvas C)
{ {
if (niceMutator.niceCounterSet[i].value != 0 || niceMutator.niceCounterSet[i].bShowZeroValue) if (niceMutator.niceCounterSet[i].value != 0 || niceMutator.niceCounterSet[i].bShowZeroValue)
{ {
DrawCounter(C, niceMutator.niceCounterSet[i], x, y, C.ViewPort.Actor.Pawn.PlayerReplicationInfo.Team); DrawCounter(C, niceMutator.niceCounterSet[i], x, y, team);
x += 128 + 4; x += 128 + 4;
} }
} }
@ -283,7 +328,7 @@ function PostRender(Canvas C)
function DrawCounter(Canvas C, NicePack.CounterDisplay counter, int x, int y, TeamInfo team){ function DrawCounter(Canvas C, NicePack.CounterDisplay counter, int x, int y, TeamInfo team){
local float borderSpace; local float borderSpace;
local Texture textureToDraw; local Texture textureToDraw;
local float textWidth, textHeight; local float textWidth, textHeight;
local string textToDraw; local string textToDraw;
// Some per-defined values for drawing // Some per-defined values for drawing
local int iconSize, backgroundWidth, backgroundHeight; local int iconSize, backgroundWidth, backgroundHeight;
@ -320,7 +365,7 @@ function DrawAbilityCooldown(Canvas C, int abilityIndex){
local class<NiceVeterancyTypes> niceVet; local class<NiceVeterancyTypes> niceVet;
local int x, y; local int x, y;
local string textToDraw; local string textToDraw;
local float textWidth, textHeight; local float textWidth, textHeight;
local NiceAbilityManager.EAbilityState abilityState; local NiceAbilityManager.EAbilityState abilityState;
if(C == none) return; if(C == none) return;
if(C.ViewPort == none) return; if(C.ViewPort == none) return;

View File

@ -74,6 +74,8 @@ State MatchInProgress{
function ScoreKill(Controller Killer, Controller Other) function ScoreKill(Controller Killer, Controller Other)
{ {
local NicePlayerController niceKiller;
local NiceHumanPawn niceKillerPawn;
local PlayerReplicationInfo OtherPRI; local PlayerReplicationInfo OtherPRI;
local float KillScore; local float KillScore;
local Controller C; local Controller C;
@ -198,7 +200,15 @@ function ScoreKill(Controller Killer, Controller Other)
} }
/* End Marco's Kill Messages */ /* End Marco's Kill Messages */
niceKiller = NicePlayerController(killer);
if (niceKiller != none && niceKiller.abilityManager != none) {
niceKillerPawn = NiceHumanPawn(niceKiller.pawn);
niceKiller.abilityManager.AddToAllCooldowns(-1);
}
if ( niceKillerPawn != none && NiceBoomStick(niceKillerPawn.weapon) != none
&& other != none && other.pawn != none && other.pawn.default.health >= 1000) {
niceKillerPawn.invincibilityTimer += 1.0;
}
} }
function DramaticEvent(float BaseZedTimePossibility, optional float DesiredZedTimeDuration){ function DramaticEvent(float BaseZedTimePossibility, optional float DesiredZedTimeDuration){

View File

@ -46,10 +46,11 @@ struct InvincExtentions{
var array<InvincExtentions> zedInvExtList; var array<InvincExtentions> zedInvExtList;
var int headshotStack; var int headshotStack;
var float bruteTimer; var float bruteTimer;
var float quadDamageRemaining;
replication{ replication{
reliable if(Role == ROLE_Authority) reliable if(Role == ROLE_Authority)
headshotStack, hmgShieldLevel, forcedZedTimeCountDown, maniacTimeout, invincibilityTimer, safeMeleeMisses, ffScale, headshotStack, hmgShieldLevel, forcedZedTimeCountDown, maniacTimeout, invincibilityTimer, safeMeleeMisses, ffScale,
currentCalibrationState, calibrationScore, gunslingerTimer; currentCalibrationState, calibrationScore, gunslingerTimer, quadDamageRemaining;
reliable if(Role == ROLE_Authority) reliable if(Role == ROLE_Authority)
ClientChangeWeapon; ClientChangeWeapon;
reliable if(Role < ROLE_AUTHORITY) reliable if(Role < ROLE_AUTHORITY)
@ -69,7 +70,7 @@ function ReplaceRequiredEquipment()
RequiredEquipment[0] = string(class'NiceMachete'); RequiredEquipment[0] = string(class'NiceMachete');
RequiredEquipment[1] = string(class'Nice9mmPlus'); RequiredEquipment[1] = string(class'Nice9mmPlus');
RequiredEquipment[2] = string(class'ScrnFrag'); RequiredEquipment[2] = string(class'ScrnFrag');
RequiredEquipment[3] = string(class'NiceSyringe'); RequiredEquipment[3] = string(class'ScrnSyringe');
RequiredEquipment[4] = string(class'KFMod.Welder'); RequiredEquipment[4] = string(class'KFMod.Welder');
} }
@ -420,10 +421,10 @@ function ServerBuyWeapon(class<Weapon> WClass, float ItemWeight){
Price = WP.Default.Cost; Price = WP.Default.Cost;
if(KFPlayerReplicationInfo(PlayerReplicationInfo).ClientVeteranSkill != none){ if(KFPlayerReplicationInfo(PlayerReplicationInfo).ClientVeteranSkill != none){
Price *= KFPlayerReplicationInfo(PlayerReplicationInfo).ClientVeteranSkill.static.GetCostScaling(KFPlayerReplicationInfo(PlayerReplicationInfo), WP); Price *= KFPlayerReplicationInfo(PlayerReplicationInfo).ClientVeteranSkill.static.GetCostScaling(KFPlayerReplicationInfo(PlayerReplicationInfo), WP);
if(class'ScrnBalance'.default.Mut.bBuyPerkedWeaponsOnly if(class'ScrnBalance'.default.Mut.bBuyPerkedWeaponsOnly
&& WP.default.CorrespondingPerkIndex != 7 && WP.default.CorrespondingPerkIndex != 7
&& WP.default.CorrespondingPerkIndex != KFPlayerReplicationInfo(PlayerReplicationInfo).ClientVeteranSkill.default.PerkIndex ) && WP.default.CorrespondingPerkIndex != KFPlayerReplicationInfo(PlayerReplicationInfo).ClientVeteranSkill.default.PerkIndex )
return; return;
} }
SellValue = Price * 0.75; SellValue = Price * 0.75;
Price = int(Price); Price = int(Price);
@ -507,11 +508,11 @@ function bool AddInventory(inventory NewItem){
if(weap != none){ if(weap != none){
if(Dualies(weap) != none){ if(Dualies(weap) != none){
if((DualDeagle(weap) != none || Dual44Magnum(weap) != none || DualMK23Pistol(weap) != none) if((DualDeagle(weap) != none || Dual44Magnum(weap) != none || DualMK23Pistol(weap) != none)
&& weap.InventoryGroup != 4 ) { && weap.InventoryGroup != 4 ) {
if(KFPRI != none && if(KFPRI != none &&
ClassIsChildOf(KFPRI.ClientVeteranSkill, class'ScrnVetGunslinger')) ClassIsChildOf(KFPRI.ClientVeteranSkill, class'ScrnVetGunslinger'))
weap.InventoryGroup = 3; weap.InventoryGroup = 3;
else else
weap.InventoryGroup = 2; weap.InventoryGroup = 2;
GroupChanged = true; GroupChanged = true;
} }
@ -521,7 +522,7 @@ function bool AddInventory(inventory NewItem){
} }
weap.bIsTier3Weapon = true; weap.bIsTier3Weapon = true;
} }
if(GroupChanged) if(GroupChanged)
ClientSetInventoryGroup(NewItem.class, NewItem.InventoryGroup); ClientSetInventoryGroup(NewItem.class, NewItem.InventoryGroup);
if(super(SRHumanPawn).AddInventory(NewItem)){ if(super(SRHumanPawn).AddInventory(NewItem)){
if(weap != none && weap.bTorchEnabled) if(weap != none && weap.bTorchEnabled)
@ -568,7 +569,7 @@ simulated function ThrowGrenade()
super.ThrowGrenade(); super.ThrowGrenade();
return; return;
} }
if(playerGrenade == none) if(playerGrenade == none)
playerGrenade = FindPlayerGrenade(); playerGrenade = FindPlayerGrenade();
if(playerGrenade != none && playerGrenade.HasAmmo()){ if(playerGrenade != none && playerGrenade.HasAmmo()){
@ -650,7 +651,7 @@ simulated function ApplyWeaponStats(Weapon NewWeapon){
InventorySpeedModifier += default.GroundSpeed * (8 - weaponWeight) * 0.025; InventorySpeedModifier += default.GroundSpeed * (8 - weaponWeight) * 0.025;
// ScrN Armor can slow down players (or even boost) -- PooSH // ScrN Armor can slow down players (or even boost) -- PooSH
InventorySpeedModifier -= default.GroundSpeed * GetCurrentVestClass().default.SpeedModifier; InventorySpeedModifier -= default.GroundSpeed * GetCurrentVestClass().default.SpeedModifier;
} }
} }
simulated function ModifyVelocity(float DeltaTime, vector OldVelocity){ simulated function ModifyVelocity(float DeltaTime, vector OldVelocity){
local NicePack NicePackMutator; local NicePack NicePackMutator;
@ -699,7 +700,7 @@ simulated function ModifyVelocity(float DeltaTime, vector OldVelocity){
GroundSpeed = StoryInv.ForcedGroundSpeed; GroundSpeed = StoryInv.ForcedGroundSpeed;
return; return;
} }
} }
if(bTraderSpeedBoost && !KFGameReplicationInfo(Level.GRI).bWaveInProgress) if(bTraderSpeedBoost && !KFGameReplicationInfo(Level.GRI).bWaveInProgress)
MovementMod *= TraderSpeedBoost; MovementMod *= TraderSpeedBoost;
if(Health < HealthMax && medicAdrenaliteTime > 0){ if(Health < HealthMax && medicAdrenaliteTime > 0){
@ -736,6 +737,7 @@ simulated function TakeDamage(int Damage, Pawn InstigatedBy, Vector Hitlocation,
local float healPotency; local float healPotency;
local bool bOldArmorStops; local bool bOldArmorStops;
local float adrResistance; local float adrResistance;
local float oldHealthToGive;
local NicePlayerController nicePlayer; local NicePlayerController nicePlayer;
ApplyWeaponStats(Weapon); ApplyWeaponStats(Weapon);
if(invincibilityTimer > 0) if(invincibilityTimer > 0)
@ -766,7 +768,12 @@ simulated function TakeDamage(int Damage, Pawn InstigatedBy, Vector Hitlocation,
damageType.default.bArmorStops = true; damageType.default.bArmorStops = true;
} }
lastExplosionDistance = 0.0; // hack, but scrn fucks with usotherwise lastExplosionDistance = 0.0; // hack, but scrn fucks with usotherwise
oldHealthToGive = healthToGive; // remember this to restore this value, in case we are using safeguard skill
super.TakeDamage(Damage, InstigatedBy, hitLocation, Momentum, damageType, HitIndex); super.TakeDamage(Damage, InstigatedBy, hitLocation, Momentum, damageType, HitIndex);
if (class'NiceVeterancyTypes'.static.HasSkill(nicePlayer, class'NiceSkillHeavySafeguard')) {
healthToGive = oldHealthToGive;
clientHealthToGive = healthToGive;
}
// Commando's zed time // Commando's zed time
if( forcedZedTimeCountDown <= 0.0 if( forcedZedTimeCountDown <= 0.0
&& health < class'NiceSkillCommandoCriticalFocus'.default.healthBoundary && KFGameType(Level.Game) != none && health < class'NiceSkillCommandoCriticalFocus'.default.healthBoundary && KFGameType(Level.Game) != none
@ -789,7 +796,7 @@ simulated function TakeDamage(int Damage, Pawn InstigatedBy, Vector Hitlocation,
if(ShieldStrength < 0) if(ShieldStrength < 0)
ShieldStrength = 0; ShieldStrength = 0;
health += HealAmount * 0.5; health += HealAmount * 0.5;
TakeHealing(self, HealAmount * 0.5, HealPotency); TakeHealing(self, HealAmount * 0.5 + 1, HealPotency);
} }
if(ShieldStrength <= 0) if(ShieldStrength <= 0)
getFreeJacket(); getFreeJacket();

View File

@ -212,20 +212,6 @@ simulated function ClientPostLogin(){
// Change HUD parameters // Change HUD parameters
class'ScrnHUD'.default.EnemyHealthBarHeight = 4.0; class'ScrnHUD'.default.EnemyHealthBarHeight = 4.0;
} }
// fix crooked camera after you die with active `ViewShake`
function StopViewShaking() {
ShakeRotMax = vect(0, 0, 0);
ShakeRotRate = vect(0, 0, 0);
ShakeRotTime = vect(0, 0, 0);
ShakeOffsetMax = vect(0, 0, 0);
ShakeOffsetRate = vect(0, 0, 0);
ShakeOffsetTime = vect(0, 0, 0);
// add missing variables
ShakeOffset = vect(0, 0, 0);
ShakeRot = Rot(0, 0, 0);
}
function ShowLobbyMenu(){ function ShowLobbyMenu(){
Super.ShowLobbyMenu(); Super.ShowLobbyMenu();
} }
@ -1239,7 +1225,7 @@ function LoadDualWieldables(){
local class<NiceWeaponPickup> WP; local class<NiceWeaponPickup> WP;
local class<NiceSingle> W; local class<NiceSingle> W;
local int i; local int i;
CPRL = class'ClientPerkRepLink'.Static.FindStats(self); CPRL = class'ClientPerkRepLink'.Static.FindStats(self);
if(CPRL == none || CPRL.ShopInventory.Length == 0) if(CPRL == none || CPRL.ShopInventory.Length == 0)
return; return;

View File

@ -71,6 +71,7 @@ simulated function CalculateDamageScales( out float scale1, out float scale2,
local Vector victimPoint1, victimPoint2; local Vector victimPoint1, victimPoint2;
local float swap; local float swap;
victimPoint1 = victim.location; victimPoint1 = victim.location;
victimPoint2.z += victim.CollisionHeight * 0.25;
victimPoint2 = victim.location; victimPoint2 = victim.location;
victimPoint2.z += victim.CollisionHeight * 0.75; victimPoint2.z += victim.CollisionHeight * 0.75;
scale1 = GetDamageScale(victim, explosionLocation, victimPoint1, scale1 = GetDamageScale(victim, explosionLocation, victimPoint1,
@ -93,40 +94,55 @@ simulated function ServerExplode
float momentum, float momentum,
Vector explLocation, Vector explLocation,
Pawn instigator, Pawn instigator,
optional bool allowDoubleExplosion,
optional Actor explosionTarget, optional Actor explosionTarget,
optional vector explosiveDirection optional vector explosiveDirection,
optional bool preventProximityHeadDamage
){ ){
local Actor victim; local Actor victim;
local int numKilled; local int numKilled;
local Vector dirToVictim; local Vector dirToVictim;
local Vector hitLocation; local Vector hitLocation;
local float scale1, scale2; local float scale1, scale2;
local NiceMonster niceVictim;
if(Role < ROLE_Authority) return; if(Role < ROLE_Authority) return;
foreach VisibleActors(class'Actor', victim, explRadius, explLocation){ foreach VisibleActors(class'Actor', victim, explRadius, explLocation){
if(victim == none || victim == self) continue; if(victim == none || victim == self) continue;
if(victim.role < ROLE_Authority) continue; if(victim.role < ROLE_Authority) continue;
if(ExtendedZCollision(victim) != none) continue; if(ExtendedZCollision(victim) != none) continue;
if(Trigger(victim) != none) continue; if(Trigger(victim) != none) continue;
dirToVictim = Normal(victim.location - explLocation);
hitLocation = victim.location - 0.5 * niceVictim = NiceMonster(victim);
(victim.collisionHeight + victim.collisionRadius) * dirToVictim; dirToVictim = Normal(victim.location - explLocation);
CalculateDamageScales( scale1, scale2, hitLocation = victim.location - 0.5 *
victim, explLocation, explRadius, explExp); (victim.collisionHeight + victim.collisionRadius) * dirToVictim;
// Deal main damage CalculateDamageScales( scale1, scale2,
if(scale1 > 0){ victim, explLocation, explRadius, explExp);
ServerDealDamage( victim, explDamage * scale1, instigator, // Deal head damage if explosion is close enough to the victim's head
hitLocation, scale1 * momentum * dirToVictim, if ( niceVictim != none && !preventProximityHeadDamage
explDmgType); && niceVictim.GetDistanceToHead(explLocation) <= explRadius * 0.1)
} {
// Deal secondary damage ServerDealDamage( victim, explDamage, instigator,
if(allowDoubleExplosion && victim != none && scale2 > 0){ hitLocation, 0.0 * dirToVictim,
ServerDealDamage( victim, explDamage * scale2, instigator, explDmgType, 0.5);
hitLocation, scale2 * momentum * dirToVictim, }
explDmgType); // Deal main damage
} if(scale1 > 0 || scale2 > 0) {
if(NiceMonster(victim) != none && NiceMonster(victim).health <= 0) ServerDealDamage(
numKilled ++; victim,
explDamage * FMax(scale1, scale2),
instigator,
hitLocation,
FMax(scale1, scale2) * momentum * dirToVictim,
explDmgType);
}
if(niceVictim != none) {
if (niceVictim.health <= 0) {
numKilled += 1;
}
else {
niceVictim.concussionCountdown = 10.0;
}
}
} }
if(numKilled >= 4) if(numKilled >= 4)
KFGameType(level.game).DramaticEvent(0.05); KFGameType(level.game).DramaticEvent(0.05);
@ -203,34 +219,45 @@ simulated function RemovePoisonAndBleed(NiceHumanPawn healed)
} }
// Tells server to heal given human pawn. // Tells server to heal given human pawn.
simulated function ServerHealTarget(NiceHumanPawn healed, float charPotency, simulated function ServerHealTarget(
Pawn instigator){ NiceHumanPawn healed,
float charPotency,
Pawn instigator
) {
local NiceHumanPawn healer; local NiceHumanPawn healer;
local PlayerController healedPC;
local KFPlayerReplicationInfo KFPRI; local KFPlayerReplicationInfo KFPRI;
local NiceMedicGun healingTool;
local float healTotal; local float healTotal;
local float healPotency; local float healPotency;
if(instigator == none || healed == none) return; if(instigator == none || healed == none) return;
if(healed.health <= 0 || healed.health >= healed.healthMax) return; if(healed.health <= 0 || healed.health >= healed.healthMax) return;
KFPRI = KFPlayerReplicationInfo(instigator.PlayerReplicationInfo); KFPRI = KFPlayerReplicationInfo(instigator.PlayerReplicationInfo);
if(KFPRI == none || KFPRI.ClientVeteranSkill == none) if(KFPRI == none || KFPRI.ClientVeteranSkill == none) return;
return;
healer = NiceHumanPawn(instigator); healer = NiceHumanPawn(instigator);
if(healer == none) if(healer == none) return;
return;
healingTool = NiceMedicGun(healer.weapon);
healPotency = KFPRI.ClientVeteranSkill.static.GetHealPotency(KFPRI); healPotency = KFPRI.ClientVeteranSkill.static.GetHealPotency(KFPRI);
healTotal = charPotency * healPotency; healTotal = charPotency * healPotency;
healer.AlphaAmount = 255; healer.AlphaAmount = 255;
if(NiceMedicGun(healer.weapon) != none) if(healingTool != none) {
NiceMedicGun(healer.weapon).ClientSuccessfulHeal(healer, healed); healingTool.ClientSuccessfulHeal(healer, healed);
if(healed.health >= healed.healthMax){ }
healedPC = PlayerController(healed.controller);
if(healedPC != none) {
healedPC.ClientMessage(
"You've been healed by" @ healer.GetPlayerName(),
'CriticalEvent');
}
if(healed.health >= healed.healthMax) {
healed.GiveHealth(healTotal, healed.healthMax); healed.GiveHealth(healTotal, healed.healthMax);
return; return;
} }
HandleNiceHealingMechanicsAndSkills(healer, healed, healPotency); HandleNiceHealingMechanicsAndSkills(healer, healed, healPotency);
if(healed.health < healed.healthMax){ if(healed.health < healed.healthMax) {
healed.TakeHealing( healed, healTotal, healPotency, healed.TakeHealing(healed, healTotal, healPotency, healingTool);
KFWeapon(instigator.weapon));
} }
RemovePoisonAndBleed(healed); RemovePoisonAndBleed(healed);
} }
@ -261,9 +288,6 @@ simulated function HandleNiceDamageMechanicsAndSkills
hasSkill(nicePlayer, class'NiceSkillCommandoTranquilizer'); hasSkill(nicePlayer, class'NiceSkillCommandoTranquilizer');
hasZEDFrenzy = class'NiceVeterancyTypes'.static. hasZEDFrenzy = class'NiceVeterancyTypes'.static.
hasSkill(nicePlayer, class'NiceSkillMedicZEDFrenzy'); hasSkill(nicePlayer, class'NiceSkillMedicZEDFrenzy');
// Medic's suppression
if(hasTranquilizer)
niceZed.mind = FMin(niceZed.mind, 0.5);
// Medic's frenzy // Medic's frenzy
if(hasZEDFrenzy && nicePlayer.IsZedTimeActive()){ if(hasZEDFrenzy && nicePlayer.IsZedTimeActive()){
niceZed.madnessCountDown = niceZed.madnessCountDown =
@ -310,7 +334,7 @@ simulated function UpdateMeleeInvincibility
nicePawn.TryExtendingInv(niceZed, false, headshotLevel > 0.0); nicePawn.TryExtendingInv(niceZed, false, headshotLevel > 0.0);
// Handle melee-cases // Handle melee-cases
if(mainTarget && class<niceDamageTypeVetBerserker>(damageType) != none) if(mainTarget && class<niceDamageTypeVetBerserker>(damageType) != none)
nicePawn.TryExtendingInv(niceZed, true, headshotLevel > 0.0); nicePawn.TryExtendingInv(niceZed, true, headshotLevel > 0.0);
nicePawn.ApplyWeaponStats(nicePawn.weapon); nicePawn.ApplyWeaponStats(nicePawn.weapon);
} }
simulated function UpdateArdour(bool isKill, NicePlayerController nicePlayer){ simulated function UpdateArdour(bool isKill, NicePlayerController nicePlayer){

View File

@ -128,7 +128,7 @@ function bool PreventDeath(Pawn Killed, Controller Killer, class<DamageType> dam
class'NiceSkillDemoReactiveArmor'.default.explExponent, class'NiceSkillDemoReactiveArmor'.default.explExponent,
class'NiceDamTypeDemoSafeExplosion', class'NiceDamTypeDemoSafeExplosion',
class'NiceSkillDemoReactiveArmor'.default.explMomentum, class'NiceSkillDemoReactiveArmor'.default.explMomentum,
killed.location, killed, true killed.location, killed
); );
return true; return true;
} }

View File

@ -29,19 +29,19 @@ struct NiceAbilityDescription{
// Image to be used as an ability's icon // Image to be used as an ability's icon
var Texture icon; var Texture icon;
// Default cooldown duration // Default cooldown duration
var float cooldownLength; var int cooldownLength;
// Can ability be canceled once activated? // Can ability be canceled once activated?
var bool canBeCancelled; var bool canBeCancelled;
}; };
// Complete description of current status of an ability, // Complete description of current status of an ability,
// including it's complete description. // including it's complete description.
struct NiceAbilityStatus{ struct NiceAbilityStatus{
// Complete description of ability in question // Complete description of ability in question
var NiceAbilityDescription description; var NiceAbilityDescription description;
// Current cooldown value // Current cooldown value
var float cooldown; var int cooldown;
// Current state of an ability // Current state of an ability
var EAbilityState myState; var EAbilityState myState;
}; };
var NiceAbilityStatus currentAbilities[5]; var NiceAbilityStatus currentAbilities[5];
var int currentAbilitiesAmount; var int currentAbilitiesAmount;
@ -65,7 +65,7 @@ function AddAbility(NiceAbilityDescription description){
if(currentAbilities[i].description.ID ~= description.ID) if(currentAbilities[i].description.ID ~= description.ID)
return; return;
newRecord.description = description; newRecord.description = description;
newRecord.cooldown = 0.0; newRecord.cooldown = 0;
newRecord.myState = ASTATE_READY; newRecord.myState = ASTATE_READY;
currentAbilities[currentAbilitiesAmount] = newRecord; currentAbilities[currentAbilitiesAmount] = newRecord;
currentAbilitiesAmount += 1; currentAbilitiesAmount += 1;
@ -120,34 +120,34 @@ function SetAbilityState(int abilityIndex, EAbilityState newState){
if(abilityIndex < 0 || abilityIndex >= currentAbilitiesAmount) return; if(abilityIndex < 0 || abilityIndex >= currentAbilitiesAmount) return;
currentState = currentAbilities[abilityIndex].myState; currentState = currentAbilities[abilityIndex].myState;
if(currentState == newState) if(currentState == newState)
return; return;
if( currentState == ASTATE_ACTIVE && newState == ASTATE_READY if( currentState == ASTATE_ACTIVE && newState == ASTATE_READY
&& !currentAbilities[abilityIndex].description.canBeCancelled) && !currentAbilities[abilityIndex].description.canBeCancelled)
return; return;
currentAbilities[abilityIndex].myState = newState; currentAbilities[abilityIndex].myState = newState;
if(newState == ASTATE_COOLDOWN){ if(newState == ASTATE_COOLDOWN){
cooldown = currentAbilities[abilityIndex].description.cooldownLength; cooldown = currentAbilities[abilityIndex].description.cooldownLength;
events.static.CallModAbilityCooldown( events.static.CallModAbilityCooldown(
currentAbilities[abilityIndex].description.ID, currentAbilities[abilityIndex].description.ID,
relatedPlayer, relatedPlayer,
cooldown cooldown
); );
currentAbilities[abilityIndex].cooldown = cooldown; currentAbilities[abilityIndex].cooldown = cooldown;
} }
hackCounter ++; hackCounter ++;
netUpdateTime = level.timeSeconds - 1; netUpdateTime = level.timeSeconds - 1;
// Fire off events // Fire off events
if(newState == ASTATE_ACTIVE){ if(newState == ASTATE_ACTIVE){
events.static.CallAbilityActivated( events.static.CallAbilityActivated(
currentAbilities[abilityIndex].description.ID, currentAbilities[abilityIndex].description.ID,
relatedPlayer relatedPlayer
); );
} }
} }
// Changes ability's cooldown by a given amount. // Changes ability's cooldown by a given amount.
// If this brings cooldown to zero or below - // If this brings cooldown to zero or below -
// resets current ability to a 'ready' (ASTATE_READY) state. // resets current ability to a 'ready' (ASTATE_READY) state.
function AddToCooldown(int abilityIndex, float delta){ function AddToCooldown(int abilityIndex, int delta){
if(abilityIndex < 0 || abilityIndex >= currentAbilitiesAmount) return; if(abilityIndex < 0 || abilityIndex >= currentAbilitiesAmount) return;
if(currentAbilities[abilityIndex].myState != ASTATE_COOLDOWN) return; if(currentAbilities[abilityIndex].myState != ASTATE_COOLDOWN) return;
currentAbilities[abilityIndex].cooldown += delta; currentAbilities[abilityIndex].cooldown += delta;
@ -155,12 +155,21 @@ function AddToCooldown(int abilityIndex, float delta){
SetAbilityState(abilityIndex, ASTATE_READY); SetAbilityState(abilityIndex, ASTATE_READY);
hackCounter ++; hackCounter ++;
} }
function Tick(float deltaTime){
function AddToAllCooldowns(int delta){
local int i; local int i;
if(Role != Role_AUTHORITY) return;
for(i = 0;i < currentAbilitiesAmount;i ++) for (i = 0; i < currentAbilitiesAmount; i += 1) {
AddToCooldown(i, -deltaTime); if (currentAbilities[i].myState == ASTATE_COOLDOWN) {
currentAbilities[i].cooldown += delta;
if(currentAbilities[i].cooldown <= 0) {
SetAbilityState(i, ASTATE_READY);
}
}
}
hackCounter ++;
} }
defaultproperties defaultproperties
{ {
maxAbilitiesAmount=5 maxAbilitiesAmount=5

View File

@ -1,4 +1,4 @@
class NiceDamTypeMedicDart extends NiceDamageTypeVetCommando class NiceDamTypeMedicDart extends NiceDamageTypeVetDemolitions
abstract; abstract;
defaultproperties defaultproperties
{ {

View File

@ -35,6 +35,16 @@ static function float GetMagCapacityMod(KFPlayerReplicationInfo KFPRI, KFWeapon
return class'NiceSkillCommandoLargerMags'.default.sizeBonus; return class'NiceSkillCommandoLargerMags'.default.sizeBonus;
return 1.0; return 1.0;
} }
// Change the cost of particular ammo
static function float GetAmmoCostScaling(KFPlayerReplicationInfo KFPRI, class<Pickup> Item)
{
local class<NiceWeaponPickup> pickupClass;
pickupClass = class<NiceWeaponPickup>(Item);
if(IsPerkedPickup(pickupClass) && HasSkill(NicePlayerController(KFPRI.Owner), class'NiceSkillCommandoLargerMags')) {
return class'NiceSkillCommandoLargerMags'.default.sizeBonus;
}
return 1.0;
}
static function float GetSyringeChargeRate(KFPlayerReplicationInfo KFPRI){ static function float GetSyringeChargeRate(KFPlayerReplicationInfo KFPRI){
return 1.5; return 1.5;
} }
@ -102,7 +112,7 @@ defaultproperties
OnHUDIcons(3)=(PerkIcon=Texture'ScrnTex.Perks.Perk_Commando_Blue',StarIcon=Texture'ScrnTex.Perks.Hud_Perk_Star_Blue',DrawColor=(B=255,G=255,R=255,A=255)) OnHUDIcons(3)=(PerkIcon=Texture'ScrnTex.Perks.Perk_Commando_Blue',StarIcon=Texture'ScrnTex.Perks.Hud_Perk_Star_Blue',DrawColor=(B=255,G=255,R=255,A=255))
OnHUDIcons(4)=(PerkIcon=Texture'ScrnTex.Perks.Perk_Commando_Purple',StarIcon=Texture'ScrnTex.Perks.Hud_Perk_Star_Purple',DrawColor=(B=255,G=255,R=255,A=255)) OnHUDIcons(4)=(PerkIcon=Texture'ScrnTex.Perks.Perk_Commando_Purple',StarIcon=Texture'ScrnTex.Perks.Hud_Perk_Star_Purple',DrawColor=(B=255,G=255,R=255,A=255))
OnHUDIcons(5)=(PerkIcon=Texture'ScrnTex.Perks.Perk_Commando_Orange',StarIcon=Texture'ScrnTex.Perks.Hud_Perk_Star_Orange',DrawColor=(B=255,G=255,R=255,A=255)) OnHUDIcons(5)=(PerkIcon=Texture'ScrnTex.Perks.Perk_Commando_Orange',StarIcon=Texture'ScrnTex.Perks.Hud_Perk_Star_Orange',DrawColor=(B=255,G=255,R=255,A=255))
CustomLevelInfo="Level up by doing damage with perked weapons|15% faster reload with all weapons|10% faster movement speed|You get four additional Zed-Time Extensions|See health and cloacked zeds from 16 meters distance|Better Syringe handling" CustomLevelInfo="Level up by doing damage with perked weapons|15% faster reload with all weapons|10% faster movement speed|You get four additional Zed-Time Extensions|See health and cloaked zeds from 16 meters distance|Better Syringe handling"
PerkIndex=3 PerkIndex=3
OnHUDIcon=Texture'KillingFloorHUD.Perks.Perk_Commando' OnHUDIcon=Texture'KillingFloorHUD.Perks.Perk_Commando'
OnHUDGoldIcon=Texture'KillingFloor2HUD.Perk_Icons.Perk_Commando_Gold' OnHUDGoldIcon=Texture'KillingFloor2HUD.Perk_Icons.Perk_Commando_Gold'

View File

@ -8,6 +8,7 @@ static function GetHitEffects(out class<xEmitter> HitEffects[4], int VictimHealt
} }
defaultproperties defaultproperties
{ {
stoppingPower=0.5
stunMultiplier=0.600000 stunMultiplier=0.600000
bIsExplosive=True bIsExplosive=True
DeathString="%o filled %k's body with shrapnel." DeathString="%o filled %k's body with shrapnel."

View File

@ -39,12 +39,13 @@ static function int AddDamage(KFPlayerReplicationInfo KFPRI, KFMonster Injured,
perkDamage = float(InDamage); perkDamage = float(InDamage);
if(DmgType == class'NiceDamTypeDemoExplosion') if(DmgType == class'NiceDamTypeDemoExplosion')
return 1.6 * perkDamage; return 1.6 * perkDamage;
if(IsPerkedPickup(pickupClass)) if(IsPerkedPickup(pickupClass) && class<NiceDamTypeDemoExplosion>(DmgType) != none)
perkDamage *= 1.25; perkDamage *= 1.25;
else if( pickupClass != none && pickupClass.default.weight <= class'NiceSkillDemoOffperk'.default.weightBound else if( pickupClass != none && pickupClass.default.weight <= class'NiceSkillDemoOffperk'.default.weightBound
&& HasSkill(NicePlayerController(KFPRI.Owner), class'NiceSkillDemoOffperk') ) && HasSkill(NicePlayerController(KFPRI.Owner), class'NiceSkillDemoOffperk') )
perkDamage *= class'NiceSkillDemoOffperk'.default.damageBonus; perkDamage *= class'NiceSkillDemoOffperk'.default.damageBonus;
if( KFPRI != none && class<NiceDamTypeDemoBlunt>(DmgType) != none if( KFPRI != none && class<NiceDamTypeDemoExplosion>(DmgType) == none
&& IsPerkedPickup(pickupClass)
&& SomeoneHasSkill(NicePlayerController(KFPRI.Owner), class'NiceSkillDemoOnperk') ) && SomeoneHasSkill(NicePlayerController(KFPRI.Owner), class'NiceSkillDemoOnperk') )
perkDamage *= class'NiceSkillDemoOnperk'.default.damageBonus; perkDamage *= class'NiceSkillDemoOnperk'.default.damageBonus;
return perkDamage; return perkDamage;

View File

@ -15,7 +15,6 @@ static function AbilityActivated(
NicePlayerController relatedPlayer) NicePlayerController relatedPlayer)
{ {
local NiceHumanPawn nicePawn; local NiceHumanPawn nicePawn;
local NiceMonster victim;
if (relatedPlayer == none) return; if (relatedPlayer == none) return;
nicePawn = NiceHumanPawn(relatedPlayer.pawn); nicePawn = NiceHumanPawn(relatedPlayer.pawn);
@ -37,6 +36,23 @@ static function AbilityActivated(
{ {
nicePawn.bruteTimer = nicePawn.bruteTimer =
class'NiceSkillEnforcerBruteA'.default.abilityDuration; class'NiceSkillEnforcerBruteA'.default.abilityDuration;
nicePawn.quadDamageRemaining = class'NiceSkillEnforcerBruteA'.default.maximumDamageAdded;
}
}
static function ModAbilityCooldown( string abilityID,
NicePlayerController relatedPlayer,
out float cooldown)
{
local NiceHumanPawn nicePawn;
if (relatedPlayer == none) return;
nicePawn = NiceHumanPawn(relatedPlayer.pawn);
if (nicePawn == none) return;
if (abilityID == "brute")
{
nicePawn.quadDamageRemaining = 0;
} }
} }

View File

@ -16,12 +16,15 @@ static function array<int> GetProgressArray(byte ReqNum, optional out int Double
// Other bonuses // Other bonuses
static function int AddDamage(KFPlayerReplicationInfo KFPRI, KFMonster Injured, KFPawn DamageTaker, int InDamage, class<DamageType> DmgType) static function int AddDamage(KFPlayerReplicationInfo KFPRI, KFMonster Injured, KFPawn DamageTaker, int InDamage, class<DamageType> DmgType)
{ {
local float fDamage; local int bruteAbilityIndex;
local float fDamage, addedDamage;
local NicePlayerController nicePlayer; local NicePlayerController nicePlayer;
local NiceHumanPawn nicePawn;
local NiceMonster niceTarget; local NiceMonster niceTarget;
fDamage = float(InDamage); fDamage = float(InDamage);
nicePlayer = NicePlayerController(KFPRI.Owner); nicePlayer = NicePlayerController(KFPRI.Owner);
nicePawn = NiceHumanPawn(nicePlayer.pawn);
niceTarget = NiceMonster(injured); niceTarget = NiceMonster(injured);
if ( niceTarget != none if ( niceTarget != none
&& niceTarget.bFrozenZed && niceTarget.bFrozenZed
@ -31,9 +34,20 @@ static function int AddDamage(KFPlayerReplicationInfo KFPRI, KFMonster Injured,
(1 + class'NiceSkillEnforcerFinisherRounds'.default.damageBonus); (1 + class'NiceSkillEnforcerFinisherRounds'.default.damageBonus);
} }
if( nicePlayer != none && nicePlayer.abilityManager != none if( nicePlayer != none && nicePlayer.abilityManager != none
&& nicePawn != none && nicePawn.quadDamageRemaining > 0
&& nicePlayer.abilityManager.IsAbilityActive(class'NiceSkillEnforcerBruteA'.default.abilityID)) && nicePlayer.abilityManager.IsAbilityActive(class'NiceSkillEnforcerBruteA'.default.abilityID))
{ {
fDamage *= class'NiceSkillEnforcerBruteA'.default.damageMult; addedDamage = fDamage * class'NiceSkillEnforcerBruteA'.default.damageMult - fDamage;
if (addedDamage >= nicePawn.quadDamageRemaining) {
addedDamage = nicePawn.quadDamageRemaining;
nicePawn.quadDamageRemaining = 0.0;
bruteAbilityIndex = nicePlayer.abilityManager.GetAbilityIndex(class'NiceSkillEnforcerBruteA'.default.abilityID);
nicePlayer.abilityManager.SetAbilityState(bruteAbilityIndex, ASTATE_COOLDOWN);
}
else {
nicePawn.quadDamageRemaining -= addedDamage;
}
fDamage += addedDamage;
} }
return int(fDamage); return int(fDamage);
} }
@ -45,7 +59,7 @@ static function float GetPenetrationDamageMulti(KFPlayerReplicationInfo KFPRI, f
return DefaultPenDamageReduction; return DefaultPenDamageReduction;
if(HasSkill(NicePlayerController(KFPRI.Owner), class'NiceSkillSupportStubbornness')) if(HasSkill(NicePlayerController(KFPRI.Owner), class'NiceSkillSupportStubbornness'))
bonusReduction = class'NiceSkillSupportStubbornness'.default.penLossRed; bonusReduction = class'NiceSkillSupportStubbornness'.default.penLossRed;
PenDamageInverse = (1.0 - FMax(0, DefaultPenDamageReduction)); PenDamageInverse = (1.0 - FMax(0, DefaultPenDamageReduction));
return DefaultPenDamageReduction + PenDamageInverse * (0.6 + 0.4 * bonusReduction); // 60% better penetrations + bonus return DefaultPenDamageReduction + PenDamageInverse * (0.6 + 0.4 * bonusReduction); // 60% better penetrations + bonus
} }
@ -64,15 +78,6 @@ static function class<Grenade> GetNadeType(KFPlayerReplicationInfo KFPRI){
return class'NiceCryoNade'; return class'NiceCryoNade';
} }
static function float AddExtraAmmoFor(KFPlayerReplicationInfo KFPRI, Class<Ammunition> AmmoType){
local float bonusNades;
// Default bonus
bonusNades = 2;
if(AmmoType == class'FragAmmo')
return 1.0 + 0.2 * bonusNades;
return 1.0;
}
static function int ReduceDamage(KFPlayerReplicationInfo KFPRI, KFPawn Injured, Pawn Instigator, int InDamage, class<DamageType> DmgType){ static function int ReduceDamage(KFPlayerReplicationInfo KFPRI, KFPawn Injured, Pawn Instigator, int InDamage, class<DamageType> DmgType){
local float fDamage; local float fDamage;
fDamage = float(inDamage); fDamage = float(inDamage);
@ -180,7 +185,7 @@ defaultproperties
SkillGroupA(4)=class'NiceSkillEnforcerZEDBarrage' SkillGroupA(4)=class'NiceSkillEnforcerZEDBarrage'
SkillGroupB(0)=class'NiceSkillEnforcerUnkillable' SkillGroupB(0)=class'NiceSkillEnforcerUnkillable'
SkillGroupB(1)=class'NiceSkillEnforcerMultitasker' SkillGroupB(1)=class'NiceSkillEnforcerMultitasker'
SkillGroupB(2)=class'NiceSkillEnforcerFinisherRounds' SkillGroupB(2)=class'NiceSkillHeavySafeguard'
SkillGroupB(3)=class'NiceSkillEnforcerBruteA' SkillGroupB(3)=class'NiceSkillEnforcerBruteA'
SkillGroupB(4)=class'NiceSkillEnforcerZEDIceGiant' SkillGroupB(4)=class'NiceSkillEnforcerZEDIceGiant'
progressArray0(0)=100 progressArray0(0)=100

View File

@ -7,5 +7,5 @@ defaultproperties
stunMult=3.000000 stunMult=3.000000
spreadMult=0.500000 spreadMult=0.500000
SkillName="Bombard" SkillName="Bombard"
SkillEffects="Your perked weapons are 3 times as good at stunning." SkillEffects="Your perked weapons are 3 times as good at stunning and have omly half as much spread."
} }

View File

@ -5,6 +5,7 @@ var string abilityID;
var float coolDown; var float coolDown;
var float abilityDuration; var float abilityDuration;
var float damageMult; var float damageMult;
var float maximumDamageAdded;
function static SkillSelected(NicePlayerController nicePlayer) function static SkillSelected(NicePlayerController nicePlayer)
{ {
@ -29,6 +30,7 @@ function static SkillDeSelected(NicePlayerController nicePlayer)
defaultproperties defaultproperties
{ {
maximumDamageAdded=10000
abilityID="brute" abilityID="brute"
cooldown=60.000000 cooldown=60.000000
abilityDuration=5.0 abilityDuration=5.0

View File

@ -219,8 +219,6 @@ static function int AddRegDamage(KFPlayerReplicationInfo KFPRI, KFMonster Injure
} }
// Allows to buff only fire component of damage. // Allows to buff only fire component of damage.
static function int AddFireDamage(KFPlayerReplicationInfo KFPRI, KFMonster Injured, KFPawn DamageTaker, int InDamage, class<NiceWeaponDamageType> DmgType){ static function int AddFireDamage(KFPlayerReplicationInfo KFPRI, KFMonster Injured, KFPawn DamageTaker, int InDamage, class<NiceWeaponDamageType> DmgType){
if(DmgType != none)
return InDamage * DmgType.default.heatPart;
return InDamage; return InDamage;
} }
static function float stunDurationMult(KFPlayerReplicationInfo KFPRI, KFMonster Injured, KFPawn DamageTaker, class<NiceWeaponDamageType> DmgType){ static function float stunDurationMult(KFPlayerReplicationInfo KFPRI, KFMonster Injured, KFPawn DamageTaker, class<NiceWeaponDamageType> DmgType){

View File

@ -2,5 +2,6 @@ class NiceHeavyFire extends NiceFire;
defaultproperties defaultproperties
{ {
maxBonusContLenght=3 maxBonusContLenght = 3
aimingSpreadReductionCoefficient = 0.0
} }

View File

@ -66,15 +66,19 @@ simulated function WeaponTick(float dt){
} }
super.WeaponTick(dt); super.WeaponTick(dt);
} }
simulated function ClientSuccessfulHeal(NiceHumanPawn healer, NiceHumanPawn healed){
if(healed == none) simulated function ClientSuccessfulHeal(
return; NiceHumanPawn healer,
if(instigator != none && PlayerController(instigator.controller) != none) NiceHumanPawn healed
PlayerController(instigator.controller). ){
ClientMessage("You've healed"@healed.GetPlayerName(), 'CriticalEvent'); if(healed == none) {
if(NiceHumanPawn(instigator) != none && PlayerController(healed.controller) != none) return;
PlayerController(healed.controller). }
ClientMessage("You've been healed by"@healer.GetPlayerName(), 'CriticalEvent'); if(instigator != none && PlayerController(instigator.controller) != none) {
PlayerController(instigator.controller).ClientMessage(
"You've healed" @ healed.GetPlayerName(),
'CriticalEvent');
}
} }
defaultproperties defaultproperties

View File

@ -272,19 +272,19 @@ simulated function HandleRecoil(float Rec){}
defaultproperties defaultproperties
{ {
weaponRange=70.000000 weaponRange=70.000000
damageDelay=0.300000 damageDelay=0.300000
ImpactShakeRotMag=(X=50.000000,Y=50.000000,Z=50.000000) ImpactShakeRotMag=(X=50.000000,Y=50.000000,Z=50.000000)
ImpactShakeRotRate=(X=10000.000000,Y=10000.000000,Z=10000.000000) ImpactShakeRotRate=(X=10000.000000,Y=10000.000000,Z=10000.000000)
ImpactShakeRotTime=2.000000 ImpactShakeRotTime=2.000000
ImpactShakeOffsetMag=(X=10.000000,Y=10.000000,Z=10.000000) ImpactShakeOffsetMag=(X=10.000000,Y=10.000000,Z=10.000000)
ImpactShakeOffsetRate=(X=1000.000000,Y=1000.000000,Z=1000.000000) ImpactShakeOffsetRate=(X=1000.000000,Y=1000.000000,Z=1000.000000)
ImpactShakeOffsetTime=2.000000 ImpactShakeOffsetTime=2.000000
MeleeHitVolume=1.000000 MeleeHitVolume=1.000000
HitEffectClass=Class'KFMod.KFMeleeHitEffect' HitEffectClass=Class'KFMod.KFMeleeHitEffect'
WideDamageMinHitAngle=1.000000 WideDamageMinHitAngle=1.000000
bFiringDoesntAffectMovement=True bFiringDoesntAffectMovement=True
FireEndAnim= FireEndAnim=
FireForce="ShockRifleFire" FireForce="ShockRifleFire"
aimerror=100.000000 aimerror=100.000000
} }

View File

@ -3,7 +3,7 @@ class NiceScopedWeapon extends NiceWeapon
#exec OBJ LOAD FILE=ScopeShaders.utx #exec OBJ LOAD FILE=ScopeShaders.utx
#exec OBJ LOAD FILE=..\Textures\NicePackT.utx #exec OBJ LOAD FILE=..\Textures\NicePackT.utx
#exec OBJ LOAD FILE=ScrnWeaponPack_T.utx #exec OBJ LOAD FILE=ScrnWeaponPack_T.utx
#exec OBJ LOAD FILE=ScrnWeaponPack_A.ukx #exec OBJ LOAD FILE=ScrnWeaponPack_A.ukx
var() Material ZoomMat; var() Material ZoomMat;
var() Sound ZoomSound; var() Sound ZoomSound;
var() int lenseMaterialID; // used since material id's seem to change alot var() int lenseMaterialID; // used since material id's seem to change alot
@ -18,31 +18,47 @@ var Shader ScopeScriptedShader; // The shader that combi
var Material ScriptedTextureFallback; // The texture to render if the users system doesn't support shaders var Material ScriptedTextureFallback; // The texture to render if the users system doesn't support shaders
// new scope vars // new scope vars
var Combiner ScriptedScopeCombiner; var Combiner ScriptedScopeCombiner;
var texture TexturedScopeTexture; var Material TexturedScopeTexture;
var bool bInitializedScope; // Set to true when the scope has been initialized var bool bInitializedScope; // Set to true when the scope has been initialized
var string ZoomMatRef; var string ZoomMatRef;
var string ScriptedTextureFallbackRef; var string ScriptedTextureFallbackRef;
var texture CrosshairTex; var Material CrosshairTex;
var string CrosshairTexRef; var string CrosshairTexRef;
static function Material PreloadUnknownMaterial(string reference) {
local Material result;
// Try to load as various types of materials
result = FinalBlend(DynamicLoadObject(reference, class'FinalBlend', true));
if(result != none) {
return result;
}
result = Combiner(DynamicLoadObject(reference, class'Combiner', true));
if(result != none) {
return result;
}
result = Shader(DynamicLoadObject(reference, class'Shader', true));
if(result != none) {
return result;
}
result = Texture(DynamicLoadObject(reference, class'Texture', true));
if(result != none) {
return result;
}
result = Material(DynamicLoadObject(reference, class'Material'));
return result;
}
static function PreloadAssets(Inventory Inv, optional bool bSkipRefCount){ static function PreloadAssets(Inventory Inv, optional bool bSkipRefCount){
local NiceScopedWeapon W; local NiceScopedWeapon W;
super.PreloadAssets(Inv, bSkipRefCount); super.PreloadAssets(Inv, bSkipRefCount);
if(default.ZoomMat == none && default.ZoomMatRef != ""){ if(default.ZoomMat == none && default.ZoomMatRef != ""){
// Try to load as various types of materials default.ZoomMat = PreloadUnknownMaterial(default.ZoomMatRef);
default.ZoomMat = FinalBlend(DynamicLoadObject(default.ZoomMatRef, class'FinalBlend', true));
if(default.ZoomMat == none)
default.ZoomMat = Combiner(DynamicLoadObject(default.ZoomMatRef, class'Combiner', true));
if(default.ZoomMat == none)
default.ZoomMat = Shader(DynamicLoadObject(default.ZoomMatRef, class'Shader', true));
if(default.ZoomMat == none)
default.ZoomMat = Texture(DynamicLoadObject(default.ZoomMatRef, class'Texture', true));
if(default.ZoomMat == none)
default.ZoomMat = Material(DynamicLoadObject(default.ZoomMatRef, class'Material'));
} }
if(default.ScriptedTextureFallback == none && default.ScriptedTextureFallbackRef != "") if(default.ScriptedTextureFallback == none && default.ScriptedTextureFallbackRef != "")
default.ScriptedTextureFallback = texture(DynamicLoadObject(default.ScriptedTextureFallbackRef, class'texture')); default.ScriptedTextureFallback = PreloadUnknownMaterial(default.ScriptedTextureFallbackRef);
if(default.CrosshairTex == none && default.CrosshairTexRef != "") if(default.CrosshairTex == none && default.CrosshairTexRef != "")
default.CrosshairTex = Texture(DynamicLoadObject(default.CrosshairTexRef, class'texture')); default.CrosshairTex = PreloadUnknownMaterial(default.CrosshairTexRef);
W = NiceScopedWeapon(Inv); W = NiceScopedWeapon(Inv);
if(W != none){ if(W != none){
W.ZoomMat = default.ZoomMat; W.ZoomMat = default.ZoomMat;

View File

@ -14,6 +14,7 @@ var float prReqPrecise; // How precise must head-shot be
var float lockonTime; var float lockonTime;
var float flinchMultiplier; // How effective is weapon for flinching zeds var float flinchMultiplier; // How effective is weapon for flinching zeds
var float stunMultiplier; // How effective is weapon for stunning zeds var float stunMultiplier; // How effective is weapon for stunning zeds
var float stunLengthMultiplier; // For how long is weapon going to stun zeds
var float heatPart; // How much of this damage should be a heat component? var float heatPart; // How much of this damage should be a heat component?
var float freezePower; // How good is weapon at freezing? var float freezePower; // How good is weapon at freezing?
var float bodyDestructionMult; // How much more damage do to body on a head-shot? var float bodyDestructionMult; // How much more damage do to body on a head-shot?
@ -27,6 +28,7 @@ var const int MediumZedMinHealth; // If zed's base Health >= this
var float PenDmgReduction; // Penetration damage reduction after hitting small zed var float PenDmgReduction; // Penetration damage reduction after hitting small zed
var float penDecapReduction; // Penetration decapitaion effectiveness reduction after hitting small zed var float penDecapReduction; // Penetration decapitaion effectiveness reduction after hitting small zed
var float penIncapReduction; // Penetration incapacitation (flinch or stun) effectiveness reduction after hitting small zed var float penIncapReduction; // Penetration incapacitation (flinch or stun) effectiveness reduction after hitting small zed
var float stoppingPower; // How much stopping power the gun has - % amount zeds will be made to slow down when shot
var bool bIsProjectile; // If original damage type's version was derived from 'KFProjectileWeaponDamageType', then set this to true var bool bIsProjectile; // If original damage type's version was derived from 'KFProjectileWeaponDamageType', then set this to true
// Scales exp gain according to given HardcoreLevel // Scales exp gain according to given HardcoreLevel
static function float getScale(int HL){ static function float getScale(int HL){
@ -83,11 +85,13 @@ defaultproperties
prReqPrecise=0.750000 prReqPrecise=0.750000
flinchMultiplier=1.000000 flinchMultiplier=1.000000
stunMultiplier=1.000000 stunMultiplier=1.000000
stunLengthMultiplier=1.000000
bodyDestructionMult=1.000000 bodyDestructionMult=1.000000
headSizeModifier=1.000000 headSizeModifier=1.000000
BigZedPenDmgReduction=0.500000 BigZedPenDmgReduction=0.500000
BigZedMinHealth=1000 BigZedMinHealth=1000
MediumZedPenDmgReduction=0.750000 MediumZedPenDmgReduction=0.750000
stoppingPower=0.0
MediumZedMinHealth=500 MediumZedMinHealth=500
PenDmgReduction=0.700000 PenDmgReduction=0.700000
PawnDamageEmitter=None PawnDamageEmitter=None

File diff suppressed because it is too large Load Diff

View File

@ -9,57 +9,132 @@
// E-mail: dkanus@gmail.com // E-mail: dkanus@gmail.com
//====================================================================================================================== //======================================================================================================================
class NiceBulletAdapter extends Object; class NiceBulletAdapter extends Object;
var const int BigZedMinHealth; // If zed's base Health >= this value, zed counts as Big
var const int MediumZedMinHealth; // If zed's base Health >= this value, zed counts as Medium-size var const int BigZedMinHealth; // If zed's base Health >= this value, zed counts as Big
static function Explode(NiceBullet bullet, NiceReplicationInfo niceRI, Vector hitLocation, optional Actor explosionTarget){ var const int MediumZedMinHealth; // If zed's base Health >= this value, zed counts as Medium-size
if(!bullet.bGhost){
niceRI.ServerExplode(bullet.charExplosionDamage, bullet.charExplosionRadius, bullet.charExplosionExponent, static function Explode(
bullet.charExplosionDamageType, bullet.charExplosionMomentum, hitLocation, bullet.instigator, true, NiceBullet bullet,
explosionTarget, Vector(bullet.Rotation)); NiceReplicationInfo niceRI,
if(KFMonster(bullet.base) != none && bullet.bStuck && bullet.bStuckToHead) Vector hitLocation,
niceRI.ServerDealDamage(KFMonster(bullet.base), bullet.charExplosionDamage, bullet.instigator, hitLocation, optional Actor explosionTarget
bullet.charExplosionMomentum * vect(0,0,-1), bullet.charExplosionDamageType, 1.0); ) {
if (!bullet.bGhost) {
niceRI.ServerExplode(
bullet.charExplosionDamage,
bullet.charExplosionRadius,
bullet.charExplosionExponent,
bullet.charExplosionDamageType,
bullet.charExplosionMomentum,
hitLocation,
bullet.instigator,
explosionTarget,
Vector(bullet.Rotation),
bullet.bStuck
);
if (KFMonster(bullet.base) != none && bullet.bStuck && bullet.bStuckToHead) {
niceRI.ServerDealDamage(
KFMonster(bullet.base),
bullet.charExplosionDamage,
bullet.instigator,
hitLocation,
bullet.charExplosionMomentum * vect(0, 0, -1),
bullet.charExplosionDamageType,
1.0
);
}
} }
} }
static function HandleCalibration
( static function HandleCalibration (
bool isHeadshot, bool isHeadshot,
NiceHumanPawn nicePawn, NiceHumanPawn nicePawn,
NiceMonster targetZed NiceMonster targetZed
){ ) {
if(nicePawn == none) return; if (nicePawn == none || nicePawn.currentCalibrationState != CALSTATE_ACTIVE) {
if(nicePawn.currentCalibrationState != CALSTATE_ACTIVE) return; return;
}
nicePawn.ServerUpdateCalibration(isHeadshot, targetZed); nicePawn.ServerUpdateCalibration(isHeadshot, targetZed);
} }
static function HitWall(NiceBullet bullet, NiceReplicationInfo niceRI, Actor targetWall,
Vector hitLocation, Vector hitNormal){ static function HitWall(
NiceBullet bullet,
NiceReplicationInfo niceRI,
Actor targetWall,
Vector hitLocation,
Vector hitNormal
) {
local NicePlayerController nicePlayer; local NicePlayerController nicePlayer;
nicePlayer = NicePlayerController(bullet.Instigator.Controller); nicePlayer = NicePlayerController(bullet.Instigator.Controller);
if(nicePlayer == none) if (nicePlayer == none) {
return; return;
if(!bullet.bAlreadyHitZed) }
HandleCalibration(false, NiceHumanPawn(bullet.Instigator), none); if (!bullet.bAlreadyHitZed) {
if(!targetWall.bStatic && !targetWall.bWorldGeometry && nicePlayer != none && (nicePlayer.wallHitsLeft > 0 || Projectile(targetWall) != none)){ HandleCalibration(false, NiceHumanPawn(bullet.Instigator), none);
niceRI.ServerDealDamage(targetWall, bullet.charOrigDamage, bullet.Instigator, hitLocation, }
bullet.charMomentumTransfer * hitNormal, bullet.charDamageType); if (
nicePlayer.wallHitsLeft --; !targetWall.bStatic &&
!targetWall.bWorldGeometry &&
nicePlayer != none &&
(nicePlayer.wallHitsLeft > 0 || Projectile(targetWall) != none)
) {
niceRI.ServerDealDamage(
targetWall,
bullet.charOrigDamage,
bullet.Instigator,
hitLocation,
bullet.charMomentumTransfer * hitNormal,
bullet.charDamageType
);
nicePlayer.wallHitsLeft --;
} }
} }
static function HandleScream(NiceBullet bullet, NiceReplicationInfo niceRI, Vector location, Vector entryDirection){
static function HandleScream(
NiceBullet bullet,
NiceReplicationInfo niceRI,
Vector location,
Vector entryDirection
) {
bullet.charIsDud = true; bullet.charIsDud = true;
} }
static function HitPawn(NiceBullet bullet, NiceReplicationInfo niceRI, KFPawn targetPawn, Vector hitLocation,
Vector hitNormal, array<int> hitPoints){ static function HitPawn(
NiceBullet bullet,
NiceReplicationInfo niceRI,
KFPawn targetPawn,
Vector hitLocation,
Vector hitNormal,
array<int> hitPoints
) {
local NiceMedicProjectile niceDart; local NiceMedicProjectile niceDart;
niceDart = NiceMedicProjectile(bullet); niceDart = NiceMedicProjectile(bullet);
if(niceDart == none) if (niceDart == none) {
niceRI.ServerDealDamage(targetPawn, bullet.charDamage, bullet.instigator, HitLocation, niceRI.ServerDealDamage(
hitNormal * bullet.charMomentumTransfer, bullet.charDamageType); targetPawn,
else bullet.charDamage,
niceRI.ServerHealTarget(NiceHumanPawn(targetPawn), bullet.charDamage, bullet.instigator); bullet.instigator,
HitLocation,
hitNormal * bullet.charMomentumTransfer,
bullet.charDamageType
);
} else {
niceRI.ServerHealTarget(NiceHumanPawn(targetPawn), bullet.charDamage, bullet.instigator);
}
} }
static function HitZed(NiceBullet bullet, NiceReplicationInfo niceRI, KFMonster kfZed, Vector hitLocation,
Vector hitNormal, float headshotLevel){ static function HitZed(
NiceBullet bullet,
NiceReplicationInfo niceRI,
KFMonster kfZed,
Vector hitLocation,
Vector hitNormal,
float headshotLevel
) {
local bool bIsHeadshot, bIsPreciseHeadshot; local bool bIsHeadshot, bIsPreciseHeadshot;
local float actualDamage; local float actualDamage;
local int lockonTicks; local int lockonTicks;
@ -68,74 +143,113 @@ static function HitZed(NiceBullet bullet, NiceReplicationInfo niceRI, KFMonster
local NiceHumanPawn nicePawn; local NiceHumanPawn nicePawn;
local NicePlayerController nicePlayer; local NicePlayerController nicePlayer;
local class<NiceVeterancyTypes> niceVet; local class<NiceVeterancyTypes> niceVet;
nicePlayer = NicePlayerController(bullet.Instigator.Controller); nicePlayer = NicePlayerController(bullet.Instigator.Controller);
if ( nicePlayer != none && nicePlayer.abilityManager != none if (
&& nicePlayer.abilityManager.IsAbilityActive(class'NiceSkillEnforcerBruteA'.default.abilityID)) { nicePlayer != none &&
nicePlayer.abilityManager != none &&
nicePlayer.abilityManager.IsAbilityActive(class'NiceSkillEnforcerBruteA'.default.abilityID)
) {
headshotLevel = 0.0; headshotLevel = 0.0;
} }
bIsHeadshot = (headshotLevel > 0.0); bIsHeadshot = (headshotLevel > 0.0);
bIsPreciseHeadshot = (headshotLevel > bullet.charDamageType.default.prReqPrecise); bIsPreciseHeadshot = (headshotLevel > bullet.charDamageType.default.prReqPrecise);
if(!bullet.bAlreadyHitZed || bIsHeadshot) if (!bullet.bAlreadyHitZed || bIsHeadshot) {
HandleCalibration(bIsHeadshot, NiceHumanPawn(bullet.Instigator), NiceMonster(kfZed)); HandleCalibration(bIsHeadshot, NiceHumanPawn(bullet.Instigator), NiceMonster(kfZed));
if(bIsHeadshot && bullet.sourceWeapon != none) }
bullet.sourceWeapon.lastHeadshotTime = bullet.Level.TimeSeconds; if (bIsHeadshot && bullet.sourceWeapon != none) {
if(nicePlayer == none) bullet.sourceWeapon.lastHeadshotTime = bullet.Level.TimeSeconds;
return; }
nicePawn = NiceHumanPawn(bullet.instigator); if (nicePlayer == none) {
if( !bIsHeadshot return;
&& nicePawn != none }
&& nicePlayer.abilityManager != none nicePawn = NiceHumanPawn(bullet.instigator);
&& nicePlayer.abilityManager.IsAbilityActive(class'NiceSkillSharpshooterReaperA'.default.abilityID)) if (
nicePawn.ServerCooldownAbility(class'NiceSkillSharpshooterReaperA'.default.abilityID); !bIsHeadshot &&
niceVet = class'NiceVeterancyTypes'.static.GetVeterancy(KFPlayerReplicationInfo(nicePlayer.PlayerReplicationInfo)); nicePawn != none &&
if(bullet.charCausePain) nicePlayer.abilityManager != none &&
actualDamage = bullet.charOrigDamage; nicePlayer.abilityManager.IsAbilityActive(class'NiceSkillSharpshooterReaperA'.default.abilityID)
else ) {
actualDamage = bullet.charDamage; nicePawn.ServerCooldownAbility(class'NiceSkillSharpshooterReaperA'.default.abilityID);
if(headshotLevel > 0) }
actualDamage *= bullet.charContiniousBonus; niceVet = class'NiceVeterancyTypes'.static.GetVeterancy(KFPlayerReplicationInfo(nicePlayer.PlayerReplicationInfo));
if(bullet.bGrazing) if (bullet.charCausePain) {
actualDamage *= class'NiceSkillSupportGraze'.default.grazeDamageMult; actualDamage = bullet.charOrigDamage;
bullet.bGrazing = false; } else {
if(kfZed == bullet.lockonZed && bullet.lockonTime > bullet.sourceWeapon.stdFireRate actualDamage = bullet.charDamage;
&& niceVet != none && niceVet.static.hasSkill(nicePlayer, class'NiceSkillSharpshooterKillConfirmed')){ }
lockOnTickRate =class'NiceSkillSharpshooterKillConfirmed'.default.stackDelay; if (headshotLevel > 0) {
lockonTicks = Ceil(bullet.lockonTime / lockOnTickRate) - 1; actualDamage *= bullet.charContiniousBonus;
lockonTicks = Min(class'NiceSkillSharpshooterKillConfirmed'.default.maxStacks, lockonTicks); }
//actualDamage *= 1.0 + if (bullet.bGrazing) {
// 0.5 * lockonTicks * (lockonTicks + 1) * class'NiceSkillSharpshooterKillConfirmed'.default.damageBonus; actualDamage *= class'NiceSkillSupportGraze'.default.grazeDamageMult;
//damageMod *= 1.0 + lockonTicks * class'NiceSkillSharpshooterKillConfirmed'.default.damageBonus; }
actualDamage *= 1.0 + lockonTicks * class'NiceSkillSharpshooterKillConfirmed'.default.damageBonus; bullet.bGrazing = false;
if (
kfZed == bullet.lockonZed &&
bullet.lockonTime > bullet.sourceWeapon.stdFireRate &&
niceVet != none &&
niceVet.static.hasSkill(nicePlayer, class'NiceSkillSharpshooterKillConfirmed')
) {
lockOnTickRate =class'NiceSkillSharpshooterKillConfirmed'.default.stackDelay;
lockonTicks = Ceil(bullet.lockonTime / lockOnTickRate) - 1;
lockonTicks = Min(class'NiceSkillSharpshooterKillConfirmed'.default.maxStacks, lockonTicks);
// actualDamage *= 1.0 +
// 0.5 * lockonTicks * (lockonTicks + 1) * class'NiceSkillSharpshooterKillConfirmed'.default.damageBonus;
// damageMod *= 1.0 + lockonTicks * class'NiceSkillSharpshooterKillConfirmed'.default.damageBonus;
actualDamage *= 1.0 + lockonTicks * class'NiceSkillSharpshooterKillConfirmed'.default.damageBonus;
}
if (!bullet.bGhost) {
niceRI.ServerDealDamage(
kfZed,
actualDamage,
bullet.instigator,
hitLocation,
bullet.charMomentumTransfer * hitNormal,
bullet.charDamageType,
headshotLevel,
bullet.lockonTime
);
} }
if(!bullet.bGhost)
niceRI.ServerDealDamage(kfZed, actualDamage, bullet.instigator, hitLocation,
bullet.charMomentumTransfer * hitNormal, bullet.charDamageType, headshotLevel, bullet.lockonTime);
//// Handle angled shots //// Handle angled shots
angle = asin(hitNormal.Z); angle = asin(hitNormal.Z);
// Apply angled shots // Apply angled shots
if((angle > 0.8 || angle < -0.45) && bullet.bCanAngleDamage && kfZed != none){ if ((angle > 0.8 || angle < -0.45) && bullet.bCanAngleDamage && kfZed != none) {
bullet.bCanAngleDamage = false; bullet.bCanAngleDamage = false;
bullet.bAlreadyHitZed = true; bullet.bAlreadyHitZed = true;
if(ZedPenetration(bullet.charDamage, bullet, kfZed, bIsHeadshot, bIsPreciseHeadshot)) if (ZedPenetration(bullet.charDamage, bullet, kfZed, bIsHeadshot, bIsPreciseHeadshot)) {
HitZed(bullet, niceRI, kfZed, hitLocation, hitNormal, headshotLevel); HitZed(bullet, niceRI, kfZed, hitLocation, hitNormal, headshotLevel);
}
} }
//// 'Bore' support skill //// 'Bore' support skill
if( niceVet != none && nicePlayer.IsZedTimeActive() && bullet.insideBouncesLeft > 0 if (
&& niceVet.static.hasSkill(nicePlayer, class'NiceSkillSupportZEDBore')){ niceVet != none &&
// Count one bounce nicePlayer.IsZedTimeActive() &&
bullet.insideBouncesLeft --; bullet.insideBouncesLeft > 0 &&
// Swap head-shot level niceVet.static.hasSkill(nicePlayer, class'NiceSkillSupportZEDBore')
if(headshotLevel <= 0.0) ) {
headshotLevel = class'NiceSkillSupportZEDBore'.default.minHeadshotPrecision; // Count one bounce
else bullet.insideBouncesLeft --;
headshotLevel = -headshotLevel; // Swap head-shot level
// Deal next batch of damage if (headshotLevel <= 0.0) {
ZedPenetration(bullet.charDamage, bullet, kfZed, false, false); headshotLevel = class'NiceSkillSupportZEDBore'.default.minHeadshotPrecision;
HitZed(bullet, niceRI, kfZed, hitLocation, hitNormal, headshotLevel); } else {
headshotLevel = -headshotLevel;
}
// Deal next batch of damage
ZedPenetration(bullet.charDamage, bullet, kfZed, false, false);
HitZed(bullet, niceRI, kfZed, hitLocation, hitNormal, headshotLevel);
} }
bullet.insideBouncesLeft = 2; bullet.insideBouncesLeft = 2;
} }
static function bool ZedPenetration(out float Damage, NiceBullet bullet, KFMonster targetZed, bool bIsHeadshot, bool bIsPreciseHeadshot){
static function bool ZedPenetration(
out float Damage,
NiceBullet bullet,
KFMonster targetZed,
bool bIsHeadshot,
bool bIsPreciseHeadshot
) {
local float reductionMod; local float reductionMod;
local NiceMonster niceZed; local NiceMonster niceZed;
local NicePlayerController nicePlayer; local NicePlayerController nicePlayer;
@ -144,52 +258,74 @@ static function bool ZedPenetration(out float Damage, NiceBullet bullet, KFMonst
local class<NiceWeaponDamageType> niceDmgType; local class<NiceWeaponDamageType> niceDmgType;
// True if we can penetrate even body, but now penetrating a head and shouldn't reduce damage too much // True if we can penetrate even body, but now penetrating a head and shouldn't reduce damage too much
local bool bEasyHeadPenetration; local bool bEasyHeadPenetration;
// Init variables // Init variables
niceZed = NiceMonster(targetZed); niceZed = NiceMonster(targetZed);
nicePlayer = NicePlayerController(bullet.Instigator.Controller); nicePlayer = NicePlayerController(bullet.Instigator.Controller);
niceVet = none; niceVet = none;
if(nicePlayer != none) if (nicePlayer != none) {
niceVet = class'NiceVeterancyTypes'.static.GetVeterancy(KFPlayerReplicationInfo(nicePlayer.PlayerReplicationInfo)); niceVet = class'NiceVeterancyTypes'.static.GetVeterancy(KFPlayerReplicationInfo(nicePlayer.PlayerReplicationInfo));
}
niceDmgType = bullet.charDamageType; niceDmgType = bullet.charDamageType;
bEasyHeadPenetration = bIsHeadshot && !niceDmgType.default.bPenetrationHSOnly; bEasyHeadPenetration = bIsHeadshot && !niceDmgType.default.bPenetrationHSOnly;
reductionMod = 1.0f; reductionMod = 1.0f;
// Apply zed reduction and perk reduction of reduction` // Apply zed reduction and perk reduction of reduction`
if(niceZed != none){ if (niceZed != none) {
// Railgun skill exception // Railgun skill exception
if(niceVet != none && niceVet.static.hasSkill(nicePlayer, class'NiceSkillSharpshooterZEDRailgun') && nicePlayer.IsZedTimeActive()) if (
return true; niceVet != none &&
if(niceZed.default.Health >= default.BigZedMinHealth && !bEasyHeadPenetration) niceVet.static.hasSkill(nicePlayer, class'NiceSkillSharpshooterZEDRailgun') &&
reductionMod *= niceDmgType.default.BigZedPenDmgReduction; nicePlayer.IsZedTimeActive()
else if(niceZed.default.Health >= default.MediumZedMinHealth && !bEasyHeadPenetration) ) {
reductionMod *= niceDmgType.default.MediumZedPenDmgReduction; return true;
} }
else if (niceZed.default.Health >= default.BigZedMinHealth && !bEasyHeadPenetration) {
reductionMod *= niceDmgType.default.BigZedPenDmgReduction;
} else if (niceZed.default.Health >= default.MediumZedMinHealth && !bEasyHeadPenetration) {
reductionMod *= niceDmgType.default.MediumZedPenDmgReduction;
}
} else {
reductionMod *= niceDmgType.default.BigZedPenDmgReduction; reductionMod *= niceDmgType.default.BigZedPenDmgReduction;
if(niceVet != none) }
reductionMod = niceVet.static.GetPenetrationDamageMulti(KFPlayerReplicationInfo(nicePlayer.PlayerReplicationInfo), reductionMod, niceDmgType); if (niceVet != none) {
actualMaxPenetrations = niceDmgType.default.maxPenetrations; reductionMod = niceVet.static.GetPenetrationDamageMulti(
if(niceVet != none && !bullet.charWasHipFired && niceVet.static.hasSkill(nicePlayer, class'NiceSkillSharpshooterSurgical') && bIsHeadshot){ KFPlayerReplicationInfo(nicePlayer.PlayerReplicationInfo),
actualMaxPenetrations += 1; reductionMod,
reductionMod = FMax(reductionMod, class'NiceSkillSharpshooterSurgical'.default.penDmgReduction); niceDmgType
} );
}
actualMaxPenetrations = niceDmgType.default.maxPenetrations;
if (
niceVet != none &&
!bullet.charWasHipFired &&
niceVet.static.hasSkill(nicePlayer, class'NiceSkillSharpshooterSurgical') &&
bIsHeadshot
) {
actualMaxPenetrations += 1;
reductionMod = FMax(reductionMod, class'NiceSkillSharpshooterSurgical'.default.penDmgReduction);
}
// Assign new damage value and tell us if we should stop with penetration // Assign new damage value and tell us if we should stop with penetration
Damage *= reductionMod * niceDmgType.default.PenDmgReduction; Damage *= reductionMod * niceDmgType.default.PenDmgReduction;
bullet.decapMod *= reductionMod * niceDmgType.default.PenDecapReduction; bullet.decapMod *= reductionMod * niceDmgType.default.PenDecapReduction;
bullet.incapMod *= reductionMod * niceDmgType.default.PenIncapReduction; bullet.incapMod *= reductionMod * niceDmgType.default.PenIncapReduction;
if(niceVet != none && actualMaxPenetrations >= 0) if (niceVet != none && actualMaxPenetrations >= 0) {
actualMaxPenetrations += actualMaxPenetrations +=
niceVet.static.GetAdditionalPenetrationAmount(KFPlayerReplicationInfo(nicePlayer.PlayerReplicationInfo)); niceVet.static.GetAdditionalPenetrationAmount(KFPlayerReplicationInfo(nicePlayer.PlayerReplicationInfo));
if(!bIsHeadshot && niceDmgType.default.bPenetrationHSOnly) }
return false; if (!bIsHeadshot && niceDmgType.default.bPenetrationHSOnly) {
if(actualMaxPenetrations < 0) return false;
return true; }
if(Damage / bullet.charOrigDamage < (niceDmgType.default.PenDmgReduction ** (actualMaxPenetrations + 1)) + 0.0001 || Damage < 1) if (actualMaxPenetrations < 0) {
return false; return true;
}
if (Damage / bullet.charOrigDamage < (niceDmgType.default.PenDmgReduction ** (actualMaxPenetrations + 1)) + 0.0001 || Damage < 1) {
return false;
}
return true; return true;
} }
defaultproperties defaultproperties {
{ BigZedMinHealth=1000
BigZedMinHealth=1000 MediumZedMinHealth=500
MediumZedMinHealth=500 }
}

View File

@ -20,6 +20,7 @@ var() bool bSemiMustBurst;
var() int MaxBurstLength; var() int MaxBurstLength;
var() int burstShotsMade; var() int burstShotsMade;
var bool bResetRecoil; // Set this flag to 'true' to disable recoil for the next shot; flag will be automatically reset to 'false' after that var bool bResetRecoil; // Set this flag to 'true' to disable recoil for the next shot; flag will be automatically reset to 'false' after that
var float aimingSpreadReductionCoefficient;
var bool zoomOutOnShot; var bool zoomOutOnShot;
var bool bShouldBounce; var bool bShouldBounce;
var bool bCausePain; var bool bCausePain;
@ -38,6 +39,10 @@ var bool projAffectedByScream;
var bool bShouldStick; var bool bShouldStick;
var int resetTicks; var int resetTicks;
var float niceNextFireTime; var float niceNextFireTime;
var float minimalSpreadScale;
var float activeSpreadScale;
var float spreadGainedPerShot;
var float spreadLostPerSecond;
struct FireModeContext{ struct FireModeContext{
var bool bHipfire; var bool bHipfire;
var NiceWeapon sourceWeapon; var NiceWeapon sourceWeapon;
@ -152,9 +157,15 @@ simulated function int GetBurstLength(){
} }
return currentContext.burstLength; return currentContext.burstLength;
} }
simulated function ModeTick(float delta){ simulated function ModeTick(float delta){
local float headLevel; local float headLevel;
local NiceMonster currTarget; local NiceMonster currTarget;
if (spreadLostPerSecond > 0 && activeSpreadScale > minimalSpreadScale
&& niceNextFireTime + fireRate <= Level.TimeSeconds) {
activeSpreadScale -= spreadLostPerSecond * delta;
activeSpreadScale = FMax(minimalSpreadScale, activeSpreadScale);
}
if(currentContext.Instigator == none) if(currentContext.Instigator == none)
currentContext.Instigator = NiceHumanPawn(Instigator); currentContext.Instigator = NiceHumanPawn(Instigator);
if(currentContext.sourceWeapon == none) if(currentContext.sourceWeapon == none)
@ -477,7 +488,7 @@ simulated function HandleRecoil(float Rec)
KFW= KFWeapon(Weapon); KFW= KFWeapon(Weapon);
if (KFW.bAimingRifle) if (KFW.bAimingRifle)
{ {
Rec *= 0.5; Rec *= aimingSpreadReductionCoefficient;
} }
if (nicePawn.stationaryTime > 0.0 && class'NiceVeterancyTypes'.static.hasSkill(nicePlayer, class'NiceSkillHeavyStablePosition')) if (nicePawn.stationaryTime > 0.0 && class'NiceVeterancyTypes'.static.hasSkill(nicePlayer, class'NiceSkillHeavyStablePosition'))
{ {
@ -548,7 +559,7 @@ function DoFireEffect(){
if(!Weapon.WeaponCentered() && !KFWeap.bAimingRifle) if(!Weapon.WeaponCentered() && !KFWeap.bAimingRifle)
StartProj = StartProj + Weapon.Hand * Y * ProjSpawnOffset.Y + Z * ProjSpawnOffset.Z; StartProj = StartProj + Weapon.Hand * Y * ProjSpawnOffset.Y + Z * ProjSpawnOffset.Z;
other = Weapon.Trace(HitLocation, HitNormal, StartProj, StartTrace, false); other = Weapon.Trace(HitLocation, HitNormal, StartProj, StartTrace, false);
activeSpread = fireShots[currentShot].spread; activeSpread = fireShots[currentShot].spread * activeSpreadScale;
if(class'NiceVeterancyTypes'.static.hasSkill(nicePlayer, class'NiceSkillEnforcerBombard')){ if(class'NiceVeterancyTypes'.static.hasSkill(nicePlayer, class'NiceSkillEnforcerBombard')){
bPinpoint = true; bPinpoint = true;
activeSpread *= class'NiceSkillEnforcerBombard'.default.spreadMult; activeSpread *= class'NiceSkillEnforcerBombard'.default.spreadMult;
@ -607,6 +618,15 @@ function DoFireEffect(){
else if(Instigator.Physics == PHYS_Falling && Instigator.PhysicsVolume.Gravity.Z > class'PhysicsVolume'.default.Gravity.Z) else if(Instigator.Physics == PHYS_Falling && Instigator.PhysicsVolume.Gravity.Z > class'PhysicsVolume'.default.Gravity.Z)
Instigator.AddVelocity((KickMomentum * LowGravKickMomentumScale) >> Instigator.GetViewRotation()); Instigator.AddVelocity((KickMomentum * LowGravKickMomentumScale) >> Instigator.GetViewRotation());
} }
if (activeSpreadScale < 1.0) {
if (KFWeap.bAimingRifle) {
activeSpreadScale += spreadGainedPerShot * 0.5;
}
else {
activeSpreadScale += spreadGainedPerShot;
}
activeSpreadScale = FMin(1.0, activeSpreadScale);
}
} }
simulated function float TraceZed(out NiceMonster tracedZed, optional out Vector hitLoc, optional out Vector hitNorm, simulated function float TraceZed(out NiceMonster tracedZed, optional out Vector hitLoc, optional out Vector hitNorm,
optional float hsMultiplier){ optional float hsMultiplier){
@ -678,7 +698,8 @@ simulated function UpdateFireSpeed(){
ReloadAnimRate = default.ReloadAnimRate * fireSpeedMod; ReloadAnimRate = default.ReloadAnimRate * fireSpeedMod;
} }
// This function is called when next fire time needs to be updated // This function is called when next fire time needs to be updated
simulated function float UpdateNextFireTime(float fireTimeVar){ simulated function float UpdateNextFireTime(float fireTimeVar) {
local float usedFireRate;
local float burstSlowDown; local float burstSlowDown;
local NiceHumanPawn nicePawn; local NiceHumanPawn nicePawn;
local class<NiceVeterancyTypes> niceVet; local class<NiceVeterancyTypes> niceVet;
@ -686,11 +707,19 @@ simulated function float UpdateNextFireTime(float fireTimeVar){
if(nicePawn != none) if(nicePawn != none)
niceVet = class'NiceVeterancyTypes'.static.GetVeterancy(nicePawn.PlayerReplicationInfo); niceVet = class'NiceVeterancyTypes'.static.GetVeterancy(nicePawn.PlayerReplicationInfo);
fireTimeVar = FMax(fireTimeVar, Level.TimeSeconds); fireTimeVar = FMax(fireTimeVar, Level.TimeSeconds);
usedFireRate = fireRate;
if (maxBonusContLenght > 1) {
if (currentContLenght <= maxBonusContLenght) {
usedFireRate *= 0.8 + 0.2 * (maxBonusContLenght - currentContLenght);
} else {
usedFireRate *= 0.8;
}
}
if(bFireOnRelease){ if(bFireOnRelease){
if(bIsFiring) if(bIsFiring)
fireTimeVar += MaxHoldTime + FireRate; fireTimeVar += MaxHoldTime + usedFireRate;
else else
fireTimeVar = Level.TimeSeconds + FireRate; fireTimeVar = Level.TimeSeconds + usedFireRate;
} }
else{ else{
if(currentContext.bIsBursting && GetBurstLength() > 1){ if(currentContext.bIsBursting && GetBurstLength() > 1){
@ -701,10 +730,10 @@ simulated function float UpdateNextFireTime(float fireTimeVar){
burstSlowDown = 1.0; burstSlowDown = 1.0;
else else
burstSlowDown = 1.3; burstSlowDown = 1.3;
fireTimeVar += FireRate * burstSlowDown; fireTimeVar += usedFireRate * burstSlowDown;
} }
else else
fireTimeVar += FireRate; fireTimeVar += usedFireRate;
fireTimeVar = FMax(fireTimeVar, Level.TimeSeconds); fireTimeVar = FMax(fireTimeVar, Level.TimeSeconds);
} }
return fireTimeVar; return fireTimeVar;
@ -712,13 +741,19 @@ simulated function float UpdateNextFireTime(float fireTimeVar){
defaultproperties defaultproperties
{ {
zedTimeFireSpeedUp=1.000000 zedTimeFireSpeedUp=1.000000
ProjPerFire=1 ProjPerFire=1
ProjectileSpeed=1524.000000 ProjectileSpeed=1524.000000
MaxBurstLength=3 MaxBurstLength=3
bulletClass=class'NiceBullet' bulletClass=class'NiceBullet'
contBonus=1.200000 contBonus=1.200000
contBonusReset=True contBonusReset=True
maxBonusContLenght=1 maxBonusContLenght=1
AmmoPerFire=1 AmmoPerFire=1
minimalSpreadScale=1
activeSpreadScale=1
spreadGainedPerShot=0
spreadLostPerSecond=0
RecoilVelocityScale = 0
aimingSpreadReductionCoefficient = 0.5
} }

View File

@ -1,76 +1,160 @@
class NiceProjectileSpawner extends Actor class NiceProjectileSpawner extends Actor
dependson(NiceBullet); dependson(NiceBullet);
// NICETODO: use flags correctly // NICETODO: use flags correctly
static function MakeProjectile(Vector start, Rotator dir, NiceFire.ShotType shotParams, NiceFire.FireModeContext fireContext, optional bool bForceComplexTraj, static function MakeProjectile(
optional bool bDuplReal, optional bool bSkipGhosts){ Vector start,
Rotator dir,
NiceFire.ShotType shotParams,
NiceFire.FireModeContext fireContext,
optional bool bForceComplexTraj,
optional bool bDuplReal,
optional bool bSkipGhosts
) {
local int i; local int i;
local NicePack niceMut; local NicePack niceMut;
niceMut = class'NicePack'.static.Myself(fireContext.Instigator.Level); niceMut = class'NicePack'.static.Myself(fireContext.Instigator.Level);
if(niceMut == none) if (niceMut == none) {
return; return;
if(fireContext.Instigator.Role < ROLE_Authority || bDuplReal) }
SpawnProjectile(Start, Dir, shotParams, fireContext, false, bForceComplexTraj); if (fireContext.Instigator.Role < ROLE_Authority || bDuplReal) {
if(fireContext.Instigator.Role == ROLE_Authority && niceMut != none && !bSkipGhosts){ SpawnProjectile(Start, Dir, shotParams, fireContext, false, bForceComplexTraj);
for(i = 0;i < niceMut.playersList.Length;i ++){ }
if(niceMut.playersList[i] != fireContext.Instigator.Controller) if (fireContext.Instigator.Role == ROLE_Authority && niceMut != none && !bSkipGhosts) {
niceMut.playersList[i].ClientSpawnGhostProjectile(start, dir.pitch, dir.yaw, dir.roll, shotParams, fireContext, bForceComplexTraj); for (i = 0; i < niceMut.playersList.Length; i++) {
} if (niceMut.playersList[i] != fireContext.Instigator.Controller) {
niceMut.playersList[i].ClientSpawnGhostProjectile(
start,
dir.pitch,
dir.yaw,
dir.roll,
shotParams,
fireContext,
bForceComplexTraj
);
}
}
} }
} }
static function StickProjectile(KFHumanPawn instigator, Actor base, name bone, Vector shift, Rotator direction,
NiceBullet.ExplosionData expData, optional bool bDuplReal, optional bool bSkipGhosts){ static function StickProjectile(
KFHumanPawn instigator,
Actor base,
name bone,
Vector shift,
Rotator direction,
NiceBullet.ExplosionData expData,
optional bool bDuplReal,
optional bool bSkipGhosts
) {
local int i; local int i;
local NicePack niceMut; local NicePack niceMut;
niceMut = class'NicePack'.static.Myself(expData.Instigator.Level); niceMut = class'NicePack'.static.Myself(expData.Instigator.Level);
if(niceMut == none) if (niceMut == none) {
return; return;
}
niceMut.stuckCounter ++; niceMut.stuckCounter ++;
if(expData.Instigator.Role < ROLE_Authority) if (expData.Instigator.Role < ROLE_Authority) {
SpawnStuckProjectile(instigator, base, bone, shift, direction, expData, false, niceMut.stuckCounter); SpawnStuckProjectile(
if(expData.Instigator.Role == ROLE_Authority && niceMut != none){ instigator,
for(i = 0;i < niceMut.playersList.Length;i ++){ base,
if( (niceMut.playersList[i] != expData.Instigator.Controller && !bSkipGhosts) bone,
|| (niceMut.playersList[i] == expData.Instigator.Controller && bDuplReal) ) shift,
niceMut.playersList[i].ClientStickGhostProjectile(instigator, base, bone, shift, direction, expData, direction,
niceMut.stuckCounter); expData,
} false,
niceMut.stuckCounter
);
}
if (expData.Instigator.Role == ROLE_Authority && niceMut != none) {
for (i = 0; i < niceMut.playersList.Length; i++) {
if (
(niceMut.playersList[i] != expData.Instigator.Controller && !bSkipGhosts) ||
(niceMut.playersList[i] == expData.Instigator.Controller && bDuplReal)
) {
niceMut.playersList[i].ClientStickGhostProjectile(
instigator,
base,
bone,
shift,
direction,
expData,
niceMut.stuckCounter
);
}
}
} }
} }
static function NiceBullet SpawnProjectile(Vector Start, Rotator Dir, NiceFire.ShotType shotParams, NiceFire.FireModeContext fireContext, optional bool bIsGhost, optional bool bForceComplexTraj){
static function NiceBullet SpawnProjectile(
Vector Start,
Rotator Dir,
NiceFire.ShotType shotParams,
NiceFire.FireModeContext fireContext,
optional bool bIsGhost,
optional bool bForceComplexTraj
) {
local Actor other; local Actor other;
local NiceBullet niceProj; local NiceBullet niceProj;
local Vector HitLocation, HitNormal; local Vector HitLocation, HitNormal;
local NicePlayerController nicePlayer; local NicePlayerController nicePlayer;
local class<NiceVeterancyTypes> niceVet; local class<NiceVeterancyTypes> niceVet;
// No class - no projectile // No class - no projectile
if(shotParams.bulletClass == none) if (shotParams.bulletClass == none) {
return none; return none;
}
// Try to spawn // Try to spawn
if(fireContext.Instigator != none) if (fireContext.Instigator != none) {
niceProj = fireContext.Instigator.Spawn(shotParams.bulletClass,,, Start, Dir); niceProj = fireContext.Instigator.Spawn(shotParams.bulletClass,,, Start, Dir);
}
// Try harder // Try harder
if(niceProj == none && fireContext.Instigator != none){ if (niceProj == none && fireContext.Instigator != none) {
other = fireContext.Instigator.Trace(HitLocation, HitNormal, Start, fireContext.Instigator.Location + fireContext.Instigator.EyePosition(), false, Vect(0,0,1)); other = fireContext.Instigator.Trace(
if(other != none) HitLocation,
Start = HitLocation; HitNormal,
niceProj = fireContext.Instigator.Spawn(shotParams.bulletClass,,, Start, Dir); Start,
fireContext.Instigator.Location + fireContext.Instigator.EyePosition(),
false,
Vect(0, 0, 1)
);
if (other != none) {
Start = HitLocation;
}
niceProj = fireContext.Instigator.Spawn(shotParams.bulletClass,,, Start, Dir);
} }
// Give up if failed after these two attempts // Give up if failed after these two attempts
if(niceProj == none) if (niceProj == none) {
return none; return none;
}
niceProj.Renew(); niceProj.Renew();
// Initialize projectile // Initialize projectile
if(fireContext.Instigator != none) if (fireContext.Instigator != none) {
nicePlayer = NicePlayerController(fireContext.Instigator.Controller); nicePlayer = NicePlayerController(fireContext.Instigator.Controller);
if(nicePlayer != none) }
niceVet = class'NiceVeterancyTypes'.static.GetVeterancy(nicePlayer.PlayerReplicationInfo); if (nicePlayer != none) {
niceVet = class'NiceVeterancyTypes'.static.GetVeterancy(nicePlayer.PlayerReplicationInfo);
}
niceProj.bGhost = bIsGhost; niceProj.bGhost = bIsGhost;
// Fill-up data about what damage should projectile deal // Fill-up data about what damage should projectile deal
niceProj.charDamage = shotParams.damage; niceProj.charDamage = shotParams.damage;
if(niceVet != none && fireContext.bIsBursting && niceVet.static.hasSkill(nicePlayer, class'NiceSkillCommandoExplosivePower')) if (
niceVet != none &&
fireContext.bIsBursting &&
niceVet.static.hasSkill(nicePlayer, class'NiceSkillCommandoExplosivePower')
) {
niceProj.charDamage *= class'NiceSkillCommandoExplosivePower'.default.dmgMod; niceProj.charDamage *= class'NiceSkillCommandoExplosivePower'.default.dmgMod;
if(niceVet != none && niceVet.static.hasSkill(nicePlayer, class'NiceSkillSupportZEDBulletStorm') && nicePlayer.IsZedTimeActive()) }
if (
niceVet != none &&
niceVet.static.hasSkill(nicePlayer, class'NiceSkillSupportZEDBulletStorm') &&
nicePlayer.IsZedTimeActive()
) {
niceProj.charDamage = shotParams.damage * class'NiceSkillSupportZEDBulletStorm'.default.damageCut; niceProj.charDamage = shotParams.damage * class'NiceSkillSupportZEDBulletStorm'.default.damageCut;
}
niceProj.charOrigDamage = niceProj.charDamage; niceProj.charOrigDamage = niceProj.charDamage;
niceProj.charDamageType = shotParams.shotDamageType; niceProj.charDamageType = shotParams.shotDamageType;
niceProj.charExplosionDamageType = shotParams.explosionDamageType; niceProj.charExplosionDamageType = shotParams.explosionDamageType;
@ -92,76 +176,95 @@ static function NiceBullet SpawnProjectile(Vector Start, Rotator Dir, NiceFire.S
niceProj.charContiniousBonus = fireContext.continiousBonus; niceProj.charContiniousBonus = fireContext.continiousBonus;
// Fill-up data about at what speed should projectile travel // Fill-up data about at what speed should projectile travel
niceProj.movementSpeed = shotParams.projSpeed; niceProj.movementSpeed = shotParams.projSpeed;
if(niceVet != none && niceVet.static.hasSkill(nicePlayer, class'NiceSkillDemoOnperk')) if (niceVet != none && niceVet.static.hasSkill(nicePlayer, class'NiceSkillDemoOnperk')) {
niceProj.movementSpeed *= class'NiceSkillDemoOnperk'.default.speedBonus; niceProj.movementSpeed *= class'NiceSkillDemoOnperk'.default.speedBonus;
}
niceProj.movementDirection = Vector(niceProj.rotation); niceProj.movementDirection = Vector(niceProj.rotation);
niceProj.charAffectedByScream = shotParams.projAffectedByScream; niceProj.charAffectedByScream = shotParams.projAffectedByScream;
niceProj.charIsSticky = shotParams.bShouldStick; niceProj.charIsSticky = shotParams.bShouldStick;
niceProj.nicePlayer = nicePlayer; niceProj.nicePlayer = nicePlayer;
if(niceVet != none && niceVet.static.hasSkill(nicePlayer, class'NiceSkillDemoVolatile')){ if (niceVet != none && niceVet.static.hasSkill(nicePlayer, class'NiceSkillDemoVolatile')) {
niceProj.charExplosionRadius *= class'NiceSkillDemoVolatile'.default.explRangeMult; niceProj.charExplosionRadius *= class'NiceSkillDemoVolatile'.default.explRangeMult;
niceProj.charExplosionExponent *= class'NiceSkillDemoVolatile'.default.falloffMult; niceProj.charExplosionExponent *= class'NiceSkillDemoVolatile'.default.falloffMult;
niceProj.charMinExplosionDist *= class'NiceSkillDemoVolatile'.default.safeDistanceMult; niceProj.charMinExplosionDist *= class'NiceSkillDemoVolatile'.default.safeDistanceMult;
} }
if(niceVet != none && niceVet.static.hasSkill(nicePlayer, class'NiceSkillDemoZEDFullBlast') && nicePlayer.IsZedTimeActive()){ if (
niceProj.charExplosionRadius *= class'NiceSkillDemoZEDFullBlast'.default.explRadiusMult; niceVet != none &&
niceProj.charExplosionExponent = 0.0; niceVet.static.hasSkill(nicePlayer, class'NiceSkillDemoZEDFullBlast') &&
nicePlayer.IsZedTimeActive()
) {
niceProj.charExplosionRadius *= class'NiceSkillDemoZEDFullBlast'.default.explRadiusMult;
niceProj.charExplosionExponent = 0.0;
}
if (bForceComplexTraj) {
niceProj.bDisableComplexMovement = false;
}
if (niceProj.Instigator != none && NicePlayerController(niceProj.Instigator.Controller) != none) {
niceProj.niceRI = NicePlayerController(niceProj.Instigator.Controller).NiceRI;
} }
if(bForceComplexTraj)
niceProj.bDisableComplexMovement = false;
if(niceProj.Instigator != none && NicePlayerController(niceProj.Instigator.Controller) != none)
niceProj.niceRI = NicePlayerController(niceProj.Instigator.Controller).NiceRI;
// And some leftovers // And some leftovers
//niceProj.bShouldBounce = shotParams.bShouldBounce; //niceProj.bShouldBounce = shotParams.bShouldBounce;
niceProj.bInitFinished = true; niceProj.bInitFinished = true;
return niceProj; return niceProj;
} }
static function SpawnStuckProjectile(KFHumanPawn instigator, Actor base, name bone, Vector shift, Rotator direction,
NiceBullet.ExplosionData expData, bool bIsGhost, int stuckID){ static function SpawnStuckProjectile(
local Pawn justPawn; KFHumanPawn instigator,
local NiceFire.ShotType shotParams; Actor base,
local NiceFire.FireModeContext fireContext; name bone,
local NiceBullet spawnedBullet; Vector shift,
local NicePlayerController nicePlayer; Rotator direction,
NiceBullet.ExplosionData expData,
bool bIsGhost,
int stuckID
) {
local Pawn justPawn;
local NiceFire.ShotType shotParams;
local NiceFire.FireModeContext fireContext;
local NiceBullet spawnedBullet;
local NicePlayerController nicePlayer;
nicePlayer = NicePlayerController(instigator.Controller); nicePlayer = NicePlayerController(instigator.Controller);
if(base == none || nicePlayer == none) if (base == none || nicePlayer == none) {
return; return;
}
justPawn = Pawn(base); justPawn = Pawn(base);
fireContext.instigator = NiceHumanPawn(instigator); fireContext.instigator = NiceHumanPawn(instigator);
fireContext.sourceWeapon = expData.sourceWeapon; fireContext.sourceWeapon = expData.sourceWeapon;
shotParams.bulletClass = expData.bulletClass; shotParams.bulletClass = expData.bulletClass;
shotParams.explosionDamageType = expData.explosionDamageType; shotParams.explosionDamageType = expData.explosionDamageType;
shotParams.explosionDamage = expData.explosionDamage; shotParams.explosionDamage = expData.explosionDamage;
shotParams.explosionRadius = expData.explosionRadius; shotParams.explosionRadius = expData.explosionRadius;
shotParams.explosionExponent = expData.explosionExponent; shotParams.explosionExponent = expData.explosionExponent;
shotParams.explosionMomentum = expData.explosionMomentum; shotParams.explosionMomentum = expData.explosionMomentum;
shotParams.fuseTime = expData.fuseTime; shotParams.fuseTime = expData.fuseTime;
shotParams.explodeOnFuse = expData.explodeOnFuse; shotParams.explodeOnFuse = expData.explodeOnFuse;
shotParams.projAffectedByScream = expData.affectedByScream; shotParams.projAffectedByScream = expData.affectedByScream;
spawnedBullet = SpawnProjectile(base.location, direction, shotParams, fireContext, bIsGhost); spawnedBullet = SpawnProjectile(base.location, direction, shotParams, fireContext, bIsGhost);
if(spawnedBullet == none) if (spawnedBullet == none) {
return; return;
}
spawnedBullet.stuckID = stuckID; spawnedBullet.stuckID = stuckID;
spawnedBullet.bStuck = true; spawnedBullet.bStuck = true;
nicePlayer.RegisterStuckBullet(spawnedBullet); nicePlayer.RegisterStuckBullet(spawnedBullet);
if(justPawn != none){ if (justPawn != none) {
spawnedBullet.bStuckToHead = expData.stuckToHead; spawnedBullet.bStuckToHead = expData.stuckToHead;
spawnedBullet.SetBase(base); spawnedBullet.SetBase(base);
justPawn.AttachToBone(spawnedBullet, bone); justPawn.AttachToBone(spawnedBullet, bone);
spawnedBullet.SetRelativeLocation(shift); spawnedBullet.SetRelativeLocation(shift);
spawnedBullet.SetRelativeRotation(Rotator(Vector(direction) << justPawn.GetBoneRotation(bone, 0))); spawnedBullet.SetRelativeRotation(Rotator(Vector(direction) << justPawn.GetBoneRotation(bone, 0)));
spawnedBullet.bUseBone = true; spawnedBullet.bUseBone = true;
spawnedBullet.stuckBone = bone; spawnedBullet.stuckBone = bone;
} } else {
else{ spawnedBullet.SetBase(base);
spawnedBullet.SetBase(base); spawnedBullet.SetRelativeLocation(shift);
spawnedBullet.SetRelativeLocation(shift); spawnedBullet.SetRelativeRotation(direction - base.rotation);
} }
} }
defaultproperties defaultproperties {
{ bHidden=True
bHidden=True RemoteRole=ROLE_SimulatedProxy
RemoteRole=ROLE_SimulatedProxy LifeSpan=1.000000
LifeSpan=1.000000 }
}

View File

@ -146,6 +146,7 @@ var bool bAutoReloadPaused; // This is used to 'pause' auto relo
var float autoReloadPauseFrame; // Frame at which current pause began var float autoReloadPauseFrame; // Frame at which current pause began
var bool bAutoReloadRateApplied; // Flag that remembers whether or not we've already applied reload speed up for current auto reload (to avoid constant animation's speed updates) var bool bAutoReloadRateApplied; // Flag that remembers whether or not we've already applied reload speed up for current auto reload (to avoid constant animation's speed updates)
var float autoReloadSpeedModifier; var float autoReloadSpeedModifier;
var bool updatedDefaultReloadValues;
// Acrtive reload-related variables // Acrtive reload-related variables
// Active reload state // Active reload state
enum EActiveReloadState{ enum EActiveReloadState{
@ -219,6 +220,8 @@ static function bool UnloadAssets(){
return default.ReferenceCount == 0; return default.ReferenceCount == 0;
} }
simulated function PostBeginPlay(){ simulated function PostBeginPlay(){
local float swapSpeedMod, reloadSpeedMod;
if(default.recordedZoomTime < 0) if(default.recordedZoomTime < 0)
default.recordedZoomTime = ZoomTime; default.recordedZoomTime = ZoomTime;
recordedZoomTime = default.recordedZoomTime; recordedZoomTime = default.recordedZoomTime;
@ -240,6 +243,31 @@ simulated function PostBeginPlay(){
if(FireModeClass[0] != none) if(FireModeClass[0] != none)
stdFireRate = FireModeClass[0].default.fireRate; stdFireRate = FireModeClass[0].default.fireRate;
super.PostBeginPlay(); super.PostBeginPlay();
// Hack solution - speed up reload and swap speed
swapSpeedMod = 2.0;
reloadSpeedMod = 1.5;
bringUpTime /= swapSpeedMod;
putDownTime /= swapSpeedMod;
selectAnimRate *= swapSpeedMod;
putDownAnimRate *= swapSpeedMod;
quickPutDownTime /= swapSpeedMod;
quickBringUpTime /= swapSpeedMod;
if (!default.updatedDefaultReloadValues) {
if(reloadType == RTYPE_AUTO) {
if (fireModeClass[0] != none) {
fireModeClass[0].default.FireAnimRate *= reloadSpeedMod;
}
if (fireModeClass[1] != none) {
fireModeClass[1].default.FireAnimRate *= reloadSpeedMod;
}
} else {
reloadRate /= reloadSpeedMod;
reloadAnimRate *= reloadSpeedMod;
default.reloadRate = reloadRate;
default.reloadAnimRate = reloadAnimRate;
}
default.updatedDefaultReloadValues = true;
}
} }
// Allows to prevent leaving iron sights unwillingly // Allows to prevent leaving iron sights unwillingly
@ -1094,6 +1122,7 @@ simulated function int GetMagazineAmmo(){
else else
return MagAmmoRemaining; return MagAmmoRemaining;
} }
simulated function bool AllowReload(){ simulated function bool AllowReload(){
local int actualMagSize; local int actualMagSize;
actualMagSize = GetMagazineAmmo(); actualMagSize = GetMagazineAmmo();
@ -1127,6 +1156,7 @@ simulated function float GetCurrentReloadMult(){
local NiceHumanPawn nicePawn; local NiceHumanPawn nicePawn;
local NicePlayerController nicePlayer; local NicePlayerController nicePlayer;
local class<NiceVeterancyTypes> niceVet; local class<NiceVeterancyTypes> niceVet;
nicePawn = NiceHumanPawn(Instigator); nicePawn = NiceHumanPawn(Instigator);
nicePlayer = NicePlayerController(Instigator.Controller); nicePlayer = NicePlayerController(Instigator.Controller);
if(nicePawn != none) if(nicePawn != none)
@ -1624,17 +1654,17 @@ simulated function float GetAmmoMulti()
defaultproperties defaultproperties
{ {
recordedZoomTime=-1.000000 recordedZoomTime=-1.000000
SecondaryCharge=1 SecondaryCharge=1
LaserAttachmentClass=Class'ScrnLaserAttachmentFirstPerson' LaserAttachmentClass=Class'ScrnLaserAttachmentFirstPerson'
LaserDotClass=Class'ScrnLocalLaserDot' LaserDotClass=Class'ScrnLocalLaserDot'
LaserAttachmentBone="LightBone" LaserAttachmentBone="LightBone"
MagazineBone="Magazine" MagazineBone="Magazine"
bHasChargePhase=True bHasChargePhase=True
autoReloadSpeedModifier=1.000000 autoReloadSpeedModifier=1.000000
bCanActiveReload=True bCanActiveReload=True
activeSlowdown=0.850000 activeSlowdown=0.850000
activeSpeedup=1.150000 activeSpeedup=1.150000
activeWindow=0.060000 activeWindow=0.060000
bModeZeroCanDryFire=True bModeZeroCanDryFire=True
} }

View File

@ -3,7 +3,7 @@ defaultproperties
{ {
Weight=6.000000 Weight=6.000000
cost=750 cost=750
AmmoCost=19 AmmoCost=25
BuyClipSize=40 BuyClipSize=40
PowerValue=55 PowerValue=55
SpeedValue=80 SpeedValue=80

View File

@ -3,7 +3,7 @@ defaultproperties
{ {
Weight=6.000000 Weight=6.000000
cost=750 cost=750
AmmoCost=19 AmmoCost=26
BuyClipSize=30 BuyClipSize=30
PowerValue=40 PowerValue=40
SpeedValue=80 SpeedValue=80

View File

@ -3,7 +3,7 @@ defaultproperties
{ {
Weight=6.000000 Weight=6.000000
cost=750 cost=750
AmmoCost=22 AmmoCost=19
BuyClipSize=30 BuyClipSize=30
PowerValue=40 PowerValue=40
SpeedValue=85 SpeedValue=85

View File

@ -19,7 +19,7 @@ defaultproperties
StereoFireSoundRef="KF_LAWSnd.LAW_FireST" StereoFireSoundRef="KF_LAWSnd.LAW_FireST"
NoAmmoSoundRef="KF_LAWSnd.LAW_DryFire" NoAmmoSoundRef="KF_LAWSnd.LAW_DryFire"
DamageType=class'NiceDamTypeLAWBlunt' DamageType=class'NiceDamTypeLAWBlunt'
DamageMax=750 DamageMax=350
bSplashDamage=True bSplashDamage=True
bRecommendSplashDamage=True bRecommendSplashDamage=True
bWaitForRelease=True bWaitForRelease=True

View File

@ -39,114 +39,32 @@ function TakeDamage(int Damage, Pawn InstigatedBy, Vector HitLocation, Vector Mo
Explode(HitLocation, vect(0,0,1)); Explode(HitLocation, vect(0,0,1));
} }
} }
simulated function HurtRadius( float DamageAmount, float DamageRadius, class<DamageType> DamageType, float Momentum, vector HitLocation )
{
local actor Victims;
local float damageScale, dist;
local vector dir;
local int NumKilled;
local KFMonster KFMonsterVictim;
local bool bMonster;
local Pawn P;
local KFPawn KFP;
local array<Pawn> CheckedPawns;
local int i;
local bool bAlreadyChecked;
local SRStatsBase Stats;
if ( bHurtEntry ) simulated function HurtRadius(
return; float damageAmount,
bHurtEntry = true; float damageRadius,
class<DamageType> damageType,
if( Role == ROLE_Authority && Instigator != none && Instigator.PlayerReplicationInfo != none ) float momentum,
Stats = SRStatsBase(Instigator.PlayerReplicationInfo.SteamStatsAndAchievements); Vector hitLocation
) {
foreach CollidingActors (class 'Actor', Victims, DamageRadius, HitLocation) local NicePlayerController niceController;
{ local NiceReplicationInfo niceRI;
P = none;
KFMonsterVictim = none;
bMonster = false;
KFP = none;
bAlreadyChecked = false;
// don't let blast damage affect fluid - VisibleCollisingActors doesn't really work for them - jag if (instigator == none) return;
if( (Victims != self) && (Hurtwall != Victims) && (Victims.Role == ROLE_Authority) && !Victims.IsA('FluidSurfaceInfo') niceController = NicePlayerController(instigator.controller);
&& ExtendedZCollision(Victims)==None ) if (niceController == none) return;
{ niceRI = niceController.niceRI;
if( (Instigator==None || Instigator.Health<=0) && KFPawn(Victims)!=None ) if (niceRI == none) return;
Continue;
dir = Victims.Location - HitLocation;
dist = FMax(1,VSize(dir));
dir = dir/dist;
damageScale = 1 - FMax(0,(dist - Victims.CollisionRadius)/DamageRadius);
if ( Instigator == None || Instigator.Controller == None ) Destroy();
{
Victims.SetDelayedDamageInstigatorController( InstigatorController );
}
P = Pawn(Victims); niceRI.ServerExplode(damageAmount,
if( P != none ) { damageRadius,
for (i = 0; i < CheckedPawns.Length; i++) { 1.0,
if (CheckedPawns[i] == P) { niceExplosiveDamage,
bAlreadyChecked = true; momentum,
break; hitLocation,
} instigator);
}
if( bAlreadyChecked )
continue;
CheckedPawns[CheckedPawns.Length] = P;
KFMonsterVictim = KFMonster(Victims);
if( KFMonsterVictim != none && KFMonsterVictim.Health <= 0 )
KFMonsterVictim = none;
KFP = KFPawn(Victims);
if( KFMonsterVictim != none ) {
damageScale *= KFMonsterVictim.GetExposureTo(Location + 15 * -Normal(PhysicsVolume.Gravity));
bMonster = true; // in case TakeDamage() and further Die() deletes the monster
}
else if( KFP != none ) {
damageScale *= KFP.GetExposureTo(Location + 15 * -Normal(PhysicsVolume.Gravity));
}
if ( damageScale <= 0)
continue;
}
if(NiceMonster(Victims) != none)
Victims.TakeDamage(damageScale * DamageAmount,Instigator,Victims.Location - 0.5 * (Victims.CollisionHeight + Victims.CollisionRadius) * dir
,(damageScale * Momentum * dir), niceExplosiveDamage);
else
Victims.TakeDamage(damageScale * DamageAmount,Instigator,Victims.Location - 0.5 * (Victims.CollisionHeight + Victims.CollisionRadius) * dir
,(damageScale * Momentum * dir), DamageType);
if( bMonster && (KFMonsterVictim == none || KFMonsterVictim.Health < 1) ) {
NumKilled++;
}
if (Vehicle(Victims) != None && Vehicle(Victims).Health > 0)
{
Vehicle(Victims).DriverRadiusDamage(DamageAmount, DamageRadius, InstigatorController, DamageType, Momentum, HitLocation);
}
}
}
if( Role == ROLE_Authority )
{
if ( bBlewInHands && NumKilled >= 5 && Stats != none )
class'ScrnAchievements'.static.ProgressAchievementByID(Stats.Rep, 'SuicideBomber', 1);
if ( NumKilled >= 4 )
{
KFGameType(Level.Game).DramaticEvent(0.05);
}
else if ( NumKilled >= 2 )
{
KFGameType(Level.Game).DramaticEvent(0.03);
}
}
bHurtEntry = false;
} }
// Overridden to spawn different AvoidMarker // Overridden to spawn different AvoidMarker
simulated function HitWall( vector HitNormal, actor Wall ){ simulated function HitWall( vector HitNormal, actor Wall ){

View File

@ -4,8 +4,8 @@ defaultproperties
ProjectileSpeed=48250.000000 ProjectileSpeed=48250.000000
FireAimedAnim="Fire" FireAimedAnim="Fire"
RecoilRate=0.040000 RecoilRate=0.040000
maxVerticalRecoilAngle=550 maxVerticalRecoilAngle=115
maxHorizontalRecoilAngle=225 maxHorizontalRecoilAngle=0
ShellEjectClass=Class'ROEffects.KFShellEjectAK' ShellEjectClass=Class'ROEffects.KFShellEjectAK'
ShellEjectBoneName="Shell_eject" ShellEjectBoneName="Shell_eject"
bAccuracyBonusForSemiAuto=True bAccuracyBonusForSemiAuto=True

View File

@ -10,4 +10,6 @@ defaultproperties
KDeathVel=1400.000000 KDeathVel=1400.000000
KDeathUpKick=150.000000 KDeathUpKick=150.000000
VehicleDamageScaling=0.700000 VehicleDamageScaling=0.700000
stunMultiplier=3.0
stunLengthMultiplier=2.0
} }

View File

@ -4,8 +4,8 @@ defaultproperties
{ {
WeaponPickupClass=class'NiceM41APickup' WeaponPickupClass=class'NiceM41APickup'
AmmoPickupAmount=66 AmmoPickupAmount=66
MaxAmmo=300 MaxAmmo=264
InitialAmount=75 InitialAmount=66
PickupClass=class'NiceM41AAmmoPickup' PickupClass=class'NiceM41AAmmoPickup'
IconMaterial=Texture'KillingFloorHUD.Generic.HUD' IconMaterial=Texture'KillingFloorHUD.Generic.HUD'
IconCoords=(X1=336,Y1=82,X2=382,Y2=125) IconCoords=(X1=336,Y1=82,X2=382,Y2=125)

View File

@ -3,7 +3,7 @@ class NiceM41APickup extends NiceM41APrimaryPickup;
defaultproperties defaultproperties
{ {
crossPerkIndecies(0)=6 crossPerkIndecies(0)=6
AmmoCost=60 AmmoCost=24
BuyClipSize=1 BuyClipSize=1
SecondaryAmmoShortName="M41A Frag Grenades" SecondaryAmmoShortName="M41A Frag Grenades"
PrimaryWeaponPickup=class'NiceM41APrimaryPickup' PrimaryWeaponPickup=class'NiceM41APrimaryPickup'

View File

@ -3,7 +3,7 @@ defaultproperties
{ {
cost=750 cost=750
Weight=7.000000 Weight=7.000000
AmmoCost=66 AmmoCost=25
BuyClipSize=66 BuyClipSize=66
PowerValue=70 PowerValue=70
SpeedValue=100 SpeedValue=100

View File

@ -3,7 +3,7 @@ defaultproperties
{ {
WeaponPickupClass=class'NiceM41APickup' WeaponPickupClass=class'NiceM41APickup'
AmmoPickupAmount=1 AmmoPickupAmount=1
MaxAmmo=8 MaxAmmo=5
InitialAmount=2 InitialAmount=2
IconMaterial=Texture'KillingFloorHUD.Generic.HUD' IconMaterial=Texture'KillingFloorHUD.Generic.HUD'
IconCoords=(X1=434,Y1=253,X2=506,Y2=292) IconCoords=(X1=434,Y1=253,X2=506,Y2=292)

View File

@ -5,8 +5,8 @@ defaultproperties
contBonus=1.400000 contBonus=1.400000
FireAimedAnim="Fire_Iron" FireAimedAnim="Fire_Iron"
RecoilRate=0.050000 RecoilRate=0.050000
maxVerticalRecoilAngle=400 maxVerticalRecoilAngle=100
maxHorizontalRecoilAngle=200 maxHorizontalRecoilAngle=0
ShellEjectClass=Class'ROEffects.KFShellEjectAK' ShellEjectClass=Class'ROEffects.KFShellEjectAK'
ShellEjectBoneName="Shell_eject" ShellEjectBoneName="Shell_eject"
bAccuracyBonusForSemiAuto=True bAccuracyBonusForSemiAuto=True

View File

@ -17,7 +17,7 @@ defaultproperties
MagazineBone="clip" MagazineBone="clip"
bHasScope=True bHasScope=True
ZoomedDisplayFOVHigh=50.000000 ZoomedDisplayFOVHigh=50.000000
MagCapacity=30 MagCapacity=60
ReloadRate=3.500000 ReloadRate=3.500000
ReloadAnim="Reload" ReloadAnim="Reload"
ReloadAnimRate=1.000000 ReloadAnimRate=1.000000

View File

@ -2,7 +2,7 @@ class NiceSA80LSWAmmo extends NiceAmmo;
defaultproperties defaultproperties
{ {
WeaponPickupClass=class'NiceSA80LSWPickup' WeaponPickupClass=class'NiceSA80LSWPickup'
AmmoPickupAmount=30 AmmoPickupAmount=60
MaxAmmo=360 MaxAmmo=360
InitialAmount=90 InitialAmount=90
PickupClass=class'NiceSA80LSWAmmoPickup' PickupClass=class'NiceSA80LSWAmmoPickup'

View File

@ -1,7 +1,7 @@
class NiceSA80LSWAmmoPickup extends NiceAmmoPickup; class NiceSA80LSWAmmoPickup extends NiceAmmoPickup;
defaultproperties defaultproperties
{ {
AmmoAmount=30 AmmoAmount=60
InventoryType=class'NiceSA80LSWAmmo' InventoryType=class'NiceSA80LSWAmmo'
PickupMessage="5.56x45" PickupMessage="5.56x45"
StaticMesh=StaticMesh'KillingFloorStatics.L85Ammo' StaticMesh=StaticMesh'KillingFloorStatics.L85Ammo'

View File

@ -4,8 +4,8 @@ defaultproperties
ProjectileSpeed=46500.000000 ProjectileSpeed=46500.000000
FireAimedAnim="Iron_Idle" FireAimedAnim="Iron_Idle"
RecoilRate=0.050000 RecoilRate=0.050000
maxVerticalRecoilAngle=300 maxVerticalRecoilAngle=75
maxHorizontalRecoilAngle=150 maxHorizontalRecoilAngle=0
ShellEjectClass=Class'ROEffects.KFShellEjectBullpup' ShellEjectClass=Class'ROEffects.KFShellEjectBullpup'
ShellEjectBoneName="Shell_eject" ShellEjectBoneName="Shell_eject"
bAccuracyBonusForSemiAuto=True bAccuracyBonusForSemiAuto=True

View File

@ -3,8 +3,8 @@ defaultproperties
{ {
cost=200 cost=200
Weight=5.000000 Weight=5.000000
AmmoCost=5 AmmoCost=10
BuyClipSize=30 BuyClipSize=60
PowerValue=41 PowerValue=41
SpeedValue=60 SpeedValue=60
RangeValue=60 RangeValue=60

View File

@ -12,12 +12,12 @@ simulated function HandleRecoil(float Rec)
defaultproperties defaultproperties
{ {
ProjectileSpeed=42650.000000 ProjectileSpeed=42650.000000
maxBonusContLenght=5 maxBonusContLenght=10
contBonusReset=false contBonusReset=false
FireAimedAnim="FireLoop" FireAimedAnim="FireLoop"
RecoilRate=0.040000 RecoilRate=0.040000
maxVerticalRecoilAngle=450 maxVerticalRecoilAngle=25
maxHorizontalRecoilAngle=225 maxHorizontalRecoilAngle=0
ShellEjectClass=Class'ROEffects.KFShellEjectSCAR' ShellEjectClass=Class'ROEffects.KFShellEjectSCAR'
ShellEjectBoneName="ejector" ShellEjectBoneName="ejector"
FireSoundRef="HMG_S.XMV.XMV-Fire-1" FireSoundRef="HMG_S.XMV.XMV-Fire-1"

View File

@ -1,19 +0,0 @@
class NiceDamTypeHFRAssaultRifle extends NiceDamTypeFire
abstract;
defaultproperties
{
heatPart=0.500000
HeadShotDamageMult=6.000000
bCheckForHeadShots=True
WeaponClass=class'NiceHFR'
DeathString="%k killed %o (Horzine Flame Rifle)."
FemaleSuicide="%o shot herself in the foot."
MaleSuicide="%o shot himself in the foot."
bRagdollBullet=True
PawnDamageEmitter=Class'ROEffects.ROBloodPuff'
LowGoreDamageEmitter=Class'ROEffects.ROBloodPuffNoGore'
LowDetailEmitter=Class'ROEffects.ROBloodPuffSmall'
KDamageImpulse=5500.000000
KDeathVel=175.000000
KDeathUpKick=15.000000
}

View File

@ -1,316 +1,5 @@
// Modification of the AAR525 weapons by: [B.R]HekuT class NiceHFR extends NiceScopedWeapon;
class NiceHFR extends KFWeapon;
#exec OBJ LOAD FILE=KillingFloorWeapons.utx
#exec OBJ LOAD FILE=KillingFloorHUD.utx
#exec OBJ LOAD FILE=Inf_Weapons_Foley.uax
#exec OBJ LOAD FILE=KF_Weapons5_Scopes_Trip_T.utx
var() Material ZoomMat;
var() int lenseMaterialID;
var() float scopePortalFOVHigh;
var() float scopePortalFOV;
var() vector XoffsetScoped;
var() vector XoffsetHighDetail;
var() int scopePitch;
var() int scopeYaw;
var() int scopePitchHigh;
var() int scopeYawHigh;
var ScriptedTexture ScopeScriptedTexture;
var Shader ScopeScriptedShader;
var Material ScriptedTextureFallback;
var Combiner ScriptedScopeCombiner;
var Combiner ScriptedScopeStatic;
var texture TexturedScopeTexture;
var bool bInitializedScope;
var string ZoomMatRef;
var string ScriptedTextureFallbackRef;
static function PreloadAssets(Inventory Inv, optional bool bSkipRefCount)
{
super.PreloadAssets(Inv, bSkipRefCount);
default.ZoomMat = FinalBlend(DynamicLoadObject(default.ZoomMatRef, class'FinalBlend', true));
default.ScriptedTextureFallback = texture(DynamicLoadObject(default.ScriptedTextureFallbackRef, class'texture', true));
if ( M99SniperRifle(Inv) != none )
{
M99SniperRifle(Inv).ZoomMat = default.ZoomMat;
M99SniperRifle(Inv).ScriptedTextureFallback = default.ScriptedTextureFallback;
}
}
static function bool UnloadAssets()
{
if ( super.UnloadAssets() )
{
default.ZoomMat = none;
default.ScriptedTextureFallback = none;
}
return true;
}
exec function pfov(int thisFOV)
{
if( !class'ROEngine.ROLevelInfo'.static.RODebugMode() )
return;
scopePortalFOV = thisFOV;
}
exec function pPitch(int num)
{
if( !class'ROEngine.ROLevelInfo'.static.RODebugMode() )
return;
scopePitch = num;
scopePitchHigh = num;
}
exec function pYaw(int num)
{
if( !class'ROEngine.ROLevelInfo'.static.RODebugMode() )
return;
scopeYaw = num;
scopeYawHigh = num;
}
simulated exec function TexSize(int i, int j)
{
if( !class'ROEngine.ROLevelInfo'.static.RODebugMode() )
return;
ScopeScriptedTexture.SetSize(i, j);
}
simulated function bool ShouldDrawPortal()
{
if( bAimingRifle )
return true;
else
return false;
}
simulated function PostBeginPlay()
{
super.PostBeginPlay();
KFScopeDetail = class'KFMod.KFWeapon'.default.KFScopeDetail;
UpdateScopeMode();
}
simulated function UpdateScopeMode()
{
if (Level.NetMode != NM_DedicatedServer && Instigator != none && Instigator.IsLocallyControlled() &&
Instigator.IsHumanControlled() )
{
if( KFScopeDetail == KF_ModelScope )
{
scopePortalFOV = default.scopePortalFOV;
ZoomedDisplayFOV = CalcAspectRatioAdjustedFOV(default.ZoomedDisplayFOV);
if (bAimingRifle)
{
PlayerViewOffset = XoffsetScoped;
}
if( ScopeScriptedTexture == none )
{
ScopeScriptedTexture = ScriptedTexture(Level.ObjectPool.AllocateObject(class'ScriptedTexture'));
}
ScopeScriptedTexture.FallBackMaterial = ScriptedTextureFallback;
ScopeScriptedTexture.SetSize(512,512);
ScopeScriptedTexture.Client = Self;
if( ScriptedScopeCombiner == none )
{
ScriptedScopeCombiner = Combiner(Level.ObjectPool.AllocateObject(class'Combiner'));
ScriptedScopeCombiner.Material1 = Texture'KF_Weapons5_Scopes_Trip_T.Scope.MilDot';
ScriptedScopeCombiner.FallbackMaterial = Shader'ScopeShaders.Zoomblur.LensShader';
ScriptedScopeCombiner.CombineOperation = CO_Multiply;
ScriptedScopeCombiner.AlphaOperation = AO_Use_Mask;
ScriptedScopeCombiner.Material2 = ScopeScriptedTexture;
}
if( ScopeScriptedShader == none )
{
ScopeScriptedShader = Shader(Level.ObjectPool.AllocateObject(class'Shader'));
ScopeScriptedShader.Diffuse = ScriptedScopeCombiner;
ScopeScriptedShader.SelfIllumination = ScriptedScopeCombiner;
ScopeScriptedShader.FallbackMaterial = Shader'ScopeShaders.Zoomblur.LensShader';
}
bInitializedScope = true;
}
else if( KFScopeDetail == KF_ModelScopeHigh )
{
scopePortalFOV = scopePortalFOVHigh;
ZoomedDisplayFOV = CalcAspectRatioAdjustedFOV(default.ZoomedDisplayFOVHigh);
if (bAimingRifle)
{
PlayerViewOffset = XoffsetHighDetail;
}
if( ScopeScriptedTexture == none )
{
ScopeScriptedTexture = ScriptedTexture(Level.ObjectPool.AllocateObject(class'ScriptedTexture'));
}
ScopeScriptedTexture.FallBackMaterial = ScriptedTextureFallback;
ScopeScriptedTexture.SetSize(1024,1024);
ScopeScriptedTexture.Client = Self;
if( ScriptedScopeCombiner == none )
{
ScriptedScopeCombiner = Combiner(Level.ObjectPool.AllocateObject(class'Combiner'));
ScriptedScopeCombiner.Material1 = Texture'KF_Weapons5_Scopes_Trip_T.Scope.MilDot';
ScriptedScopeCombiner.FallbackMaterial = Shader'ScopeShaders.Zoomblur.LensShader';
ScriptedScopeCombiner.CombineOperation = CO_Multiply;
ScriptedScopeCombiner.AlphaOperation = AO_Use_Mask;
ScriptedScopeCombiner.Material2 = ScopeScriptedTexture;
}
if( ScopeScriptedShader == none )
{
ScopeScriptedShader = Shader(Level.ObjectPool.AllocateObject(class'Shader'));
ScopeScriptedShader.Diffuse = ScriptedScopeCombiner;
ScopeScriptedShader.SelfIllumination = ScriptedScopeCombiner;
ScopeScriptedShader.FallbackMaterial = Shader'ScopeShaders.Zoomblur.LensShader';
}
bInitializedScope = true;
}
else if (KFScopeDetail == KF_TextureScope)
{
ZoomedDisplayFOV = CalcAspectRatioAdjustedFOV(default.ZoomedDisplayFOV);
PlayerViewOffset.X = default.PlayerViewOffset.X;
bInitializedScope = true;
}
}
}
simulated event RenderTexture(ScriptedTexture Tex)
{
local rotator RollMod;
RollMod = Instigator.GetViewRotation();
if(Owner != none && Instigator != none && Tex != none && Tex.Client != none)
Tex.DrawPortal(0,0,Tex.USize,Tex.VSize,Owner,(Instigator.Location + Instigator.EyePosition()), RollMod, scopePortalFOV );
}
/**
* Handles all the functionality for zooming in including
* setting the parameters for the weapon, pawn, and playercontroller
*
* @param bAnimateTransition whether or not to animate this zoom transition
*/
simulated function ZoomIn(bool bAnimateTransition)
{
super(BaseKFWeapon).ZoomIn(bAnimateTransition);
bAimingRifle = True;
if( KFHumanPawn(Instigator)!=none )
KFHumanPawn(Instigator).SetAiming(True);
if( Level.NetMode != NM_DedicatedServer && KFPlayerController(Instigator.Controller) != none )
{
if( AimInSound != none )
{
PlayOwnedSound(AimInSound, SLOT_Interact,,,,, false);
}
}
}
/**
* Handles all the functionality for zooming out including
* setting the parameters for the weapon, pawn, and playercontroller
*
* @param bAnimateTransition whether or not to animate this zoom transition
*/
simulated function ZoomOut(bool bAnimateTransition)
{
super.ZoomOut(bAnimateTransition);
bAimingRifle = False;
if( KFHumanPawn(Instigator)!=none )
KFHumanPawn(Instigator).SetAiming(False);
if( Level.NetMode != NM_DedicatedServer && KFPlayerController(Instigator.Controller) != none )
{
if( AimOutSound != none )
{
PlayOwnedSound(AimOutSound, SLOT_Interact,,,,, false);
}
KFPlayerController(Instigator.Controller).TransitionFOV(KFPlayerController(Instigator.Controller).DefaultFOV,0.0);
}
}
simulated event OnZoomInFinished()
{
local name anim;
local float frame, rate;
GetAnimParams(0, anim, frame, rate);
if (ClientState == WS_ReadyToFire)
{
if (anim == IdleAnim)
{
PlayIdle();
}
}
if( Level.NetMode != NM_DedicatedServer && KFPlayerController(Instigator.Controller) != none &&
KFScopeDetail == KF_TextureScope )
{
KFPlayerController(Instigator.Controller).TransitionFOV(PlayerIronSightFOV,0.0);
}
}
simulated event RenderOverlays(Canvas Canvas)
{
local int m;
local PlayerController PC;
if (Instigator == none)
return;
PC = PlayerController(Instigator.Controller);
if(PC == none)
return;
if(!bInitializedScope && PC != none )
{
UpdateScopeMode();
}
Canvas.DrawActor(none, false, true);
for (m = 0; m < NUM_FIRE_MODES; m++)
{
if (FireMode[m] != none)
{
FireMode[m].DrawMuzzleFlash(Canvas);
}
}
SetLocation( Instigator.Location + Instigator.CalcDrawOffset(self) );
SetRotation( Instigator.GetViewRotation() + ZoomRotInterp);
PreDrawFPWeapon();
if(bAimingRifle && PC != none && (KFScopeDetail == KF_ModelScope || KFScopeDetail == KF_ModelScopeHigh))
{
if (ShouldDrawPortal())
{
if ( ScopeScriptedTexture != none )
{
Skins[LenseMaterialID] = ScopeScriptedShader;
ScopeScriptedTexture.Client = Self;
ScopeScriptedTexture.Revision = (ScopeScriptedTexture.Revision +1);
}
}
bDrawingFirstPerson = true;
Canvas.DrawBoundActor(self, false, false,DisplayFOV,PC.Rotation,rot(0,0,0),Instigator.CalcZoomedDrawOffset(self));
bDrawingFirstPerson = false;
}
else if( KFScopeDetail == KF_TextureScope && PC.DesiredFOV == PlayerIronSightFOV && bAimingRifle)
{
Skins[LenseMaterialID] = ScriptedTextureFallback;
SetZoomBlendColor(Canvas);
Canvas.Style = ERenderStyle.STY_Normal;
Canvas.SetPos(0, 0);
Canvas.DrawTile(ZoomMat, (Canvas.SizeX - Canvas.SizeY) / 2, Canvas.SizeY, 0.0, 0.0, 8, 8);
Canvas.SetPos(Canvas.SizeX, 0);
Canvas.DrawTile(ZoomMat, -(Canvas.SizeX - Canvas.SizeY) / 2, Canvas.SizeY, 0.0, 0.0, 8, 8);
Canvas.Style = 255;
Canvas.SetPos((Canvas.SizeX - Canvas.SizeY) / 2,0);
Canvas.DrawTile(ZoomMat, Canvas.SizeY, Canvas.SizeY, 0.0, 0.0, 1024, 1024);
Canvas.Font = Canvas.MedFont;
Canvas.SetDrawColor(200,150,0);
Canvas.SetPos(Canvas.SizeX * 0.16, Canvas.SizeY * 0.43);
Canvas.DrawText("Zoom: 3.0");
Canvas.SetPos(Canvas.SizeX * 0.16, Canvas.SizeY * 0.47);
}
else
{
Skins[LenseMaterialID] = ScriptedTextureFallback;
bDrawingFirstPerson = true;
Canvas.DrawActor(self, false, false, DisplayFOV);
bDrawingFirstPerson = false;
}
}
simulated function float CalcAspectRatioAdjustedFOV(float AdjustFOV) simulated function float CalcAspectRatioAdjustedFOV(float AdjustFOV)
{ {
local KFPlayerController KFPC; local KFPlayerController KFPC;
@ -333,204 +22,15 @@ simulated function float CalcAspectRatioAdjustedFOV(float AdjustFOV)
return AdjustFOV; return AdjustFOV;
} }
} }
simulated function AdjustIngameScope()
{
local PlayerController PC;
if(Instigator == none || PlayerController(Instigator.Controller) == none)
return;
PC = PlayerController(Instigator.Controller);
if( !bHasScope )
return;
switch (KFScopeDetail)
{
case KF_ModelScope:
if( bAimingRifle )
DisplayFOV = CalcAspectRatioAdjustedFOV(default.ZoomedDisplayFOV);
if ( PC.DesiredFOV == PlayerIronSightFOV && bAimingRifle )
{
if( Level.NetMode != NM_DedicatedServer && KFPlayerController(Instigator.Controller) != none )
{
KFPlayerController(Instigator.Controller).TransitionFOV(KFPlayerController(Instigator.Controller).DefaultFOV,0.0);
}
}
break;
case KF_TextureScope:
if( bAimingRifle )
DisplayFOV = CalcAspectRatioAdjustedFOV(default.ZoomedDisplayFOV);
if ( bAimingRifle && PC.DesiredFOV != PlayerIronSightFOV )
{
if( Level.NetMode != NM_DedicatedServer && KFPlayerController(Instigator.Controller) != none )
{
KFPlayerController(Instigator.Controller).TransitionFOV(PlayerIronSightFOV,0.0);
}
}
break;
case KF_ModelScopeHigh:
if( bAimingRifle )
{
if( ZoomedDisplayFOVHigh > 0 )
{
DisplayFOV = CalcAspectRatioAdjustedFOV(default.ZoomedDisplayFOVHigh);
}
else
{
DisplayFOV = CalcAspectRatioAdjustedFOV(default.ZoomedDisplayFOV);
}
}
if ( bAimingRifle && PC.DesiredFOV == PlayerIronSightFOV )
{
if( Level.NetMode != NM_DedicatedServer && KFPlayerController(Instigator.Controller) != none )
{
KFPlayerController(Instigator.Controller).TransitionFOV(KFPlayerController(Instigator.Controller).DefaultFOV,0.0);
}
}
break;
}
UpdateScopeMode();
}
simulated event Destroyed()
{
if (ScopeScriptedTexture != none)
{
ScopeScriptedTexture.Client = none;
Level.ObjectPool.FreeObject(ScopeScriptedTexture);
ScopeScriptedTexture=none;
}
if (ScriptedScopeCombiner != none)
{
ScriptedScopeCombiner.Material2 = none;
Level.ObjectPool.FreeObject(ScriptedScopeCombiner);
ScriptedScopeCombiner = none;
}
if (ScopeScriptedShader != none)
{
ScopeScriptedShader.Diffuse = none;
ScopeScriptedShader.SelfIllumination = none;
Level.ObjectPool.FreeObject(ScopeScriptedShader);
ScopeScriptedShader = none;
}
Super.Destroyed();
}
simulated function PreTravelCleanUp()
{
if (ScopeScriptedTexture != none)
{
ScopeScriptedTexture.Client = none;
Level.ObjectPool.FreeObject(ScopeScriptedTexture);
ScopeScriptedTexture=none;
}
if (ScriptedScopeCombiner != none)
{
ScriptedScopeCombiner.Material2 = none;
Level.ObjectPool.FreeObject(ScriptedScopeCombiner);
ScriptedScopeCombiner = none;
}
if (ScopeScriptedShader != none)
{
ScopeScriptedShader.Diffuse = none;
ScopeScriptedShader.SelfIllumination = none;
Level.ObjectPool.FreeObject(ScopeScriptedShader);
ScopeScriptedShader = none;
}
}
state PendingClientWeaponSet
{
simulated function Timer()
{
if ( Pawn(Owner) != none && !bIsReloading )
{
ClientWeaponSet(bPendingSwitch);
}
if ( IsInState('PendingClientWeaponSet') )
{
SetTimer(0.1, false);
}
}
simulated function BeginState()
{
SetTimer(0.1, false);
}
simulated function EndState()
{
}
}
simulated function SetZoomBlendColor(Canvas c)
{
local Byte val;
local Color clr;
local Color fog;
clr.R = 255;
clr.G = 255;
clr.B = 255;
clr.A = 255;
if( Instigator.Region.Zone.bDistanceFog )
{
fog = Instigator.Region.Zone.DistanceFogColor;
val = 0;
val = Max( val, fog.R);
val = Max( val, fog.G);
val = Max( val, fog.B);
if( val > 128 )
{
val -= 128;
clr.R -= val;
clr.G -= val;
clr.B -= val;
}
}
c.DrawColor = clr;
}
function bool RecommendRangedAttack()
{
return true;
}
function float SuggestAttackStyle()
{
return -1.0;
}
function bool RecommendLongRangedAttack()
{
return true;
}
simulated function AnimEnd(int channel)
{
if(!FireMode[1].IsInState('FireLoop'))
{
Super.AnimEnd(channel);
}
}
simulated function WeaponTick(float dt)
{
Super.WeaponTick(dt);
}
simulated function bool StartFire(int Mode)
{
if( Mode == 0 )
return super.StartFire(Mode);
if( !super.StartFire(Mode) )
return false;
if( AmmoAmount(0) <= 0 )
{
return false;
}
AnimStopLooping();
if( !FireMode[Mode].IsInState('FireLoop') && (AmmoAmount(0) > 0) )
{
FireMode[Mode].StartFiring();
return true;
}
else
{
return false;
}
return true;
}
defaultproperties defaultproperties
{ {
reloadPreEndFrame=0.339
reloadEndFrame=0.732
reloadChargeEndFrame=-1.000000
reloadMagStartFrame=0.643
reloadChargeStartFrame=-1.000000
magazineBone="Magazine"
lenseMaterialID=3 lenseMaterialID=3
scopePortalFOVHigh=22.000000 scopePortalFOVHigh=22.000000
scopePortalFOV=12.000000 scopePortalFOV=12.000000
@ -538,13 +38,13 @@ defaultproperties
ScriptedTextureFallbackRef="NicePackT.HFR.CBLens_cmb" ScriptedTextureFallbackRef="NicePackT.HFR.CBLens_cmb"
bHasScope=True bHasScope=True
ZoomedDisplayFOVHigh=35.000000 ZoomedDisplayFOVHigh=35.000000
MagCapacity=10 MagCapacity=50
ReloadRate=3.000000 ReloadRate=3.000000
ReloadAnim="Reload" ReloadAnim="Reload"
ReloadAnimRate=0.600000 ReloadAnimRate=0.600000
WeaponReloadAnim="Reload_M4" WeaponReloadAnim="Reload_M4"
bSteadyAim=True bSteadyAim=True
Weight=7.000000 Weight=5.000000
bHasAimingMode=True bHasAimingMode=True
IdleAimAnim="Idle" IdleAimAnim="Idle"
StandardDisplayFOV=60.000000 StandardDisplayFOV=60.000000
@ -562,7 +62,7 @@ defaultproperties
PlayerIronSightFOV=65.000000 PlayerIronSightFOV=65.000000
ZoomedDisplayFOV=32.000000 ZoomedDisplayFOV=32.000000
FireModeClass(0)=class'NiceHFRPFire' FireModeClass(0)=class'NiceHFRPFire'
FireModeClass(1)=class'NiceHFRBurstFire' FireModeClass(1)=Class'KFMod.NoFire'
PutDownAnim="PutDown" PutDownAnim="PutDown"
AIRating=0.700000 AIRating=0.700000
CurrentRating=0.700000 CurrentRating=0.700000

View File

@ -1,10 +1,10 @@
class NiceHFRAmmo extends KFAmmunition; class NiceHFRAmmo extends NiceAmmo;
#EXEC OBJ LOAD FILE=KillingFloorHUD.utx #EXEC OBJ LOAD FILE=KillingFloorHUD.utx
defaultproperties defaultproperties
{ {
AmmoPickupAmount=15 AmmoPickupAmount=75
MaxAmmo=100 MaxAmmo=300
InitialAmount=40 InitialAmount=75
PickupClass=class'NiceHFRAmmoPickup' PickupClass=class'NiceHFRAmmoPickup'
IconMaterial=Texture'KillingFloorHUD.Generic.HUD' IconMaterial=Texture'KillingFloorHUD.Generic.HUD'
IconCoords=(X1=336,Y1=82,X2=382,Y2=125) IconCoords=(X1=336,Y1=82,X2=382,Y2=125)

View File

@ -1,7 +1,7 @@
class NiceHFRAmmoPickup extends KFAmmoPickup; class NiceHFRAmmoPickup extends NiceAmmoPickup;
defaultproperties defaultproperties
{ {
AmmoAmount=15 AmmoAmount=50
InventoryType=class'NiceHFRAmmo' InventoryType=class'NiceHFRAmmo'
PickupMessage="Fire balloon" PickupMessage="Fire balloon"
StaticMesh=StaticMesh'KillingFloorStatics.L85Ammo' StaticMesh=StaticMesh'KillingFloorStatics.L85Ammo'

View File

@ -0,0 +1,11 @@
class NiceHFRBullet extends NiceBullet;
defaultproperties
{
bDisableComplexMovement=False
trailXClass=None
StaticMeshRef="ZED_FX_SM.Energy.ZED_FX_Energy_Card"
DrawScale=0.500000
ambientSoundRef="KF_FY_ZEDV2SND.WEP_ZEDV2_Projectile_Loop"
explosionImpact=(bImportanEffect=True,decalClass=Class'KFMod.FlameThrowerBurnMark_Medium',EmitterClass=Class'KFMod.ZEDMKIIPrimaryProjectileImpact',emitterShiftWall=20.000000,emitterShiftPawn=20.000000,noiseRef="KF_FY_ZEDV2SND.WEP_ZEDV2_Projectile_Explode",noiseVolume=2.000000)
}

View File

@ -1,25 +1,29 @@
class NiceHFRPFire extends KFFire; class NiceHFRPFire extends NiceFire;
defaultproperties defaultproperties
{ {
ProjectileSpeed=2000.000000
FireAimedAnim="Fire_Iron" FireAimedAnim="Fire_Iron"
RecoilRate=0.120000 RecoilRate=0.070000
maxVerticalRecoilAngle=500 maxVerticalRecoilAngle=70
maxHorizontalRecoilAngle=35
bAccuracyBonusForSemiAuto=True bAccuracyBonusForSemiAuto=True
bRandomPitchFireSound=False bRandomPitchFireSound=False
FireSoundRef="KF_SP_LongmusketSnd.KFO_Sniper_Fire_M" FireSoundRef="KF_FY_ZEDV2SND.WEP_ZEDV2_Fire_M"
StereoFireSoundRef="KF_SP_LongmusketSnd.KFO_Sniper_Fire_S" StereoFireSoundRef="KF_FY_ZEDV2SND.WEP_ZEDV2_Fire_S"
NoAmmoSoundRef="KF_AK47Snd.AK47_DryFire" NoAmmoSoundRef="KF_ZEDGunSnd.KF_WEP_ZED_Dryfire"
DamageType=class'NiceDamTypeHFRAssaultRifle' DamageType=class'NiceDamTypeHFR'
DamageMax=50 DamageMax=50
Momentum=8500.000000 Momentum=8500.000000
bWaitForRelease=True bWaitForRelease=False
TransientSoundVolume=1.200000 TransientSoundVolume=1.200000
TransientSoundRadius=500.000000 TransientSoundRadius=500.000000
FireLoopAnim="Fire" FireLoopAnim="Fire"
FireAnimRate=0.909000 FireAnimRate=0.909000
TweenTime=0.025000 TweenTime=0.025000
FireForce="AssaultRifleFire" FireForce="AssaultRifleFire"
FireRate=0.600000 FireRate=0.096000
bulletClass=class'NiceHFRBullet'
AmmoClass=class'NiceHFRAmmo' AmmoClass=class'NiceHFRAmmo'
AmmoPerFire=1 AmmoPerFire=1
ShakeRotMag=(X=50.000000,Y=50.000000,Z=350.000000) ShakeRotMag=(X=50.000000,Y=50.000000,Z=350.000000)
@ -32,5 +36,4 @@ defaultproperties
FlashEmitterClass=Class'ROEffects.MuzzleFlash1stSPSniper' FlashEmitterClass=Class'ROEffects.MuzzleFlash1stSPSniper'
aimerror=42.000000 aimerror=42.000000
Spread=0.015000 Spread=0.015000
SpreadStyle=SS_Random
} }

View File

@ -1,18 +1,19 @@
class NiceHFRPickup extends KFWeaponPickup; class NiceHFRPickup extends NiceWeaponPickup;
defaultproperties defaultproperties
{ {
Weight=7.000000 Weight=5.000000
AmmoCost=30 AmmoCost=26
BuyClipSize=15 BuyClipSize=50
PowerValue=100 PowerValue=100
SpeedValue=100 SpeedValue=100
RangeValue=40 RangeValue=40
cost=750
Description="Advanced horzine flame rifle." Description="Advanced horzine flame rifle."
ItemName="Horzine flame rifle" ItemName="Horzine flame rifle"
ItemShortName="HFR" ItemShortName="HFR"
AmmoItemName="Fire balloon" AmmoItemName="Fire balloon"
AmmoMesh=StaticMesh'KillingFloorStatics.FT_AmmoMesh' AmmoMesh=StaticMesh'KillingFloorStatics.FT_AmmoMesh'
CorrespondingPerkIndex=5 CorrespondingPerkIndex=3
EquipmentCategoryID=3 EquipmentCategoryID=3
InventoryType=class'NiceHFR' InventoryType=class'NiceHFR'
PickupMessage="You got the HFR." PickupMessage="You got the HFR."

View File

@ -1,6 +1,6 @@
class NiceHFRTendril extends FlameTendril; class NiceHFRTendril extends FlameTendril;
defaultproperties defaultproperties
{ {
Damage=36.000000 Damage=16.000000
MyDamageType=class'NiceDamTypeHFR' MyDamageType=class'NiceDamTypeHFR'
} }

View File

@ -1,6 +1,8 @@
class NiceDamTypeKrissM extends NiceDamageTypeVetCommando class NiceDamTypeKrissM extends NiceDamageTypeVetDemolitions
abstract; abstract;
defaultproperties defaultproperties
{ {
stoppingPower=0.25
HeadShotDamageMult=1.500000
WeaponClass=class'NiceKrissMMedicGun' WeaponClass=class'NiceKrissMMedicGun'
} }

View File

@ -13,8 +13,8 @@ defaultproperties
ShellEjectBoneName="Shell_eject" ShellEjectBoneName="Shell_eject"
NoAmmoSoundRef="KF_MP7Snd.MP7_DryFire" NoAmmoSoundRef="KF_MP7Snd.MP7_DryFire"
DamageType=class'NiceDamTypeKrissM' DamageType=class'NiceDamTypeKrissM'
DamageMin=35 DamageMin=48
DamageMax=35 DamageMax=48
Momentum=12500.000000 Momentum=12500.000000
FireRate=0.040000 FireRate=0.040000
AmmoClass=class'NiceKrissMAmmo' AmmoClass=class'NiceKrissMAmmo'
@ -27,4 +27,8 @@ defaultproperties
FlashEmitterClass=Class'ROEffects.MuzzleFlash1stMP' FlashEmitterClass=Class'ROEffects.MuzzleFlash1stMP'
Spread=500.0 Spread=500.0
SpreadStyle=SS_Random SpreadStyle=SS_Random
minimalSpreadScale=0.0
activeSpreadScale=0.0
spreadGainedPerShot=0.125
spreadLostPerSecond=0.5
} }

View File

@ -17,7 +17,7 @@ defaultproperties
AmmoItemName="45. ACP Ammo" AmmoItemName="45. ACP Ammo"
AmmoMesh=StaticMesh'KillingFloorStatics.L85Ammo' AmmoMesh=StaticMesh'KillingFloorStatics.L85Ammo'
EquipmentCategoryID=3 EquipmentCategoryID=3
CorrespondingPerkIndex=3 CorrespondingPerkIndex=6
InventoryType=class'NiceKrissMMedicGun' InventoryType=class'NiceKrissMMedicGun'
PickupMessage="You got the KRISS Vector Medic Gun" PickupMessage="You got the KRISS Vector Medic Gun"
PickupSound=Sound'KF_KrissSND.Handling.KF_WEP_KRISS_Handling_Pickup' PickupSound=Sound'KF_KrissSND.Handling.KF_WEP_KRISS_Handling_Pickup'

View File

@ -1,7 +1,8 @@
class NiceDamTypeM7A3M extends NiceDamageTypeVetCommando class NiceDamTypeM7A3M extends NiceDamageTypeVetDemolitions
abstract; abstract;
defaultproperties defaultproperties
{ {
stoppingPower=0.15
HeadShotDamageMult=2.000000 HeadShotDamageMult=2.000000
WeaponClass=class'NiceM7A3MMedicGun' WeaponClass=class'NiceM7A3MMedicGun'
} }

View File

@ -3,8 +3,8 @@ defaultproperties
{ {
WeaponPickupClass=class'NiceM7A3MPickup' WeaponPickupClass=class'NiceM7A3MPickup'
AmmoPickupAmount=30 AmmoPickupAmount=30
MaxAmmo=180 MaxAmmo=160
InitialAmount=45 InitialAmount=40
PickupClass=class'NiceM7A3MAmmoPickup' PickupClass=class'NiceM7A3MAmmoPickup'
IconMaterial=Texture'KillingFloorHUD.Generic.HUD' IconMaterial=Texture'KillingFloorHUD.Generic.HUD'
IconCoords=(X1=336,Y1=82,X2=382,Y2=125) IconCoords=(X1=336,Y1=82,X2=382,Y2=125)

View File

@ -1,7 +1,7 @@
class NiceM7A3MAmmoPickup extends NiceAmmoPickup; class NiceM7A3MAmmoPickup extends NiceAmmoPickup;
defaultproperties defaultproperties
{ {
AmmoAmount=15 AmmoAmount=30
InventoryType=class'NiceM7A3MAmmo' InventoryType=class'NiceM7A3MAmmo'
PickupMessage="Rounds 7.6x40mm" PickupMessage="Rounds 7.6x40mm"
StaticMesh=StaticMesh'KillingFloorStatics.L85Ammo' StaticMesh=StaticMesh'KillingFloorStatics.L85Ammo'

View File

@ -34,4 +34,8 @@ defaultproperties
aimerror=42.000000 aimerror=42.000000
Spread=500.0 Spread=500.0
SpreadStyle=SS_Random SpreadStyle=SS_Random
minimalSpreadScale=0.0
activeSpreadScale=0.0
spreadGainedPerShot=0.25
spreadLostPerSecond=0.5
} }

View File

@ -3,7 +3,7 @@ defaultproperties
{ {
Weight=5.000000 Weight=5.000000
cost=1250 cost=1250
AmmoCost=33 AmmoCost=50
BuyClipSize=30 BuyClipSize=30
PowerValue=45 PowerValue=45
SpeedValue=60 SpeedValue=60
@ -14,7 +14,7 @@ defaultproperties
AmmoItemName="7.6x40mm Ammo" AmmoItemName="7.6x40mm Ammo"
AmmoMesh=StaticMesh'KillingFloorStatics.L85Ammo' AmmoMesh=StaticMesh'KillingFloorStatics.L85Ammo'
EquipmentCategoryID=3 EquipmentCategoryID=3
CorrespondingPerkIndex=3 CorrespondingPerkIndex=6
InventoryType=class'NiceM7A3MMedicGun' InventoryType=class'NiceM7A3MMedicGun'
PickupMessage="You got the M7A3 Medic Gun" PickupMessage="You got the M7A3 Medic Gun"
PickupSound=Sound'KF_M7A3Snd.M7A3_Pickup' PickupSound=Sound'KF_M7A3Snd.M7A3_Pickup'

View File

@ -1,7 +1,8 @@
class NiceDamTypeMP5M extends NiceDamageTypeVetCommando class NiceDamTypeMP5M extends NiceDamageTypeVetDemolitions
abstract; abstract;
defaultproperties defaultproperties
{ {
stoppingPower=0.15
HeadShotDamageMult=2.000000 HeadShotDamageMult=2.000000
WeaponClass=class'NiceMP5MMedicGun' WeaponClass=class'NiceMP5MMedicGun'
} }

View File

@ -5,9 +5,9 @@ defaultproperties
FireEndStereoSoundRef="KF_MP5Snd.MP5_Fire_Loop_End_S" FireEndStereoSoundRef="KF_MP5Snd.MP5_Fire_Loop_End_S"
AmbientFireSoundRef="KF_MP5Snd.MP5_Fire_Loop" AmbientFireSoundRef="KF_MP5Snd.MP5_Fire_Loop"
ProjectileSpeed=21250.000000 ProjectileSpeed=21250.000000
RecoilRate=0.0075000 RecoilRate=0.0100000
maxVerticalRecoilAngle=160 maxVerticalRecoilAngle=40
maxHorizontalRecoilAngle=80 maxHorizontalRecoilAngle=20
RecoilVelocityScale=0.000000 RecoilVelocityScale=0.000000
ShellEjectClass=Class'ROEffects.KFShellEjectMP5SMG' ShellEjectClass=Class'ROEffects.KFShellEjectMP5SMG'
ShellEjectBoneName="Shell_eject" ShellEjectBoneName="Shell_eject"
@ -15,8 +15,12 @@ defaultproperties
DamageType=class'NiceDamTypeMP5M' DamageType=class'NiceDamTypeMP5M'
DamageMin=35 DamageMin=35
DamageMax=35 DamageMax=35
Spread=500.0 Spread=750.0
SpreadStyle=SS_Random SpreadStyle=SS_Random
minimalSpreadScale=0.0
activeSpreadScale=0.0
spreadGainedPerShot=0.25
spreadLostPerSecond=1.0
Momentum=5500.000000 Momentum=5500.000000
FireRate=0.075000 FireRate=0.075000
AmmoClass=class'NiceMP5MAmmo' AmmoClass=class'NiceMP5MAmmo'

View File

@ -14,7 +14,7 @@ defaultproperties
AmmoItemName="9x19mm Ammo" AmmoItemName="9x19mm Ammo"
AmmoMesh=StaticMesh'KillingFloorStatics.L85Ammo' AmmoMesh=StaticMesh'KillingFloorStatics.L85Ammo'
EquipmentCategoryID=3 EquipmentCategoryID=3
CorrespondingPerkIndex=3 CorrespondingPerkIndex=6
VariantClasses(0)=Class'KFMod.CamoMP5MPickup' VariantClasses(0)=Class'KFMod.CamoMP5MPickup'
InventoryType=class'NiceMP5MMedicGun' InventoryType=class'NiceMP5MMedicGun'
PickupMessage="You got the MP5M Medic Gun" PickupMessage="You got the MP5M Medic Gun"

View File

@ -1,9 +1,10 @@
class NiceDamTypeMP7M extends NiceDamageTypeVetCommando class NiceDamTypeMP7M extends NiceDamageTypeVetDemolitions
abstract; abstract;
defaultproperties defaultproperties
{ {
bPenetrationHSOnly=True bPenetrationHSOnly=True
MaxPenetrations=1 MaxPenetrations=1
HeadShotDamageMult=2.250000 HeadShotDamageMult=2.250000
stoppingPower=0.15
WeaponClass=class'NiceMP7MMedicGun' WeaponClass=class'NiceMP7MMedicGun'
} }

View File

@ -25,6 +25,10 @@ defaultproperties
ShakeOffsetRate=(X=1000.000000,Y=1000.000000,Z=1000.000000) ShakeOffsetRate=(X=1000.000000,Y=1000.000000,Z=1000.000000)
ShakeOffsetTime=1.250000 ShakeOffsetTime=1.250000
FlashEmitterClass=Class'ROEffects.MuzzleFlash1stMP' FlashEmitterClass=Class'ROEffects.MuzzleFlash1stMP'
Spread=500.0 Spread=750.0
SpreadStyle=SS_Random SpreadStyle=SS_Random
minimalSpreadScale=0.0
activeSpreadScale=0.0
spreadGainedPerShot=0.1
spreadLostPerSecond=0.5
} }

View File

@ -15,7 +15,7 @@ defaultproperties
AmmoItemName="4.6x30mm Ammo" AmmoItemName="4.6x30mm Ammo"
AmmoMesh=StaticMesh'KillingFloorStatics.L85Ammo' AmmoMesh=StaticMesh'KillingFloorStatics.L85Ammo'
EquipmentCategoryID=3 EquipmentCategoryID=3
CorrespondingPerkIndex=3 CorrespondingPerkIndex=6
InventoryType=class'NiceMP7MMedicGun' InventoryType=class'NiceMP7MMedicGun'
PickupMessage="You got the MP7M Medic Gun" PickupMessage="You got the MP7M Medic Gun"
PickupSound=Sound'KF_MP7Snd.MP7_Pickup' PickupSound=Sound'KF_MP7Snd.MP7_Pickup'

View File

@ -1,13 +1,13 @@
class NiceBoomStickAltFire extends NiceBoomStickFire; class NiceBoomStickAltFire extends NiceBoomStickFire;
// Overload to force last shot to have a different animation with reload // Overload to force last shot to have a different animation with reload
// NICETODO: uncomment this // NICETODO: uncomment this
function name GetCorrectAnim(bool bLoop, bool bAimed){ function name GetCorrectAnim(bool bLoop, bool bAimed) {
if(currentContext.sourceWeapon != none && currentContext.sourceWeapon.MagAmmoRemainingClient > 0) if(currentContext.sourceWeapon != none && currentContext.sourceWeapon.MagAmmoRemainingClient > 0)
return super.GetCorrectAnim(bLoop, bAimed); return super.GetCorrectAnim(bLoop, bAimed);
if(bAimed) if(bAimed)
return 'Fire_Last_Iron'; return 'Fire_Last_Iron';
else else
return 'Fire_Last'; return 'Fire_Last';
return FireAnim; return FireAnim;
} }
defaultproperties defaultproperties

View File

@ -58,5 +58,6 @@ defaultproperties
ShakeOffsetTime=3.500000 ShakeOffsetTime=3.500000
BotRefireRate=2.500000 BotRefireRate=2.500000
aimerror=2.000000 aimerror=2.000000
Spread=3000.000000 Spread=2000.000000
FireAnimRate=1.25
} }

View File

@ -10,7 +10,7 @@ defaultproperties
reloadMagStartFrame=0.278000 reloadMagStartFrame=0.278000
reloadChargeStartFrame=-1.000000 reloadChargeStartFrame=-1.000000
FirstPersonFlashlightOffset=(X=-20.000000,Y=-22.000000,Z=8.000000) FirstPersonFlashlightOffset=(X=-20.000000,Y=-22.000000,Z=8.000000)
MagCapacity=28 MagCapacity=42
ReloadRate=2.600000 ReloadRate=2.600000
ReloadAnim="Reload" ReloadAnim="Reload"
ReloadAnimRate=1.000000 ReloadAnimRate=1.000000

View File

@ -3,6 +3,9 @@ defaultproperties
{ {
bCanFireIncomplete=True bCanFireIncomplete=True
ProjectileSpeed=3500.000000 ProjectileSpeed=3500.000000
maxVerticalRecoilAngle=1250
maxHorizontalRecoilAngle=750
FireRate=0.600000
DamageType=class'NiceDamTypeNailGunWeak' DamageType=class'NiceDamTypeNailGunWeak'
AmmoPerFire=7 AmmoPerFire=7
SpreadStyle=SS_Random SpreadStyle=SS_Random

View File

@ -3,9 +3,9 @@ class NiceNailGunAmmo extends NiceAmmo;
defaultproperties defaultproperties
{ {
WeaponPickupClass=class'NiceNailGunPickup' WeaponPickupClass=class'NiceNailGunPickup'
AmmoPickupAmount=28 AmmoPickupAmount=42
MaxAmmo=168 MaxAmmo=210
InitialAmount=84 InitialAmount=52
IconMaterial=Texture'KillingFloorHUD.Generic.HUD' IconMaterial=Texture'KillingFloorHUD.Generic.HUD'
IconCoords=(X1=451,Y1=445,X2=510,Y2=500) IconCoords=(X1=451,Y1=445,X2=510,Y2=500)
} }

View File

@ -10,8 +10,8 @@ defaultproperties
bShouldBounce=True bShouldBounce=True
bCausePain=True bCausePain=True
bulletClass=class'NiceNail' bulletClass=class'NiceNail'
maxVerticalRecoilAngle=1250 maxVerticalRecoilAngle=0
maxHorizontalRecoilAngle=750 maxHorizontalRecoilAngle=0
bRandomPitchFireSound=True bRandomPitchFireSound=True
FireSoundRef="KF_NailShotgun.NailShotgun_Fire_Single_M" FireSoundRef="KF_NailShotgun.NailShotgun_Fire_Single_M"
StereoFireSoundRef="KF_NailShotgun.NailShotgun_Fire_Single_S" StereoFireSoundRef="KF_NailShotgun.NailShotgun_Fire_Single_S"
@ -19,7 +19,7 @@ defaultproperties
DamageType=class'NiceDamTypeNailGun' DamageType=class'NiceDamTypeNailGun'
DamageMax=66 DamageMax=66
FireAnimRate=1.250000 FireAnimRate=1.250000
FireRate=0.400000 FireRate=0.300000
AmmoClass=class'NiceNailGunAmmo' AmmoClass=class'NiceNailGunAmmo'
ShakeRotTime=3.000000 ShakeRotTime=3.000000
ShakeOffsetTime=2.000000 ShakeOffsetTime=2.000000

View File

@ -3,8 +3,8 @@ defaultproperties
{ {
Weight=8.000000 Weight=8.000000
cost=250 cost=250
AmmoCost=17 AmmoCost=27
BuyClipSize=28 BuyClipSize=42
PowerValue=70 PowerValue=70
SpeedValue=55 SpeedValue=55
RangeValue=25 RangeValue=25

View File

@ -1,6 +1,7 @@
class NiceSpasAltFire extends NiceSpasFire; class NiceSpasAltFire extends NiceSpasFire;
defaultproperties defaultproperties
{ {
ProjPerFire=8
maxVerticalRecoilAngle=300 maxVerticalRecoilAngle=300
maxHorizontalRecoilAngle=180 maxHorizontalRecoilAngle=180
FireAnimRate=0.650000 FireAnimRate=0.650000

View File

@ -6,7 +6,7 @@ defaultproperties
{ {
Weight=6.000000 Weight=6.000000
cost=750 cost=750
AmmoCost=34 AmmoCost=22
BuyClipSize=5 BuyClipSize=5
PowerValue=55 PowerValue=55
SpeedValue=42 SpeedValue=42

View File

@ -1,8 +1,108 @@
class NiceSyringe extends ScrnSyringe; class NiceSyringe extends NiceMeleeWeapon;
defaultproperties { var () int HealBoostAmount;
ItemName="Nice Med-Syringe" var float RegenTimer;
FireModeClass(0)=class'NiceSyringeFire' var localized string SuccessfulHealMessage;
FireModeClass(1)=class'NiceSyringeAltFire'
PickupClass=class'NiceSyringePickup' replication
} {
reliable if( Role == ROLE_Authority )
ClientSuccessfulHeal;
}
simulated function PostBeginPlay()
{
// Weapon will handle FireMode instantiation
Super.PostBeginPlay();
if( Role == ROLE_Authority ) {
HealBoostAmount = default.HealBoostAmount;
}
}
// The server lets the client know they successfully healed someone
simulated function ClientSuccessfulHeal(String HealedName)
{
if( PlayerController(Instigator.Controller) != none )
{
PlayerController(Instigator.controller).ClientMessage(SuccessfulHealMessage$HealedName, 'CriticalEvent');
}
}
simulated function Timer()
{
Super.Timer();
if( KFPawn(Instigator)!=None && KFPawn(Instigator).bIsQuickHealing>0 && ClientState==WS_ReadyToFire )
{
if( KFPawn(Instigator).bIsQuickHealing==1 )
{
if( !HackClientStartFire() )
{
if( Instigator.Health>=Instigator.HealthMax || ChargeBar()<0.75 )
KFPawn(Instigator).bIsQuickHealing = 2; // Was healed by someone else or some other error occurred.
SetTimer(0.2,False);
return;
}
KFPawn(Instigator).bIsQuickHealing = 2;
SetTimer(FireMode[1].FireRate+0.5,False);
}
else
{
Instigator.SwitchToLastWeapon();
KFPawn(Instigator).bIsQuickHealing = 0;
}
}
else if( ClientState==WS_Hidden && KFPawn(Instigator)!=None )
KFPawn(Instigator).bIsQuickHealing = 0; // Weapon was changed, ensure to reset this.
}
simulated function bool HackClientStartFire()
{
if( StartFire(1) )
{
if( Role<ROLE_Authority )
ServerStartFire(1);
FireMode[1].ModeDoFire(); // Force to start animating.
return true;
}
return false;
}
defaultproperties
{
MagCapacity=1
bChangeClipIcon=True
hudClipTexture=Texture'KillingFloorHUD.HUD.Hud_Syringe'
BloodSkinSwitchArray=0
HealBoostAmount = 100
TraderInfoTexture=Texture'KillingFloorHUD.WeaponSelect.Syringe'
FireModeClass(0)=Class'NicePack.NiceSyringeFire'
FireModeClass(1)=Class'NicePack.NiceSyringeAltFire'
PickupClass=Class'NicePack.NiceSyringePickup'
bKFNeverThrow = false
Skins(0)=Combiner'KF_Weapons_Trip_T.equipment.medInjector_cmb'
weaponRange=90.000000
Weight=0.000000
AIRating=-2.000000
bMeleeWeapon=False
Priority=6
InventoryGroup=5
GroupOffset=2
BobDamping=8.000000
AttachmentClass=Class'KFMod.SyringeAttachment'
IconCoords=(X1=169,Y1=39,X2=241,Y2=77)
ItemName="Med-Syringe"
Mesh=SkeletalMesh'KF_Weapons_Trip.Syringe_Trip'
AmbientGlow=2
AmmoCharge(0)=500
DisplayFOV=85.000000
StandardDisplayFOV=85.0
HudImage=texture'KillingFloorHUD.WeaponSelect.Syring_unselected'
SelectedHudImage=texture'KillingFloorHUD.WeaponSelect.Syringe'
bConsumesPhysicalAmmo=true
SuccessfulHealMessage="You healed "
}

View File

@ -1 +1,90 @@
class NiceSyringeAltFire extends ScrnSyringeAltFire; class NiceSyringeAltFire extends NiceMeleeFire;
var float InjectDelay;
var float HealeeRange;
function DoFireEffect()
{
SetTimer(InjectDelay, False);
if ( Level.NetMode != NM_StandAlone && Level.Game.NumPlayers > 1 && KFPlayerController(Instigator.Controller) != none &&
KFSteamStatsAndAchievements(KFPlayerController(Instigator.Controller).SteamStatsAndAchievements) != none )
{
KFSteamStatsAndAchievements(KFPlayerController(Instigator.Controller).SteamStatsAndAchievements).AddSelfHeal();
}
}
function Timer()
{
local float HealSum, HealPotency;
local KFPlayerReplicationInfo KFPRI;
KFPRI = KFPlayerReplicationInfo(Instigator.PlayerReplicationInfo);
HealSum = NiceSyringe(Weapon).HealBoostAmount;
HealPotency = 1.0;
if ( KFPRI != none && KFPRI.ClientVeteranSkill != none )
HealPotency = KFPRI.ClientVeteranSkill.Static.GetHealPotency(KFPRI);
HealSum *= HealPotency;
Load = 1;
ReduceAmmoClient();
if ( NiceHumanPawn(Instigator) != none )
NiceHumanPawn(Instigator).TakeHealing(NiceHumanPawn(Instigator), HealSum, HealPotency, KFWeapon(Instigator.Weapon));
else
KFPawn(Instigator).GiveHealth(HealSum, Instigator.HealthMax);
}
function bool AllowFire()
{
if (Instigator.Health >= Instigator.HealthMax)
return false;
return Weapon.AmmoAmount(ThisModeNum) >= AmmoPerFire;
}
event ModeDoFire()
{
Load = 1;
Super.ModeDoFire();
}
function PlayFiring()
{
if ( Weapon.Mesh != None )
{
if ( FireCount > 0 )
{
if ( Weapon.HasAnim(FireLoopAnim) )
{
Weapon.PlayAnim(FireLoopAnim, FireLoopAnimRate, 0.0);
}
else
{
Weapon.PlayAnim(FireAnim, FireAnimRate, 0.0);
}
}
else
{
Weapon.PlayAnim(FireAnim, FireAnimRate, 0.0);
}
}
Weapon.PlayOwnedSound(FireSound,SLOT_Interact,TransientSoundVolume,,TransientSoundRadius,Default.FireAnimRate/FireAnimRate,false);
ClientPlayForceFeedback(FireForce); // jdf
FireCount++;
}
defaultproperties {
AmmoClass=class'NiceSyringeAmmo'
AmmoPerFire=1
TweenTime=0.1
TransientSoundVolume=1.8
FireAnim="AltFire"
FireRate=3.60000
bModeExclusive=true
InjectDelay=0.1
HealeeRange=70.000000
}

View File

@ -0,0 +1,12 @@
class NiceSyringeAmmo extends NiceAmmo;
defaultproperties {
WeaponPickupClass=class'NiceSyringePickup'
AmmoPickupAmount=0
MaxAmmo=4
InitialAmount=1
PickupClass=class'NiceSyringeAmmoPickup'
IconMaterial=Texture'KillingFloorHUD.Generic.HUD'
IconCoords=(X1=336,Y1=82,X2=382,Y2=125)
ItemName="Healing juice"
}

View File

@ -0,0 +1,8 @@
class NiceSyringeAmmoPickup extends NiceAmmoPickup;
defaultproperties {
AmmoAmount=1
InventoryType=class'NiceSyringe'
PickupMessage="Healing juice"
StaticMesh=StaticMesh'KillingFloorStatics.L85Ammo'
}

View File

@ -1,23 +1,208 @@
class NiceSyringeFire extends ScrnSyringeFire; class NiceSyringeFire extends NiceMeleeFire;
// default == 80 var float LastHealAttempt;
const SEARCH_RADIUS=120.0; var float HealAttemptDelay;
var float LastHealMessageTime;
var float HealMessageDelay;
var localized string NoHealTargetMessage;
var KFHumanPawn CachedHealee;
var transient float PendingHealTime;
function KFHumanPawn GetHealee() { simulated function DestroyEffects()
{
super.DestroyEffects();
if (CachedHealee != None)
CachedHealee = none;
}
simulated function bool AllowFire() {
local KFHumanPawn Healtarget;
local string healeeName;
if (!super.AllowFire()) {
return false;
}
if (CanFindHealee()) {
if( CachedHealee.PlayerReplicationInfo != none &&
CachedHealee.PlayerReplicationInfo.PlayerName != "")
{
HealeeName = CachedHealee.PlayerReplicationInfo.PlayerName;
}
else {
HealeeName = CachedHealee.MenuName;
}
NiceSyringe(Weapon).ClientSuccessfulHeal(HealeeName);
// Give the messages if we missed our heal, can't find a target, etc
if ( KFPlayerController(Instigator.Controller) != none )
{
if ( LastHealAttempt + HealAttemptDelay < Level.TimeSeconds)
{
PlayerController(Instigator.controller).ClientMessage(NoHealTargetMessage, 'CriticalEvent');
LastHealAttempt = Level.TimeSeconds;
}
if ( Level.TimeSeconds - LastHealMessageTime > HealMessageDelay )
{
// if there's a Player within 2 meters who needs healing, say that we're trying to heal them
foreach Instigator.VisibleCollidingActors(class'KFHumanPawn', Healtarget, 100)
{
if ( Healtarget != Instigator && Healtarget.Health < Healtarget.HealthMax )
{
PlayerController(Instigator.Controller).Speech('AUTO', 5, "");
LastHealMessageTime = Level.TimeSeconds;
break;
}
}
}
}
return true;
}
return false;
}
function Timer()
{
local KFPlayerReplicationInfo PRI;
local int MedicReward;
local KFHumanPawn Healed;
local float HealSum, HealPotency; // for modifying based on perks
PRI = KFPlayerReplicationInfo(Instigator.PlayerReplicationInfo);
Healed = CachedHealee;
HealPotency = 1.0;
CachedHealee = none;
if ( Healed != none && Healed.Health > 0 && Healed != Instigator )
{
Load = 1;
ReduceAmmoClient();
if ( PRI != none && PRI.ClientVeteranSkill != none )
HealPotency = PRI.ClientVeteranSkill.Static.GetHealPotency(PRI);
HealSum = NiceSyringe(Weapon).HealBoostAmount;
HealSum *= HealPotency;
MedicReward = HealSum;
if ( (Healed.Health + Healed.healthToGive + MedicReward) > Healed.HealthMax )
{
MedicReward = Healed.HealthMax - (Healed.Health + Healed.healthToGive);
if ( MedicReward < 0 )
{
MedicReward = 0;
}
}
if ( NiceHumanPawn(Healed) != none )
NiceHumanPawn(Healed).TakeHealing(NiceHumanPawn(Instigator), HealSum, HealPotency, KFWeapon(Instigator.Weapon));
else
Healed.GiveHealth(HealSum, Healed.HealthMax);
// Tell them we're healing them
PlayerController(Instigator.Controller).Speech('AUTO', 5, "");
LastHealMessageTime = Level.TimeSeconds;
if ( PRI != None )
{
if ( MedicReward > 0 && KFSteamStatsAndAchievements(PRI.SteamStatsAndAchievements) != none )
{
KFSteamStatsAndAchievements(PRI.SteamStatsAndAchievements).AddDamageHealed(MedicReward);
}
// Give the medic reward money as a percentage of how much of the person's health they healed
MedicReward = int((FMin(float(MedicReward),Healed.HealthMax)/Healed.HealthMax) * 60); // Increased to 80 in Balance Round 6, reduced to 60 in Round 7
if ( class'ScrnBalance'.default.Mut.bMedicRewardFromTeam && Healed.PlayerReplicationInfo != none && Healed.PlayerReplicationInfo.Team != none ) {
// give money from team wallet
if ( Healed.PlayerReplicationInfo.Team.Score >= MedicReward ) {
Healed.PlayerReplicationInfo.Team.Score -= MedicReward;
PRI.Score += MedicReward;
}
}
else
PRI.Score += MedicReward;
if ( KFHumanPawn(Instigator) != none )
{
KFHumanPawn(Instigator).AlphaAmount = 255;
}
}
}
}
function KFHumanPawn GetHealee()
{
local KFHumanPawn KFHP, BestKFHP; local KFHumanPawn KFHP, BestKFHP;
local vector Dir; local vector Dir;
local float TempDot, BestDot; local float TempDot, BestDot;
Dir = vector(Instigator.GetViewRotation()); Dir = vector(Instigator.GetViewRotation());
foreach Instigator.VisibleCollidingActors(class'KFHumanPawn', KFHP, SEARCH_RADIUS) { foreach Instigator.VisibleCollidingActors(class'KFHumanPawn', KFHP, 80.0)
if (KFHP.Health < KFHP.HealthMax && KFHP.Health > 0) { {
if ( KFHP.Health < KFHP.HealthMax && KFHP.Health > 0 )
{
TempDot = Dir dot (KFHP.Location - Instigator.Location); TempDot = Dir dot (KFHP.Location - Instigator.Location);
if (TempDot > 0.7 && TempDot > BestDot) { if ( TempDot > 0.7 && TempDot > BestDot )
{
BestKFHP = KFHP; BestKFHP = KFHP;
BestDot = TempDot; BestDot = TempDot;
} }
} }
} }
return BestKFHP; return BestKFHP;
} }
// Can we find someone to heal
function bool CanFindHealee()
{
local KFHumanPawn Healtarget;
Healtarget = GetHealee();
CachedHealee = Healtarget;
// Can't use syringe if we can't find a target
if ( Healtarget == none )
{
if ( KFPlayerController(Instigator.Controller) != none )
{
KFPlayerController(Instigator.Controller).CheckForHint(53);
}
return false;
}
// Can't use syringe if our target is already being healed to full health.
if ( (Healtarget.Health == Healtarget.Healthmax) || ((Healtarget.healthToGive + Healtarget.Health) >= Healtarget.Healthmax) )
{
return false;
}
return true;
}
function float GetFireSpeed()
{
if ( KFPlayerReplicationInfo(Instigator.PlayerReplicationInfo) != none && KFPlayerReplicationInfo(Instigator.PlayerReplicationInfo).ClientVeteranSkill != none )
{
return KFPlayerReplicationInfo(Instigator.PlayerReplicationInfo).ClientVeteranSkill.Static.GetFireSpeedMod(KFPlayerReplicationInfo(Instigator.PlayerReplicationInfo), Weapon);
}
return 1;
}
defaultproperties {
AmmoClass=class'NiceSyringeAmmo'
ammoPerFire=1
FireAnims(0)="Fire"
FireRate=2.800000
damageDelay=0.36
HealAttemptDelay=0.5
HealMessageDelay=10.0
NoHealTargetMessage="You must be near another player to heal them!"
bWaitForRelease=true
}

View File

@ -1,6 +1,19 @@
class NiceSyringePickup extends ScrnSyringePickup; class NiceSyringePickup extends NiceWeaponPickup;
defaultproperties { defaultproperties {
ItemName="Nice Med-Syringe" ItemName="Med-Syringe"
InventoryType=class'NiceSyringe' InventoryType=Class'NicePack.NiceSyringe'
} Weight=0.000000
cost=100
AmmoCost=40
BuyClipSize=1
PickupMessage="You got the Med-Syringe."
PickupSound=Sound'Inf_Weapons_Foley.AmmoPickup'
PickupForce="AssaultRiflePickup"
StaticMesh=StaticMesh'KF_pickups_Trip.Syringe_pickup'
CollisionHeight=5.000000
EquipmentCategoryID=0
ItemShortName="Syringe"
AmmoItemName="Healing juice"
Description="Basic equipment, necessary for survival."
}

View File

@ -27,23 +27,20 @@ Ignores StartChargingFP;
bFrustrated = false; bFrustrated = false;
if(Controller != none) if(Controller != none)
NiceZombieFleshPoundController(Controller).RageFrustrationTimer = 0; NiceZombieFleshPoundController(Controller).RageFrustrationTimer = 0;
if( Health>0 && !bZapped )
{
SetGroundSpeed(GetOriginalGroundSpeed());
}
if( Level.NetMode!=NM_DedicatedServer ) if( Level.NetMode!=NM_DedicatedServer )
ClientChargingAnims(); ClientChargingAnims();
NetUpdateTime = Level.TimeSeconds - 1; NetUpdateTime = Level.TimeSeconds - 1;
} }
simulated function UpdateGroundSpeed() {
super(NiceMonster).UpdateGroundSpeed();
if (!bShotAnim) {
groundSpeed *= 2.3;
}
}
function Tick( float Delta ) function Tick( float Delta )
{ {
if( !bShotAnim )
{
SetGroundSpeed(OriginalGroundSpeed * 2.3);//2.0;
}
// Keep the flesh pound moving toward its target when attacking // Keep the flesh pound moving toward its target when attacking
if( Role == ROLE_Authority && bShotAnim) if( Role == ROLE_Authority && bShotAnim)
{ {

View File

@ -37,7 +37,7 @@ function RangedAttack(Actor A) {
//Increment the number of consecutive shtos taken and apply the cool down if needed //Increment the number of consecutive shtos taken and apply the cool down if needed
totalShots ++; totalShots ++;
consecutiveShots ++; consecutiveShots ++;
if(consecutiveShots < 3 && totalShots > maxNormalShots) if(consecutiveShots < 3 && totalShots > maxNormalShots && VSize(a.location - location) <= 900)
NextFireProjectileTime = Level.TimeSeconds; NextFireProjectileTime = Level.TimeSeconds;
else{ else{
NextFireProjectileTime = Level.TimeSeconds + ProjectileFireInterval + (FRand() * 2.0); NextFireProjectileTime = Level.TimeSeconds + ProjectileFireInterval + (FRand() * 2.0);

View File

@ -1,30 +0,0 @@
class NiceBloatVomit extends KFBloatVomit;
// limit how much you can damage zeds
const DAMAGECOUNT=10;
var private transient int DamageTicked;
auto state Flying {
simulated function ProcessTouch(Actor Other, Vector HitLocation) {
// add damage limit
if (DamageTicked >= DAMAGECOUNT) {
BlowUp(HitLocation);
return;
}
if (ExtendedZCollision(Other) != none) {
return;
}
if (
Other != Instigator &&
(Other.IsA('Pawn') || Other.IsA('DestroyableObjective') || Other.bProjTarget)
) {
DamageTicked += 1;
// warn("DamageTicked: " $ DamageTicked);
// use server DelayedHurtRadius() instead?
HurtRadius(Damage, DamageRadius, MyDamageType, MomentumTransfer, HitLocation);
}
else if (Other != Instigator && Other.bBlockActors) {
HitWall(Normal(HitLocation - Location), Other);
}
}
}

View File

@ -173,8 +173,7 @@ function SpawnTwoShots()
if ( !SavedFireProperties.bInitialized ) if ( !SavedFireProperties.bInitialized )
{ {
SavedFireProperties.AmmoClass = Class'SkaarjAmmo'; SavedFireProperties.AmmoClass = Class'SkaarjAmmo';
// use fixed bile class, to prevent super high damage to zeds SavedFireProperties.ProjectileClass = Class'KFBloatVomit';
SavedFireProperties.ProjectileClass = Class'NiceBloatVomit';
SavedFireProperties.WarnTargetPct = 1; SavedFireProperties.WarnTargetPct = 1;
SavedFireProperties.MaxRange = 500; SavedFireProperties.MaxRange = 500;
SavedFireProperties.bTossed = False; SavedFireProperties.bTossed = False;
@ -186,13 +185,13 @@ function SpawnTwoShots()
// Turn off extra collision before spawning vomit, otherwise spawn fails // Turn off extra collision before spawning vomit, otherwise spawn fails
ToggleAuxCollision(false); ToggleAuxCollision(false);
FireRotation = Controller.AdjustAim(SavedFireProperties,FireStart,600); FireRotation = Controller.AdjustAim(SavedFireProperties,FireStart,600);
Spawn(SavedFireProperties.ProjectileClass,,,FireStart,FireRotation); Spawn(Class'KFBloatVomit',,,FireStart,FireRotation);
FireStart-=(0.5*CollisionRadius*Y); FireStart-=(0.5*CollisionRadius*Y);
FireRotation.Yaw -= 1200; FireRotation.Yaw -= 1200;
spawn(SavedFireProperties.ProjectileClass,,,FireStart, FireRotation); spawn(Class'KFBloatVomit',,,FireStart, FireRotation);
FireStart+=(CollisionRadius*Y); FireStart+=(CollisionRadius*Y);
FireRotation.Yaw += 2400; FireRotation.Yaw += 2400;
spawn(SavedFireProperties.ProjectileClass,,,FireStart, FireRotation); spawn(Class'KFBloatVomit',,,FireStart, FireRotation);
// Turn extra collision back on // Turn extra collision back on
ToggleAuxCollision(true); ToggleAuxCollision(true);
} }

View File

@ -915,9 +915,16 @@ state Charging
// How many charge attacks we can do randomly 1-3 // How many charge attacks we can do randomly 1-3
NumChargeAttacks = Rand(2) + 1; NumChargeAttacks = Rand(2) + 1;
} }
simulated function UpdateGroundSpeed() {
super.UpdateGroundSpeed();
if (bShotAnim) {
groundSpeed *= 1.25;
} else {
groundSpeed *= 2.5;
}
}
function EndState() function EndState()
{ {
SetGroundSpeed(GetOriginalGroundSpeed());
bChargingPlayer = False; bChargingPlayer = False;
ChargeDamage = 0; ChargeDamage = 0;
if( Level.NetMode!=NM_DedicatedServer ) if( Level.NetMode!=NM_DedicatedServer )
@ -942,7 +949,6 @@ state Charging
if( Level.NetMode!=NM_DedicatedServer ) if( Level.NetMode!=NM_DedicatedServer )
PostNetReceive(); PostNetReceive();
} }
SetGroundSpeed(OriginalGroundSpeed * 1.25);
if( LookTarget!=none ) if( LookTarget!=none )
{ {
Acceleration = AccelRate * Normal(LookTarget.Location - Location); Acceleration = AccelRate * Normal(LookTarget.Location - Location);
@ -956,16 +962,6 @@ state Charging
if( Level.NetMode!=NM_DedicatedServer ) if( Level.NetMode!=NM_DedicatedServer )
PostNetReceive(); PostNetReceive();
} }
// Zapping slows him down, but doesn't stop him
if( bZapped )
{
SetGroundSpeed(OriginalGroundSpeed * 1.5);
}
else
{
SetGroundSpeed(OriginalGroundSpeed * 2.5);
}
} }
Global.Tick(Delta); Global.Tick(Delta);
@ -1071,7 +1067,6 @@ State Escaping extends Charging // Got hurt and running away...
if( Level.NetMode!=NM_DedicatedServer ) if( Level.NetMode!=NM_DedicatedServer )
PostNetReceive(); PostNetReceive();
} }
SetGroundSpeed(GetOriginalGroundSpeed());
} }
else else
{ {
@ -1081,23 +1076,20 @@ State Escaping extends Charging // Got hurt and running away...
if( Level.NetMode!=NM_DedicatedServer ) if( Level.NetMode!=NM_DedicatedServer )
PostNetReceive(); PostNetReceive();
} }
// Zapping slows him down, but doesn't stop him
if( bZapped )
{
SetGroundSpeed(OriginalGroundSpeed * 1.5);
}
else
{
SetGroundSpeed(OriginalGroundSpeed * 2.5);
}
} }
Global.Tick(Delta); Global.Tick(Delta);
} }
simulated function UpdateGroundSpeed() {
super.UpdateGroundSpeed();
if (bShotAnim) {
groundSpeed *= 1.25;
} else {
groundSpeed *= 2.5;
}
}
function EndState() function EndState()
{ {
SetGroundSpeed(GetOriginalGroundSpeed());
bChargingPlayer = False; bChargingPlayer = False;
if( Level.NetMode!=NM_DedicatedServer ) if( Level.NetMode!=NM_DedicatedServer )
PostNetReceive(); PostNetReceive();

View File

@ -52,7 +52,6 @@ defaultproperties
ClawMeleeDamageRange=85.000000 ClawMeleeDamageRange=85.000000
ImpaleMeleeDamageRange=45.000000 ImpaleMeleeDamageRange=45.000000
fuelRatio=0.400000 fuelRatio=0.400000
bFrugalFuelUsage=False
clientHeadshotScale=1.200000 clientHeadshotScale=1.200000
ZapThreshold=5.000000 ZapThreshold=5.000000
ZappedDamageMod=1.250000 ZappedDamageMod=1.250000
@ -98,6 +97,9 @@ defaultproperties
HealthMax=8000.000000 HealthMax=8000.000000
Health=8000 Health=8000
HeadScale=1.300000 HeadScale=1.300000
stoppingRecoveryRate=0.1
maxStoppingEffect=0.2
minStoppingThreshold=0.6
MenuName="Nice Patriarch" MenuName="Nice Patriarch"
MovementAnims(0)="WalkF" MovementAnims(0)="WalkF"
MovementAnims(1)="WalkF" MovementAnims(1)="WalkF"

View File

@ -182,18 +182,6 @@ function TakeDamageClient(int Damage, Pawn InstigatedBy, Vector HitLocation, Vec
if (bDecapitated) if (bDecapitated)
Died(InstigatedBy.Controller, damageType, HitLocation); Died(InstigatedBy.Controller, damageType, HitLocation);
} }
function TakeFireDamage(int Damage, Pawn Instigator)
{
Super.TakeFireDamage(Damage, Instigator);
// Adjust movement speed if not charging
if (!bChargingPlayer)
{
if (bBurnified)
GroundSpeed = GetOriginalGroundSpeed() * BurnGroundSpeedMul;
else
GroundSpeed = GetOriginalGroundSpeed();
}
}
function ClawDamageTarget() function ClawDamageTarget()
{ {
local KFHumanPawn HumanTarget; local KFHumanPawn HumanTarget;
@ -311,19 +299,16 @@ Ignores StartCharging;
NetUpdateTime = Level.TimeSeconds - 1; NetUpdateTime = Level.TimeSeconds - 1;
} }
simulated function UpdateGroundSpeed() {
super.UpdateGroundSpeed();
groundSpeed = groundSpeed + ((groundSpeed * 0.75 / maxRageCounter * (rageCounter + 1) * rageSpeedTween));
}
function EndState() function EndState()
{ {
bChargingPlayer = false; bChargingPlayer = false;
NiceZombieBruteController(Controller).RageFrustrationTimer = 0; NiceZombieBruteController(Controller).RageFrustrationTimer = 0;
if (Health > 0)
{
GroundSpeed = GetOriginalGroundSpeed();
if (bBurnified)
GroundSpeed *= BurnGroundSpeedMul;
}
if( Level.NetMode!=NM_DedicatedServer ) if( Level.NetMode!=NM_DedicatedServer )
ClientChargingAnims(); ClientChargingAnims();
@ -331,12 +316,8 @@ Ignores StartCharging;
} }
function Tick(float Delta) function Tick(float Delta)
{ {
if (!bShotAnim) if (!bShotAnim) {
{
RageSpeedTween = FClamp(RageSpeedTween + (Delta * 0.75), 0, 1.0); RageSpeedTween = FClamp(RageSpeedTween + (Delta * 0.75), 0, 1.0);
GroundSpeed = OriginalGroundSpeed + ((OriginalGroundSpeed * 0.75 / MaxRageCounter * (RageCounter + 1) * RageSpeedTween));
if (bBurnified)
GroundSpeed *= BurnGroundSpeedMul;
} }
Global.Tick(Delta); Global.Tick(Delta);

View File

@ -33,7 +33,6 @@ var bool bServerBlock;
var bool bClientBlock; var bool bClientBlock;
var float BlockDmgMul; // Multiplier for damage taken from blocked shots var float BlockDmgMul; // Multiplier for damage taken from blocked shots
var float BlockFireDmgMul; var float BlockFireDmgMul;
var float BurnGroundSpeedMul; // Multiplier for ground speed when burning
replication replication
{ {
reliable if(Role == ROLE_Authority) reliable if(Role == ROLE_Authority)
@ -61,7 +60,6 @@ defaultproperties
BlockAddScale=2.500000 BlockAddScale=2.500000
BlockDmgMul=0.100000 BlockDmgMul=0.100000
BlockFireDmgMul=1.000000 BlockFireDmgMul=1.000000
BurnGroundSpeedMul=0.700000
StunThreshold=4.000000 StunThreshold=4.000000
flameFuel=0.500000 flameFuel=0.500000
clientHeadshotScale=1.300000 clientHeadshotScale=1.300000
@ -110,6 +108,7 @@ defaultproperties
Health=1000 Health=1000
HeadHeight=2.500000 HeadHeight=2.500000
HeadScale=1.300000 HeadScale=1.300000
minStoppingThreshold=0.1
MenuName="Brute" MenuName="Brute"
MovementAnims(0)="BruteWalkC" MovementAnims(0)="BruteWalkC"
MovementAnims(1)="BruteWalkC" MovementAnims(1)="BruteWalkC"
@ -123,7 +122,7 @@ defaultproperties
AmbientSound=SoundGroup'ScrnZedPack_S.Brute.BruteIdle1Shot' AmbientSound=SoundGroup'ScrnZedPack_S.Brute.BruteIdle1Shot'
Mesh=SkeletalMesh'ScrnZedPack_A.BruteMesh' Mesh=SkeletalMesh'ScrnZedPack_A.BruteMesh'
PrePivot=(Z=0.000000) PrePivot=(Z=0.000000)
Skins(0)=Combiner'ScrnZedPack_T.Brute.Brute_Final' Skins(0)=Texture'NicePackT.MonsterBrute.WPCBruteT'
Mass=600.000000 Mass=600.000000
RotationRate=(Yaw=45000,Roll=0) RotationRate=(Yaw=45000,Roll=0)
} }

View File

@ -5,6 +5,8 @@ class NiceZombieClot extends NiceZombieClotBase;
#exec OBJ LOAD FILE=KF_Specimens_Trip_T.utx #exec OBJ LOAD FILE=KF_Specimens_Trip_T.utx
#exec OBJ LOAD FILE=MeanZedSkins.utx #exec OBJ LOAD FILE=MeanZedSkins.utx
var float sirenBoostTimeout;
function ClawDamageTarget() function ClawDamageTarget()
{ {
local vector PushDir; local vector PushDir;
@ -109,9 +111,33 @@ simulated function int DoAnimAction( name AnimName )
} }
return super.DoAnimAction( AnimName ); return super.DoAnimAction( AnimName );
} }
function DealDecapDamage( int damage,
Pawn instigatedBy,
Vector hitLocation,
Vector momentum,
class<NiceWeaponDamageType> damageType,
float headshotLevel,
KFPlayerReplicationInfo KFPRI,
optional float lockonTime) {
if (sirenBoostTimeout > 0) {
RemoveHead();
} else {
super.DealDecapDamage(damage, instigatedBy, hitLocation, momentum,
damageType, headshotLevel, KFPRI, lockonTime);
}
}
simulated function UpdateGroundSpeed() {
super.UpdateGroundSpeed();
if (sirenBoostTimeout > 0) {
groundSpeed *= 1.5;
}
}
simulated function Tick(float DeltaTime) simulated function Tick(float DeltaTime)
{ {
super.Tick(DeltaTime); super.Tick(DeltaTime);
if (sirenBoostTimeout >= 0) {
sirenBoostTimeout -= deltaTime;
}
if( bShotAnim && Role == ROLE_Authority ) if( bShotAnim && Role == ROLE_Authority )
{ {
if( LookTarget!=none ) if( LookTarget!=none )

View File

@ -34,17 +34,20 @@ event Landed(vector HitNormal)
} }
event Bump(actor Other) event Bump(actor Other)
{ {
local int actualDamage;
// TODO: is there a better way // TODO: is there a better way
if(bPouncing && KFHumanPawn(Other)!=none ) if(bPouncing && KFHumanPawn(Other)!=none )
{ {
KFHumanPawn(Other).TakeDamage(((MeleeDamage - (MeleeDamage * 0.05)) + (MeleeDamage * (FRand() * 0.1))), self ,self.Location,self.velocity, class'NiceZedMeleeDamageType'); actualDamage = MeleeDamage;
if (KFHumanPawn(Other).Health <=0) ModDamageFromZed(actualDamage, class'NiceZedMeleeDamageType');
{ KFHumanPawn(Other).TakeDamage(((actualDamage * 0.95) + (actualDamage * (FRand() * 0.1))), self ,self.Location,self.velocity, class'NiceZedMeleeDamageType');
//TODO - move this to humanpawn.takedamage? Also see KFMonster.MeleeDamageTarget if (KFHumanPawn(Other).Health <=0)
KFHumanPawn(Other).SpawnGibs(self.rotation, 1); {
} //TODO - move this to humanpawn.takedamage? Also see KFMonster.MeleeDamageTarget
//After impact, there'll be no momentum for further bumps KFHumanPawn(Other).SpawnGibs(self.rotation, 1);
bPouncing=false; }
//After impact, there'll be no momentum for further bumps
bPouncing=false;
} }
} }
// Blend his attacks so he can hit you in mid air. // Blend his attacks so he can hit you in mid air.

View File

@ -49,7 +49,6 @@ function SetMindControlled(bool bNewMindControlled)
if( bNewMindControlled != bZedUnderControl ) if( bNewMindControlled != bZedUnderControl )
{ {
SetGroundSpeed(OriginalGroundSpeed * 1.25);
Health *= 1.25; Health *= 1.25;
HealthMax *= 1.25; HealthMax *= 1.25;
} }
@ -252,21 +251,21 @@ Ignores StartChargingFP;
if(fpController == none) if(fpController == none)
fpController.RageFrustrationTimer = 0; fpController.RageFrustrationTimer = 0;
if( Health>0 && !bZapped )
{
SetGroundSpeed(GetOriginalGroundSpeed());
}
if( Level.NetMode!=NM_DedicatedServer ) if( Level.NetMode!=NM_DedicatedServer )
ClientChargingAnims(); ClientChargingAnims();
NetUpdateTime = Level.TimeSeconds - 1; NetUpdateTime = Level.TimeSeconds - 1;
} }
simulated function UpdateGroundSpeed() {
super.UpdateGroundSpeed();
if (!bShotAnim) {
groundSpeed *= 2.3;
}
}
function Tick( float Delta ) function Tick( float Delta )
{ {
if( !bShotAnim ) if( !bShotAnim )
{ {
SetGroundSpeed(OriginalGroundSpeed * 2.3);//2.0;
if( !bFrustrated && !bZedUnderControl && Level.TimeSeconds>RageEndTime ) if( !bFrustrated && !bZedUnderControl && Level.TimeSeconds>RageEndTime )
{ {
GoToState(''); GoToState('');
@ -330,11 +329,16 @@ Ignores StartChargingFP;
state ChargeToMarker extends RageCharging state ChargeToMarker extends RageCharging
{ {
Ignores StartChargingFP; Ignores StartChargingFP;
simulated function UpdateGroundSpeed() {
super.UpdateGroundSpeed();
if (!bShotAnim) {
groundSpeed *= 2.3;
}
}
function Tick( float Delta ) function Tick( float Delta )
{ {
if( !bShotAnim ) if( !bShotAnim )
{ {
SetGroundSpeed(OriginalGroundSpeed * 2.3);
if( !bFrustrated && !bZedUnderControl && Level.TimeSeconds>RageEndTime ) if( !bFrustrated && !bZedUnderControl && Level.TimeSeconds>RageEndTime )
{ {
GoToState(''); GoToState('');
@ -437,7 +441,7 @@ function SpinDamage(actor Target)
local vector HitLocation; local vector HitLocation;
local Name TearBone; local Name TearBone;
local Float dummy; local Float dummy;
local float DamageAmount; local int damageAmount;
local vector PushDir; local vector PushDir;
local KFHumanPawn HumanTarget; local KFHumanPawn HumanTarget;
if(target==none) if(target==none)
@ -452,8 +456,9 @@ function SpinDamage(actor Target)
} }
if (Target !=none && Target.IsA('KFDoorMover')) if (Target !=none && Target.IsA('KFDoorMover'))
{ {
Target.TakeDamage(DamageAmount , self ,HitLocation,pushdir, class'NiceZedMeleeDamageType'); ModDamageFromZed(DamageAmount, class'NiceZedMeleeDamageType');
PlaySound(MeleeAttackHitSound, SLOT_Interact, 1.25); Target.TakeDamage(DamageAmount , self ,HitLocation,pushdir, class'NiceZedMeleeDamageType');
PlaySound(MeleeAttackHitSound, SLOT_Interact, 1.25);
} }
if (KFHumanPawn(Target)!=none) if (KFHumanPawn(Target)!=none)
{ {
@ -461,8 +466,9 @@ function SpinDamage(actor Target)
if (HumanTarget.Controller != none) if (HumanTarget.Controller != none)
HumanTarget.Controller.ShakeView(RotMag, RotRate, RotTime, OffsetMag, OffsetRate, OffsetTime); HumanTarget.Controller.ShakeView(RotMag, RotRate, RotTime, OffsetMag, OffsetRate, OffsetTime);
//TODO - line below was KFPawn. Does this whole block need to be KFPawn, or is it OK as KFHumanPawn? ModDamageFromZed(DamageAmount, class'NiceZedMeleeDamageType');
KFHumanPawn(Target).TakeDamage(DamageAmount, self ,HitLocation,pushdir, class'NiceZedMeleeDamageType'); //TODO - line below was KFPawn. Does this whole block need to be KFPawn, or is it OK as KFHumanPawn?
KFHumanPawn(Target).TakeDamage(DamageAmount, self ,HitLocation,pushdir, class'NiceZedMeleeDamageType');
if (KFHumanPawn(Target).Health <=0) if (KFHumanPawn(Target).Health <=0)
{ {

View File

@ -80,6 +80,8 @@ defaultproperties
Health=1650 Health=1650
HeadHeight=2.500000 HeadHeight=2.500000
HeadScale=1.300000 HeadScale=1.300000
maxStoppingEffect=0.05
minStoppingThreshold=0.68
MenuName="Nice Flesh Pound" MenuName="Nice Flesh Pound"
MovementAnims(0)="PoundWalk" MovementAnims(0)="PoundWalk"
MovementAnims(1)="WalkB" MovementAnims(1)="WalkB"

View File

@ -45,7 +45,6 @@ function SetMindControlled(bool bNewMindControlled)
if( bNewMindControlled != bZedUnderControl ) if( bNewMindControlled != bZedUnderControl )
{ {
SetGroundSpeed(OriginalGroundSpeed * 1.25);
Health *= 1.25; Health *= 1.25;
HealthMax *= 1.25; HealthMax *= 1.25;
} }
@ -73,13 +72,6 @@ function RangedAttack(Actor A){
if(!bShotAnim && !bDecapitated && VSize(A.Location - Location) <= 700) if(!bShotAnim && !bDecapitated && VSize(A.Location - Location) <= 700)
GoToState('RunningState'); GoToState('RunningState');
} }
simulated function Tick(float DeltaTime){
super.Tick(DeltaTime);
if(IsInState('RunningState'))
SetGroundSpeed(GetOriginalGroundSpeed() * 1.875);
else
SetGroundSpeed(GetOriginalGroundSpeed());
}
state RunningState{ state RunningState{
// Set the zed to the zapped behavior // Set the zed to the zapped behavior
simulated function SetZappedBehavior(){ simulated function SetZappedBehavior(){
@ -94,7 +86,6 @@ state RunningState{
if(bZapped) if(bZapped)
GoToState(''); GoToState('');
else{ else{
SetGroundSpeed(OriginalGroundSpeed * 1.875);
bRunning = true; bRunning = true;
if(Level.NetMode != NM_DedicatedServer) if(Level.NetMode != NM_DedicatedServer)
PostNetReceive(); PostNetReceive();
@ -103,7 +94,6 @@ state RunningState{
} }
} }
function EndState(){ function EndState(){
SetGroundSpeed(GetOriginalGroundSpeed());
bRunning = false; bRunning = false;
if(Level.NetMode != NM_DedicatedServer) if(Level.NetMode != NM_DedicatedServer)
PostNetReceive(); PostNetReceive();
@ -112,6 +102,10 @@ state RunningState{
NetUpdateTime = Level.TimeSeconds - 1; NetUpdateTime = Level.TimeSeconds - 1;
} }
simulated function UpdateGroundSpeed() {
super.UpdateGroundSpeed();
groundSpeed *= 1.875;
}
function RemoveHead(){ function RemoveHead(){
GoToState(''); GoToState('');
Global.RemoveHead(); Global.RemoveHead();

View File

@ -60,6 +60,7 @@ defaultproperties
HeadHeight=1.000000 HeadHeight=1.000000
HeadScale=1.350000 HeadScale=1.350000
AmbientSoundScaling=8.000000 AmbientSoundScaling=8.000000
stoppingRecoveryRate=0.05
MenuName="Nice Husk" MenuName="Nice Husk"
MovementAnims(0)="WalkF" MovementAnims(0)="WalkF"
MovementAnims(1)="WalkB" MovementAnims(1)="WalkB"

View File

@ -105,15 +105,11 @@ State SawingLoop
else GoToState(''); else GoToState('');
} }
} }
simulated function float GetOriginalGroundSpeed() simulated function UpdateGroundSpeed() {
{ super.UpdateGroundSpeed();
local float result; if (bWasRaged || bCharging) {
result = OriginalGroundSpeed; groundSpeed *= 3.5;
if ( bWasRaged || bCharging ) }
result *= 3.5;
else if( bZedUnderControl )
result *= 1.25;
return result;
} }
state RunningState state RunningState
{ {
@ -124,7 +120,6 @@ state RunningState
GoToState(''); GoToState('');
else { else {
bCharging = true; bCharging = true;
SetGroundSpeed(GetOriginalGroundSpeed());
if( Level.NetMode!=NM_DedicatedServer ) if( Level.NetMode!=NM_DedicatedServer )
PostNetReceive(); PostNetReceive();
NetUpdateTime = Level.TimeSeconds - 1; NetUpdateTime = Level.TimeSeconds - 1;
@ -133,8 +128,6 @@ state RunningState
function EndState() function EndState()
{ {
bCharging = False; bCharging = False;
if( !bZapped )
SetGroundSpeed(GetOriginalGroundSpeed());
if( Level.NetMode!=NM_DedicatedServer ) if( Level.NetMode!=NM_DedicatedServer )
PostNetReceive(); PostNetReceive();
} }
@ -163,6 +156,8 @@ defaultproperties
ChallengeSound(2)=None ChallengeSound(2)=None
ChallengeSound(3)=None ChallengeSound(3)=None
ScoringValue=300 ScoringValue=300
maxStoppingEffect=0.25
minStoppingThreshold=0.25
MenuName="Jason" MenuName="Jason"
AmbientSound=Sound'ScrnZedPack_S.Jason.Jason_Sound' AmbientSound=Sound'ScrnZedPack_S.Jason.Jason_Sound'
Mesh=SkeletalMesh'ScrnZedPack_A.JasonMesh' Mesh=SkeletalMesh'ScrnZedPack_A.JasonMesh'

View File

@ -83,7 +83,6 @@ function SetMindControlled(bool bNewMindControlled)
if( bNewMindControlled != bZedUnderControl ) if( bNewMindControlled != bZedUnderControl )
{ {
SetGroundSpeed(OriginalGroundSpeed * 1.25);
Health *= 1.25; Health *= 1.25;
HealthMax *= 1.25; HealthMax *= 1.25;
} }
@ -185,8 +184,9 @@ state RunningState
{ {
return false; return false;
} }
simulated function float GetOriginalGroundSpeed() { simulated function UpdateGroundSpeed() {
return 3.5 * OriginalGroundSpeed; super.UpdateGroundSpeed();
groundSpeed *= 3.5;
} }
function BeginState(){ function BeginState(){
local NiceHumanPawn rageTarget, rageCause; local NiceHumanPawn rageTarget, rageCause;
@ -214,7 +214,6 @@ state RunningState
if(bZapped) if(bZapped)
GoToState(''); GoToState('');
else{ else{
SetGroundSpeed(OriginalGroundSpeed * 3.5);
bCharging = true; bCharging = true;
if( Level.NetMode!=NM_DedicatedServer ) if( Level.NetMode!=NM_DedicatedServer )
PostNetReceive(); PostNetReceive();
@ -224,10 +223,6 @@ state RunningState
} }
function EndState() function EndState()
{ {
if( !bZapped )
{
SetGroundSpeed(GetOriginalGroundSpeed());
}
bCharging = False; bCharging = False;
if( Level.NetMode!=NM_DedicatedServer ) if( Level.NetMode!=NM_DedicatedServer )
PostNetReceive(); PostNetReceive();
@ -265,8 +260,9 @@ State SawingLoop
{ {
return false; return false;
} }
simulated function float GetOriginalGroundSpeed() { simulated function UpdateGroundSpeed() {
return OriginalGroundSpeed * AttackChargeRate; super.UpdateGroundSpeed();
groundSpeed *= attackChargeRate;
} }
function bool CanGetOutOfWay() function bool CanGetOutOfWay()
{ {
@ -279,7 +275,6 @@ State SawingLoop
// Randomly have the scrake charge during an attack so it will be less predictable // Randomly have the scrake charge during an attack so it will be less predictable
if(Health/HealthMax < 0.5 || FRand() <= 0.95) if(Health/HealthMax < 0.5 || FRand() <= 0.95)
{ {
SetGroundSpeed(OriginalGroundSpeed * AttackChargeRate);
bCharging = true; bCharging = true;
if( Level.NetMode!=NM_DedicatedServer ) if( Level.NetMode!=NM_DedicatedServer )
PostNetReceive(); PostNetReceive();
@ -327,8 +322,6 @@ State SawingLoop
{ {
AmbientSound=default.AmbientSound; AmbientSound=default.AmbientSound;
MeleeDamage = Max( DifficultyDamageModifer() * default.MeleeDamage, 1 ); MeleeDamage = Max( DifficultyDamageModifer() * default.MeleeDamage, 1 );
SetGroundSpeed(GetOriginalGroundSpeed());
bCharging = False; bCharging = False;
if(Level.NetMode != NM_DedicatedServer) if(Level.NetMode != NM_DedicatedServer)
PostNetReceive(); PostNetReceive();

View File

@ -63,6 +63,8 @@ defaultproperties
HealthMax=1000.000000 HealthMax=1000.000000
Health=1000 Health=1000
HeadHeight=2.200000 HeadHeight=2.200000
maxStoppingEffect=0.15
minStoppingThreshold=0.15
MenuName="Nice Scrake" MenuName="Nice Scrake"
MovementAnims(0)="SawZombieWalk" MovementAnims(0)="SawZombieWalk"
MovementAnims(1)="SawZombieWalk" MovementAnims(1)="SawZombieWalk"

View File

@ -3,6 +3,7 @@ class NiceZombieShiver extends NiceZombieShiverBase;
var float TeleportBlockTime; var float TeleportBlockTime;
var float HeadOffsetY; var float HeadOffsetY;
var transient bool bRunning, bClientRunning; var transient bool bRunning, bClientRunning;
var float teleportAttackCooldownEndTime;
replication replication
{ {
reliable if ( Role == ROLE_Authority) reliable if ( Role == ROLE_Authority)
@ -38,6 +39,39 @@ simulated function PostBeginPlay()
} }
} }
} }
function bool CanAttack(Actor target) {
if (level.timeSeconds < teleportAttackCooldownEndTime)
return false;
return super.CanAttack(target);
}
simulated event SetAnimAction(name NewAction) {
local int meleeAnimIndex;
if (bFrozenZed) return;
if (newAction == '') return;
if (newAction == 'Claw') {
meleeAnimIndex = Rand(2); // Shivers only have two animations now
newAction = meleeAnims[meleeAnimIndex];
currentDamtype = zombieDamType[meleeAnimIndex];
} else if(newAction == 'DoorBash') {
currentDamtype = zombieDamType[Rand(3)];
}
expectingChannel = DoAnimAction(NewAction);
if (AnimNeedsWait(newAction)) {
bWaitForAnim = true;
} else {
bWaitForAnim = false;
}
if (level.netMode != NM_Client) {
animAction = newAction;
bResetAnimAct = True;
resetAnimActTime = level.timeSeconds + 0.3;
}
}
simulated function Destroyed() simulated function Destroyed()
{ {
if (Level.NetMode != NM_DedicatedServer && MatAlphaSkin != none) if (Level.NetMode != NM_DedicatedServer && MatAlphaSkin != none)
@ -179,7 +213,6 @@ state Running
Global.Tick(Delta); Global.Tick(Delta);
if (RunUntilTime < Level.TimeSeconds) if (RunUntilTime < Level.TimeSeconds)
GotoState(''); GotoState('');
GroundSpeed = GetOriginalGroundSpeed();
} }
function BeginState() function BeginState()
{ {
@ -190,13 +223,12 @@ state Running
function EndState() function EndState()
{ {
bRunning = false; bRunning = false;
GroundSpeed = global.GetOriginalGroundSpeed();
RunCooldownEnd = Level.TimeSeconds + PeriodRunCoolBase + FRand() * PeriodRunCoolRan; RunCooldownEnd = Level.TimeSeconds + PeriodRunCoolBase + FRand() * PeriodRunCoolRan;
MovementAnims[0] = WalkAnim; MovementAnims[0] = WalkAnim;
} }
function float GetOriginalGroundSpeed() simulated function UpdateGroundSpeed() {
{ super.UpdateGroundSpeed();
return global.GetOriginalGroundSpeed() * 2.5; groundSpeed *= 2.5;
} }
function bool CanSpeedAdjust() function bool CanSpeedAdjust()
{ {
@ -219,14 +251,6 @@ simulated function bool AnimNeedsWait(name TestAnim)
} }
return ExpectingChannel == 0; return ExpectingChannel == 0;
} }
simulated function float GetOriginalGroundSpeed()
{
local float result;
result = OriginalGroundSpeed;
if( bZedUnderControl )
result *= 1.25;
return result;
}
simulated function HandleAnimation(float Delta) simulated function HandleAnimation(float Delta)
{ {
// hehehe // hehehe
@ -291,7 +315,7 @@ simulated function Tick(float Delta)
{ {
SetCollision(true, true); SetCollision(true, true);
FlashTeleport(); FlashTeleport();
SetCollision(false, false); SetCollision(true, false);
FadeStage = 2; FadeStage = 2;
} }
} }
@ -332,7 +356,7 @@ function StartTeleport()
{ {
FadeStage = 1; FadeStage = 1;
AlphaFader = 255; AlphaFader = 255;
SetCollision(false, false); SetCollision(true, false);
bFlashTeleporting = true; bFlashTeleporting = true;
} }
function FlashTeleport() function FlashTeleport()
@ -390,6 +414,7 @@ function FlashTeleport()
Teleported: Teleported:
bFlashTeleporting = false; bFlashTeleporting = false;
LastFlashTime = Level.TimeSeconds; LastFlashTime = Level.TimeSeconds;
teleportAttackCooldownEndTime = level.timeSeconds + 0.5;
} }
function Died(Controller Killer, class<DamageType> damageType, vector HitLocation) function Died(Controller Killer, class<DamageType> damageType, vector HitLocation)
{ {
@ -439,10 +464,16 @@ simulated function int DoAnimAction( name AnimName )
} }
defaultproperties defaultproperties
{ {
HeadOffsetY=-3.000000 headOffsetY=-3.000000
idleInsertFrame=0.468000 idleInsertFrame=0.468000
OnlineHeadshotOffset=(X=19.000000,Z=39.000000) onlineHeadshotOffset=(X=19.000000,Z=39.000000)
ScoringValue=15 scoringValue=15
HeadRadius=8.000000 headRadius=8.000000
HeadHeight=3.000000 headHeight=3.000000
// Override third animation just in case.
// However it shouldn't be required since we've already changed
// `SetAnimAction` function to only use first two animations
meleeAnims(0)="Claw"
meleeAnims(1)="Claw2"
meleeAnims(2)="Claw"
} }

View File

@ -223,9 +223,10 @@ simulated function HurtRadius(float DamageAmount, float DamageRadius, class<Dama
local float InitMomentum; local float InitMomentum;
local float damageScale, dist; local float damageScale, dist;
local vector dir; local vector dir;
local float UsedDamageAmount; local int UsedDamageAmount;
local KFHumanPawn humanPawn; local KFHumanPawn humanPawn;
local class<NiceVeterancyTypes> niceVet; local class<NiceVeterancyTypes> niceVet;
local NiceZombieClot niceClot;
if (bHurtEntry || Health <= 0 || HeadHealth <= 0 || bIsStunned) if (bHurtEntry || Health <= 0 || HeadHealth <= 0 || bIsStunned)
return; return;
@ -243,6 +244,10 @@ simulated function HurtRadius(float DamageAmount, float DamageRadius, class<Dama
if (Victims.bStatic || Victims.Physics == PHYS_None || !FastTrace(Victims.Location, Location) ) if (Victims.bStatic || Victims.Physics == PHYS_None || !FastTrace(Victims.Location, Location) )
continue; // skip this actor continue; // skip this actor
niceClot = NiceZombieClot(victims);
if (niceClot != none) {
niceClot.sirenBoostTimeout = 10.0;
}
Momentum = InitMomentum; Momentum = InitMomentum;
// don't let blast damage affect fluid - VisibleCollisingActors doesn't really work for them - jag // don't let blast damage affect fluid - VisibleCollisingActors doesn't really work for them - jag
// Or Karma actors in this case. Self inflicted Death due to flying chairs is uncool for a zombie of your stature. // Or Karma actors in this case. Self inflicted Death due to flying chairs is uncool for a zombie of your stature.
@ -266,7 +271,7 @@ simulated function HurtRadius(float DamageAmount, float DamageRadius, class<Dama
UsedDamageAmount = 100000; // Siren always shatters glass UsedDamageAmount = 100000; // Siren always shatters glass
else else
UsedDamageAmount = DamageAmount; UsedDamageAmount = DamageAmount;
ModDamageFromZed(UsedDamageAmount, DamageType);
Victims.TakeDamage(damageScale * UsedDamageAmount,Instigator, Victims.Location - 0.5 * (Victims.CollisionHeight + Victims.CollisionRadius) * dir, (damageScale * Momentum * dir), DamageType); Victims.TakeDamage(damageScale * UsedDamageAmount,Instigator, Victims.Location - 0.5 * (Victims.CollisionHeight + Victims.CollisionRadius) * dir, (damageScale * Momentum * dir), DamageType);
if (Instigator != none && Vehicle(Victims) != none && Vehicle(Victims).Health > 0) if (Instigator != none && Vehicle(Victims) != none && Vehicle(Victims).Health > 0)
@ -281,6 +286,12 @@ simulated function HurtRadius(float DamageAmount, float DamageRadius, class<Dama
function RemoveHead(){ function RemoveHead(){
Super.RemoveHead(); Super.RemoveHead();
} }
simulated function UpdateGroundSpeed() {
super.UpdateGroundSpeed();
if (bShotAnim) {
groundSpeed *= 0.65;
}
}
simulated function Tick( float Delta ) simulated function Tick( float Delta )
{ {
local float currScreamTime; local float currScreamTime;
@ -295,17 +306,11 @@ simulated function Tick( float Delta )
{ {
if( bShotAnim ) if( bShotAnim )
{ {
SetGroundSpeed(GetOriginalGroundSpeed() * 0.65);
if( LookTarget!=none ) if( LookTarget!=none )
{ {
Acceleration = AccelRate * Normal(LookTarget.Location - Location); Acceleration = AccelRate * Normal(LookTarget.Location - Location);
} }
} }
else
{
SetGroundSpeed(GetOriginalGroundSpeed());
}
} }
if(Role == ROLE_Authority && screamStartTime > 0){ if(Role == ROLE_Authority && screamStartTime > 0){
currScreamTime = Level.TimeSeconds - screamStartTime; currScreamTime = Level.TimeSeconds - screamStartTime;

Some files were not shown because too many files have changed in this diff Show More