diff --git a/src/app/components/EngagementRange.jsx b/src/app/components/EngagementRange.jsx
index ef851b01..724a197f 100644
--- a/src/app/components/EngagementRange.jsx
+++ b/src/app/components/EngagementRange.jsx
@@ -27,7 +27,7 @@ export default class Range extends TranslatedComponent {
this.state = {
maxRange,
- rangeLevel: 0.5,
+ rangeLevel: 1000 / maxRange,
};
}
diff --git a/src/app/components/Offence.jsx b/src/app/components/Offence.jsx
index 45a1841e..65327fe1 100644
--- a/src/app/components/Offence.jsx
+++ b/src/app/components/Offence.jsx
@@ -81,7 +81,7 @@ export default class Offence extends TranslatedComponent {
* @return {boolean} Returns true if the component should be rerendered
*/
componentWillReceiveProps(nextProps) {
- if (this.props.marker != nextProps.marker || this.props.sys != nextProps.sys) {
+ if (this.props.marker != nextProps.marker || this.props.eng != nextProps.eng) {
const damage = Calc.offenceMetrics(nextProps.ship, nextProps.opponent, nextProps.wep, nextProps.engagementrange);
this.setState({ damage });
}
@@ -101,27 +101,24 @@ export default class Offence extends TranslatedComponent {
desc = true;
}
- this._sort(this.props.ship, predicate, desc);
+ this._sort(predicate, desc);
this.setState({ predicate, desc });
}
/**
* Sorts the weapon list
- * @param {Ship} ship Ship instance
* @param {string} predicate Sort predicate
* @param {Boolean} desc Sort order descending
*/
- _sort(ship, predicate, desc) {
+ _sort(predicate, desc) {
let comp = weaponComparator.bind(null, this.context.language.translate);
switch (predicate) {
case 'n': comp = comp(null, desc); break;
- case 'edpss': comp = comp((a, b) => a.effectiveDpsShields - b.effectiveDpsShields, desc); break;
- case 'esdpss': comp = comp((a, b) => a.effectiveSDpsShields - b.effectiveSDpsShields, desc); break;
- case 'es': comp = comp((a, b) => a.effectivenessShields - b.effectivenessShields, desc); break;
- case 'edpsh': comp = comp((a, b) => a.effectiveDpsHull - b.effectiveDpsHull, desc); break;
- case 'esdpsh': comp = comp((a, b) => a.effectiveSDpsHull - b.effectiveSDpsHull, desc); break;
- case 'eh': comp = comp((a, b) => a.effectivenessHull - b.effectivenessHull, desc); break;
+ case 'esdpss': comp = comp((a, b) => a.sdps.shields.total - b.sdps.shields.total, desc); break;
+ case 'es': comp = comp((a, b) => a.effectiveness.shields.total - b.effectiveness.shields.total, desc); break;
+ case 'esdpsh': comp = comp((a, b) => a.sdps.armour.total - b.sdps.armour.total, desc); break;
+ case 'eh': comp = comp((a, b) => a.effectiveness.armour.total - b.effectiveness.armour.total, desc); break;
}
this.state.damage.sort(comp);
@@ -141,104 +138,43 @@ export default class Offence extends TranslatedComponent {
const rows = [];
for (let i = 0; i < damage.length; i++) {
const weapon = damage[i];
- rows.push(
- |
- {weapon.mount == 'F' ? : null}
- {weapon.mount == 'G' ? : null}
- {weapon.mount == 'T' ? : null}
- {weapon.classRating} {translate(weapon.name)}
- {weapon.engineering ? ' (' + weapon.engineering + ')' : null }
- |
- {formats.f1(weapon.sdpsShields)} |
- {formats.pct1(weapon.effectivenessShields)} |
- {formats.f1(weapon.sdpsArmour)} |
- {formats.pct1(weapon.effectivenessArmour)} |
-
);
+
+ const effectivenessShieldsTooltipDetails = [];
+ effectivenessShieldsTooltipDetails.push({translate('range') + ' ' + formats.pct1(weapon.effectiveness.shields.range)}
);
+ effectivenessShieldsTooltipDetails.push({translate('resistance') + ' ' + formats.pct1(weapon.effectiveness.shields.resistance)}
);
+ effectivenessShieldsTooltipDetails.push({translate('sys') + ' ' + formats.pct1(weapon.effectiveness.shields.sys)}
);
+
+ const effectiveShieldsSDpsTooltipDetails = [];
+ if (weapon.sdps.shields.absolute) effectiveShieldsSDpsTooltipDetails.push({translate('absolute') + ' ' + formats.f1(weapon.sdps.shields.absolute)}
);
+ if (weapon.sdps.shields.explosive) effectiveShieldsSDpsTooltipDetails.push({translate('explosive') + ' ' + formats.f1(weapon.sdps.shields.explosive)}
);
+ if (weapon.sdps.shields.kinetic) effectiveShieldsSDpsTooltipDetails.push({translate('kinetic') + ' ' + formats.f1(weapon.sdps.shields.kinetic)}
);
+ if (weapon.sdps.shields.thermal) effectiveShieldsSDpsTooltipDetails.push({translate('thermal') + ' ' + formats.f1(weapon.sdps.shields.thermal)}
);
+
+ const effectivenessArmourTooltipDetails = [];
+ effectivenessArmourTooltipDetails.push({translate('range') + ' ' + formats.pct1(weapon.effectiveness.armour.range)}
);
+ effectivenessArmourTooltipDetails.push({translate('resistance') + ' ' + formats.pct1(weapon.effectiveness.armour.resistance)}
);
+ effectivenessArmourTooltipDetails.push({translate('hardness') + ' ' + formats.pct1(weapon.effectiveness.armour.hardness)}
);
+ const effectiveArmourSDpsTooltipDetails = [];
+ if (weapon.sdps.armour.absolute) effectiveArmourSDpsTooltipDetails.push({translate('absolute') + ' ' + formats.f1(weapon.sdps.armour.absolute)}
);
+ if (weapon.sdps.armour.explosive) effectiveArmourSDpsTooltipDetails.push({translate('explosive') + ' ' + formats.f1(weapon.sdps.armour.explosive)}
);
+ if (weapon.sdps.armour.kinetic) effectiveArmourSDpsTooltipDetails.push({translate('kinetic') + ' ' + formats.f1(weapon.sdps.armour.kinetic)}
);
+ if (weapon.sdps.armour.thermal) effectiveArmourSDpsTooltipDetails.push({translate('thermal') + ' ' + formats.f1(weapon.sdps.armour.thermal)}
);
+
+ rows.push(
+
+ |
+ {weapon.mount == 'F' ? : null}
+ {weapon.mount == 'G' ? : null}
+ {weapon.mount == 'T' ? : null}
+ {weapon.classRating} {translate(weapon.name)}
+ {weapon.engineering ? ' (' + weapon.engineering + ')' : null }
+ |
+ {formats.f1(weapon.sdps.shields.total)} |
+ {formats.pct1(weapon.effectiveness.shields.total)} |
+ {formats.f1(weapon.sdps.armour.total)} |
+ {formats.pct1(weapon.effectiveness.armour.total)} |
+
);
}
-// const shieldSourcesData = [];
-// const effectiveShieldData = [];
-// const shieldDamageTakenData = [];
-// const shieldTooltipDetails = [];
-// const shieldAbsoluteTooltipDetails = [];
-// const shieldExplosiveTooltipDetails = [];
-// const shieldKineticTooltipDetails = [];
-// const shieldThermalTooltipDetails = [];
-// 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') });
-
-// shieldTooltipDetails.push({translate('generator') + ' ' + formats.int(shield.generator)}{units.MJ}
);
-// shieldTooltipDetails.push({translate('boosters') + ' ' + formats.int(shield.boosters)}{units.MJ}
);
-// shieldTooltipDetails.push({translate('cells') + ' ' + formats.int(shield.cells)}{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)}
);
-
-// 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)}
);
-
-// 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)}
);
-
-// 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)}
);
-
-// const effectiveAbsoluteShield = shield.total / shield.absolute.total;
-// effectiveShieldData.push({ value: Math.round(effectiveAbsoluteShield), label: translate('absolute') });
-// const effectiveExplosiveShield = shield.total / shield.explosive.total;
-// effectiveShieldData.push({ value: Math.round(effectiveExplosiveShield), label: translate('explosive') });
-// const effectiveKineticShield = shield.total / shield.kinetic.total;
-// effectiveShieldData.push({ value: Math.round(effectiveKineticShield), label: translate('kinetic') });
-// const effectiveThermalShield = shield.total / shield.thermal.total;
-// effectiveShieldData.push({ value: Math.round(effectiveThermalShield), label: translate('thermal') });
-
-// shieldDamageTakenData.push({ value: Math.round(shield.absolute.total * 100), label: translate('absolute') });
-// shieldDamageTakenData.push({ value: Math.round(shield.explosive.total * 100), label: translate('explosive') });
-// shieldDamageTakenData.push({ value: Math.round(shield.kinetic.total * 100), label: translate('kinetic') });
-// shieldDamageTakenData.push({ value: Math.round(shield.thermal.total * 100), label: translate('thermal') });
-
-// maxEffectiveShield = Math.max(shield.total / shield.absolute.max, shield.total / shield.explosive.max, shield.total / shield.kinetic.max, shield.total / shield.thermal.max);
-// }
-
-// const armourSourcesData = [];
-// armourSourcesData.push({ value: Math.round(armour.bulkheads), label: translate('bulkheads') });
-// armourSourcesData.push({ value: Math.round(armour.reinforcement), label: translate('reinforcement') });
-
-// const armourTooltipDetails = [];
-// armourTooltipDetails.push({translate('bulkheads') + ' ' + formats.int(armour.bulkheads)}
);
-// armourTooltipDetails.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 armourExplosiveTooltipDetails = [];
-// armourExplosiveTooltipDetails.push({translate('bulkheads') + ' ' + formats.pct1(armour.explosive.bulkheads)}
);
-// armourExplosiveTooltipDetails.push({translate('reinforcement') + ' ' + formats.pct1(armour.explosive.reinforcement)}
);
-
-// const armourKineticTooltipDetails = [];
-// armourKineticTooltipDetails.push({translate('bulkheads') + ' ' + formats.pct1(armour.kinetic.bulkheads)}
);
-// armourKineticTooltipDetails.push({translate('reinforcement') + ' ' + formats.pct1(armour.kinetic.reinforcement)}
);
-
-// const armourThermalTooltipDetails = [];
-// armourThermalTooltipDetails.push({translate('bulkheads') + ' ' + formats.pct1(armour.thermal.bulkheads)}
);
-// armourThermalTooltipDetails.push({translate('reinforcement') + ' ' + formats.pct1(armour.thermal.reinforcement)}
);
-
-// const effectiveArmourData = [];
-// const effectiveAbsoluteArmour = armour.total / armour.absolute.total;
-// effectiveArmourData.push({ value: Math.round(effectiveAbsoluteArmour), label: translate('absolute') });
-// const effectiveExplosiveArmour = armour.total / armour.explosive.total;
-// effectiveArmourData.push({ value: Math.round(effectiveExplosiveArmour), label: translate('explosive') });
-// const effectiveKineticArmour = armour.total / armour.kinetic.total;
-// effectiveArmourData.push({ value: Math.round(effectiveKineticArmour), label: translate('kinetic') });
-// const effectiveThermalArmour = armour.total / armour.thermal.total;
-// effectiveArmourData.push({ value: Math.round(effectiveThermalArmour), label: translate('thermal') });
// const armourDamageTakenData = [];
// armourDamageTakenData.push({ value: Math.round(armour.absolute.total * 100), label: translate('absolute') });
@@ -248,24 +184,26 @@ export default class Offence extends TranslatedComponent {
return (
+
| {translate('weapon')} |
- {translate('opponent shields')} |
- {translate('opponent armour')} |
+ {translate('opponent\`s shields')} |
+ {translate('opponent\`s armour')} |
- | {translate('effective sdps')} |
- {translate('effectiveness')} |
- {translate('effective sdps')} |
- {translate('effectiveness')} |
+ {'sdps'} |
+ {'eft'} |
+ {'sdps'} |
+ {'eft'} |
{rows}
+
);
}
}
diff --git a/src/app/i18n/en.js b/src/app/i18n/en.js
index 1f7d8cb5..37683424 100644
--- a/src/app/i18n/en.js
+++ b/src/app/i18n/en.js
@@ -55,6 +55,11 @@ export const terms = {
TT_MODULE_PROTECTION_EXTERNAL: 'Percentage of damage diverted from hardpoints to module reinforcement packages',
TT_MODULE_PROTECTION_INTERNAL: 'Percentage of damage diverted from non-hardpoint modules to module reinforcement packages',
+ TT_EFFECTIVE_SDPS_SHIELDS: 'Actual sustained DPS whilst WEP capacitor is not empty',
+ TT_EFFECTIVENESS_SHIELDS: 'Effectivness compared to hitting a 0-resistance target with 0 pips to SYS at 0m',
+ TT_EFFECTIVE_SDPS_ARMOUR: 'Actual sustained DPS whilst WEP capacitor is not empty',
+ TT_EFFECTIVENESS_ARMOUR: 'Effectivness compared to hitting a 0-resistance target at 0m',
+
HELP_MODIFICATIONS_MENU: 'Click on a number to enter a new value, or drag along the bar for small changes',
// Other languages fallback to these values
diff --git a/src/app/pages/OutfittingPage.jsx b/src/app/pages/OutfittingPage.jsx
index ad6e773a..b96c2ef3 100644
--- a/src/app/pages/OutfittingPage.jsx
+++ b/src/app/pages/OutfittingPage.jsx
@@ -100,7 +100,7 @@ export default class OutfittingPage extends Page {
fuel: ship.fuelCapacity,
cargo: 0,
boost: false,
- engagementRange: 1500,
+ engagementRange: 1000,
opponent: new Ship('anaconda', Ships['anaconda'].properties, Ships['anaconda'].slots).buildWith(Ships['anaconda'].defaults)
};
}
diff --git a/src/app/shipyard/Calculations.js b/src/app/shipyard/Calculations.js
index 549fcf2a..597b279d 100644
--- a/src/app/shipyard/Calculations.js
+++ b/src/app/shipyard/Calculations.js
@@ -602,10 +602,8 @@ export function offenceMetrics(ship, opponent, wep, engagementrange) {
name: m.name || m.grp,
classRating,
engineering,
- sdpsShields: weaponSustainedDps.damage.shields.total,
- sdpsArmour: weaponSustainedDps.damage.armour.total,
- effectivenessShields: weaponSustainedDps.effectiveness.shields.total,
- effectivenessArmour: weaponSustainedDps.effectiveness.armour.total
+ sdps: weaponSustainedDps.damage,
+ effectiveness: weaponSustainedDps.effectiveness
});
}
}
diff --git a/src/less/app.less b/src/less/app.less
index f1234db6..5c015eff 100755
--- a/src/less/app.less
+++ b/src/less/app.less
@@ -24,6 +24,7 @@
@import 'movement';
@import 'shippicker';
@import 'defence';
+@import 'offence';
html, body {
height: 100%;
diff --git a/src/less/offence.less b/src/less/offence.less
new file mode 100755
index 00000000..39679f27
--- /dev/null
+++ b/src/less/offence.less
@@ -0,0 +1,14 @@
+#offence {
+ table {
+ background-color: @bgBlack;
+ color: @fg;
+ margin: 0 auto;
+ }
+
+ .icon {
+ stroke: @fg;
+ stroke-width: 20;
+ fill: transparent;
+ }
+}
+