Advertisement
poosh

ScrnAchHandlerBase - ScrN Balance - Killing Floor

Nov 29th, 2013
447
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. class ScrnAchHandlerBase extends Info
  2.     abstract;
  3.  
  4. var protected ScrnGameRules GameRules;
  5.  
  6. const IGNORE_STAT = 0x7FFFFFFF;
  7.  
  8. // Damage flags
  9. // copy-pasted from ScrnGameRules for easy access
  10. const DF_STUNNED   = 0x01; // stun shot
  11. const DF_RAGED     = 0x02; // rage shot
  12. const DF_STUPID    = 0x04; // damage shouldn't be done to this zed
  13. const DF_DECAP     = 0x08; // decapitaion shot
  14. const DF_HEADSHOT  = 0x10; // 100% sure that this damage was made by headshot
  15.  
  16. function PostBeginPlay()
  17. {
  18.     FindGameRules();
  19. }
  20.  
  21. function FindGameRules()
  22. {
  23.     local GameRules G;
  24.    
  25.     if ( GameRules != none )
  26.         return;
  27.        
  28.     for ( G=Level.Game.GameRulesModifiers; G!=None; G=G.NextGameRules ) {
  29.         if ( ScrnGameRules(G) != none ) {
  30.             GameRules = ScrnGameRules(G);
  31.             GameRules.RegisterAchHandler(self);
  32.             return;
  33.         }
  34.     }
  35.     log(GetItemName(String(self)) $ ": unable to find ScrnGameRules. Trying again in 5 seconds.", class.outer.name);
  36.     SetTimer(5.0, false);
  37. }
  38.  
  39. function Timer()
  40. {
  41.     FindGameRules();
  42. }
  43.  
  44. // -----------------------------------------------------------------------------------
  45. // STATIC FUNCTIONS
  46. // -----------------------------------------------------------------------------------
  47.  
  48. /*
  49.     Helper function for quickly determining whether a pawn is rotated at a point in space.
  50.     original authors :  Alex Quick, Ron Prestenback.
  51.  
  52.  * @param    Pawn            pawn, which rotation needs to be checked    
  53.  * @param    TargetLocation    the location to check
  54.  * @param    MinDotResult    a value between 0 and 1 representing the minimum dot result value that should be
  55.  *                            considered acceptable for testing whether the location is within our field of
  56.  *                            view.  Default value (0) is corresponds to a maximum angle of around 180 degrees
  57.  *
  58.  * @return    TRUE if the location is within the angle specified from the pawn's rotation.
  59.  */
  60. static function bool IsRotatedAtLocation(Pawn Pawn, vector TargetLocation, optional float MinDotResult)
  61. {
  62.     local vector DirectionNormal;
  63.     local float ViewAngleCosine;
  64.  
  65.     // get the normalized distance between the two locations
  66.     DirectionNormal = Normal(TargetLocation - Pawn.Location);
  67.  
  68.     // get the dot result of the pawn's rotation and the target location
  69.     ViewAngleCosine = DirectionNormal dot vector(Pawn.Rotation);
  70.  
  71.     // determine if the angle between pawn's rotation and the target location is within range.
  72. //    log("IS LOOKING AT LOCATION - "@ViewAngleCosine@" Required : "@MinDotResult);
  73.     return ViewAngleCosine >= MinDotResult;
  74. }
  75.  
  76. // returns number of not triggered pipeboms, which detonation range covers Pawn's location
  77. // and are in lone of sight of a given pawn
  78. static function int InPipeBombRange(Pawn Pawn, float PipeDetonationRange)
  79. {
  80.     local PipeBombProjectile pipe;
  81.     local int count;
  82.     local Controller C;
  83.  
  84.     C = Pawn.Controller;
  85.     if ( C == none )
  86.         return 0;
  87.    
  88.     foreach Pawn.VisibleCollidingActors( class 'PipeBombProjectile', pipe, PipeDetonationRange, Pawn.Location ) {
  89.         if ( !pipe.bTriggered && !pipe.bHasExploded && !pipe.bDisintegrated && !pipe.bEnemyDetected
  90.                 && IsRotatedAtLocation(Pawn, pipe.Location, 0.5) )
  91.             count++;
  92.     }
  93.     return count;
  94. }
  95.  
  96. //returns how much damage Instigator made to Victim
  97. static function int GetTotalDamageMade(KFMonster Victim, Pawn Instigator)
  98. {
  99.     if ( Victim == none || Instigator == none )
  100.         return 0;
  101.        
  102.     return GetTotalDamageMadeC(KFMonsterController(Victim.Controller), Instigator.Controller);
  103. }
  104.  
  105. //returns how much damage PC made to MC
  106. static function int GetTotalDamageMadeC(KFMonsterController MC, Controller PC)
  107. {
  108.     local int i;
  109.    
  110.     if ( MC == none || PC == none )
  111.         return 0;
  112.        
  113.     for ( i = 0; i < MC.KillAssistants.Length; ++i ) {
  114.         if ( PC == MC.KillAssistants[i].PC )
  115.             return MC.KillAssistants[i].Damage;
  116.     }
  117.     return 0;
  118. }
  119.  
  120. static function bool IsPistolDamage(ScrnPlayerInfo InstigatorSPI, class<KFWeaponDamageType> DamageType)
  121. {
  122.     local KFPlayerReplicationInfo KFPRI;
  123.    
  124.     if ( DamageType == none || InstigatorSPI == none || InstigatorSPI.PlayerOwner == none )
  125.         return false;
  126.      
  127.     KFPRI =  KFPlayerReplicationInfo(InstigatorSPI.PlayerOwner.PlayerReplicationInfo);
  128.     if ( KFPRI == none )
  129.         return false;
  130.     // Gunslinger gets damage bonus on all pistols (even level 0).
  131.     // So if output damage > input damage, DamageType is pistol damage
  132.     return  class'ScrnVetGunslinger'.static.AddDamage(KFPRI, none, none, 100, DamageType) > 100;
  133. }
  134.  
  135. static function bool IsAssaultRifleDamage(ScrnPlayerInfo InstigatorSPI, class<KFWeaponDamageType> DamageType)
  136. {
  137.     local KFPlayerReplicationInfo KFPRI;
  138.    
  139.     if ( DamageType == none || InstigatorSPI == none || InstigatorSPI.PlayerOwner == none )
  140.         return false;
  141.      
  142.     KFPRI =  KFPlayerReplicationInfo(InstigatorSPI.PlayerOwner.PlayerReplicationInfo);
  143.     if ( KFPRI == none )
  144.         return false;
  145.        
  146.     return  class'ScrnVetCommando'.static.AddDamage(KFPRI, none, none, 100, DamageType) > 100;
  147. }
  148.  
  149. // returns true, if player is using medic perk
  150. static function bool IsMedic(ScrnPlayerInfo SPI)
  151. {
  152.     local KFPlayerReplicationInfo KFPRI;
  153.    
  154.     if ( SPI == none || SPI.PlayerOwner == none )
  155.         return false;
  156.  
  157.     KFPRI = KFPlayerReplicationInfo(SPI.PlayerOwner.PlayerReplicationInfo);
  158.     if ( KFPRI != none && KFPRI.ClientVeteranSkill != none )
  159.         return KFPRI.ClientVeteranSkill.static.GetHealPotency(KFPRI) > 1.01;
  160.  
  161.     return false;
  162. }
  163. // -----------------------------------------------------------------------------------
  164.  
  165.  
  166.  
  167. // give achievement to all players, except ExcludeSPI
  168. final function Ach2All(name AchID, int Inc, optional ScrnPlayerInfo ExcludeSPI)
  169. {
  170.     if ( GameRules != none )
  171.         GameRules.ProgressAchievementForAllPlayers(AchID, Inc, false);
  172. }
  173. // give achievement to alive players, except ExcludeSPI
  174. final function Ach2Alive(name AchID, int Inc, optional ScrnPlayerInfo ExcludeSPI)
  175. {
  176.     if ( GameRules != none )
  177.         GameRules.ProgressAchievementForAllPlayers(AchID, Inc, true);
  178. }
  179.  
  180. /**
  181.  * Function is called every time after the start of new wave
  182.  * @param WaveNum - wave number, where 0 is first wave
  183.  */
  184. function WaveStarted(byte WaveNum) { }
  185. /**
  186.  * Function is called every time after the end of new wave
  187.  * ScrnPlayerInfos aren't reset yet and can be used freely here
  188.  * @param WaveNum - wave number, where 0 is first wave
  189.  */
  190. function WaveEnded(byte WaveNum) { }
  191.  
  192. // Function is called only when squad is survived.
  193. // Map name without .rom, e.g. "KF-Farm". MapName is already checked for GameRules.MapAliases before
  194. // calling GameWon()
  195. function GameWon(string MapName) { }
  196.  
  197. // override this to catch all NetDamage() calls passed to GameRules.
  198. // NetDamage is executed after MonsterDamaged() or PlayerDamaged()
  199. function NetDamage( int Damage, pawn injured, pawn instigatedBy, vector HitLocation, out vector Momentum,
  200.     class<DamageType> DamType ) {}
  201. // override this to catch all ScoreKill() calls passed to GameRules.
  202. // score killed is executed after MonsterDied() or PlayerDied()
  203. function ScoreKill(Controller Killer, Controller Killed) {}
  204.  
  205. // player-to-monster damages
  206. // called from ScrnPlayerInfo.MadeDamage()
  207. // At this moment InstigatorInfo.LastDmgTime still stores previos damage time (not the given one).
  208. // So time between subsequent damages can be calculated by Level.TimeSeconds - InstigatorInfo.LastKillTime
  209. function MonsterDamaged(int Damage, KFMonster Victim, ScrnPlayerInfo InstigatorInfo,
  210.     class<KFWeaponDamageType> DamType, bool bIsHeadshot, bool bWasDecapitated) {}
  211.  
  212. // monster got killed by a player    
  213. // called from ScrnPlayerInfo.KilledMonster()
  214. // At this moment KillerInfo.LastKillTime still stores previos kill time (not the given one).
  215. // So time between subsequent kills can be calculated by Level.TimeSeconds - KillerInfo.LastKillTime
  216. function MonsterKilled(KFMonster Victim, ScrnPlayerInfo KillerInfo, class<KFWeaponDamageType> DamType) {}
  217.  
  218. // player took a hit from monster
  219. // called from ScrnPlayerInfo.TookDamage()
  220. function PlayerDamaged(int Damage, ScrnPlayerInfo VictimSPI, KFMonster InstigatedBy, class<DamageType> DamType) {}
  221.  
  222. // player got killed
  223. // called from ScrnPlayerInfo.Died()
  224. // DeadPlayerInfo already has bDead = true and increased Deaths
  225. function PlayerDied(ScrnPlayerInfo DeadPlayerInfo, Controller Killer, class<DamageType> DamType) {}
  226.    
  227. /**
  228.  * Triggers when end game boss spawned on the map.
  229.  * This function is called before KFMonster.PostBeginPlay(), where difficulty multipliers are applied,
  230.  * so it can't be used for checking actual monster parameters such as health or damage!
  231.  * @param EndGameBoss The monster to spawned as end game boss (usually Patriarch)
  232.  */
  233. function BossSpawned(KFMonster EndGameBoss) {}
  234.  
  235. /**
  236.  * Triggers when monster of a new class first time spawns in the game, i.e. it triggers on first Clot, first Gorefast etc.
  237.  * This function is called before KFMonster.PostBeginPlay(), where difficulty multipliers are applied,
  238.  * so it can't be used for checking actual monster parameters such as health or damage!
  239.  *
  240.  * @param Monster The momnster who spawned first time in the game
  241.  */
  242. function MonsterIntroduced(KFMonster Monster) {}
  243.  
  244.  
  245.  
  246. // Functions below are triggered, if stat value reaches a given number.
  247. // AchHandler must return the minimal number, which it wants to be triggered.
  248. // If AchHandler isn't interested in a given stat, it must return IGNORE_STAT.
  249. // Keep in mind that return value is used as recomendation, not as a rule. It means that even
  250. // if function had returned 5, there are no guaranties that it won't be triggered with a lower value
  251. // e.g. 3. So input value must be checked always.
  252.  
  253. /**
  254.  * Triggers when player scored multiple headshots in a row.
  255.  * @param SPI Intigator's ScrnPlayerInfo record
  256.  * @param Count Headhot count in a row
  257.  * @return Minimal headshot count to be reached before the next call of this function
  258.  */
  259. function int RowHeadhots(ScrnPlayerInfo SPI, int Count)
  260. {
  261.     return IGNORE_STAT;
  262. }
  263.  
  264. /**
  265.  * Triggers when player scored multiple headshots in a row with one weapon.
  266.  * @param SPI Intigator's ScrnPlayerInfo record
  267.  * @param Weapon Weapon that PROBABLY was used to produce this damage type
  268.  * @param DamType Damage type that was catched by GameRules
  269.  * @param Count Headhot count in a row
  270.  * @return Minimal headshot count to be reached before the next call of this function
  271.  */
  272. function int WRowHeadhots(ScrnPlayerInfo SPI, KFWeapon Weapon, class<KFWeaponDamageType> DamType, int Count)
  273. {
  274.     return IGNORE_STAT;
  275. }
  276.    
  277. /**
  278.  * Triggers when players scored multiple kills with one shot or without releasing a trigger
  279.  * (depends from a weapon). Sometimes shot isn't registred and multiple shots are registred as one.
  280.  * So DeltaTime needs to be checked too.
  281.  *
  282.  * @param SPI Intigator's ScrnPlayerInfo record
  283.  * @param Weapon Weapon that PROBABLY was used to produce this damage type
  284.  * @param DamType Damage type that was catched by GameRules
  285.  * @param Count Kill count in one shot
  286.  * @param DeltaTime time between last and previous kill
  287.  * @return Minimal headshot count to be reached before the next call of this function
  288.  */
  289. function int WKillsPerShot(ScrnPlayerInfo SPI, KFWeapon Weapon, class<KFWeaponDamageType> DamType, int Count, float DeltaTime)
  290. {
  291.     return IGNORE_STAT;
  292. }    
  293. // Same as WKillsPerShot, but triggers on kills without reloading
  294. function int WKillsPerMagazine(ScrnPlayerInfo SPI, KFWeapon Weapon, class<KFWeaponDamageType> DamType, int Count)
  295. {
  296.     return IGNORE_STAT;
  297. }    
  298. // number of decapitaions per shot
  299. function int WDecapsPerShot(ScrnPlayerInfo SPI, KFWeapon Weapon, class<KFWeaponDamageType> DamType, int Count, float DeltaTime)
  300. {
  301.     return IGNORE_STAT;
  302. }    
  303. // Same as WKillsPerShot, but triggers on kills without reloading
  304. function int WDecapsPerMagazine(ScrnPlayerInfo SPI, KFWeapon Weapon, class<KFWeaponDamageType> DamType, int Count)
  305. {
  306.     return IGNORE_STAT;
  307. }
  308. // number of decapitaions per shot
  309. function int WDamagePerShot(ScrnPlayerInfo SPI, KFWeapon Weapon, class<KFWeaponDamageType> DamType, int Damage, float DeltaTime)
  310. {
  311.     return IGNORE_STAT;
  312. }    
  313. // Same as WKillsPerShot, but triggers on kills without reloading
  314. function int WDamagePerMagazine(ScrnPlayerInfo SPI, KFWeapon Weapon, class<KFWeaponDamageType> DamType, int Damage)
  315. {
  316.     return IGNORE_STAT;
  317. }
  318.  
  319.  
  320. /**
  321.  * Triggers each time when one player healed another one. Doesn't trigger if player already had 100% hp.
  322.  * @param HealAmount    the amount of health Patient received
  323.  * @param Patient        player, who received healing
  324.  * @param InstigatorSPI    Instigator's player info. Player, who made healing.
  325.  * @param MedicGun        Instigator's weapon, which was used for healing
  326.  *  
  327.  */
  328. function HealingMade(int HealAmount, ScrnHumanPawn Patient, ScrnPlayerInfo InstigatorSPI, KFWeapon MedicGun) {}
  329.  
  330.  
  331. /**
  332.  * Triggers when player picks up the cash. ReceiverInfo.CashReceived and CashFound and DonatorInfo.CashDonated,
  333.  * as well as their PerWave variables, already include CashAmount.
  334.  * Function isn't triggered, when player picks up own cash.
  335.  *
  336.  * @param CashAmount     amount of cash picked up
  337.  * @param ReceiverInfo     player, who received cash (always != none)
  338.  * @param DonatorInfo    player, who dropped the cash (can be none)
  339.  * @param bDroppedCash    if true, cash was dropped by a player. False means it was spawned on the map.
  340.  *                        There can be situations when bDroppedCash=true and DonatorInfo=none, so
  341.  *                        DonatorInfo must be always checked for none.
  342.  */
  343. function PickedCash(int CashAmount, ScrnPlayerInfo ReceiverInfo, ScrnPlayerInfo DonatorInfo, bool bDroppedCash) {}
  344.  
  345. /**
  346.  * Triggers when player picks up a weapon. Weapon is not added to player's inventory yet.
  347.  * Function is triggered on picking up own weapons too.
  348.  * @param SPI Player's info, who picked up a weapon
  349.  * @param WeaponPickup The weapon picked up by the player
  350.  */
  351. function PickedWeapon(ScrnPlayerInfo SPI, KFWeaponPickup WeaponPickup) {}
  352.  
  353. /**
  354.  * Triggers when player picks up an item from the ground, excluding cash and weapons,
  355.  * which have own trigger functions. Item is not added to player's inventory yet.
  356.  * Function is triggered on picking up own items too.
  357.  * @param SPI Player's info, who picked up an item
  358.  * @param Item The item picked up by the player.
  359.  */
  360. function PickedItem(ScrnPlayerInfo SPI, Pickup Item) {}
  361.    
  362. defaultproperties
  363. {
  364. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement