UNPKG

mh3-data

Version:

Monster Hunter Tri data for monsters, quests, and weapons

85 lines 3.76 kB
import { Weapons } from '../../model'; import { WeaponClass } from '../../model/weapons'; import { isCutHit } from '../../model/weapons/weapon-util'; import { applyDefenseMultiplier, calculateElementalDamage, getRawMultiplier, getSharpnessRawMultiplier, getWeaponClassMultiplier, validateWeaponSharpness } from './damage-util'; const LANCE_VAR_MULTIPLIER = 0.78; const LANCE_CHARGE_ELEMENTAL_MULTIPLIER = 0.25; /** * @returns Attack properties for a {@link LanceTypes.LanceAttack} */ function getLanceAttack(attackName) { const lanceAttacks = Weapons.getWeaponDamageProperties(WeaponClass.LANCE) .attackModes[0]; const result = lanceAttacks.attacks.find(atk => atk.name === attackName); if (!result) { throw new Error(`'${attackName}' is not a valid Lance attack`); } return result; } /** * If the impact hitzone * .72 is greater than the cut hitzone then * that modified impact value will be used instead. Otherwise take cut. */ function getLanceHitzoneMultiplier(hit, hitzoneValues) { if (isCutHit(hit)) { const varImpact = hitzoneValues.impact * LANCE_VAR_MULTIPLIER; return varImpact > hitzoneValues.cut ? varImpact : hitzoneValues.cut; } // Shield bash should always be impact return hitzoneValues.impact; } function validateLance(weapon) { if (weapon.type !== WeaponClass.LANCE) { throw new Error(`'${weapon.name}' is not a '${WeaponClass.LANCE}'`); } } /** * Calculates damage for a {@link LanceTypes.Lance}. */ export function calculateLanceDamage(weaponArgs, monsterMultipliers, damageBuffArgs) { const { weaponId, attackName, sharpness } = weaponArgs; const { hitzoneValues, statMultipliers: levelMultipliers } = monsterMultipliers; const { rawArgs, elementArgs, weaponClassArgs } = damageBuffArgs; const lance = Weapons.getWeapon(Weapons.WeaponClass.LANCE, weaponId); validateLance(lance); validateWeaponSharpness(lance, sharpness); const { classModifier } = Weapons.getWeaponDamageProperties(WeaponClass.LANCE); const attack = getLanceAttack(attackName); const sharpnessMultiplier = getSharpnessRawMultiplier(sharpness); const rawMultiplier = getRawMultiplier(rawArgs); const attackBuffMultiplier = getWeaponClassMultiplier(weaponClassArgs); const attackWithBuffs = lance.attack + attackBuffMultiplier * classModifier; return attack.hits.map(hit => { const hitzoneMultiplier = getLanceHitzoneMultiplier(hit, hitzoneValues); const rawDamage = (attackWithBuffs * hit.power * rawMultiplier * sharpnessMultiplier * hitzoneMultiplier * 1) / // Lance does not have a [SpecialVar], but this is here for consistency classModifier; const baseElementalDamage = calculateElementalDamage({ weapon: lance, sharpness, hitzoneValues, elementArgs }); // Lance charge elemental damage is cut by 75% const elementalDamage = attack.name === 'Charge' ? baseElementalDamage * LANCE_CHARGE_ELEMENTAL_MULTIPLIER : baseElementalDamage; // Decimal is dropped const totalDamage = applyDefenseMultiplier(rawDamage + elementalDamage, levelMultipliers.defense); // KO is always rounded down const koDamage = !isCutHit(hit) ? Math.floor(hit.ko * sharpnessMultiplier) : undefined; return { rawDamage: applyDefenseMultiplier(rawDamage, levelMultipliers.defense), elementalDamage: applyDefenseMultiplier(elementalDamage, levelMultipliers.defense), totalDamage, koDamage }; }); } //# sourceMappingURL=lance-damage.js.map