diff --git a/ChangeLog.md b/ChangeLog.md index 4d35d1c7..6b9a9582 100644 --- a/ChangeLog.md +++ b/ChangeLog.md @@ -1,3 +1,10 @@ +#2.2.6 + * Add pitch/roll/yaw information + * Use combination of pitch, roll and yaw to provide a more useful agility metric + * Add movement summary to outfitting page + * Add standard internal class sizes to shipyard page + * Fix issue when importing Viper Mk IV + #2.2.5 * Calculate rate of fire for multi-burst weapons * Add note to disable ghostery in error situation diff --git a/__tests__/fixtures/agility-data.json b/__tests__/fixtures/agility-data.json new file mode 100644 index 00000000..e78f4ea5 --- /dev/null +++ b/__tests__/fixtures/agility-data.json @@ -0,0 +1,30 @@ +{ + "adder": { + "t3": {"speed": 205, "boost": 298, "pitch": 35.37, "roll": 93.09, "yaw": 13.03}, + "t2": {"speed": 209, "boost": 304, "pitch": 36.06, "roll": 94.90, "yaw": 13.29}, + "t1": {"speed": 213, "boost": 310, "pitch": 36.80, "roll": 96.84, "yaw": 13.56}, + "t0": {"speed": 218, "boost": 317, "pitch": 37.70, "roll": 99.20, "yaw": 13.89}, + "t9": {"speed": 220, "boost": 321, "pitch": 38.08, "roll": 100.21, "yaw": 14.03}, + "t8": {"speed": 225, "boost": 327, "pitch": 38.86, "roll": 102.26, "yaw": 14.32}, + "t7": {"speed": 230, "boost": 334, "pitch": 39.69, "roll": 104.44, "yaw": 14.62}, + "t6": {"speed": 234, "boost": 340, "pitch": 40.41, "roll": 106.34, "yaw": 14.89}, + "t5": {"speed": 242, "boost": 351, "pitch": 41.71, "roll": 109.78, "yaw": 15.37} + }, + "eagle": { + "t2": {"speed": 223, "boost": 325, "pitch": 46.45, "roll": 111.48, "yaw": 16.72}, + "t1": {"speed": 229, "boost": 334, "pitch": 47.69, "roll": 114.46, "yaw": 17.17}, + "t0": {"speed": 235, "boost": 343, "pitch": 49.00, "roll": 117.60, "yaw": 17.64}, + "t9": {"speed": 239, "boost": 349, "pitch": 49.80, "roll": 119.53, "yaw": 17.93}, + "t8": {"speed": 243, "boost": 355, "pitch": 50.70, "roll": 121.69, "yaw": 18.25}, + "t7": {"speed": 248, "boost": 361, "pitch": 51.62, "roll": 123.89, "yaw": 18.58}, + "t6": {"speed": 252, "boost": 367, "pitch": 52.46, "roll": 125.91, "yaw": 18.89}, + "t5": {"speed": 259, "boost": 378, "pitch": 53.99, "roll": 129.56, "yaw": 19.43} + }, + "hauler": { + "t4": {"speed": 203, "boost": 305, "pitch": 36.61, "roll": 101.71, "yaw": 14.24}, + "t3": {"speed": 209, "boost": 314, "pitch": 37.63, "roll": 104.54, "yaw": 14.64}, + "t2": {"speed": 216, "boost": 324, "pitch": 38.89, "roll": 108.03, "yaw": 15.12}, + "t1": {"speed": 222, "boost": 333, "pitch": 39.97, "roll": 111.02, "yaw": 15.54}, + "t0": {"speed": 232, "boost": 348, "pitch": 41.76, "roll": 116.00, "yaw": 16.24} + } +} diff --git a/__tests__/fixtures/anaconda-test-detailed-export-v4.json b/__tests__/fixtures/anaconda-test-detailed-export-v4.json index c925f052..b80dc53e 100644 --- a/__tests__/fixtures/anaconda-test-detailed-export-v4.json +++ b/__tests__/fixtures/anaconda-test-detailed-export-v4.json @@ -264,22 +264,21 @@ "topBoost": 248.62, "topSpeed": 186.46, "totalCost": 882362058, - "totalDpe": 127.26, - "totalDps": 97.74, + "totalDpe": 143.01, + "totalDps": 102.83, "totalEps": 22.71, "totalHps": 677.29, "totalExplDpe": 0, "totalExplDps": 0, "totalExplSDps": 0, "totalHps": 33.62, - "totalKinDpe": 103.97, - "totalKinDps": 28.92, - "totalKinSDps": 21.23, - "totalSDps": 85.77, - "totalThermDpe": 23.29, - "totalThermDps": 68.82, - "totalThermSDps": 64.53, - "agility": 2, + "totalKinDpe": 119.43, + "totalKinDps": 32.51, + "totalKinSDps": 24.79, + "totalSDps": 91.3, + "totalThermDpe": 23.58, + "totalThermDps": 70.32, + "totalThermSDps": 66.51, "baseShieldStrength": 350, "baseArmour": 945, "hullExplRes": 0.78, @@ -288,6 +287,7 @@ "hullThermRes": 1.37, "masslock": 23, "pipSpeed": 0.14, + "pitch": 25, "moduleCostMultiplier": 1, "fuelCapacity": 32, "cargoCapacity": 128, @@ -297,8 +297,10 @@ "unladenMass": 1179.2, "powerAvailable": 39.6, "powerRetracted": 23.33, - "powerDeployed": 34.76, + "powerDeployed": 34.13, + "roll": 60, "unladenRange": 18.49, + "yaw": 10, "fullTankRange": 18.12, "ladenRange": 16.39, "unladenFastestRange": 73.21, diff --git a/__tests__/test-agility.js b/__tests__/test-agility.js new file mode 100644 index 00000000..e3bd87cb --- /dev/null +++ b/__tests__/test-agility.js @@ -0,0 +1,90 @@ +import Ship from '../src/app/shipyard/Ship'; +import { Ships } from 'coriolis-data/dist'; +import * as ModuleUtils from '../src/app/shipyard/ModuleUtils'; + +describe("Agility", function() { + + it("correctly calculates speed", function() { + let agilityData = require('./fixtures/agility-data'); + + for (let shipId in agilityData) { + for (let thrusterId in agilityData[shipId]) { + const thrusterData = agilityData[shipId][thrusterId]; + let shipData = Ships[shipId]; + let ship = new Ship(shipId, shipData.properties, shipData.slots); + ship.buildWith(shipData.defaults); + ship.use(ship.standard[1], ModuleUtils.findModule('t', thrusterId)); + + expect(Math.round(ship.topSpeed)).toBe(thrusterData.speed); + } + } + }); + + it("correctly calculates boost", function() { + let agilityData = require('./fixtures/agility-data'); + + for (let shipId in agilityData) { + for (let thrusterId in agilityData[shipId]) { + const thrusterData = agilityData[shipId][thrusterId]; + let shipData = Ships[shipId]; + let ship = new Ship(shipId, shipData.properties, shipData.slots); + ship.buildWith(shipData.defaults); + // Turn off internals to ensure we have enough power to boost + for (let internal in ship.internal) { + ship.internal[internal].enabled = 0; + } + ship.use(ship.standard[1], ModuleUtils.findModule('t', thrusterId)); + + expect(Math.round(ship.topBoost)).toBe(thrusterData.boost); + } + } + }); + + it("correctly calculates pitch", function() { + let agilityData = require('./fixtures/agility-data'); + + for (let shipId in agilityData) { + for (let thrusterId in agilityData[shipId]) { + const thrusterData = agilityData[shipId][thrusterId]; + let shipData = Ships[shipId]; + let ship = new Ship(shipId, shipData.properties, shipData.slots); + ship.buildWith(shipData.defaults); + ship.use(ship.standard[1], ModuleUtils.findModule('t', thrusterId)); + + expect(Math.round(ship.pitches[4] * 100) / 100).toBeCloseTo(thrusterData.pitch, 1); + } + } + }); + + it("correctly calculates roll", function() { + let agilityData = require('./fixtures/agility-data'); + + for (let shipId in agilityData) { + for (let thrusterId in agilityData[shipId]) { + const thrusterData = agilityData[shipId][thrusterId]; + let shipData = Ships[shipId]; + let ship = new Ship(shipId, shipData.properties, shipData.slots); + ship.buildWith(shipData.defaults); + ship.use(ship.standard[1], ModuleUtils.findModule('t', thrusterId)); + + expect(Math.round(ship.rolls[4] * 100) / 100).toBeCloseTo(thrusterData.roll, 1); + } + } + }); + + it("correctly calculates yaw", function() { + let agilityData = require('./fixtures/agility-data'); + + for (let shipId in agilityData) { + for (let thrusterId in agilityData[shipId]) { + const thrusterData = agilityData[shipId][thrusterId]; + let shipData = Ships[shipId]; + let ship = new Ship(shipId, shipData.properties, shipData.slots); + ship.buildWith(shipData.defaults); + ship.use(ship.standard[1], ModuleUtils.findModule('t', thrusterId)); + + expect(Math.round(ship.yaws[4] * 100) / 100).toBeCloseTo(thrusterData.yaw, 1); + } + } + }); +}); diff --git a/package.json b/package.json index c84efaea..40992cd2 100644 --- a/package.json +++ b/package.json @@ -31,6 +31,7 @@ "jsx" ], "automock": true, + "bail": false, "unmockedModulePathPatterns": [ "/node_modules/lodash", "/node_modules/react", diff --git a/src/app/components/MovementSummary.jsx b/src/app/components/MovementSummary.jsx new file mode 100644 index 00000000..14fba3bf --- /dev/null +++ b/src/app/components/MovementSummary.jsx @@ -0,0 +1,125 @@ +import React from 'react'; +import cn from 'classnames'; +import TranslatedComponent from './TranslatedComponent'; +import { DamageKinetic, DamageThermal, DamageExplosive } from './SvgIcons'; + +/** + * Movement summary + */ +export default class MovementSummary extends TranslatedComponent { + static PropTypes = { + ship: React.PropTypes.object.isRequired + }; + + /** + * Constructor + * @param {Object} props React Component properties + */ + constructor(props) { + super(props); + } + + /** + * Render movement summary + * @return {React.Component} contents + */ + render() { + let ship = this.props.ship; + let { language, tooltip, termtip } = this.context; + let { formats, translate, units } = language; + let hide = tooltip.bind(null, null); + let boostMultiplier = ship.topBoost / ship.topSpeed; + + return ( + +

{translate('movement summary')}

+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
 {translate('engine pips')}
 012344B
{translate('speed')} ({units['m/s']}){formats.int(ship.speeds[0])}{formats.int(ship.speeds[1])}{formats.int(ship.speeds[2])}{formats.int(ship.speeds[3])}{formats.int(ship.speeds[4])}{formats.int(ship.speeds[4] * boostMultiplier)}
{translate('pitch')} ({units['°/s']}){formats.int(ship.pitches[0])}{formats.int(ship.pitches[1])}{formats.int(ship.pitches[2])}{formats.int(ship.pitches[3])}{formats.int(ship.pitches[4])}{formats.int(ship.pitches[4] * boostMultiplier)}
{translate('roll')} ({units['°/s']}){formats.int(ship.rolls[0])}{formats.int(ship.rolls[1])}{formats.int(ship.rolls[2])}{formats.int(ship.rolls[3])}{formats.int(ship.rolls[4])}{formats.int(ship.rolls[4] * boostMultiplier)}
{translate('yaw')} ({units['°/s']}){formats.int(ship.yaws[0])}{formats.int(ship.yaws[1])}{formats.int(ship.yaws[2])}{formats.int(ship.yaws[3])}{formats.int(ship.yaws[4])}{formats.int(ship.yaws[4] * boostMultiplier)}
+
+ ); +// return ( +// +//

{translate('movement summary')}

+// +// +// +// +// +// +// +// +// +// +// +// +// +// +// +// +// +// +// +// +// +// +// +// +// +// +// +//

{translate('normal')}

{translate('speed')} {formats.int(ship.topSpeed)}{units['m/s']}{translate('pitch')} {formats.f1(ship.pitches[4])}{units['°/s']}{translate('roll')} {formats.f1(ship.rolls[4])}{units['°/s']}{translate('yaw')} {formats.f1(ship.yaws[4])}{units['°/s']}

{translate('boost')}

{translate('speed')} {formats.int(ship.topSpeed * boostMultiplier)}{units['m/s']}{translate('pitch')} {formats.f1(ship.pitches[4] * boostMultiplier)}{units['°/s']}{translate('roll')} {formats.f1(ship.rolls[4] * boostMultiplier)}{units['°/s']}{translate('yaw')} {formats.f1(ship.yaws[4] * boostMultiplier)}{units['°/s']}

Frame Shift

Maximum {formats.f2(ship.fullTankRange)} {units.LY}
+//
+// ); + } +} diff --git a/src/app/i18n/Language.jsx b/src/app/i18n/Language.jsx index 5a6a5ee4..d16b2e1f 100644 --- a/src/app/i18n/Language.jsx +++ b/src/app/i18n/Language.jsx @@ -65,6 +65,7 @@ export function getLanguage(langCode) { LY: {translate('LY')}, // Light Years MJ: {translate('MJ')}, // Mega Joules 'm/s': {translate('m/s')}, // Meters per second + '°/s': {translate('°/s')}, // Degrees per second MW: {translate('MW')}, // Mega Watts (same as Mega Joules per second) ps: {translate('/s')}, // per second pm: {translate('/min')}, // per minute diff --git a/src/app/i18n/en.js b/src/app/i18n/en.js index b8b7f0ff..08fa074f 100644 --- a/src/app/i18n/en.js +++ b/src/app/i18n/en.js @@ -94,7 +94,7 @@ export const terms = { // Unit for seconds secs: 's', - // Weapon, offence and defence + // Weapon, offence, defence and movement dpe: 'Damage per MJ of energy', dps: 'Damage per second', sdps: 'Sustained damage per second', @@ -106,6 +106,13 @@ export const terms = { 'damage by': 'Damage by', 'damage from': 'Damage from', 'shield cells': 'Shield cells', + 'recovery': 'Recovery', + 'recharge': 'Recharge', + 'engine pips': 'Engine Pips', + 'speed': 'Speed', + 'pitch': 'Pitch', + 'roll': 'Roll', + 'yaw': 'Yaw', // Modifications ammo: 'Ammunition maximum', diff --git a/src/app/pages/OutfittingPage.jsx b/src/app/pages/OutfittingPage.jsx index c7831e9d..9e3793fc 100644 --- a/src/app/pages/OutfittingPage.jsx +++ b/src/app/pages/OutfittingPage.jsx @@ -16,6 +16,7 @@ import InternalSlotSection from '../components/InternalSlotSection'; import UtilitySlotSection from '../components/UtilitySlotSection'; import OffenceSummary from '../components/OffenceSummary'; import DefenceSummary from '../components/DefenceSummary'; +import MovementSummary from '../components/MovementSummary'; import LineChart from '../components/LineChart'; import PowerManagement from '../components/PowerManagement'; import CostSection from '../components/CostSection'; @@ -344,19 +345,7 @@ export default class OutfittingPage extends Page {
-

{translate('speed')}

- +
@@ -402,3 +391,19 @@ export default class OutfittingPage extends Page { // func={state.jumpRangeChartFunc} // /> //
+//
+//

{translate('speed')}

+// +//
+ diff --git a/src/app/pages/ShipyardPage.jsx b/src/app/pages/ShipyardPage.jsx index f794eb10..136931a5 100644 --- a/src/app/pages/ShipyardPage.jsx +++ b/src/app/pages/ShipyardPage.jsx @@ -40,7 +40,9 @@ function shipSummary(shipId, shipData) { intCount: 0, maxCargo: 0, hp: [0, 0, 0, 0, 0], // Utility, Small, Medium, Large, Huge - int: [0, 0, 0, 0, 0, 0, 0, 0] // Sizes 1 - 8 + int: [0, 0, 0, 0, 0, 0, 0, 0], // Sizes 1 - 8 + standard: shipData.slots.standard, + agility: shipData.properties.pitch + shipData.properties.yaw + shipData.properties.roll }; Object.assign(summary, shipData.properties); let ship = new Ship(shipId, shipData.properties, shipData.slots); @@ -139,7 +141,7 @@ export default class ShipyardPage extends Page { > {s.manufacturer} {translate(SizeMap[s.class])} - {s.agility} + {fInt(s.agility)} {fInt(s.speed)}{u['m/s']} {fInt(s.boost)}{u['m/s']} {fInt(s.baseArmour)} @@ -148,6 +150,12 @@ export default class ShipyardPage extends Page { {fInt(s.topBoost)}{u['m/s']} {fRound(s.maxJumpRange)}{u.LY} {fInt(s.maxCargo)}{u.T} + {s.standard[0]} + {s.standard[1]} + {s.standard[2]} + {s.standard[3]} + {s.standard[4]} + {s.standard[5]} {s.hp[1]} {s.hp[2]} {s.hp[3]} @@ -260,9 +268,10 @@ export default class ShipyardPage extends Page { {translate('manufacturer')} {translate('size')} - {translate('mnv')} + {translate('agility')} {translate('base')} {translate('max')} + {translate('core module classes')} {translate('hardpoints')} {translate('internal compartments')} {translate('hull')} @@ -280,6 +289,13 @@ export default class ShipyardPage extends Page { {translate('jump')} {translate('cargo')} + {'pp'} + {'th'} + {'fsd'} + {'ls'} + {'pd'} + {'s'} + {translate('S')} {translate('M')} {translate('L')} diff --git a/src/app/shipyard/Calculations.js b/src/app/shipyard/Calculations.js index 96c7b0fe..44cccab0 100644 --- a/src/app/shipyard/Calculations.js +++ b/src/app/shipyard/Calculations.js @@ -67,14 +67,35 @@ export function shieldStrength(mass, baseShield, sg, multiplier) { /** * Calculate the a ships speed based on mass, and thrusters. * - * @param {number} mass Current mass of the ship - * @param {number} baseSpeed Base speed m/s for ship - * @param {number} baseBoost Base boost speed m/s for ship - * @param {object} thrusters The Thrusters used - * @param {number} pipSpeed Speed pip multiplier - * @return {object} Approximate speed by pips + * @param {number} mass the mass of the ship + * @param {number} baseSpeed base speed m/s for ship + * @param {object} thrusters The ship's thrusters + * @param {number} engpip the multiplier per pip to engines + * @return {array} Speed by pips */ -export function speed(mass, baseSpeed, baseBoost, thrusters, pipSpeed) { +export function speed(mass, baseSpeed, thrusters, engpip) { + // thrusters might be a module or a template; handle either here + const minMass = thrusters instanceof Module ? thrusters.getMinMass() : thrusters.minmass; + const optMass = thrusters instanceof Module ? thrusters.getOptMass() : thrusters.optmass; + const maxMass = thrusters instanceof Module ? thrusters.getMaxMass() : thrusters.maxmass; + const minMul = thrusters instanceof Module ? thrusters.getMinMul() : thrusters.minmul; + const optMul = thrusters instanceof Module ? thrusters.getOptMul() : thrusters.optmul; + const maxMul = thrusters instanceof Module ? thrusters.getMaxMul() : thrusters.maxmul; + + let results = normValues(minMass, optMass, maxMass, minMul, optMul, maxMul, mass, baseSpeed, engpip); + + return results; +} + +/** + * Calculate pitch of a ship based on mass and thrusters + * @param {number} mass the mass of the ship + * @param {number} basePitch base pitch of the ship + * @param {object} thrusters the ship's thrusters + * @param {number} engpip the multiplier per pip to engines + * @return {array} Pitch by pips + */ +export function pitch(mass, basePitch, thrusters, engpip) { // thrusters might be a module or a template; handle either here let minMass = thrusters instanceof Module ? thrusters.getMinMass() : thrusters.minmass; let optMass = thrusters instanceof Module ? thrusters.getOptMass() : thrusters.optmass; @@ -83,16 +104,79 @@ export function speed(mass, baseSpeed, baseBoost, thrusters, pipSpeed) { let optMul = thrusters instanceof Module ? thrusters.getOptMul() : thrusters.optmul; let maxMul = thrusters instanceof Module ? thrusters.getMaxMul() : thrusters.maxmul; - let xnorm = Math.min(1, (maxMass - mass) / (maxMass - minMass)); - let exponent = Math.log((optMul - minMul) / (maxMul - minMul)) / Math.log(Math.min(1, (maxMass - optMass) / (maxMass - minMass))); - let ynorm = Math.pow(xnorm, exponent); - let mul = minMul + ynorm * (maxMul - minMul); - let speed = baseSpeed * mul; - - return { - '0 Pips': speed * (1 - (pipSpeed * 4)), - '2 Pips': speed * (1 - (pipSpeed * 2)), - '4 Pips': speed, - 'boost': baseBoost * mul - }; + return normValues(minMass, optMass, maxMass, minMul, optMul, maxMul, mass, basePitch, engpip); +} + +/** + * Calculate yaw of a ship based on mass and thrusters + * @param {number} mass the mass of the ship + * @param {number} baseYaw base yaw of the ship + * @param {object} thrusters the ship's thrusters + * @param {number} engpip the multiplier per pip to engines + * @return {array} Yaw by pips + */ +export function yaw(mass, baseYaw, thrusters, engpip) { + // thrusters might be a module or a template; handle either here + let minMass = thrusters instanceof Module ? thrusters.getMinMass() : thrusters.minmass; + let optMass = thrusters instanceof Module ? thrusters.getOptMass() : thrusters.optmass; + let maxMass = thrusters instanceof Module ? thrusters.getMaxMass() : thrusters.maxmass; + let minMul = thrusters instanceof Module ? thrusters.getMinMul() : thrusters.minmul; + let optMul = thrusters instanceof Module ? thrusters.getOptMul() : thrusters.optmul; + let maxMul = thrusters instanceof Module ? thrusters.getMaxMul() : thrusters.maxmul; + + return normValues(minMass, optMass, maxMass, minMul, optMul, maxMul, mass, baseYaw, engpip); +} + +/** + * Calculate roll of a ship based on mass and thrusters + * @param {number} mass the mass of the ship + * @param {number} baseRoll base roll of the ship + * @param {object} thrusters the ship's thrusters + * @param {number} engpip the multiplier per pip to engines + * @return {array} Roll by pips + */ +export function roll(mass, baseRoll, thrusters, engpip) { + // thrusters might be a module or a template; handle either here + let minMass = thrusters instanceof Module ? thrusters.getMinMass() : thrusters.minmass; + let optMass = thrusters instanceof Module ? thrusters.getOptMass() : thrusters.optmass; + let maxMass = thrusters instanceof Module ? thrusters.getMaxMass() : thrusters.maxmass; + let minMul = thrusters instanceof Module ? thrusters.getMinMul() : thrusters.minmul; + let optMul = thrusters instanceof Module ? thrusters.getOptMul() : thrusters.optmul; + let maxMul = thrusters instanceof Module ? thrusters.getMaxMul() : thrusters.maxmul; + + return normValues(minMass, optMass, maxMass, minMul, optMul, maxMul, mass, baseRoll, engpip); +} + +/** + * Normalise according to FD's calculations and return suitable values + * @param {number} minMass the minimum mass of the thrusters + * @param {number} optMass the optimum mass of the thrusters + * @param {number} maxMass the maximum mass of the thrusters + * @param {number} minMul the minimum multiplier of the thrusters + * @param {number} optMul the optimum multiplier of the thrusters + * @param {number} maxMul the maximum multiplier of the thrusters + * @param {number} mass the mass of the ship + * @param {base} base the base value from which to calculate + * @param {number} engpip the multiplier per pip to engines + * @return {array} values by pips + */ +function normValues(minMass, optMass, maxMass, minMul, optMul, maxMul, mass, base, engpip) { + const xnorm = Math.min(1, (maxMass - mass) / (maxMass - minMass)); + const exponent = Math.log((optMul - minMul) / (maxMul - minMul)) / Math.log(Math.min(1, (maxMass - optMass) / (maxMass - minMass))); + const ynorm = Math.pow(xnorm, exponent); + const mul = minMul + ynorm * (maxMul - minMul); + const res = base * mul; + + return [res * (1 - (engpip * 4)), + res * (1 - (engpip * 3)), + res * (1 - (engpip * 2)), + res * (1 - (engpip * 1)), + res]; + //return { + // '0 Pips': res * (1 - (engpip * 4)), + // '1 Pip': res * (1 - (engpip * 3)), + // '2 Pips': res * (1 - (engpip * 2)), + // '3 Pips': res * (1 - (engpip)), + // '4 Pips': res + //}; } diff --git a/src/app/shipyard/Ship.js b/src/app/shipyard/Ship.js index be771cbc..32a1a969 100755 --- a/src/app/shipyard/Ship.js +++ b/src/app/shipyard/Ship.js @@ -188,10 +188,10 @@ export default class Ship { * Calculate the hypothetical top speeds at cargo and fuel tonnage * @param {Number} fuel Fuel available in tons * @param {Number} cargo Cargo in tons - * @return {Object} Speed at pip settings and boost + * @return {array} Speed at pip settings */ calcSpeedsWith(fuel, cargo) { - return Calc.speed(this.unladenMass + fuel + cargo, this.speed, this.boost, this.standard[1].m, this.pipSpeed); + return Calc.speed(this.unladenMass + fuel + cargo, this.speed, this.standard[1].m, this.pipSpeed); } /** @@ -432,7 +432,7 @@ export default class Ship { let newMass = m.getMass(); this.unladenMass = this.unladenMass - oldMass + newMass; this.ladenMass = this.ladenMass - oldMass + newMass; - this.updateTopSpeed(); + this.updateMovement(); this.updateJumpStats(); } else if (name === 'maxfuel') { m.setModValue(name, value); @@ -440,13 +440,13 @@ export default class Ship { } else if (name === 'optmass') { m.setModValue(name, value); // Could be for any of thrusters, FSD or shield - this.updateTopSpeed(); + this.updateMovement(); this.updateJumpStats(); this.recalculateShield(); } else if (name === 'optmul') { m.setModValue(name, value); // Could be for any of thrusters, FSD or shield - this.updateTopSpeed(); + this.updateMovement(); this.updateJumpStats(); this.recalculateShield(); } else if (name === 'shieldboost') { @@ -597,7 +597,7 @@ export default class Ship { .recalculateDps() .recalculateEps() .recalculateHps() - .updateTopSpeed(); + .updateMovement(); } return this.updatePowerPrioritesString().updatePowerEnabledString().updateModificationsString(); @@ -876,7 +876,7 @@ export default class Ship { if (shieldCellsChange) { this.recalculateShieldCells(); } - this.updateTopSpeed(); + this.updateMovement(); this.updateJumpStats(); } return this; @@ -1088,13 +1088,20 @@ export default class Ship { } /** - * Update top speed and boost + * Update movement values * @return {this} The ship instance (for chaining operations) */ - updateTopSpeed() { - let speeds = Calc.speed(this.unladenMass + this.fuelCapacity, this.speed, this.boost, this.standard[1].m, this.pipSpeed); - this.topSpeed = speeds['4 Pips']; - this.topBoost = this.canBoost() ? speeds.boost : 0; + updateMovement() { + this.speeds = Calc.speed(this.unladenMass + this.fuelCapacity, this.speed, this.standard[1].m, this.pipSpeed); + this.topSpeed = this.speeds[4]; + this.topBoost = this.canBoost() ? this.speeds[4] * this.boost / this.speed : 0; + + this.pitches = Calc.pitch(this.unladenMass + this.fuelCapacity, this.pitch, this.standard[1].m, this.pipSpeed); + + this.rolls = Calc.roll(this.unladenMass + this.fuelCapacity, this.roll, this.standard[1].m, this.pipSpeed); + + this.yaws = Calc.yaw(this.unladenMass + this.fuelCapacity, this.yaw, this.standard[1].m, this.pipSpeed); + return this; } diff --git a/src/app/utils/CompanionApiUtils.js b/src/app/utils/CompanionApiUtils.js index 6d90bc7f..46d7fc05 100644 --- a/src/app/utils/CompanionApiUtils.js +++ b/src/app/utils/CompanionApiUtils.js @@ -33,7 +33,7 @@ const SHIP_FD_NAME_TO_CORIOLIS_NAME = { 'Type7': 'type_7_transport', 'Type9': 'type_9_heavy', 'Viper': 'viper', - 'Viper_MKIV': 'viper_mk_iv', + 'Viper_MkIV': 'viper_mk_iv', 'Vulture': 'vulture' };