@elite-dangerous-almanac/core 0.2.8 → 0.2.10

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (263) hide show
  1. package/PROVENANCE/astro/SOURCES.md +13 -12
  2. package/PROVENANCE/commodities/SOURCES.md +50 -6
  3. package/PROVENANCE/equipment/SOURCES.md +137 -45
  4. package/PROVENANCE/i18n/SOURCES.md +187 -81
  5. package/PROVENANCE/ships/SOURCES.md +344 -200
  6. package/README.md +10 -2
  7. package/THIRD_PARTY_NOTICES.md +11 -3
  8. package/dist/astro/body-rings.d.ts +2 -2
  9. package/dist/astro/codex-region-lookup.d.ts +1 -1
  10. package/dist/astro/codex-region-lookup.js +1 -1
  11. package/dist/astro/hand-authored-regions.d.ts +1 -1
  12. package/dist/astro/index.d.ts +1 -1
  13. package/dist/astro/index.js +1 -1
  14. package/dist/astro/naming-region-origins.d.ts +1 -1
  15. package/dist/astro/naming-region-origins.js +1 -1
  16. package/dist/astro/nebulae-all.d.ts +4 -6
  17. package/dist/astro/nebulae-all.js +1 -1
  18. package/dist/astro/nebulae-all.js.map +1 -1
  19. package/dist/astro/nebulae-planetary.d.ts +4 -5
  20. package/dist/astro/nebulae-planetary.js +1 -1
  21. package/dist/astro/nebulae-procgen.d.ts +3 -3
  22. package/dist/astro/nebulae-real.d.ts +3 -3
  23. package/dist/astro/nebulae.d.ts +8 -8
  24. package/dist/astro/permit-locked-regions.d.ts +2 -2
  25. package/dist/astro/permit-locked-systems.d.ts +1 -1
  26. package/dist/astro/permit-locks.d.ts +2 -2
  27. package/dist/astro/procedural-system.d.ts +3 -3
  28. package/dist/astro/procedural-system.js +1 -1
  29. package/dist/astro/system-address.d.ts +1 -1
  30. package/dist/astro/system-address.js +1 -1
  31. package/dist/astro/system-name.js +1 -1
  32. package/dist/{chunk-XSLPWM5N.js → chunk-2J6NNI3Y.js} +1 -1
  33. package/dist/{chunk-DWRNXUAX.js → chunk-2KIZN3BY.js} +1 -1
  34. package/dist/{chunk-J7BM5NGK.js → chunk-2TY42PTF.js} +1 -1
  35. package/dist/{chunk-773VO2GK.js → chunk-4T3TTYUT.js} +1 -1
  36. package/dist/{chunk-773VO2GK.js.map → chunk-4T3TTYUT.js.map} +1 -1
  37. package/dist/{chunk-W5ULI75F.js → chunk-7C7NJWCF.js} +1 -1
  38. package/dist/{chunk-W5ULI75F.js.map → chunk-7C7NJWCF.js.map} +1 -1
  39. package/dist/{chunk-IMNOEFUE.js → chunk-7Y5EK2VO.js} +1 -1
  40. package/dist/{chunk-IMNOEFUE.js.map → chunk-7Y5EK2VO.js.map} +1 -1
  41. package/dist/{chunk-2OBUSQA7.js → chunk-AAU7OM47.js} +1 -1
  42. package/dist/{chunk-2OBUSQA7.js.map → chunk-AAU7OM47.js.map} +1 -1
  43. package/dist/{chunk-BJU27V6C.js → chunk-AUBV6S7V.js} +1 -1
  44. package/dist/{chunk-BJU27V6C.js.map → chunk-AUBV6S7V.js.map} +1 -1
  45. package/dist/{chunk-DI5RXSJR.js → chunk-BVLBS2QY.js} +1 -1
  46. package/dist/{chunk-DI5RXSJR.js.map → chunk-BVLBS2QY.js.map} +1 -1
  47. package/dist/{chunk-IN36YSS4.js → chunk-C3YZ5KTA.js} +1 -1
  48. package/dist/{chunk-IN36YSS4.js.map → chunk-C3YZ5KTA.js.map} +1 -1
  49. package/dist/{chunk-6UNAD74Z.js → chunk-C4FUV6GF.js} +1 -1
  50. package/dist/{chunk-6UNAD74Z.js.map → chunk-C4FUV6GF.js.map} +1 -1
  51. package/dist/chunk-C6G7IN74.js +1 -0
  52. package/dist/chunk-C6G7IN74.js.map +1 -0
  53. package/dist/chunk-CEF7SMB2.js +1 -0
  54. package/dist/chunk-CEF7SMB2.js.map +1 -0
  55. package/dist/chunk-E2HDF6PJ.js +1 -0
  56. package/dist/chunk-E2HDF6PJ.js.map +1 -0
  57. package/dist/{chunk-OFZGNWBT.js → chunk-ETREYN5U.js} +1 -1
  58. package/dist/{chunk-OFZGNWBT.js.map → chunk-ETREYN5U.js.map} +1 -1
  59. package/dist/{chunk-KBCA4GEZ.js → chunk-FP2TQJZP.js} +1 -1
  60. package/dist/{chunk-YJAH6DFY.js → chunk-G7WARJ3X.js} +1 -1
  61. package/dist/chunk-G7WARJ3X.js.map +1 -0
  62. package/dist/{chunk-Z4OUB4SJ.js → chunk-GLTCCDN5.js} +1 -1
  63. package/dist/{chunk-Z4OUB4SJ.js.map → chunk-GLTCCDN5.js.map} +1 -1
  64. package/dist/chunk-GVNTKCVF.js +1 -0
  65. package/dist/chunk-GVNTKCVF.js.map +1 -0
  66. package/dist/{chunk-Q6YDPREF.js → chunk-GZLD7RTK.js} +1 -1
  67. package/dist/{chunk-Q6YDPREF.js.map → chunk-GZLD7RTK.js.map} +1 -1
  68. package/dist/{chunk-SC4MEHVY.js → chunk-HIJR7DOC.js} +1 -1
  69. package/dist/{chunk-SC4MEHVY.js.map → chunk-HIJR7DOC.js.map} +1 -1
  70. package/dist/{chunk-ETWMPMZP.js → chunk-K5JK3XQB.js} +1 -1
  71. package/dist/{chunk-GRIK3EDH.js → chunk-KY7KSPU6.js} +1 -1
  72. package/dist/{chunk-GRIK3EDH.js.map → chunk-KY7KSPU6.js.map} +1 -1
  73. package/dist/{chunk-EHFHRQEP.js → chunk-M4STXLXO.js} +1 -1
  74. package/dist/{chunk-EHFHRQEP.js.map → chunk-M4STXLXO.js.map} +1 -1
  75. package/dist/{chunk-5YEHJM6V.js → chunk-OSMBAFRW.js} +1 -1
  76. package/dist/{chunk-5YEHJM6V.js.map → chunk-OSMBAFRW.js.map} +1 -1
  77. package/dist/chunk-PIU24HRN.js +1 -0
  78. package/dist/chunk-PIU24HRN.js.map +1 -0
  79. package/dist/{chunk-ELT3FEA4.js → chunk-PKKBYBL4.js} +1 -1
  80. package/dist/{chunk-ELT3FEA4.js.map → chunk-PKKBYBL4.js.map} +1 -1
  81. package/dist/{chunk-6HMIF2RJ.js → chunk-Q647OXON.js} +1 -1
  82. package/dist/{chunk-6HMIF2RJ.js.map → chunk-Q647OXON.js.map} +1 -1
  83. package/dist/{chunk-BMQM4JBL.js → chunk-QPT2WJYN.js} +1 -1
  84. package/dist/{chunk-BMQM4JBL.js.map → chunk-QPT2WJYN.js.map} +1 -1
  85. package/dist/{chunk-3WGXGBW5.js → chunk-R2AEZYX7.js} +1 -1
  86. package/dist/{chunk-FJIWJYKO.js → chunk-RA4YJBU5.js} +1 -1
  87. package/dist/chunk-RA4YJBU5.js.map +1 -0
  88. package/dist/{chunk-MRLUWHGI.js → chunk-RJ3ZLQRB.js} +1 -1
  89. package/dist/{chunk-MRLUWHGI.js.map → chunk-RJ3ZLQRB.js.map} +1 -1
  90. package/dist/chunk-SFEQXUIA.js +1 -0
  91. package/dist/{chunk-WV7QCDL5.js → chunk-SIL356HB.js} +1 -1
  92. package/dist/{chunk-WV7QCDL5.js.map → chunk-SIL356HB.js.map} +1 -1
  93. package/dist/{chunk-OLKOWR7S.js → chunk-SS7HVNP5.js} +1 -1
  94. package/dist/{chunk-OLKOWR7S.js.map → chunk-SS7HVNP5.js.map} +1 -1
  95. package/dist/chunk-TRGHPX2O.js +1 -0
  96. package/dist/chunk-TRGHPX2O.js.map +1 -0
  97. package/dist/{chunk-GMTAFUAG.js → chunk-TYRH73MO.js} +1 -1
  98. package/dist/{chunk-GMTAFUAG.js.map → chunk-TYRH73MO.js.map} +1 -1
  99. package/dist/{chunk-7TVFV3VO.js → chunk-U3IRMXMR.js} +1 -1
  100. package/dist/{chunk-A7IVMYNF.js → chunk-U73MBQ45.js} +1 -1
  101. package/dist/{chunk-A7IVMYNF.js.map → chunk-U73MBQ45.js.map} +1 -1
  102. package/dist/{chunk-IZIIGK3W.js → chunk-UE22QU7A.js} +1 -1
  103. package/dist/{chunk-IZIIGK3W.js.map → chunk-UE22QU7A.js.map} +1 -1
  104. package/dist/{chunk-DBDCOHI4.js → chunk-UI5RROGI.js} +1 -1
  105. package/dist/{chunk-DBDCOHI4.js.map → chunk-UI5RROGI.js.map} +1 -1
  106. package/dist/chunk-URRPEUIK.js +1 -0
  107. package/dist/{chunk-QJECDMQQ.js.map → chunk-URRPEUIK.js.map} +1 -1
  108. package/dist/chunk-UVX7RCMP.js +1 -0
  109. package/dist/chunk-UVX7RCMP.js.map +1 -0
  110. package/dist/{chunk-7ATBEOVC.js → chunk-WG4DPXJI.js} +1 -1
  111. package/dist/{chunk-XFDMCPDW.js → chunk-WZIBBJHA.js} +1 -1
  112. package/dist/{chunk-XFDMCPDW.js.map → chunk-WZIBBJHA.js.map} +1 -1
  113. package/dist/{chunk-7EWZGDWY.js → chunk-X3MXPE7G.js} +1 -1
  114. package/dist/{chunk-7EWZGDWY.js.map → chunk-X3MXPE7G.js.map} +1 -1
  115. package/dist/{chunk-JCYOE3C4.js → chunk-XQJERZUS.js} +1 -1
  116. package/dist/{chunk-JCYOE3C4.js.map → chunk-XQJERZUS.js.map} +1 -1
  117. package/dist/{chunk-SD6GNFDX.js → chunk-YBE5M27G.js} +1 -1
  118. package/dist/{chunk-SD6GNFDX.js.map → chunk-YBE5M27G.js.map} +1 -1
  119. package/dist/chunk-YI5XKWW2.js +1 -0
  120. package/dist/{chunk-GIGRBFIJ.js.map → chunk-YI5XKWW2.js.map} +1 -1
  121. package/dist/chunk-ZBUTGTZ3.js +1 -0
  122. package/dist/chunk-ZBUTGTZ3.js.map +1 -0
  123. package/dist/commodities/commodities-all.d.ts +2 -2
  124. package/dist/commodities/commodities-all.js +1 -1
  125. package/dist/commodities/commodities-rare.d.ts +3 -4
  126. package/dist/commodities/commodities-rare.js +1 -1
  127. package/dist/commodities/commodities-standard.d.ts +7 -7
  128. package/dist/commodities/commodities-standard.js +1 -1
  129. package/dist/commodities/commodities.d.ts +12 -12
  130. package/dist/commodities/commodities.js +1 -1
  131. package/dist/commodities/index.js +1 -1
  132. package/dist/equipment/engineering.d.ts +11 -6
  133. package/dist/equipment/engineering.js +1 -1
  134. package/dist/equipment/index.d.ts +4 -4
  135. package/dist/equipment/index.js +1 -1
  136. package/dist/equipment/modification-journal.js +1 -1
  137. package/dist/equipment/modifications.d.ts +23 -14
  138. package/dist/equipment/modifications.js +1 -1
  139. package/dist/equipment/suits.d.ts +2 -145
  140. package/dist/equipment/suits.js +1 -1
  141. package/dist/equipment/tools.d.ts +102 -0
  142. package/dist/equipment/tools.js +1 -0
  143. package/dist/equipment/tools.js.map +1 -0
  144. package/dist/equipment/upgrade-costs.d.ts +2 -3
  145. package/dist/equipment/upgrade-costs.js +1 -1
  146. package/dist/equipment/weapons.d.ts +2 -135
  147. package/dist/equipment/weapons.js +1 -1
  148. package/dist/i18n/blueprints.d.ts +2 -3
  149. package/dist/i18n/blueprints.js +1 -1
  150. package/dist/i18n/commodities.d.ts +36 -0
  151. package/dist/i18n/commodities.js +1 -0
  152. package/dist/i18n/commodities.js.map +1 -0
  153. package/dist/i18n/experimental-effect-descriptions.d.ts +5 -6
  154. package/dist/i18n/experimental-effect-descriptions.js +1 -1
  155. package/dist/i18n/experimental-effects.d.ts +2 -3
  156. package/dist/i18n/experimental-effects.js +1 -1
  157. package/dist/i18n/index.d.ts +19 -9
  158. package/dist/i18n/index.js +1 -1
  159. package/dist/i18n/materials.d.ts +2 -4
  160. package/dist/i18n/materials.js +1 -1
  161. package/dist/i18n/micro-resources.d.ts +2 -4
  162. package/dist/i18n/micro-resources.js +1 -1
  163. package/dist/i18n/module-families.d.ts +3 -5
  164. package/dist/i18n/module-families.js +1 -1
  165. package/dist/i18n/modules.d.ts +3 -6
  166. package/dist/i18n/modules.js +1 -1
  167. package/dist/i18n/personal-modifications.d.ts +4 -6
  168. package/dist/i18n/personal-modifications.js +1 -1
  169. package/dist/i18n/personal-tools.d.ts +33 -0
  170. package/dist/i18n/personal-tools.js +1 -0
  171. package/dist/i18n/personal-tools.js.map +1 -0
  172. package/dist/i18n/personal-weapons.d.ts +3 -4
  173. package/dist/i18n/personal-weapons.js +1 -1
  174. package/dist/i18n/pre-engineered.d.ts +1 -1
  175. package/dist/i18n/slots.d.ts +2 -2
  176. package/dist/i18n/suits.d.ts +36 -6
  177. package/dist/i18n/suits.js +1 -1
  178. package/dist/materials/index.d.ts +4 -3
  179. package/dist/materials/index.js +1 -1
  180. package/dist/materials/materials-all.d.ts +2 -2
  181. package/dist/materials/materials-all.js +1 -1
  182. package/dist/materials/materials-raw.d.ts +3 -4
  183. package/dist/materials/materials-raw.js +1 -1
  184. package/dist/materials/materials.d.ts +18 -15
  185. package/dist/materials/materials.js +1 -1
  186. package/dist/materials/micro-resources-all.d.ts +2 -2
  187. package/dist/materials/micro-resources-all.js +1 -1
  188. package/dist/materials/micro-resources-component.d.ts +2 -2
  189. package/dist/materials/micro-resources-consumable.d.ts +2 -2
  190. package/dist/materials/micro-resources-data.d.ts +2 -2
  191. package/dist/materials/micro-resources-item.d.ts +2 -2
  192. package/dist/materials/micro-resources.d.ts +17 -14
  193. package/dist/materials/micro-resources.js +1 -1
  194. package/dist/ships/ammunition.d.ts +4 -4
  195. package/dist/ships/blueprint-costs.d.ts +13 -13
  196. package/dist/ships/blueprint-costs.js +1 -1
  197. package/dist/ships/blueprint-journal.d.ts +3 -3
  198. package/dist/ships/blueprint-journal.js +1 -1
  199. package/dist/ships/blueprints.d.ts +3 -3
  200. package/dist/ships/build-metrics.d.ts +2 -1
  201. package/dist/ships/build-metrics.js +1 -1
  202. package/dist/ships/default-loadouts.d.ts +2 -3
  203. package/dist/ships/default-loadouts.js +1 -1
  204. package/dist/ships/engineering-options.d.ts +29 -32
  205. package/dist/ships/engineering-options.js +1 -1
  206. package/dist/ships/engineering.d.ts +1 -2
  207. package/dist/ships/engineering.js +1 -1
  208. package/dist/ships/experimental-effect-costs.d.ts +1 -1
  209. package/dist/ships/gunsights.d.ts +3 -3
  210. package/dist/ships/heat.d.ts +1 -1
  211. package/dist/ships/index.d.ts +4 -5
  212. package/dist/ships/index.js +1 -1
  213. package/dist/ships/loadout-validation.d.ts +1 -1
  214. package/dist/ships/module-families.d.ts +1 -1
  215. package/dist/ships/modules-all.d.ts +2 -3
  216. package/dist/ships/modules-all.js +1 -1
  217. package/dist/ships/modules-core.d.ts +3 -3
  218. package/dist/ships/modules-hardpoint.d.ts +4 -5
  219. package/dist/ships/modules-hardpoint.js +1 -1
  220. package/dist/ships/modules-internal.d.ts +5 -6
  221. package/dist/ships/modules-internal.js +1 -1
  222. package/dist/ships/modules-utility.d.ts +3 -4
  223. package/dist/ships/modules-utility.js +1 -1
  224. package/dist/ships/modules.d.ts +26 -24
  225. package/dist/ships/modules.js +1 -1
  226. package/dist/ships/pre-engineered-stats.d.ts +1 -1
  227. package/dist/ships/pre-engineered-stats.js +1 -1
  228. package/dist/ships/pre-engineered.d.ts +9 -10
  229. package/dist/ships/pre-engineered.js +1 -1
  230. package/dist/ships/shield-capacitor.js +1 -1
  231. package/dist/ships/ship-loadout.d.ts +7 -7
  232. package/dist/ships/ship-loadout.js +1 -1
  233. package/dist/ships/ships.d.ts +1 -2
  234. package/dist/ships/ships.js +1 -1
  235. package/dist/ships/slots.d.ts +5 -5
  236. package/dist/ships/weapons.js +1 -1
  237. package/dist/suits-B4sQMLFe.d.ts +450 -0
  238. package/dist/{system-address-cyJaeZIS.d.ts → system-address-DmzXRD48.d.ts} +6 -4
  239. package/package.json +13 -1
  240. package/dist/chunk-77TT4K53.js +0 -1
  241. package/dist/chunk-DAQ3PJ4R.js +0 -1
  242. package/dist/chunk-DAQ3PJ4R.js.map +0 -1
  243. package/dist/chunk-DHACRCLI.js +0 -1
  244. package/dist/chunk-DHACRCLI.js.map +0 -1
  245. package/dist/chunk-FJIWJYKO.js.map +0 -1
  246. package/dist/chunk-GIGRBFIJ.js +0 -1
  247. package/dist/chunk-IUSMAX5T.js +0 -1
  248. package/dist/chunk-IUSMAX5T.js.map +0 -1
  249. package/dist/chunk-LWNBWRKL.js +0 -1
  250. package/dist/chunk-LWNBWRKL.js.map +0 -1
  251. package/dist/chunk-MT5AHPNP.js +0 -1
  252. package/dist/chunk-MT5AHPNP.js.map +0 -1
  253. package/dist/chunk-QJECDMQQ.js +0 -1
  254. package/dist/chunk-YJAH6DFY.js.map +0 -1
  255. /package/dist/{chunk-XSLPWM5N.js.map → chunk-2J6NNI3Y.js.map} +0 -0
  256. /package/dist/{chunk-DWRNXUAX.js.map → chunk-2KIZN3BY.js.map} +0 -0
  257. /package/dist/{chunk-J7BM5NGK.js.map → chunk-2TY42PTF.js.map} +0 -0
  258. /package/dist/{chunk-KBCA4GEZ.js.map → chunk-FP2TQJZP.js.map} +0 -0
  259. /package/dist/{chunk-ETWMPMZP.js.map → chunk-K5JK3XQB.js.map} +0 -0
  260. /package/dist/{chunk-3WGXGBW5.js.map → chunk-R2AEZYX7.js.map} +0 -0
  261. /package/dist/{chunk-77TT4K53.js.map → chunk-SFEQXUIA.js.map} +0 -0
  262. /package/dist/{chunk-7TVFV3VO.js.map → chunk-U3IRMXMR.js.map} +0 -0
  263. /package/dist/{chunk-7ATBEOVC.js.map → chunk-WG4DPXJI.js.map} +0 -0
@@ -24,9 +24,9 @@
24
24
 
25
25
  ## Nebulae
26
26
 
27
- - **Files:** `nebulae-real.jsonc` (180 catalogued real-world nebulae and dark regions),
28
- `nebulae-procgen.jsonc` (166 procedurally generated nebulae) and
29
- `nebulae-planetary.jsonc` (5489 planetary nebulae), split by class.
27
+ - **Files:** `nebulae-real.jsonc` (catalogued real-world nebulae and dark regions),
28
+ `nebulae-procgen.jsonc` (procedurally generated nebulae) and
29
+ `nebulae-planetary.jsonc` (planetary nebulae), split by class.
30
30
  - **Source:** the EDAstro nebulae coordinates dataset (`nebulae-coordinates.csv`, columns
31
31
  `Name,System,X,Y,Z,Type,RegionID`). Original observations are community exploration
32
32
  data.
@@ -36,10 +36,10 @@
36
36
  - **Derivation:** records retain their name, catalogued system, galactic X/Y/Z in
37
37
  light-years with Sol at the origin, class and region id. They are grouped by `type`
38
38
  into one file per class and sorted by name; the class is represented by that file and
39
- is not repeated on every record. In the planetary file, `system` is omitted for the
40
- 5210 records where it is identical to `name`; all 279 differing systems remain.
39
+ is not repeated on every record. In the planetary file, `system` is omitted where it
40
+ is identical to `name`; every differing system remains.
41
41
  `regionId` is the galactic codex region id from the source CSV — a column the
42
- canonn-signals JSON drops — and all 5835 values were verified to agree with this
42
+ canonn-signals JSON drops — and every value was verified to agree with this
43
43
  project's own codex-region lookup.
44
44
  - **Caveat:** a nebula is a volume, but the dataset records a single point — the position
45
45
  of the system it is catalogued at.
@@ -52,18 +52,19 @@
52
52
  permit flag), so the list is hand-maintained by the community and is best-effort.
53
53
  - **Obtained via:** canonn-signals, `src/app/data/permit-locked-systems.ts`, which
54
54
  transcribes the sheet into two arrays.
55
- - **Derivation:** the 54 exact system names are carried over unchanged and sorted
56
- case-insensitively. Permit state is split by lookup domain. The 28 region entries are
55
+ - **Derivation:** the exact system names are carried over unchanged and sorted
56
+ case-insensitively. Permit state is split by lookup domain. The region entries are
57
57
  names of regions in
58
58
  `hand-authored-regions.jsonc`, which stores their spheres and nothing about permits.
59
59
  Each name doubles as the matching prefix, because the game names every system in a
60
60
  region after it (`Col 70 Sector AA-D b17-0`). The upstream list matches 19 lower-cased
61
61
  stems instead; the two agree except for the digit-suffixed regions, which the region
62
62
  names resolve exactly.
63
- - **System addresses:** `id64` comes from Spansh for 53 of the 54, cross-checked against
64
- EDSM for the 38 EDSM holds, with no disagreement in address or coordinates. The
65
- remaining 16 are absent from EDSM entirely, which is expected of systems no commander
66
- can enter to report. `Plaa Ain HA-Z d46` is in neither service; it is procedurally
63
+ - **System addresses:** `id64` comes from Spansh for every system but one, cross-checked
64
+ against EDSM wherever EDSM holds the system, with no disagreement in address or
65
+ coordinates. EDSM holds no entry at all for the rest — expected of systems no commander
66
+ can enter to report so their addresses rest on Spansh alone, with one exception.
67
+ `Plaa Ain HA-Z d46` is in neither service; it is procedurally
67
68
  named, so its address is encoded by this project's own procedural system encoder, whose
68
69
  output was confirmed against Spansh on the other two procedural entries in the list
69
70
  (`Dryio Flyuae IC-B c1-377`, `Scheau Bli NB-O d6-1409`). Values are stored as decimal
@@ -1,12 +1,14 @@
1
1
  # Data sources — `data/commodities/`
2
2
 
3
3
  **Acquired:** FDevIDs 2026-07-24 UTC; player-journal record 2026-08-02 UTC; in-game
4
- category verification 2026-08-12 UTC. **Upstream revision:** unavailable. One record
5
- combines the latter two sources, documented under Standard commodities.
4
+ category verification 2026-08-12 and 2026-09-03 UTC; in-game commodity registry
5
+ 2026-08-02 and 2026-09-03 UTC. **Upstream revision:** unavailable. One record combines
6
+ the journal and in-game sources, and the difference between the two registry readings
7
+ supplies the tail; both are documented under Standard commodities.
6
8
 
7
9
  ## Standard commodities
8
10
 
9
- - **File:** `commodities.jsonc` (257 tradable goods).
11
+ - **File:** `commodities.jsonc` (the tradable goods).
10
12
  - **Source:** EDCD FDevIDs, `commodity.csv` (columns `id,symbol,category,name`).
11
13
  - **Derivation:** records are carried over in registry order as
12
14
  `{ symbol, name, category }`. `symbol` is Frontier's internal id as the market and
@@ -22,14 +24,56 @@ combines the latter two sources, documented under Standard commodities.
22
24
  `symbol` (`Type`) and `name` (`Type_Localised`) verbatim. A `MarketBuy` carries **no
23
25
  category**; `Industrial Materials` is separately observed in the running game's commodity
24
26
  market (2026-08-12 UTC; no immutable revision). The record is appended after the registry
25
- order rather than inserted into it, so FDevIDs order is still recoverable by dropping the
26
- tail. Standard rather than rare: a `MarketBuy` of 388 units far exceeds any rare's
27
+ order rather than inserted into it, so FDevIDs order is still recoverable by dropping
28
+ it and every record after it. Standard rather than rare: a `MarketBuy` of 388 units far exceeds any rare's
27
29
  per-station allocation. The event's `Count`, `BuyPrice`, `TotalCost` and `MarketID` are
28
30
  dropped — this is an id/name/category registry, not a price sheet.
29
31
 
32
+ ### The tail, from the running game's own commodity registry
33
+
34
+ The game defines more commodity units than the FDevIDs snapshot carries. The registry is
35
+ read from the running game (2026-09-03 UTC; the game publishes no immutable identifier
36
+ for it, so the observation is the evidence) and compared against an earlier reading of
37
+ the same registry (2026-08-02 UTC). **The units the registry gained between the two
38
+ readings are appended, in symbol order, after `curatedcommodity`**: `Bastnasite`,
39
+ `Deuterium`, `Diamond`, `Helium`, `Helium3`, `Iridium`, `Magnesite`, `Olivine`,
40
+ `PericlaseDunite`, `QuartzPyroxenite`, `Ruby`, `Sapphire` and `Thortveitite`.
41
+
42
+ - **The symbol and the English name are the registry's**, and the name comes from the
43
+ same in-game localisation table that `data/i18n/commodity-names.jsonc` is derived from,
44
+ so an appended record's `name` and its English localized name are one string by
45
+ construction.
46
+ - **The category is separately verified in the running game** (2026-09-03 UTC; no
47
+ immutable revision), exactly as `curatedcommodity`'s is. The registry names a unit and
48
+ its display name and does not say which market group it belongs to. Every one of these is
49
+ `Minerals` except `Helium` and `Helium3`, which are `Chemicals`.
50
+ - **They are stored as standard, not rare.** The registry's English description marks a
51
+ rare good with the phrase "This rare good". No appended unit carries the marker, no
52
+ appended unit appears in FDevIDs' `rare_commodity.csv`, and every unit the marker does
53
+ name is already in `rare-commodities.jsonc`. The marker alone would be weak evidence,
54
+ because its absence does not make a good standard: five records the rare catalogue
55
+ holds — `GalacticTravelGuide`, `Nanomedicines`, `Duradrives`, `ApaVietii` and
56
+ `ClassifiedExperimentalEquipment` — are described without the phrase and keep their
57
+ place, because the CSV lists them. Here every source is silent together.
58
+ - **The units both readings already held are deliberately not carried.** The registry
59
+ has long held goods no market lists — powerplay cargo, mission and event freight, and
60
+ legacy units such as `Wood`, `Ceramics` and `Anthracene`. They are not a change the
61
+ game made, and carrying them is a separate decision about how wide this catalogue
62
+ reaches rather than a currency update. What would carry them is that decision plus a
63
+ category for each, not a new source: the same observation already names them.
64
+ - **Units the game names in no language stay out in any case.** The registry holds units
65
+ whose localisation entry is empty in all six languages — `Advert2`,
66
+ `BacteriostaticAgents`, `NvidiaTitanBlack` and others of that kind. A record needs a
67
+ display name, and the only string available for these is the internal symbol, which is
68
+ not a name. All of them predate this observation, so the rule above already excludes
69
+ them; it stands as the second reason.
70
+ - **Appending rather than inserting keeps every earlier order recoverable**, exactly as
71
+ the `curatedcommodity` record does: drop these records and the order that preceded
72
+ them remains, and drop `curatedcommodity` as well and the FDevIDs order remains.
73
+
30
74
  ## Rare commodities
31
75
 
32
- - **File:** `rare-commodities.jsonc` (142 location-specific luxury goods).
76
+ - **File:** `rare-commodities.jsonc` (the location-specific luxury goods).
33
77
  - **Source:** EDCD FDevIDs, `rare_commodity.csv` (columns
34
78
  `id,symbol,market_id,category,name`).
35
79
  - **Derivation:** records are carried over in registry order as
@@ -8,19 +8,21 @@ Referred to throughout by source name; the pin is here, once.
8
8
  | ------------------------------------------------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------- | -------------- |
9
9
  | Odyssey Materials Helper | commit `2e6d4c3e767d2b714ffddc5c9386831d66812916` (2026-08-09), the last revision before the project extracted its core data into a separately distributed dependency | 2026-08-13 UTC |
10
10
  | Frontier Elite Dangerous Gamestore | no immutable revision; the displayed weapon names were read on the acquisition date | 2026-08-13 UTC |
11
- | Elite Dangerous in-game observation | no game version recorded; direct reading of the suit and weapon stats panels, the sight magnification they show, and the on-foot engineering options | 2026-08-31 UTC |
11
+ | Elite Dangerous in-game observation | no game version recorded; direct reading of the suit and weapon stats panels, the sight magnification they show, and the on-foot engineering options, and direct observation of what a suit's two defensive layers resist and of what a weapon does when it is fired | panels 2026-08-31 UTC; firing behaviour 2026-09-03 UTC; suit shield resistances 2026-09-04 UTC |
12
+ | EDCD/EDMarketConnector | commit `2b6a0ce1ee3ba60c21f3f4e9fa093046da8825e4` (2026-07-26); `monitor.py` sha256 `800720e04e3089ee9a4b57749de56061e8d31ba877e17f1420f994c52bac08ac` | 2026-09-02 UTC |
12
13
 
13
14
  **Where a source and the game disagree, the in-game reading governs.** Odyssey Materials Helper
14
15
  supplies the identities, the slot and grade structure, the engineer availability and
15
- every material shopping list; the stat values are the ones the game itself shows.
16
+ every material shopping list; the stat values are the ones the game itself shows,
17
+ except where a derivation bullet below names the source that supplies one.
16
18
 
17
19
  ## Personal suits, handheld weapons and engineering
18
20
 
19
- - **Files:** `suits.jsonc`, `weapons.jsonc`, `upgrade-costs.jsonc`,
21
+ - **Files:** `suits.jsonc`, `weapons.jsonc`, `tools.jsonc`, `upgrade-costs.jsonc`,
20
22
  `modifications.jsonc`, `modification-costs.jsonc`,
21
23
  `modification-journal-names.jsonc`.
22
24
  - **Derivation:**
23
- - `Suit.java` supplies the four suit families, journal symbols, weapon-slot counts and
25
+ - `Suit.java` supplies the four suit families, journal symbols, weapon-mount counts and
24
26
  the grade-dependent modification slots, shield strength and shield regeneration.
25
27
  English suit display names come from
26
28
  `application/src/main/resources/locale/loadout/equipment.csv`. `family` removes
@@ -40,6 +42,14 @@ every material shopping list; the stat values are the ones the game itself shows
40
42
  `4_5` to their target grades `2` / `3` / `4` / `5`. Weapon upgrade families retain
41
43
  the source's `karma`, `takada` and `manticore` identities; `engineeringType` separately
42
44
  records the `kinetic`, `laser` or `plasma` suffix used by modification recipes.
45
+ - `Suit.java`, `StaticStat.java` and `DynamicStat.java` supply the Energylink, the
46
+ Profile Analyser, the Arc Cutter and the Genetic Sampler.
47
+ The source models a tool as a suit stat rather than as an item, and that is what
48
+ supplies the availability: the Arc Cutter figure appears on `MAVERICK` only, the
49
+ Genetic Sampler figure on `ARTEMIS` only, and the Energylink and Profile Analyser
50
+ figures sit in the shared `genericStats` list. `suitFamilies` therefore holds
51
+ `utilitysuit` for the Arc Cutter, `explorationsuit` for the Genetic Sampler, and all
52
+ four suit families for the other two.
43
53
  - `SuitModification.java` and `WeaponModification.java` supply the journal symbols.
44
54
  English engineer names come from
45
55
  `application/src/main/resources/locale/engineer/names.csv`. A recipe is keyed by its
@@ -49,14 +59,28 @@ every material shopping list; the stat values are the ones the game itself shows
49
59
  `modification-journal-names.jsonc` records that collision once for resolution against
50
60
  the weapon. `modification-costs.jsonc` is split from recipe metadata so an identity
51
61
  lookup does not bundle every shopping list, matching the ships engineering boundary.
52
- - **In-game observation supplies every stat value** described in the three sections
53
- below: the suit-wide component stats and the four resistances, the weapon combat
54
- stats and damage, and the multipliers each modification applies.
62
+ - **`mounts` carries Frontier's own journal `SlotName` for each weapon mount.**
63
+ EDMarketConnector's `monitor.py` quotes verbatim `SuitLoadout`, `CreateSuitLoadout`,
64
+ `SwitchSuitLoadout`, `LoadoutEquipModule` and `LoadoutRemoveModule` events in its
65
+ comments; those are Frontier game output rather than that project's own code. They
66
+ give `PrimaryWeapon1` and `SecondaryWeapon` on `utilitysuit_class1`, and
67
+ `PrimaryWeapon1`, `PrimaryWeapon2` and `SecondaryWeapon` on `tacticalsuit_class1`.
68
+ **The secondary mount carries no number**: the game writes `SecondaryWeapon`, not
69
+ `SecondaryWeapon1`. Each suit's mount list is the weapon-mount counts this catalogue
70
+ already held, joined to those keys, primary mounts first and numbered from 1.
71
+ - **In-game observation supplies the stat values** in the suit, weapon and
72
+ modification sections below: the suit-wide component stats and both resistance sets,
73
+ the weapon combat stats and damage, and the multipliers each modification applies.
74
+ The reload times are the exception: the panel shows no reload figure, so
75
+ `Weapon.java` supplies them. The tool figures are Odyssey Materials Helper's,
76
+ converted as the suit-tool section states.
55
77
 
56
78
  - **Manual corrections:**
57
79
  - Odyssey Materials Helper's English locale calls the four Karma weapons “Kinematic”
58
80
  and expands the three TK weapon names to “Takada”. The Frontier Elite Dangerous
59
81
  Gamestore confirms the in-game prefixes are `Karma` and `TK`, which are stored here.
82
+ - Odyssey Materials Helper calls the Profile Analyser the “profile scanner”. The
83
+ in-game name is `Profile Analyser`, which is stored here.
60
84
  - Frontier's misspelled `surveilleancelogs` symbol is kept verbatim so it joins to
61
85
  journal inventory data and the micro-resource catalogue.
62
86
  - Three modification display names are the in-game text rather than the source's:
@@ -67,7 +91,7 @@ every material shopping list; the stat values are the ones the game itself shows
67
91
 
68
92
  ### Suit stats read in-game
69
93
 
70
- The suit stats panel is read per suit family and per grade.
94
+ The suit stats are read per suit family and per grade.
71
95
 
72
96
  - **Suit-wide, identical at all five grades**, so they are stored once per family rather
73
97
  than per grade: `health` (30 on every suit), `mass` (100 kg on every suit),
@@ -75,32 +99,73 @@ The suit stats panel is read per suit family and per grade.
75
99
  `boostAcceleration` for the jump assist, the three backpack capacities
76
100
  (`goodsCapacity`, `assetsCapacity`, `dataCapacity`), `footstepAudibleRange` as a
77
101
  multiplier of the base audible range (1 on every suit), `losAnalysisRange` in metres
78
- (50 on every suit) and `losAnalysisTime` in seconds (1 on every suit). The constant
79
- ones are stored anyway: a suit-stats view reads them like any other field, and a value
80
- that is the same everywhere is still the value.
81
- - **Resistances are stored as fractions** (`0.5` means half the damage taken),
82
- matching the ships domain. The panel's own figure is the same fraction as a
83
- percentage, so a negative resistance is a weakness. Every resistance is now the
84
- panel's, which corrects nine grade rows against Odyssey Materials Helper:
102
+ (50 on every suit) and `losAnalysisTime` in seconds (1 on every suit), plus the four
103
+ shield resistances described below. The constant ones are stored anyway: a suit-stats
104
+ view reads them like any other field, and a value that is the same everywhere is still
105
+ the value.
106
+ - **A suit defends in two layers, and each layer has its own four resistances.** The
107
+ shield takes the damage first, and the armour takes what gets through. The two sets are
108
+ therefore stored separately, and each names the layer that has it. Damage Resistance is
109
+ the armour's modification: it moves the armour set and leaves the shield set alone.
110
+ Frontier's own symbol for it, `suit_improvedarmourrating`, is the evidence for that.
111
+ - **Both sets are stored as fractions** (`0.5` means half the damage taken), matching
112
+ the ships domain, and a negative value is a weakness.
113
+ - **The armour resistances are the four the suit panel shows.** The panel gives each one
114
+ as a percentage; the catalogue stores the same figure as a fraction. Every one is the
115
+ panel's figure, which corrects nine grade rows against Odyssey Materials Helper:
85
116
 
86
117
  | Suit and grade | Field → stored value |
87
118
  | ------------------- | ------------------------------------------------------------------------- |
88
- | Artemis 1 | `thermalResistance` 0.39→0.4 |
89
- | Artemis 2 | `kineticResistance` -0.42→-0.43; `plasmaResistance` 0→-0.01 |
90
- | Artemis 3 | `plasmaResistance` 0.14→0.15 |
91
- | Artemis 5 | `kineticResistance` 0.14→0.15; `plasmaResistance` 0.39→0.4 |
92
- | Flight Suit | `thermalResistance` 0.39→0.4 |
93
- | Dominator 4 | `kineticResistance` 0.19→0.11; `thermalResistance` 0.78→0.76; `plasmaResistance` 0.46→0.41; `explosiveResistance` 0.46→0.41 |
94
- | Maverick 2 | `plasmaResistance` 0.07→0.08 |
95
- | Maverick 3 | `kineticResistance` -0.13→-0.14 |
96
- | Maverick 5 | `kineticResistance` 0.19→0.2 |
97
-
98
- - **Shield strength and shield regeneration are unchanged.** Every stored value already
99
- matches the panel, which is also why the resistance disagreements are read as source
100
- rounding rather than as a different snapshot of the game.
101
- - **A grade changes the armour, the shield generator, the modification slots and the
102
- item symbol.** Nothing else on a suit moves with the grade, which is what makes the
103
- suit-wide fields safe to store once per family.
119
+ | Artemis 1 | `armourThermalResistance` 0.39→0.4 |
120
+ | Artemis 2 | `armourKineticResistance` -0.42→-0.43; `armourPlasmaResistance` 0→-0.01 |
121
+ | Artemis 3 | `armourPlasmaResistance` 0.14→0.15 |
122
+ | Artemis 5 | `armourKineticResistance` 0.14→0.15; `armourPlasmaResistance` 0.39→0.4 |
123
+ | Flight Suit | `armourThermalResistance` 0.39→0.4 |
124
+ | Dominator 4 | `armourKineticResistance` 0.19→0.11; `armourThermalResistance` 0.78→0.76; `armourPlasmaResistance` 0.46→0.41; `armourExplosiveResistance` 0.46→0.41 |
125
+ | Maverick 2 | `armourPlasmaResistance` 0.07→0.08 |
126
+ | Maverick 3 | `armourKineticResistance` -0.13→-0.14 |
127
+ | Maverick 5 | `armourKineticResistance` 0.19→0.2 |
128
+
129
+ - **The shield resistances are 0.6 kinetic, -0.5 thermal, 0 plasma and 0.5 explosive.**
130
+ The suit panel puts no figure on them. Each one is observed in-game as the multiplier
131
+ the shield applies to that damage type. A resistance is `1 −` that multiplier. Every
132
+ suit carries the same four multipliers at every grade. Reading each suit at each grade
133
+ establishes that.
134
+ - **Shield strength and shield regeneration match the panel.** That agreement is also why
135
+ the armour-resistance disagreements above are read as source rounding rather than as a
136
+ different snapshot of the game.
137
+ - **A grade changes the armour resistances, the shield's strength and regeneration, the
138
+ modification slots and the item symbol.** Nothing else on a suit changes with the
139
+ grade, which is what makes the suit-wide fields safe to store once per family.
140
+
141
+ ### Suit tools
142
+
143
+ - **A tool has no Frontier symbol, so `id` is this library's own key.** Odyssey Materials
144
+ Helper models the tools as suit stats and its English locale table has no tool row. The
145
+ game's own localisation table does name each tool, under an internal identity no
146
+ journal field carries: a
147
+ `SuitLoadout` names the suit and its weapon mounts only, and a `BackpackChange` reports
148
+ consumables, components, data and goods moving in and out of the backpack, never a
149
+ tool. Each `id` is the English name in lower case — `energylink`, `profile-analyser`,
150
+ `arc-cutter`, `genetic-sampler` — and joins to no journal field.
151
+ - **Every power figure is normalised to MW, the unit `Suit.batteryCapacity` uses**, so a
152
+ suit's battery divided by a tool's per-second drain is seconds of use. The source's
153
+ 600 kW/s Energylink discharge rate is stored as `0.6`, and its 40, 150 and 450 kW/s
154
+ power usages as `0.04`, `0.15` and `0.45`. The Energylink's 2.7 MW/s recharge rate and
155
+ its 3.0 MW overload cost are already in MW and are stored as the source holds them.
156
+ Durations stay in seconds.
157
+ - **The tools take no grade.** The source holds one figure per stat with no grade or
158
+ class axis, and Pioneer Supplies sells no tool, so a tool record carries no `grades`
159
+ field at all rather than a single-entry one.
160
+ - **Reduced Tool Battery Consumption halves `powerUsage` and the Energylink's
161
+ `overloadPowerUsage`**, and leaves the Energylink's discharge rate alone: the source
162
+ holds that rate as a static stat and applies no factor to it. The two are stored under
163
+ separate names for exactly that reason.
164
+ - **A third modification target is rejected.** The question is whether a tool takes
165
+ modifications of its own. It does not: Reduced Tool Battery Consumption is a suit
166
+ modification, offered by the suit engineers and installed in a suit modification slot,
167
+ and no other recipe touches a tool. `target` therefore stays `suit`, and adding a
168
+ `tool` value would state something the game does not do.
104
169
 
105
170
  ### Weapon stats read in-game
106
171
 
@@ -114,13 +179,26 @@ The suit stats panel is read per suit family and per grade.
114
179
  a stock suit carries, before the Extra Ammo Capacity modification.
115
180
  - **Magazine size, effective range, class, slot, damage type and headshot multiplier**
116
181
  are unchanged: every one already matches the panel.
182
+ - **`projectiles` holds the projectiles one round fires**, observed as the
183
+ weapon fires. Only `Manticore Intimidator` carries it, with 10: its round is a shotgun
184
+ shell, and each pellet does the full grade damage. The shot spends one round, not ten,
185
+ so its magazine of 2 is 2 shots. Every other weapon fires one projectile per round and
186
+ stores no `projectiles`.
187
+ - **`burstRounds` and `burstRateOfFire` hold the burst shape**, observed as the weapon
188
+ fires. `TK Zenith` is the only weapon with `fireMode` `burst`. One trigger pull fires
189
+ 3 rounds. A burst fires 12 rounds a second. The two fields are stored together, and
190
+ every other weapon stores neither.
191
+ - **`rateOfFire` counts trigger pulls**, which is what the panel shows for the Zenith:
192
+ 2.78 bursts a second. Every other weapon fires one round per trigger pull, so for
193
+ those the two readings are the same figure.
117
194
  - **Damage** is the grade-1 figure read in-game, times the grade multiplier the game
118
195
  applies to it — `1`, `1.31`, `1.73`, `2.27`, `2.98` for grades 1 to 5. Each product is
119
196
  taken in double-precision floating point and rounded to three decimals, as
120
- `Number(x.toFixed(3))` does it; that reproduces all 55 stored figures exactly. The
121
- rounding rule has to be stated rather than assumed, because twelve products land on a
197
+ `Number(x.toFixed(3))` does it; that reproduces every stored figure exactly. The
198
+ rounding rule has to be stated rather than assumed, because some products land on a
122
199
  half and are therefore broken in both directions, and because scaling before rounding
123
- (`Math.round(x * 1000) / 1000`) re-introduces error and misses eight of the 55.
200
+ (`Math.round(x * 1000) / 1000`) re-introduces error and misses some of the stored
201
+ figures.
124
202
  - **The multipliers are what Odyssey Materials Helper's own figures follow.** On the four
125
203
  weapons whose grade-1 damage needed no correction — `Karma L-6`,
126
204
  `Manticore Executioner`, `Manticore Tormentor` and `Manticore Oppressor` — its grades 2
@@ -133,7 +211,16 @@ The suit stats panel is read per suit family and per grade.
133
211
  1.7→1.668 and `Manticore Intimidator` 1.8→1.75. Damage is stored at the precision the
134
212
  game reports it, which is why two of those grade-1 figures carry three decimals where
135
213
  the panel shows one.
136
- - **`scopeMagnification` is new**: the aim-down-sights magnification the panel shows with
214
+ - **`reloadTime` holds the seconds a reload takes**, stock and with the Reload Speed
215
+ modification fitted. The panel shows no reload figure, so there is nothing to read
216
+ these values against. Odyssey Materials Helper's `Weapon.java` carries the stock figure
217
+ as each weapon's `DynamicStat.RELOAD_SPEED` entry. The upgraded figure is the stock one
218
+ divided by the factor the same file's `DynamicStat.formatValue` applies: `1.20` for
219
+ `TK Aphelion` and `1.25` for every other weapon. Each quotient is taken in
220
+ double-precision floating point and rounded to three decimals, as
221
+ `Number(x.toFixed(3))` does it. Reload Speed stores no modifier of its own because the
222
+ factor differs per weapon.
223
+ - **`scopeMagnification` holds the aim-down-sights magnification** the panel shows with
137
224
  the sight the weapon ships with, and with the sight the Scope modification fits, both
138
225
  to two decimals. Scope stores no modifier of its own because its magnitude is this
139
226
  pair, and it differs per weapon — `Manticore Executioner` gains 1.61x→3.75x where
@@ -152,19 +239,24 @@ that changes nothing — is never stored.
152
239
  like every other modifier.
153
240
  - **A resistance factor multiplies the damage taken**, not the stored resistance
154
241
  fraction. Damage Resistance is `×0.9` on damage taken, so a `0.5` resistance becomes
155
- `0.55`. This is the same convention the ships domain uses for resistances.
242
+ `0.55`. This is the same convention the ships domain uses for resistances. Damage
243
+ Resistance's four factors name the armour stats, because that is the layer it moves. No
244
+ recipe moves a shield resistance.
156
245
  - **`roundUp` marks the one result the game rounds up**: Magazine Size multiplies by 1.5
157
246
  and rounds the magazine up to a whole number, so 45 rounds become 68 rather than 67.5.
158
- - **Six recipes name a stat no catalogue field carries**, because the panel shows no
159
- base for it: the melee damage, sprint duration and tool energy drain multipliers, the
160
- reload speed, and the pressurised and unpressurised firing audible ranges. The factor
161
- is recorded against the stat it moves; the base has to come from the panel.
162
- - **Ten recipes carry an empty modifier list**, for two different reasons, and both are
247
+ - **Some recipes name a stat no catalogue field carries**, because the panel shows no
248
+ base for it: the melee damage and sprint duration multipliers, and the pressurised and
249
+ unpressurised firing audible ranges. The factor is recorded against the stat it moves;
250
+ the base has to come from the panel. `toolEnergyDrain` names no field either, and its
251
+ bases are catalogued rather than panel-only: a tool's `powerUsage` and the Energylink's
252
+ `overloadPowerUsage` in `tools.jsonc`.
253
+ - **Some recipes carry an empty modifier list**, for two different reasons, and both are
163
254
  a statement rather than a gap:
164
- - Night Vision, Scope, Stowed reloading and Combat Movement Speed apply no factor to
165
- any stat. Night Vision and Stowed reloading switch a capability on, Scope's whole
166
- numeric effect is the weapon's own `scopeMagnification`, and Combat Movement Speed
167
- changes how a suit moves while aiming without moving a displayed stat.
255
+ - Night Vision, Scope, Reload Speed, Stowed reloading and Combat Movement Speed apply
256
+ no factor to any stat. Night Vision and Stowed reloading switch a capability on,
257
+ Scope's whole numeric effect is the weapon's own `scopeMagnification`, Reload
258
+ Speed's is the weapon's own `reloadTime`, and Combat Movement Speed changes how a
259
+ suit moves while aiming without moving a displayed stat.
168
260
  - Faster Handling, Improved Hip Fire Accuracy, Stability and Improved Jump Assist do
169
261
  change stats, but ones the panel puts no number on — weapon handling, hip-fire
170
262
  jitter and recoil, and the jump assist's boost drain and recharge. Improved Jump