EliteMobDamagedByPlayerEvent

Event fired when an elite mob takes damage from a player.

This class contains the complete player → elite damage formula, which is the offensive mirror of PlayerDamagedByEliteMobEvent (the elite → player defensive formula). Together, these two events define all combat math in EliteMobs.

Design Goals

  1. No vanilla damage dependency — vanilla Minecraft weapon damage is completely replaced by the formula. The old system added vanilla damage (~7 for diamond sword) on top of exponential elite damage, which broke scaling at low levels (88% vanilla at level 5 vs 32% at level 25). Now all damage comes from the formula.
  2. Level-consistent hit counts — a standard mob (healthMultiplier=1.0) takes exactly 3 sword hits to kill at ALL levels when skill and weapon match mob level.
  3. healthMultiplier scales linearly — a mob with healthMultiplier=2.0 takes exactly 6 sword hits; healthMultiplier=10.0 takes 30 hits. This holds at all levels.
  4. Symmetric with defensive formula — weapon adjustment curve mirrors ArmorDefenseCalculator's gear reduction; offensive skill scaling mirrors defensive skill scaling.
  5. Weapon pacing by feel — melee attack-speed scaling preserves weapon identity without fully equalizing theoretical DPS, because dungeon combat rewards burst windows more than stationary target math predicts.

Full Damage Formula

formulaDamage = baseDamage × attackSpeedFactor × skillAdjustment
              × weaponAdjustment × cooldownOrVelocity × sweepMultiplier
              × potionMultiplier
              × equipmentEnchantmentMultiplier
              × enchantmentMultiplier

finalDamage = max(formulaDamage, 1) × damageModifier × combatMultiplier × critMultiplier

Formula Components

baseDamagenormalizedMobHP / 3.0scales with levelcalculateBaseDamageToElite
attackSpeedFactortuned pacing factor from weapon family and speedmelee only; 1.0 for rangedgetAttackSpeedFactor
skillAdjustment2^((skillLv - mobLv) / 7.5)(0, ∞) centered at 1.0calculateOffensiveSkillAdjustment
weaponAdjustmenttwo-part linear curve[0.5, 1.25]getWeaponAdjustment
cooldownOrVelocitytracked melee charge or arrowVelocity/3.0[0, 1]PlayerAttackCooldownTracker / normalizeArrowVelocity
sweepMultiplier0.25 for sweep targets, 1.0 primary{0.25, 1.0}getSweepMultiplier
equipmentEnchantmentMultiplier1.0 + Sharpness / Power levels × 0.025 from equipped itemsmultiplicativegetEliteEnchantmentDamage
enchantmentMultiplier1.0 + eliteEnchantLvl × 0.025[1.0, ~1.2]Smite / Bane of Arthropods (elite-only levels)
damageModifierboss-specific damage reduction[0, 1]CustomBossEntity config
combatMultiplierglobal config multiplierconfigurableMobCombatSettingsConfig
critMultiplier1.5× on crit{1.0, 1.5}ElitePlayerInventory crit chance

Event Flow (onEliteMobAttacked)

  EntityDamageByEntityEvent
    → Nullify vanilla damage modifiers (armor etc.)
    → Branch by cause:
      ├─ !validPlayer        → raw vanilla damage (NPC plugins)
      ├─ bypass              → raw event damage (custom powers)
      ├─ THORNS              → calculateThornsDamage()
      ├─ ENTITY_ATTACK  ─┐
      ├─ SWEEP_ATTACK    ├──→ playerToEliteDamageFormula()
      ├─ PROJECTILE      ─┘
      └─ other               → raw vanilla damage
    → Apply damageModifier × combatMultiplier
    → Apply critical hit (1.5×)
    → Fire EliteMobDamagedByPlayerEvent (listeners can modify)
    → Apply skill bonuses (applySkillBonuses)
    → Set final damage on event

Worked Examples

Example 1: Matched melee combat (Lv25 sword vs Lv25 elite)

Player: weaponSkillLevel=25, weapon=elite sword (itemLevel=25)
Mob:    level=25, healthMultiplier=1.0, HP=70.0

baseDamage       = 70.0 / 3 = 23.33
attackSpeedFactor = 1.6 / 1.6 = 1.0  (sword)
skillAdjustment  = 2^((25-25)/7.5) = 1.0
weaponAdjustment = 0.5 + 0.5 = 1.0   (matching)
cooldown         = 1.0                (full charge)
sweepMultiplier  = 1.0                (primary target)

formulaDamage = 23.33 × 1.0 × 1.0 × 1.0 × 1.0 × 1.0 = 23.33
Hits to kill  = 70.0 / 23.33 = 3.0 ✓

Example 2: Tuned axe pacing (Lv25 axe vs Lv25 elite)

baseDamage       = 23.33
attackSpeedFactor ≈ 1.26  (axe is slower, but no longer receives full inverse-speed burst)
formulaDamage    = 23.33 × 1.26 = 29.5 per hit
Hits to kill     = 70.0 / 29.5 = 2.37

Example 3: Under-leveled ranged (Lv20 bow vs Lv25 elite, healthMultiplier=2.0)

baseDamage       = 23.33  (from normalized HP, NOT actual HP)
attackSpeedFactor = 1.0   (ranged, skipped)
skillAdjustment  = 2^((20-25)/7.5) = 0.63
weaponAdjustment = 0.5 + 0.5*(20/25) = 0.9
arrowVelocity    = 1.0   (full draw)

formulaDamage = 23.33 × 0.63 × 0.9 × 1.0 = 13.23
Actual mob HP = 70.0 × 2.0 = 140.0
Hits to kill  = 140.0 / 13.23 = 10.6 hits

Example 4: Level consistency check

Level 5:   mobHP = 2.1875 * 2^1 = 4.375,   baseDmg = 4.375/3 = 1.46  → 3 hits ✓
Level 25:  mobHP = 2.1875 * 2^5 = 70.0,     baseDmg = 70.0/3 = 23.33  → 3 hits ✓
Level 50:  mobHP = 2.1875 * 2^10 = 2240.0,  baseDmg = 2240/3 = 746.7  → 3 hits ✓
Level 100: mobHP = 2.1875 * 2^20 = 2.29M,   baseDmg = 764K            → 3 hits ✓

Comparison to Defensive Formula

Base damageplayerMaxHP / 5normalizedMobHP / 3
Skill scaling2^((mobLv - armorLv) / 7.5)2^((weaponLv - mobLv) / 7.5)
Gear/weapon curveArmorDefenseCalculatorWeaponOffenseCalculator
Matched gear adj1.0 (50% reduction)1.0 (50% bonus)
No gear adj2.0 (double damage taken)0.5 (half damage dealt)
Target at matched~5 hits to kill player~3 hits to kill mob
1-shot protectionYes (cap at maxHP-1)No (floor at 1 damage)

Special Cases

  • Thorns: Formula-based (baseDamage × thornsLevel × 0.02), not flat damage.
  • Sweep: Secondary targets take 25% of primary damage.
  • NPC plugins: Non-valid players use raw vanilla event damage (bypass formula).
  • Custom/bypass damage: Boss powers that set bypass=true use raw event damage.
  • Skill bonuses: Applied as multiplicative modifiers AFTER the formula via applySkillBonuses.

See also

The defensive (elite → player) mirror of this event

Weapon adjustment curve and sweep/thorns constants

The defensive gear curve that this weapon curve mirrors

Skill adjustment calculation

Constructors

Link copied to clipboard
public void EliteMobDamagedByPlayerEvent(EliteEntity eliteEntity, Player player, EntityDamageByEntityEvent event, double damage, boolean criticalStrike, boolean isCustomDamage, double damageModifier)
Event fired when an elite is damaged by a player.
public void EliteMobDamagedByPlayerEvent(EliteEntity eliteEntity, Player player, double damage, boolean isRangedAttack)
Constructor for testing purposes that allows explicit ranged attack flag.
public void EliteMobDamagedByPlayerEvent(EliteEntity eliteEntity, Player player, double damage, boolean isRangedAttack, boolean criticalStrike)
Constructor for testing purposes with explicit ranged attack and critical strike flags.

Properties

Link copied to clipboard
public final double damageModifier
Link copied to clipboard
Link copied to clipboard
public final Entity entity
Link copied to clipboard
public final EntityDamageByEntityEvent entityDamageByEntityEvent
Link copied to clipboard
public final static HandlerList handlers
Link copied to clipboard
public final boolean isCustomDamage
Link copied to clipboard
public final Player player
Link copied to clipboard
public boolean rangedAttack
Link copied to clipboard
public int rangedSkillLevel
The weapon skill level from launch time (for ranged attacks).
Link copied to clipboard
The weapon skill type from launch time (for ranged attacks).

Inherited properties

Link copied to clipboard
public double damage
Link copied to clipboard
public final static HandlerList handlers
Link copied to clipboard
public boolean isCancelled

Functions

Link copied to clipboard
public void applyClassAbilityDamageMultiplier(String abilityId, double multiplier)
Applies a live class ability's damage multiplier and records its real contribution.
Link copied to clipboard
public void applySkillBonuses()
Unified method to apply all active skill bonuses to this damage event.
Link copied to clipboard
Damage present in the final hit only because one or more active class abilities modified it.
Link copied to clipboard
public Set<String> getClassAbilityDamageSources()
Link copied to clipboard
public double getDamageModifier()
Link copied to clipboard
Link copied to clipboard
Link copied to clipboard
public Entity getEntity()
Link copied to clipboard
public EntityDamageByEntityEvent getEntityDamageByEntityEvent()
Link copied to clipboard
public static HandlerList getHandlerList()
Link copied to clipboard
public HandlerList getHandlers()
Link copied to clipboard
public Player getPlayer()
Link copied to clipboard
public int getRangedSkillLevel()
The weapon skill level from launch time (for ranged attacks).
Link copied to clipboard
The weapon skill type from launch time (for ranged attacks).
Link copied to clipboard
public boolean isCriticalStrike()
Link copied to clipboard
Link copied to clipboard
public boolean isCustomDamage()
Link copied to clipboard
public boolean isRangedAttack()
Link copied to clipboard
public void setDamage(double damage)
Link copied to clipboard
public void setRangedSkillLevel(int rangedSkillLevel)
The weapon skill level from launch time (for ranged attacks).
Link copied to clipboard
public void setRangedSkillType(SkillType rangedSkillType)
The weapon skill type from launch time (for ranged attacks).

Inherited functions

Link copied to clipboard
public double getDamage()
Link copied to clipboard
public String getEventName()
Link copied to clipboard
public abstract HandlerList getHandlers()
Link copied to clipboard
public final boolean isAsynchronous()
Link copied to clipboard
public boolean isCancelled()
Link copied to clipboard
public void setCancelled(boolean b)