A unique perk called "Chaotic Revenge" that triggers when the player is hit. It validates the hit and source, then applies one random negative effect to the enemy (ignite, freeze, poison, fear, stun, shock, or teleport). It also updates perk visual highlights.
using Sandbox;
[Perk( Rarity.Unique, locked: true, alwaysOfferDebug: false, IncludedCategories = new[] { PerkCategory.Fire, PerkCategory.Poison, PerkCategory.Freeze, PerkCategory.Fear } )]
public class PerkHurtEnemyRandomEffect : Perk
{
static PerkHurtEnemyRandomEffect()
{
Register<PerkHurtEnemyRandomEffect>(
name: "Chaotic Revenge",
imagePath: "textures/icons/vector/hurt_enemy_random_effect.png",
description: level => "Enemies that hit you get ignited\nor frozen or poisoned\nor scared or shocked\nor stunned or teleported",
descriptionLineHeight: 9.5f,
descriptionFontSize: 12.8f,
descriptionImageSize: 14.8f
);
}
public override void Start()
{
base.Start();
HighlightColor = new Color( 1f, 0.4f, 1f );
HighlightDuration = 0.3f;
HighlightOpacity = 2f;
}
public override void Refresh()
{
base.Refresh();
}
public override void OnHit( float amount, DamageType damageType, bool isSelfInflicted, Vector2 dir, float force, Enemy enemySource, EnemyType enemyType, float previousHealth )
{
base.OnHit( amount, damageType, isSelfInflicted, dir, force, enemySource, enemyType, previousHealth );
if ( damageType == DamageType.Self )
return;
if ( !enemySource.IsValid() )
return;
if ( !(amount > 0f) )
return;
ApplyRandomEffect( enemySource, enemyType );
Highlight();
IconScale = 1.3f;
}
void ApplyRandomEffect( Enemy enemy, EnemyType enemyType )
{
int effect = Game.Random.Int( 0, 6 );
switch ( effect )
{
case 0:
enemy.Ignite( Player, null, enemyType, Player.Stats[PlayerStat.FireDamage], Player.Stats[PlayerStat.FireLifetime], Player.Stats[PlayerStat.FireSpreadChance], Player.Stats[PlayerStat.FireDmgStack] > 0f );
break;
case 1:
enemy.Freeze( Player, null, Player.Stats[PlayerStat.FreezeTimeScale], Player.Stats[PlayerStat.FreezeLifetime] );
break;
case 2:
enemy.Poison( Player, null, enemyType, Player.Stats[PlayerStat.PoisonDamage], Player.Stats[PlayerStat.PoisonFinishDamagePercent], Player.Stats[PlayerStat.PoisonDieSpreadChance], Player.Stats[PlayerStat.RadiusMultiplier], Player.Stats[PlayerStat.PoisonFlammable] > 0f, Player.Stats[PlayerStat.PoisonTickTimeModifier], (int)Player.Stats[PlayerStat.PoisonNumHitsToRemove] );
break;
case 3:
enemy.Fear( Player, null, Player.Stats[PlayerStat.FearLifetime] );
break;
case 4:
enemy.Stun( Player, null, lifetime: Game.Random.Float( 0.5f, 1f ) );
break;
case 5:
enemy.Shock( Player, null, damage: 10f, currSpreadCount: 0, spreadLimit: 5 );
break;
case 6:
Vector2 targetPos = new Vector2(
Game.Random.Float( Manager.Instance.BOUNDS_MIN.x, Manager.Instance.BOUNDS_MAX.x ),
Game.Random.Float( Manager.Instance.BOUNDS_MIN.y, Manager.Instance.BOUNDS_MAX.y )
);
enemy.Teleport( targetPos );
break;
}
}
}