diff --git a/src/app/components/Defence.jsx b/src/app/components/Defence.jsx index 7d6f5e78..545e6eac 100644 --- a/src/app/components/Defence.jsx +++ b/src/app/components/Defence.jsx @@ -61,50 +61,90 @@ export default class Defence extends TranslatedComponent { const shieldSourcesData = []; const effectiveShieldData = []; const shieldDamageTakenData = []; - const shieldTooltipDetails = []; - const shieldAbsoluteTooltipDetails = []; - const shieldExplosiveTooltipDetails = []; - const shieldKineticTooltipDetails = []; - const shieldThermalTooltipDetails = []; + const shieldSourcesTt = []; + const shieldDamageTakenAbsoluteTt = []; + const shieldDamageTakenExplosiveTt = []; + const shieldDamageTakenKineticTt = []; + const shieldDamageTakenThermalTt = []; + const effectiveShieldAbsoluteTt = []; + const effectiveShieldExplosiveTt = []; + const effectiveShieldKineticTt = []; + const effectiveShieldThermalTt = []; let maxEffectiveShield = 0; if (shield.total) { shieldSourcesData.push({ value: Math.round(shield.generator), label: translate('generator') }); shieldSourcesData.push({ value: Math.round(shield.boosters), label: translate('boosters') }); shieldSourcesData.push({ value: Math.round(shield.cells), label: translate('cells') }); - if (shield.generator > 0) shieldTooltipDetails.push(
{translate('generator') + ' ' + formats.int(shield.generator)}{units.MJ}
); - if (shield.boosters > 0) shieldTooltipDetails.push(
{translate('boosters') + ' ' + formats.int(shield.boosters)}{units.MJ}
); - if (shield.cells > 0) shieldTooltipDetails.push(
{translate('cells') + ' ' + formats.int(shield.cells)}{units.MJ}
); + if (shield.generator > 0) { + shieldSourcesTt.push(
{translate('generator') + ' ' + formats.int(shield.generator)}{units.MJ}
); + effectiveShieldAbsoluteTt.push(
{translate('generator') + ' ' + formats.int(shield.generator)}{units.MJ}
); + effectiveShieldExplosiveTt.push(
{translate('generator') + ' ' + formats.int(shield.generator)}{units.MJ}
); + effectiveShieldKineticTt.push(
{translate('generator') + ' ' + formats.int(shield.generator)}{units.MJ}
); + effectiveShieldThermalTt.push(
{translate('generator') + ' ' + formats.int(shield.generator)}{units.MJ}
); + if (shield.boosters > 0) { + shieldSourcesTt.push(
{translate('boosters') + ' ' + formats.int(shield.boosters)}{units.MJ}
); + effectiveShieldAbsoluteTt.push(
{translate('boosters') + ' ' + formats.int(shield.boosters)}{units.MJ}
); + effectiveShieldExplosiveTt.push(
{translate('boosters') + ' ' + formats.int(shield.boosters)}{units.MJ}
); + effectiveShieldKineticTt.push(
{translate('boosters') + ' ' + formats.int(shield.boosters)}{units.MJ}
); + effectiveShieldThermalTt.push(
{translate('boosters') + ' ' + formats.int(shield.boosters)}{units.MJ}
); + } - shieldAbsoluteTooltipDetails.push(
{translate('generator') + ' ' + formats.pct1(shield.absolute.generator)}
); - shieldAbsoluteTooltipDetails.push(
{translate('boosters') + ' ' + formats.pct1(shield.absolute.boosters)}
); - shieldAbsoluteTooltipDetails.push(
{translate('power distributor') + ' ' + formats.pct1(shield.absolute.sys)}
); + if (shield.cells > 0) { + shieldSourcesTt.push(
{translate('cells') + ' ' + formats.int(shield.cells)}{units.MJ}
); + effectiveShieldAbsoluteTt.push(
{translate('cells') + ' ' + formats.int(shield.cells)}{units.MJ}
); + effectiveShieldExplosiveTt.push(
{translate('cells') + ' ' + formats.int(shield.cells)}{units.MJ}
); + effectiveShieldKineticTt.push(
{translate('cells') + ' ' + formats.int(shield.cells)}{units.MJ}
); + effectiveShieldThermalTt.push(
{translate('cells') + ' ' + formats.int(shield.cells)}{units.MJ}
); + } - shieldExplosiveTooltipDetails.push(
{translate('generator') + ' ' + formats.pct1(shield.explosive.generator)}
); - shieldExplosiveTooltipDetails.push(
{translate('boosters') + ' ' + formats.pct1(shield.explosive.boosters)}
); - shieldExplosiveTooltipDetails.push(
{translate('power distributor') + ' ' + formats.pct1(shield.explosive.sys)}
); + // Add effective shield from resistances + const rawMj = shield.generator + shield.boosters + shield.cells; + const explosiveMj = rawMj / (shield.explosive.generator * shield.explosive.boosters) - rawMj; + if (explosiveMj != 0) effectiveShieldExplosiveTt.push(
{translate('resistance') + ' ' + formats.int(explosiveMj)}{units.MJ}
); + const kineticMj = rawMj / (shield.kinetic.generator * shield.kinetic.boosters) - rawMj; + if (kineticMj != 0) effectiveShieldKineticTt.push(
{translate('resistance') + ' ' + formats.int(kineticMj)}{units.MJ}
); + const thermalMj = rawMj / (shield.thermal.generator * shield.thermal.boosters) - rawMj; + if (thermalMj != 0) effectiveShieldThermalTt.push(
{translate('resistance') + ' ' + formats.int(thermalMj)}{units.MJ}
); - shieldKineticTooltipDetails.push(
{translate('generator') + ' ' + formats.pct1(shield.kinetic.generator)}
); - shieldKineticTooltipDetails.push(
{translate('boosters') + ' ' + formats.pct1(shield.kinetic.boosters)}
); - shieldKineticTooltipDetails.push(
{translate('power distributor') + ' ' + formats.pct1(shield.kinetic.sys)}
); + // Add effective shield from power distributor SYS pips + if (shield.absolute.sys != 1) { + effectiveShieldAbsoluteTt.push(
{translate('power distributor') + ' ' + formats.int(rawMj / shield.absolute.sys - rawMj)}{units.MJ}
); + effectiveShieldExplosiveTt.push(
{translate('power distributor') + ' ' + formats.int(rawMj / shield.explosive.sys - rawMj)}{units.MJ}
); + effectiveShieldKineticTt.push(
{translate('power distributor') + ' ' + formats.int(rawMj / shield.kinetic.sys - rawMj)}{units.MJ}
); + effectiveShieldThermalTt.push(
{translate('power distributor') + ' ' + formats.int(rawMj / shield.thermal.sys - rawMj)}{units.MJ}
); + } + } - shieldThermalTooltipDetails.push(
{translate('generator') + ' ' + formats.pct1(shield.thermal.generator)}
); - shieldThermalTooltipDetails.push(
{translate('boosters') + ' ' + formats.pct1(shield.thermal.boosters)}
); - shieldThermalTooltipDetails.push(
{translate('power distributor') + ' ' + formats.pct1(shield.thermal.sys)}
); + shieldDamageTakenAbsoluteTt.push(
{translate('generator') + ' ' + formats.pct1(shield.absolute.generator)}
); + shieldDamageTakenAbsoluteTt.push(
{translate('boosters') + ' ' + formats.pct1(shield.absolute.boosters)}
); + shieldDamageTakenAbsoluteTt.push(
{translate('power distributor') + ' ' + formats.pct1(shield.absolute.sys)}
); + + shieldDamageTakenExplosiveTt.push(
{translate('generator') + ' ' + formats.pct1(shield.explosive.generator)}
); + shieldDamageTakenExplosiveTt.push(
{translate('boosters') + ' ' + formats.pct1(shield.explosive.boosters)}
); + shieldDamageTakenExplosiveTt.push(
{translate('power distributor') + ' ' + formats.pct1(shield.explosive.sys)}
); + + shieldDamageTakenKineticTt.push(
{translate('generator') + ' ' + formats.pct1(shield.kinetic.generator)}
); + shieldDamageTakenKineticTt.push(
{translate('boosters') + ' ' + formats.pct1(shield.kinetic.boosters)}
); + shieldDamageTakenKineticTt.push(
{translate('power distributor') + ' ' + formats.pct1(shield.kinetic.sys)}
); + + shieldDamageTakenThermalTt.push(
{translate('generator') + ' ' + formats.pct1(shield.thermal.generator)}
); + shieldDamageTakenThermalTt.push(
{translate('boosters') + ' ' + formats.pct1(shield.thermal.boosters)}
); + shieldDamageTakenThermalTt.push(
{translate('power distributor') + ' ' + formats.pct1(shield.thermal.sys)}
); const effectiveAbsoluteShield = shield.total / shield.absolute.total; - effectiveShieldData.push({ value: Math.round(effectiveAbsoluteShield), label: translate('absolute') }); + effectiveShieldData.push({ value: Math.round(effectiveAbsoluteShield), label: translate('absolute'), tooltip: effectiveShieldAbsoluteTt }); const effectiveExplosiveShield = shield.total / shield.explosive.total; - effectiveShieldData.push({ value: Math.round(effectiveExplosiveShield), label: translate('explosive') }); + effectiveShieldData.push({ value: Math.round(effectiveExplosiveShield), label: translate('explosive'), tooltip: effectiveShieldExplosiveTt }); const effectiveKineticShield = shield.total / shield.kinetic.total; - effectiveShieldData.push({ value: Math.round(effectiveKineticShield), label: translate('kinetic') }); + effectiveShieldData.push({ value: Math.round(effectiveKineticShield), label: translate('kinetic'), tooltip: effectiveShieldKineticTt }); const effectiveThermalShield = shield.total / shield.thermal.total; - effectiveShieldData.push({ value: Math.round(effectiveThermalShield), label: translate('thermal') }); + effectiveShieldData.push({ value: Math.round(effectiveThermalShield), label: translate('thermal'), tooltip: effectiveShieldThermalTt }); - shieldDamageTakenData.push({ value: Math.round(shield.absolute.total * 100), label: translate('absolute'), tooltip: shieldAbsoluteTooltipDetails }); - shieldDamageTakenData.push({ value: Math.round(shield.explosive.total * 100), label: translate('explosive'), tooltip: shieldExplosiveTooltipDetails }); - shieldDamageTakenData.push({ value: Math.round(shield.kinetic.total * 100), label: translate('kinetic'), tooltip: shieldKineticTooltipDetails }); - shieldDamageTakenData.push({ value: Math.round(shield.thermal.total * 100), label: translate('thermal'), tooltip: shieldThermalTooltipDetails }); + shieldDamageTakenData.push({ value: Math.round(shield.absolute.total * 100), label: translate('absolute'), tooltip: shieldDamageTakenAbsoluteTt }); + shieldDamageTakenData.push({ value: Math.round(shield.explosive.total * 100), label: translate('explosive'), tooltip: shieldDamageTakenExplosiveTt }); + shieldDamageTakenData.push({ value: Math.round(shield.kinetic.total * 100), label: translate('kinetic'), tooltip: shieldDamageTakenKineticTt }); + shieldDamageTakenData.push({ value: Math.round(shield.thermal.total * 100), label: translate('thermal'), tooltip: shieldDamageTakenThermalTt }); maxEffectiveShield = Math.max(shield.total / shield.absolute.max, shield.total / shield.explosive.max, shield.total / shield.kinetic.max, shield.total / shield.thermal.max); } @@ -113,41 +153,62 @@ export default class Defence extends TranslatedComponent { armourSourcesData.push({ value: Math.round(armour.bulkheads), label: translate('bulkheads') }); armourSourcesData.push({ value: Math.round(armour.reinforcement), label: translate('reinforcement') }); - const armourTooltipDetails = []; - if (armour.bulkheads > 0) armourTooltipDetails.push(
{translate('bulkheads') + ' ' + formats.int(armour.bulkheads)}
); - if (armour.reinforcement > 0) armourTooltipDetails.push(
{translate('reinforcement') + ' ' + formats.int(armour.reinforcement)}
); + const armourSourcesTt = []; + const effectiveArmourAbsoluteTt = []; + const effectiveArmourExplosiveTt = []; + const effectiveArmourKineticTt = []; + const effectiveArmourThermalTt = []; + if (armour.bulkheads > 0) { + armourSourcesTt.push(
{translate('bulkheads') + ' ' + formats.int(armour.bulkheads)}
); + effectiveArmourAbsoluteTt.push(
{translate('bulkheads') + ' ' + formats.int(armour.bulkheads)}
); + effectiveArmourExplosiveTt.push(
{translate('bulkheads') + ' ' + formats.int(armour.bulkheads)}
); + effectiveArmourKineticTt.push(
{translate('bulkheads') + ' ' + formats.int(armour.bulkheads)}
); + effectiveArmourThermalTt.push(
{translate('bulkheads') + ' ' + formats.int(armour.bulkheads)}
); + if (armour.reinforcement > 0) { + armourSourcesTt.push(
{translate('reinforcement') + ' ' + formats.int(armour.reinforcement)}
); + effectiveArmourAbsoluteTt.push(
{translate('reinforcement') + ' ' + formats.int(armour.reinforcement)}
); + effectiveArmourExplosiveTt.push(
{translate('reinforcement') + ' ' + formats.int(armour.reinforcement)}
); + effectiveArmourKineticTt.push(
{translate('reinforcement') + ' ' + formats.int(armour.reinforcement)}
); + effectiveArmourThermalTt.push(
{translate('reinforcement') + ' ' + formats.int(armour.reinforcement)}
); + } + } - const armourAbsoluteTooltipDetails = []; - armourAbsoluteTooltipDetails.push(
{translate('bulkheads') + ' ' + formats.pct1(armour.absolute.bulkheads)}
); - armourAbsoluteTooltipDetails.push(
{translate('reinforcement') + ' ' + formats.pct1(armour.absolute.reinforcement)}
); + const rawArmour = armour.bulkheads + armour.reinforcement; - const armourExplosiveTooltipDetails = []; - armourExplosiveTooltipDetails.push(
{translate('bulkheads') + ' ' + formats.pct1(armour.explosive.bulkheads)}
); - armourExplosiveTooltipDetails.push(
{translate('reinforcement') + ' ' + formats.pct1(armour.explosive.reinforcement)}
); + const armourDamageTakenTt = []; + armourDamageTakenTt.push(
{translate('bulkheads') + ' ' + formats.pct1(armour.absolute.bulkheads)}
); + armourDamageTakenTt.push(
{translate('reinforcement') + ' ' + formats.pct1(armour.absolute.reinforcement)}
); - const armourKineticTooltipDetails = []; - armourKineticTooltipDetails.push(
{translate('bulkheads') + ' ' + formats.pct1(armour.kinetic.bulkheads)}
); - armourKineticTooltipDetails.push(
{translate('reinforcement') + ' ' + formats.pct1(armour.kinetic.reinforcement)}
); + const armourDamageTakenExplosiveTt = []; + armourDamageTakenExplosiveTt.push(
{translate('bulkheads') + ' ' + formats.pct1(armour.explosive.bulkheads)}
); + armourDamageTakenExplosiveTt.push(
{translate('reinforcement') + ' ' + formats.pct1(armour.explosive.reinforcement)}
); + if (armour.explosive.bulkheads * armour.explosive.reinforcement != 1) effectiveArmourExplosiveTt.push(
{translate('resistance') + ' ' + formats.int(rawArmour / (armour.explosive.bulkheads * armour.explosive.reinforcement) - rawArmour)}
); - const armourThermalTooltipDetails = []; - armourThermalTooltipDetails.push(
{translate('bulkheads') + ' ' + formats.pct1(armour.thermal.bulkheads)}
); - armourThermalTooltipDetails.push(
{translate('reinforcement') + ' ' + formats.pct1(armour.thermal.reinforcement)}
); + const armourDamageTakenKineticTt = []; + armourDamageTakenKineticTt.push(
{translate('bulkheads') + ' ' + formats.pct1(armour.kinetic.bulkheads)}
); + armourDamageTakenKineticTt.push(
{translate('reinforcement') + ' ' + formats.pct1(armour.kinetic.reinforcement)}
); + if (armour.kinetic.bulkheads * armour.kinetic.reinforcement != 1) effectiveArmourKineticTt.push(
{translate('resistance') + ' ' + formats.int(rawArmour / (armour.kinetic.bulkheads * armour.kinetic.reinforcement) - rawArmour)}
); + + const armourDamageTakenThermalTt = []; + armourDamageTakenThermalTt.push(
{translate('bulkheads') + ' ' + formats.pct1(armour.thermal.bulkheads)}
); + armourDamageTakenThermalTt.push(
{translate('reinforcement') + ' ' + formats.pct1(armour.thermal.reinforcement)}
); + if (armour.thermal.bulkheads * armour.thermal.reinforcement != 1) effectiveArmourThermalTt.push(
{translate('resistance') + ' ' + formats.int(rawArmour / (armour.thermal.bulkheads * armour.thermal.reinforcement) - rawArmour)}
); const effectiveArmourData = []; const effectiveAbsoluteArmour = armour.total / armour.absolute.total; - effectiveArmourData.push({ value: Math.round(effectiveAbsoluteArmour), label: translate('absolute') }); + effectiveArmourData.push({ value: Math.round(effectiveAbsoluteArmour), label: translate('absolute'), tooltip: effectiveArmourAbsoluteTt }); const effectiveExplosiveArmour = armour.total / armour.explosive.total; - effectiveArmourData.push({ value: Math.round(effectiveExplosiveArmour), label: translate('explosive') }); + effectiveArmourData.push({ value: Math.round(effectiveExplosiveArmour), label: translate('explosive'), tooltip: effectiveArmourExplosiveTt }); const effectiveKineticArmour = armour.total / armour.kinetic.total; - effectiveArmourData.push({ value: Math.round(effectiveKineticArmour), label: translate('kinetic') }); + effectiveArmourData.push({ value: Math.round(effectiveKineticArmour), label: translate('kinetic'), tooltip: effectiveArmourKineticTt }); const effectiveThermalArmour = armour.total / armour.thermal.total; - effectiveArmourData.push({ value: Math.round(effectiveThermalArmour), label: translate('thermal') }); + effectiveArmourData.push({ value: Math.round(effectiveThermalArmour), label: translate('thermal'), tooltip: effectiveArmourThermalTt }); const armourDamageTakenData = []; - armourDamageTakenData.push({ value: Math.round(armour.absolute.total * 100), label: translate('absolute'), tooltip: armourAbsoluteTooltipDetails }); - armourDamageTakenData.push({ value: Math.round(armour.explosive.total * 100), label: translate('explosive'), tooltip: armourExplosiveTooltipDetails }); - armourDamageTakenData.push({ value: Math.round(armour.kinetic.total * 100), label: translate('kinetic'), tooltip: armourKineticTooltipDetails }); - armourDamageTakenData.push({ value: Math.round(armour.thermal.total * 100), label: translate('thermal'), tooltip: armourThermalTooltipDetails }); + armourDamageTakenData.push({ value: Math.round(armour.absolute.total * 100), label: translate('absolute'), tooltip: armourDamageTakenTt }); + armourDamageTakenData.push({ value: Math.round(armour.explosive.total * 100), label: translate('explosive'), tooltip: armourDamageTakenExplosiveTt }); + armourDamageTakenData.push({ value: Math.round(armour.kinetic.total * 100), label: translate('kinetic'), tooltip: armourDamageTakenKineticTt }); + armourDamageTakenData.push({ value: Math.round(armour.thermal.total * 100), label: translate('thermal'), tooltip: armourDamageTakenThermalTt }); return ( @@ -155,7 +216,7 @@ export default class Defence extends TranslatedComponent {

{translate('shield metrics')}


-

{shieldTooltipDetails}

)} onMouseOut={tooltip.bind(null, null)} className='summary'>{translate('raw shield strength')}
{formats.int(shield.total)}{units.MJ} +

{shieldSourcesTt})} onMouseOut={tooltip.bind(null, null)} className='summary'>{translate('raw shield strength')}
{formats.int(shield.total)}{units.MJ}

{translate('PHRASE_TIME_TO_LOSE_SHIELDS')}
{shielddamage.totalsdps == 0 ? translate('ever') : formats.time(Calc.timeToDeplete(shield.total, shielddamage.totalsdps, shielddamage.totalseps, pd.getWeaponsCapacity(), pd.getWeaponsRechargeRate() * opponentWep / 4))}

{translate('PHRASE_TIME_TO_RECOVER_SHIELDS')}
{shield.recover === Math.Inf ? translate('never') : formats.time(shield.recover)}

{translate('PHRASE_TIME_TO_RECHARGE_SHIELDS')}
{shield.recharge === Math.Inf ? translate('never') : formats.time(shield.recharge)}

@@ -176,7 +237,7 @@ export default class Defence extends TranslatedComponent {

{translate('armour metrics')}

-

{armourTooltipDetails}

)} onMouseOut={tooltip.bind(null, null)} className='summary'>{translate('raw armour strength')}
{formats.int(armour.total)} +

{armourSourcesTt})} onMouseOut={tooltip.bind(null, null)} className='summary'>{translate('raw armour strength')}
{formats.int(armour.total)}

{translate('PHRASE_TIME_TO_LOSE_ARMOUR')}
{armourdamage.totalsdps == 0 ? translate('ever') : formats.time(Calc.timeToDeplete(armour.total, armourdamage.totalsdps, armourdamage.totalseps, pd.getWeaponsCapacity(), pd.getWeaponsRechargeRate() * opponentWep / 4))}

{translate('raw module armour')}
{formats.int(armour.modulearmour)}

{translate('PHRASE_MODULE_PROTECTION_EXTERNAL')}
{formats.pct1(armour.moduleprotection / 2)}