1
0
KF2-Dev-Scripts/KFGameContent/Classes/KFWeap_HRG_BarrierRifle.uc
2021-06-23 01:34:46 +03:00

734 lines
22 KiB
Ucode

//=============================================================================
// KFWeap_HRG_BarrierRifle
//=============================================================================
// A modified version of the Stoner63A rifle.
//=============================================================================
// Killing Floor 2
// Copyright (C) 2021 Tripwire Interactive LLC
//=============================================================================
class KFWeap_HRG_BarrierRifle extends KFWeap_LMG_Stoner63A;
`define BARRIERRIFLE_MIC_SHIELD_INDEX 4
/** Amount of shield charge that is consumed per second */
var (Shield) float ShieldConsumptionPerSecond;
/** Amount of shield chared that is recharged per second */
var (Shield) float ShieldRechargePerSecond;
/** Cooldown to apply after the shield is destroyed */
var (Shield) float CooldownAfterShieldDepleted;
/** Cooldown to apply after the shield depleted the charge */
var (Shield) float CooldownAfterShieldDestroyed;
/** VFX and SFX for blocking damage */
var (Shield) AkBaseSoundObject BlockSound;
var (Shield) ParticleSystem BlockParticleSystem;
var (Shield) name BlockEffectsSocketName;
/** Blocking information per damage type */
var (Shield) array<BlockEffectInfo> BlockDamageTypes;
/** Modifier applied to the damage received by the character */
var (Shield) float BlockDamageModifier;
/** Modifier applied to the damager that will affect the shield charge */
var (Shield) float ShieldDamageAbsorbtionModifier;
/** Angle to block with the shield */
var (Shield) float BlockingAngle;
/** Turn ON/OFF VFX duration */
var (Shield) float ShieldFXDuration;
/** Shield Block VFX duration */
var (Shield) float ShieldBlockVFXDuration;
/** Is shield active */
var protected transient bool bIsShieldActive;
/** Was shield charge depleted */
var protected transient bool bWasShieldDepleted;
/** Was the shield destroyed */
var protected transient bool bWasShielDestroyed;
/** Self explanatory */
var protected transient bool bCanRechargeShield;
/** float containing the shield charge to not be lost in the next frame
due to int conversion.
*/
var protected transient float ShieldRechargeIncrement;
var protected transient float ShieldConsumptionIncrement;
/** Cos of the blocking angle (Rads) */
var protected transient float BlockingAngleCos;
/** Wether the timer for activating the shield has expired (using the fire interval) */
var protected transient bool bShieldActionAvailable;
/** Indicates wheter we are activating/deactivating the shield fx */
var protected bool bActivatingShield;
var protected bool bDeactivatingShield;
var protected transient float FXDelta;
var transient float RedOverlayMax;
var transient float RedOverlayMin;
var protected transient float OverlayDelta;
var WeaponFireSndInfo ShieldActivateSound;
var WeaponFireSndInfo ShieldDeactivateSound;
var WeaponFireSndInfo ShieldEndSound;
var repnotify byte ShieldAmmo;
replication
{
if (bNetDirty && Role == ROLE_Authority)
bActivatingShield, bDeactivatingShield;
if (bNetDirty && Role == ROLE_Authority && bAllowClientAmmoTracking)
ShieldAmmo;
}
simulated event ReplicatedEvent(name VarName)
{
if (VarName == nameof(ShieldAmmo))
{
AmmoCount[ALTFIRE_FIREMODE] = ShieldAmmo;
}
else
{
Super.ReplicatedEvent(VarName);
}
}
simulated event PostBeginPlay()
{
super.PostBeginPlay();
BlockingAngleCos = cos((BlockingAngle / 2.f) * DegToRad);
}
simulated function Activate()
{
super.Activate();
if (WorldInfo.NetMode != NM_DedicatedServer)
{
UpdateShieldFXValue(0.0f);
}
}
simulated function UpdateShieldFXValue(float Value)
{
if( WeaponMICs.Length > `BARRIERRIFLE_MIC_SHIELD_INDEX )
{
WeaponMICs[`BARRIERRIFLE_MIC_SHIELD_INDEX].SetScalarParameterValue('Opacity', Value);
}
}
/**
* Instead of a toggle, just immediately fire alternate fire.
*/
simulated function AltFireMode()
{
// LocalPlayer Only
if ( !Instigator.IsLocallyControlled() )
{
return;
}
if( Role < Role_Authority )
{
// if we're a client, synchronize server
UseShield();
}
CustomFire();
}
reliable server function UseShield()
{
CustomFire();
}
/** Shield deploying */
simulated function CustomFire()
{
if (bWasShieldDepleted || bWasShielDestroyed || !bShieldActionAvailable || AmmoCount[ALTFIRE_FIREMODE] == 0)
{
return;
}
bIsShieldActive ? DeactivateShield() : ActivateShield();
bIsShieldActive = !bIsShieldActive;
bShieldActionAvailable = false;
}
simulated function ActivateShield()
{
WeaponPlayFireSound(ShieldActivateSound.DefaultCue, ShieldActivateSound.FirstPersonCue);
bActivatingShield = true;
bDeactivatingShield = false;
bNetDirty = true;
NotifyShieldActive(true);
SetTimer(FireInterval[ALTFIRE_FIREMODE], false, nameof(ShieldActivationCompleted));
}
simulated function DeactivateShield()
{
WeaponPlayFireSound(ShieldDeactivateSound.DefaultCue, ShieldDeactivateSound.FirstPersonCue);
bDeactivatingShield = true;
bActivatingShield = false;
bCanRechargeShield = false;
bNetDirty=true;
NotifyShieldActive(false);
SetTimer(FireInterval[ALTFIRE_FIREMODE], false, nameof(ShieldDeactivatedTimerCompleted));
}
simulated function ShieldActivationCompleted()
{
bShieldActionAvailable = true;
}
simulated function ShieldDeactivatedTimerCompleted()
{
bShieldActionAvailable = true;
bCanRechargeShield = true;
}
/** Update shield charge - client and server */
simulated event Tick(float DeltaTime)
{
// Update Shield visuals
if (WorldInfo.NetMode != NM_DedicatedServer)
{
if (bActivatingShield && FXDelta < ShieldFXDuration)
{
FXDelta = FMin(FXDelta + DeltaTime, ShieldFXDuration);
UpdateShieldFXValue(FXDelta / ShieldFXDuration);
if (FXDelta == ShieldFXDuration)
{
bActivatingShield = false;
}
}
else if (bDeactivatingShield && FXDelta > 0.0f)
{
FXDelta = FMax(FXDelta - DeltaTime, 0.0f);
UpdateShieldFXValue(FXDelta / ShieldFXDuration);
if (FXDelta == 0.0f)
{
bDeactivatingShield = false;
}
}
}
if (OverlayDelta > RedOverlayMin)
{
OverlayDelta = FMax(OverlayDelta - DeltaTime, RedOverlayMin);
UpdateShieldBlockVFX(RedOverlayMax * (OverlayDelta / ShieldBlockVFXDuration));
}
if ( Role == Role_Authority )
{
// If shield is active it needs to consume charge, otherwise it recharges itself.
if (bIsShieldActive)
{
ConsumeShield(DeltaTime);
}
else if (bCanRechargeShield && AmmoCount[ALTFIRE_FIREMODE] < MagazineCapacity[ALTFIRE_FIREMODE])
{
RechargeShield(DeltaTime);
}
}
Super.Tick(DeltaTime);
}
simulated function ConsumeShield(float DeltaTime)
{
local int Charge;
if (Role == ROLE_Authority)
{
ShieldRechargeIncrement = 0.0f;
ShieldConsumptionIncrement += ShieldConsumptionPerSecond * DeltaTime;
if (ShieldConsumptionIncrement >= 1.0f && AmmoCount[ALTFIRE_FIREMODE] > 0)
{
Charge = int(ShieldConsumptionIncrement);
AmmoCount[ALTFIRE_FIREMODE] = Max(AmmoCount[ALTFIRE_FIREMODE] - Charge, 0);
ShieldConsumptionIncrement -= Charge;
ShieldAmmo = AmmoCount[ALTFIRE_FIREMODE];
if (AmmoCount[ALTFIRE_FIREMODE] == 0)
{
OnShieldDepleted();
}
}
}
}
simulated function RechargeShield(float DeltaTime)
{
local int Charge;
if (Role == ROLE_Authority)
{
ShieldConsumptionIncrement = 0.0f;
ShieldRechargeIncrement += ShieldRechargePerSecond * DeltaTime;
if (ShieldRechargeIncrement >= 1.0f && AmmoCount[ALTFIRE_FIREMODE] < MagazineCapacity[ALTFIRE_FIREMODE])
{
Charge = int(ShieldRechargeIncrement);
AmmoCount[ALTFIRE_FIREMODE] = Min(AmmoCount[ALTFIRE_FIREMODE] + Charge, MagazineCapacity[ALTFIRE_FIREMODE]);
ShieldRechargeIncrement -= Charge;
ShieldAmmo = AmmoCount[ALTFIRE_FIREMODE];
}
}
}
/** Shield consumed all the charge by itself */
simulated function OnShieldDepleted()
{
bWasShieldDepleted = true;
bActivatingShield = false;
bDeactivatingShield = true;
bCanRechargeShield = false;
bIsShieldActive = false;
ShieldAmmo = 0;
bNetDirty = true;
NotifyShieldActive(false);
WeaponPlayFireSound(ShieldEndSound.DefaultCue, ShieldEndSound.FirstPersonCue);
SetTimer(CooldownAfterShieldDepleted, false, nameof(ShieldRepletedTimerCompleted));
}
simulated function ShieldRepletedTimerCompleted()
{
bWasShieldDepleted = false;
bCanRechargeShield = true;
}
/** Shield was destroyed by attacks */
simulated function OnShieldDestroyed()
{
bWasShielDestroyed = true;
bActivatingShield = false;
bDeactivatingShield = true;
bCanRechargeShield = false;
bIsShieldActive = false;
ShieldAmmo = 0;
bNetDirty = true;
NotifyShieldActive(false);
WeaponPlayFireSound(ShieldEndSound.DefaultCue, ShieldEndSound.FirstPersonCue);
SetTimer(CooldownAfterShieldDestroyed, false, nameof(ShieldDestroyedTimerCompleted));
}
simulated function ShieldDestroyedTimerCompleted()
{
bWasShielDestroyed = false;
bCanRechargeShield = true;
}
/** Update HUD ammo icon for shield */
simulated function int GetSecondaryAmmoForHUD()
{
return AmmoCount[ALTFIRE_FIREMODE];
}
simulated function ShieldAbsorbDamage(int DamageBase)
{
local int Damage;
// Use the carried shield reduction by time
ShieldConsumptionIncrement += DamageBase*ShieldDamageAbsorbtionModifier;
Damage = int(ShieldConsumptionIncrement);
AmmoCount[ALTFIRE_FIREMODE] = Max(AmmoCount[ALTFIRE_FIREMODE] - Damage, 0);
ShieldConsumptionIncrement -= Damage;
// Check if shield is destroyed.
if (AmmoCount[ALTFIRE_FIREMODE] == 0)
{
OnShieldDestroyed();
}
}
/**
Reduce the damage received and apply it to the shield
*/
function AdjustDamage(out int InDamage, class<DamageType> DamageType, Actor DamageCauser)
{
local KFPerk InstigatorPerk;
local byte BlockTypeIndex;
local float DmgCauserDot;
if (!bIsShieldActive)
{
return;
}
// Don't apply block effects for teammates
if (Instigator.IsSameTeam(DamageCauser.Instigator))
{
return;
}
if (CanBlockDamageType(DamageType, BlockTypeIndex))
{
if (ClassIsChildOf(DamageCauser.class, class'Projectile'))
{
// Projectile might be beyond/behind player, resulting in bad dot
// Projectile won't have a velocity to check against, either
// Assume velocity is the vector between projectile and instigator
DmgCauserDot = Normal(DamageCauser.Instigator.Location - DamageCauser.Location) dot vector(Instigator.Rotation);
}
else
{
DmgCauserDot = Normal(DamageCauser.Location - Instigator.Location) dot vector(Instigator.Rotation);
}
if (DmgCauserDot > BlockingAngleCos)
{
ShieldAbsorbDamage(InDamage);
InDamage *= BlockDamageModifier;
ClientPlayBlockEffects(BlockTypeIndex);
NotifyShieldBlockActive(true);
SetTimer(0.1f, false, nameof(ResetShieldBlockVFX));
InstigatorPerk = GetPerk();
if (InstigatorPerk != none)
{
InstigatorPerk.SetSuccessfullBlock();
}
}
}
}
/** Only DT added to BlockDamageTypes can be blocked. Check if the current one is in the list. */
function bool CanBlockDamageType(class<DamageType> DamageType, optional out byte out_Idx)
{
local int Idx;
for (Idx = 0; Idx < BlockDamageTypes.length; ++Idx)
{
if (ClassIsChildOf(DamageType, BlockDamageTypes[Idx].DmgType))
{
out_Idx = Idx;
return true;
}
}
out_Idx = INDEX_NONE;
return false;
}
unreliable client function ClientPlayBlockEffects(optional byte BlockDTIndex=255)
{
local AkBaseSoundObject Sound;
local ParticleSystem PSTemplate;
GetBlockEffects(BlockDTIndex, Sound, PSTemplate);
PlayLocalBlockEffects(Sound, PSTemplate);
UpdateShieldBlockVFX(RedOverlayMax);
OverlayDelta = ShieldBlockVFXDuration;
}
/** Called on the client when successfully block/parry an attack */
simulated function PlayLocalBlockEffects(AKBaseSoundObject Sound, ParticleSystem PSTemplate)
{
local vector Loc;
local rotator Rot;
local ParticleSystemComponent PSC;
if (Sound != None)
{
PlaySoundBase(Sound, true);
}
if (PSTemplate != None)
{
if (MySkelMesh.GetSocketWorldLocationAndRotation(BlockEffectsSocketName, Loc, Rot))
{
PSC = WorldInfo.MyEmitterPool.SpawnEmitter(PSTemplate, Loc, Rot);
PSC.SetDepthPriorityGroup(SDPG_Foreground);
}
else
{
`log(self@GetFuncName()@"missing BlockEffects Socket!");
}
}
}
/** Returns sound and particle system overrides using index into BlockDamageTypes array */
simulated function GetBlockEffects(byte BlockDTIndex, out AKBaseSoundObject outSound, out ParticleSystem outParticleSys)
{
outSound = BlockSound;
outParticleSys = BlockParticleSystem;
if (BlockDTIndex != 255)
{
if (BlockDamageTypes[BlockDTIndex].BlockSound != None)
{
outSound = BlockDamageTypes[BlockDTIndex].BlockSound;
}
if (BlockDamageTypes[BlockDTIndex].BlockParticleSys != None)
{
outParticleSys = BlockDamageTypes[BlockDTIndex].BlockParticleSys;
}
}
}
/**
Should replicate to 3P to show the shield effects
*/
simulated function NotifyShieldActive(bool bActive)
{
local KFPawn KFP;
if (WorldInfo.NetMode != NM_Client)
{
KFP = KFPawn(Instigator);
KFP.OnWeaponSpecialAction(bActive ? 1 : 0);
}
}
simulated function NotifyShieldBlockActive(bool bActive)
{
local KFPawn KFP;
if (WorldInfo.NetMode != NM_Client)
{
KFP = KFPawn(Instigator);
KFP.OnWeaponSpecialAction(bActive ? 3 : 2);
}
}
/*********************************************************************************************
* State WeaponEquipping
* The Weapon is in this state while transitioning from Inactive to Active state.
* Typically, the weapon will remain in this state while its selection animation is being played.
* While in this state, the weapon cannot be fired.
*********************************************************************************************/
simulated state WeaponEquipping
{
simulated function BeginState(Name PreviousStateName)
{
UpdateShieldFXValue(0.0f);
FXDelta = 0.0f;
bShieldActionAvailable = true;
super.BeginState(PreviousStateName);
}
}
/*********************************************************************************************
* State WeaponPuttingDown
* Putting down weapon in favor of a new one.
* Weapon is transitioning to the Inactive state.
*********************************************************************************************/
simulated state WeaponPuttingDown
{
simulated event EndState(Name NextStateName)
{
UpdateShieldFXValue(0.0f);
// Reset Values
bIsShieldActive = false;
bWasShieldDepleted = false;
bWasShielDestroyed = false;
bCanRechargeShield = true;
bShieldActionAvailable = false;
bActivatingShield = false;
bDeactivatingShield = false;
FXDelta = 0.0f;
bNetDirty=true;
super.EndState(NextStateName);
}
}
simulated function UpdateShieldBlockVFX(float Value)
{
if( WeaponMICs.Length > `BARRIERRIFLE_MIC_SHIELD_INDEX )
{
WeaponMICs[`BARRIERRIFLE_MIC_SHIELD_INDEX].SetScalarParameterValue('RedOverlay', Value);
}
}
function ResetShieldBlockVFX()
{
NotifyShieldBlockActive(false);
}
/** Shield doesn't count as ammo for purposes of inventory management (e.g. switching) */
simulated function bool HasAnyAmmo()
{
return AmmoCount[0] > 0 || SpareAmmoCount[0] > 0;
}
defaultproperties
{
// Shooting Animations
FireSightedAnims[0]=Shoot_Iron
FireSightedAnims[1]=Shoot_Iron2
FireSightedAnims[2]=Shoot_Iron3
// FOV
MeshFOV=75
MeshIronSightFOV=35
PlayerIronSightFOV=70
// Depth of field
DOF_FG_FocalRadius=85
DOF_FG_MaxNearBlurSize=2.5
// Content
PackageKey="HRG_BarrierRifle"
FirstPersonMeshName="WEP_1P_HRG_BarrierRifle_MESH.WEP_1stP_HRG_BarrielRifle_Rig"
FirstPersonAnimSetNames(0)="WEP_1P_HRG_BarrierRifle_ANIM.Wep_1stP_HRG_BarrierRifle_Anim"
PickupMeshName="WEP_3P_HRG_BarrierRifle_MESH.Wep_3rdP_HRG_BarrierRifle_Pickup"
AttachmentArchetypeName="WEP_HRG_BarrierRifle_ARCH.Wep_HRG_BarrierRifle_3P"
MuzzleFlashTemplateName="WEP_HRG_BarrierRifle_ARCH.Wep_HRG_BarrierRifle_MuzzleFlash"
// Zooming/Position
PlayerViewOffset=(X=4.0,Y=8,Z=-4)
IronSightPosition=(X=8.5,Y=0,Z=0)
// Ammo
MagazineCapacity[0]=60
SpareAmmoCapacity[0]=540 //480
InitialSpareMags[0]=2
bCanBeReloaded=true
bReloadFromMagazine=true
// Shield "Ammo"
MagazineCapacity[1]=100
SpareAmmoCapacity[1]=0
bCanRefillSecondaryAmmo=false
// Recoil
maxRecoilPitch=110 //120
minRecoilPitch=70 //70
maxRecoilYaw=80 //130
minRecoilYaw=-80 //-130
RecoilRate=0.045 //0.08
RecoilMaxYawLimit=500
RecoilMinYawLimit=65035
RecoilMaxPitchLimit=900
RecoilMinPitchLimit=65035
RecoilISMaxYawLimit=75
RecoilISMinYawLimit=65460
RecoilISMaxPitchLimit=375
RecoilISMinPitchLimit=65460
RecoilViewRotationScale=0.4 //0.25
IronSightMeshFOVCompensationScale=2.3
HippedRecoilModifier=1.5
//WalkingRecoilModifier=1.1
//JoggingRecoilModifier=1.2
// Inventory / Grouping
InventorySize=7
GroupPriority=125
WeaponSelectTexture=Texture2D'wep_ui_hrg_barrierrifle_tex.UI_WeaponSelect_HRG_BarrierRifle'
AssociatedPerkClasses(0)=class'KFPerk_SWAT'
// DEFAULT_FIREMODE
FireModeIconPaths(DEFAULT_FIREMODE)=Texture2D'ui_firemodes_tex.UI_FireModeSelect_BulletAuto'
FiringStatesArray(DEFAULT_FIREMODE)=WeaponFiring
WeaponFireTypes(DEFAULT_FIREMODE)=EWFT_InstantHit
WeaponProjectiles(DEFAULT_FIREMODE)=class'KFProj_Bullet_AssaultRifle'
InstantHitDamageTypes(DEFAULT_FIREMODE)=class'KFDT_Ballistic_HRG_BarrierRifle'
FireInterval(DEFAULT_FIREMODE)=+0.066 // 900 RPM
Spread(DEFAULT_FIREMODE)=0.025 //0.0085
InstantHitDamage(DEFAULT_FIREMODE)=33.0 //35.0
FireOffset=(X=30,Y=4.5,Z=-5)
// ALT_FIREMODE
FireModeIconPaths(ALTFIRE_FIREMODE)=Texture2D'ui_firemodes_tex.UI_FireModeSelect_BulletAuto'
WeaponFireTypes(ALTFIRE_FIREMODE)=EWFT_Custom
AmmoCost(ALTFIRE_FIREMODE)=0
FireInterval(ALTFIRE_FIREMODE)=0.01f
SecondaryAmmoTexture=Texture2D'ui_firemodes_tex.UI_FireModeSelect_Electricity'
// BASH_FIREMODE
InstantHitDamageTypes(BASH_FIREMODE)=class'KFDT_Bludgeon_HRG_BarrierRifle'
InstantHitDamage(BASH_FIREMODE)=26
// Fire Effects
WeaponFireSnd(DEFAULT_FIREMODE)=(DefaultCue=AkEvent'WW_WEP_Stoner.Play_WEP_Stoner_Fire_3P_Loop', FirstPersonCue=AkEvent'WW_WEP_Stoner.Play_WEP_Stoner_Fire_1P_Loop')
WeaponFireLoopEndSnd(DEFAULT_FIREMODE)=(DefaultCue=AkEvent'WW_WEP_Stoner.Play_WEP_Stoner_Fire_3P_EndLoop', FirstPersonCue=AkEvent'WW_WEP_Stoner.Play_WEP_Stoner_Fire_1P_EndLoop')
WeaponDryFireSnd(DEFAULT_FIREMODE)=AkEvent'WW_WEP_SA_L85A2.Play_WEP_SA_L85A2_Handling_DryFire'
EjectedShellForegroundDuration=0.8f
// Advanced (High RPM) Fire Effects
bLoopingFireAnim(DEFAULT_FIREMODE)=true
bLoopingFireSnd(DEFAULT_FIREMODE)=true
// Attachments
bHasIronSights=true
bHasFlashlight=false
// Ammo belt
AmmoBeltBulletBonePrefix="RW_Bullets"
NumAmmoBeltBullets=14
LastAmmoCount=-1
bIsShieldActive=false
bWasShieldDepleted=false
bWasShielDestroyed=false
bCanRechargeShield=true
ShieldRechargeIncrement=0.0f;
ShieldConsumptionIncrement=0.0f
ShieldConsumptionPerSecond=3.0f //10.0f
ShieldRechargePerSecond=8.0f //10.0f //15.0f
CooldownAfterShieldDepleted=3.0f //3.0f
CooldownAfterShieldDestroyed=3.0f //5.0f
ShieldActivateSound=(DefaultCue=AkEvent'WW_WEP_HRG_BarrierRifle.Play_WEP_HRG_BarrierRifle_3P_Shield_On', FirstPersonCue=AkEvent'WW_WEP_HRG_BarrierRifle.Play_WEP_HRG_BarrierRifle_1P_Shield_On')
ShieldDeactivateSound=(DefaultCue=AkEvent'WW_WEP_HRG_BarrierRifle.Play_WEP_HRG_BarrierRifle_3P_Shield_Off', FirstPersonCue=AkEvent'WW_WEP_HRG_BarrierRifle.Play_WEP_HRG_BarrierRifle_1P_Shield_Off')
ShieldEndSound=(DefaultCue=AkEvent'WW_WEP_HRG_BarrierRifle.Play_WEP_HRG_BarrierRifle_3P_Shield_End', FirstPersonCue=AkEvent'WW_WEP_HRG_BarrierRifle.Play_WEP_HRG_BarrierRifle_1P_Shield_End')
BlockSound=AkEvent'WW_WEP_HRG_BarrierRifle.Play_WEP_HRG_BarrierRifle_1P_Shield_Impact'
BlockParticleSystem=ParticleSystem'FX_Impacts_EMIT.FX_Block_melee_01'
BlockEffectsSocketName=BlockEffect
RedOverlayMax=1.0f
RedOverlayMin=0.0f
OverlayDelta=0.0f
ShieldBlockVFXDuration=0.5f
BlockDamageTypes.Add((DmgType=class'KFDT_Bludgeon', BlockSound=AkEvent'WW_WEP_HRG_BarrierRifle.Play_WEP_HRG_BarrierRifle_1P_Shield_Impact'))
BlockDamageTypes.Add((DmgType=class'KFDT_Slashing', BlockSound=AkEvent'WW_WEP_HRG_BarrierRifle.Play_WEP_HRG_BarrierRifle_1P_Shield_Impact'))
BlockDamageTypes.Add((DmgType=class'KFDT_Fire_HuskFireball', BlockSound=AkEvent'WW_WEP_HRG_BarrierRifle.Play_WEP_HRG_BarrierRifle_1P_Shield_Impact'))
BlockDamageTypes.Add((DmgType=class'KFDT_Fire_HuskFlamethrower'))
BlockDamageTypes.Add((DmgType=class'KFDT_BloatPuke'))
BlockDamageTypes.Add((DmgType=class'KFDT_EvilDAR_Rocket', BlockSound=AkEvent'WW_WEP_HRG_BarrierRifle.Play_WEP_HRG_BarrierRifle_1P_Shield_Impact'))
BlockDamageTypes.Add((DmgType=class'KFDT_EvilDAR_Laser', BlockSound=AkEvent'WW_WEP_HRG_BarrierRifle.Play_WEP_HRG_BarrierRifle_1P_Shield_Impact'))
BlockDamageTypes.Add((DmgType=class'KFDT_DAR_EMPBlast', BlockSound=AkEvent'WW_WEP_HRG_BarrierRifle.Play_WEP_HRG_BarrierRifle_1P_Shield_Impact'))
BlockDamageTypes.Add((DmgType=class'KFDT_Ballistic_PatMinigun', BlockSound=AkEvent'WW_WEP_HRG_BarrierRifle.Play_WEP_HRG_BarrierRifle_1P_Shield_Impact'))
BlockDamageTypes.Add((DmgType=class'KFDT_Explosive_PatMissile', BlockSound=AkEvent'WW_WEP_HRG_BarrierRifle.Play_WEP_HRG_BarrierRifle_1P_Shield_Impact'))
BlockDamageTypes.Add((DmgType=class'KFDT_Ballistic_HansAK12', BlockSound=AkEvent'WW_WEP_HRG_BarrierRifle.Play_WEP_HRG_BarrierRifle_1P_Shield_Impact'))
BlockDamageTypes.Add((DmgType=class'KFDT_EMP_MatriarchTeslaBlast', BlockSound=AkEvent'WW_WEP_HRG_BarrierRifle.Play_WEP_HRG_BarrierRifle_1P_Shield_Impact'))
BlockDamageTypes.Add((DmgType=class'KFDT_EMP_MatriarchPlasmaCannon'))
BlockDamageTypes.Add((DmgType=class'KFDT_FleshpoundKing_ChestBeam'))
BlockDamageModifier=0.3f //0.4f
ShieldDamageAbsorbtionModifier=1.2f //0.8f //0.8 = equal to base damage
BlockingAngle=180.f // Adjust with visuals.
bShieldActionAvailable=true
bActivatingShield=false
bDeactivatingShield=false
FXDelta=0.0f
ShieldFXDuration=0.15f
bAllowClientAmmoTracking=true
NumBloodMapMaterials=5
WeaponUpgrades[1]=(Stats=((Stat=EWUS_Damage0, Scale=1.0f), (Stat=EWUS_Weight, Add=0)))
}