mirror of
https://github.com/Sendouc/sendou.ink.git
synced 2026-10-01 23:58:36 -05:00
Add slosher class weapons damages
This commit is contained in:
@@ -25,10 +25,13 @@ export const DAMAGE_TYPE = [
|
||||
"NORMAL_MAX",
|
||||
"NORMAL_MAX_FULL_CHARGE", // Hydra Splatling goes from 32 to 40 dmg when fully charged
|
||||
"DIRECT",
|
||||
"DIRECT_MIN",
|
||||
"DIRECT_MAX",
|
||||
"FULL_CHARGE",
|
||||
"MAX_CHARGE",
|
||||
"TAP_SHOT",
|
||||
"DISTANCE",
|
||||
"SPLASH",
|
||||
"BOMB_NORMAL",
|
||||
"BOMB_DIRECT",
|
||||
] as const;
|
||||
@@ -41,10 +44,13 @@ export const damageTypeToWeaponType: Record<
|
||||
NORMAL_MAX: "MAIN",
|
||||
NORMAL_MAX_FULL_CHARGE: "MAIN",
|
||||
DIRECT: "MAIN",
|
||||
DIRECT_MIN: "MAIN",
|
||||
DIRECT_MAX: "MAIN",
|
||||
FULL_CHARGE: "MAIN",
|
||||
MAX_CHARGE: "MAIN",
|
||||
TAP_SHOT: "MAIN",
|
||||
DISTANCE: "MAIN",
|
||||
SPLASH: "MAIN",
|
||||
BOMB_NORMAL: "SUB",
|
||||
BOMB_DIRECT: "SUB",
|
||||
};
|
||||
@@ -135,12 +141,12 @@ export const objectDamageJsonKeyPriority: Record<
|
||||
Shooter: null,
|
||||
Skewer_Body: null,
|
||||
Skewer: null,
|
||||
Slosher_Bathtub: null,
|
||||
Slosher_Bear: null,
|
||||
Slosher_WashtubBombCore: null,
|
||||
Slosher_Washtub: null,
|
||||
Slosher: null,
|
||||
Spinner: ["NORMAL_MAX", "NORMAL_MIN", "NORMAL_MAX_FULL_CHARGE"],
|
||||
Slosher_Bathtub: ["DIRECT", "DIRECT_MAX", "DIRECT_MIN", "DISTANCE", "SPLASH"],
|
||||
Slosher_Bear: ["DIRECT", "DIRECT_MAX", "DIRECT_MIN", "DISTANCE", "SPLASH"],
|
||||
Slosher_WashtubBombCore: ["DIRECT", "DIRECT_MAX", "DIRECT_MIN"],
|
||||
Slosher_Washtub: ["DISTANCE", "SPLASH"],
|
||||
Slosher: ["DIRECT", "DIRECT_MAX", "DIRECT_MIN", "DISTANCE", "SPLASH"],
|
||||
Spinner: ["NORMAL_MAX", "NORMAL_MIN", "NORMAL_MAX_FULL_CHARGE", "SPLASH"],
|
||||
Sprinkler: null,
|
||||
Stringer_Short: null,
|
||||
Stringer: null,
|
||||
|
||||
@@ -82,6 +82,10 @@ const shotsToPopRM: Array<
|
||||
[2030, "TAP_SHOT", 13, 12],
|
||||
// Hydra Splatling
|
||||
[4020, "NORMAL_MAX", 32, 29],
|
||||
// Sloshing Machine
|
||||
[3020, "DIRECT_MAX", 6, 5],
|
||||
// Splat Dualies
|
||||
[5010, "NORMAL_MAX", 34, 31],
|
||||
];
|
||||
|
||||
CalculateDamage(
|
||||
|
||||
37
app/modules/analyzer/stats.test.ts
Normal file
37
app/modules/analyzer/stats.test.ts
Normal file
@@ -0,0 +1,37 @@
|
||||
import { suite } from "uvu";
|
||||
import * as assert from "uvu/assert";
|
||||
import { type MainWeaponId, mainWeaponIds } from "../in-game-lists";
|
||||
import { damageTypeToWeaponType } from "./constants";
|
||||
import { buildStats } from "./stats";
|
||||
|
||||
const AnalyzeBuild = suite("Analyze build");
|
||||
|
||||
// TODO: all weapons should have damage
|
||||
const weaponsWithoutDmg: MainWeaponId[] = [
|
||||
1000, 1010, 1020, 1030, 1100, 1110, 7010, 7020, 8000, 8010,
|
||||
];
|
||||
AnalyzeBuild("Every main weapon has damage", () => {
|
||||
const weaponsWithoutDamage: MainWeaponId[] = [];
|
||||
|
||||
for (const weaponSplId of mainWeaponIds) {
|
||||
const analyzed = buildStats({
|
||||
weaponSplId,
|
||||
});
|
||||
|
||||
const hasDamage =
|
||||
analyzed.stats.damages.filter(
|
||||
(dmg) => damageTypeToWeaponType[dmg.type] === "MAIN"
|
||||
).length > 0;
|
||||
|
||||
if (!hasDamage && !weaponsWithoutDmg.includes(weaponSplId)) {
|
||||
weaponsWithoutDamage.push(weaponSplId);
|
||||
}
|
||||
}
|
||||
|
||||
assert.ok(
|
||||
weaponsWithoutDamage.length === 0,
|
||||
`Weapons without damage set: ${weaponsWithoutDamage.join(", ")}`
|
||||
);
|
||||
});
|
||||
|
||||
AnalyzeBuild.run();
|
||||
@@ -343,7 +343,10 @@ const damageTypeToParamsKey: Record<
|
||||
NORMAL_MAX: "DamageParam_ValueMax",
|
||||
NORMAL_MAX_FULL_CHARGE: "DamageParam_ValueFullChargeMax",
|
||||
DIRECT: "DamageParam_ValueDirect",
|
||||
DIRECT_MIN: "DamageParam_ValueDirectMin",
|
||||
DIRECT_MAX: "DamageParam_ValueDirectMax",
|
||||
DISTANCE: "BlastParam_DistanceDamage",
|
||||
SPLASH: "BlastParam_SplashDamage",
|
||||
FULL_CHARGE: "DamageParam_ValueFullCharge",
|
||||
MAX_CHARGE: "DamageParam_ValueMaxCharge",
|
||||
TAP_SHOT: "DamageParam_ValueMinCharge",
|
||||
|
||||
@@ -35,6 +35,8 @@ export interface MainWeaponParams {
|
||||
DamageParam_ValueMin?: number;
|
||||
DamageParam_ValueFullChargeMax?: number;
|
||||
DamageParam_ValueDirect?: number;
|
||||
DamageParam_ValueDirectMax?: number;
|
||||
DamageParam_ValueDirectMin?: number;
|
||||
Jump_DegSwerve?: number;
|
||||
Stand_DegSwerve?: number;
|
||||
/** Damage caused by charger's full charged shot */
|
||||
@@ -43,6 +45,7 @@ export interface MainWeaponParams {
|
||||
DamageParam_ValueMaxCharge?: number;
|
||||
/** Charger tap shot damage */
|
||||
DamageParam_ValueMinCharge?: number;
|
||||
BlastParam_SplashDamage?: number;
|
||||
BlastParam_DistanceDamage?: Array<DistanceDamage>;
|
||||
// DamageParam_ReduceStartFrame?: number;
|
||||
// DamageParam_ReduceEndFrame?: number;
|
||||
|
||||
@@ -74,11 +74,14 @@ function validatedAbilityPointsFromSearchParams(searchParams: URLSearchParams) {
|
||||
}
|
||||
|
||||
export const damageTypePriorityList: Array<DamageType> = [
|
||||
"DIRECT_MAX",
|
||||
"DIRECT",
|
||||
"DIRECT_MIN",
|
||||
"FULL_CHARGE",
|
||||
"MAX_CHARGE",
|
||||
"NORMAL_MAX_FULL_CHARGE",
|
||||
"NORMAL_MIN",
|
||||
"SPLASH",
|
||||
"TAP_SHOT",
|
||||
"DISTANCE",
|
||||
"BOMB_DIRECT",
|
||||
|
||||
@@ -500,6 +500,8 @@
|
||||
"subWeaponId": 0,
|
||||
"specialWeaponId": 14,
|
||||
"MoveSpeed": 0.04,
|
||||
"DamageParam_ValueDirectMax": 700,
|
||||
"DamageParam_ValueDirectMin": 350,
|
||||
"InkRecoverStop": 40,
|
||||
"InkConsumeSlosher": 0.07
|
||||
},
|
||||
@@ -509,6 +511,8 @@
|
||||
"specialWeaponId": 10,
|
||||
"WeaponSpeedType": "Fast",
|
||||
"MoveSpeed": 0.066,
|
||||
"DamageParam_ValueDirectMax": 620,
|
||||
"DamageParam_ValueDirectMin": 350,
|
||||
"InkRecoverStop": 35,
|
||||
"InkConsumeSlosher": 0.06
|
||||
},
|
||||
@@ -517,6 +521,9 @@
|
||||
"subWeaponId": 5,
|
||||
"specialWeaponId": 6,
|
||||
"MoveSpeed": 0.07,
|
||||
"DamageParam_ValueDirectMax": 760,
|
||||
"DamageParam_ValueDirectMin": 520,
|
||||
"BlastParam_SplashDamage": 380,
|
||||
"InkRecoverStop": 42,
|
||||
"InkConsumeSlosher": 0.084
|
||||
},
|
||||
@@ -525,6 +532,7 @@
|
||||
"subWeaponId": 3,
|
||||
"specialWeaponId": 5,
|
||||
"MoveSpeed": 0.05,
|
||||
"DamageParam_ValueDirect": 300,
|
||||
"InkRecoverStop": 40,
|
||||
"InkConsumeSlosher": 0.08
|
||||
},
|
||||
@@ -534,6 +542,13 @@
|
||||
"specialWeaponId": 5,
|
||||
"WeaponSpeedType": "Slow",
|
||||
"MoveSpeed": 0.045,
|
||||
"DamageParam_ValueDirect": 550,
|
||||
"BlastParam_DistanceDamage": [
|
||||
{
|
||||
"Damage": 350,
|
||||
"Distance": 2.8
|
||||
}
|
||||
],
|
||||
"InkRecoverStop": 70,
|
||||
"InkConsumeSlosher": 0.117
|
||||
},
|
||||
|
||||
@@ -86,6 +86,7 @@
|
||||
"damage.MAX_CHARGE": "Maksimal skade fra en delvis opladning",
|
||||
"damage.TAP_SHOT": "Uopladt skud",
|
||||
"damage.DISTANCE": "eksplosionsradius",
|
||||
"damage.SPLASH": "eksplosionsradius",
|
||||
"suffix.seconds": "s",
|
||||
"suffix.hp": "HP",
|
||||
"suffix.specialPointsShort": "p",
|
||||
|
||||
@@ -82,6 +82,7 @@
|
||||
"damage.MAX_CHARGE": "Maximum teilweiser Aufladung",
|
||||
"damage.TAP_SHOT": "Tap-Schuss",
|
||||
"damage.DISTANCE": "Schuss",
|
||||
"damage.SPLASH": "Schuss",
|
||||
"suffix.seconds": "s",
|
||||
"suffix.hp": "hp",
|
||||
"suffix.specialPointsShort": "p",
|
||||
|
||||
@@ -82,10 +82,13 @@
|
||||
"damage.NORMAL_MAX": "Maximum",
|
||||
"damage.NORMAL_MAX_FULL_CHARGE": "Maximum (Fully charged)",
|
||||
"damage.DIRECT": "Direct",
|
||||
"damage.DIRECT_MIN": "Direct (Minimum)",
|
||||
"damage.DIRECT_MAX": "Direct (Maximum)",
|
||||
"damage.FULL_CHARGE": "Fully charged shot",
|
||||
"damage.MAX_CHARGE": "Maximum partial charge",
|
||||
"damage.TAP_SHOT": "Tap shot",
|
||||
"damage.DISTANCE": "Splash",
|
||||
"damage.SPLASH": "Splash",
|
||||
"suffix.seconds": "s",
|
||||
"suffix.hp": "hp",
|
||||
"suffix.specialPointsShort": "p",
|
||||
|
||||
@@ -79,6 +79,7 @@
|
||||
"damage.MAX_CHARGE": "Carga parcial máxima",
|
||||
"damage.TAP_SHOT": "Disparo rapido",
|
||||
"damage.DISTANCE": "Daño de salpicadura",
|
||||
"damage.SPLASH": "Daño de salpicadura",
|
||||
"suffix.seconds": "s",
|
||||
"suffix.hp": "hp",
|
||||
"suffix.specialPointsShort": "p",
|
||||
|
||||
@@ -79,6 +79,7 @@
|
||||
"damage.MAX_CHARGE": "Charge maximale partielle",
|
||||
"damage.TAP_SHOT": "Tir tapoté",
|
||||
"damage.DISTANCE": "Encrage",
|
||||
"damage.SPLASH": "Encrage",
|
||||
"suffix.seconds": "s",
|
||||
"suffix.hp": "pv",
|
||||
"suffix.specialPointsShort": "p",
|
||||
|
||||
@@ -86,6 +86,7 @@
|
||||
"damage.MAX_CHARGE": "最大半チャージ",
|
||||
"damage.TAP_SHOT": "チャージ無し射撃",
|
||||
"damage.DISTANCE": "飛沫",
|
||||
"damage.SPLASH": "飛沫",
|
||||
"suffix.seconds": "秒",
|
||||
"suffix.hp": "耐久値",
|
||||
"suffix.specialPointsShort": "ポイント",
|
||||
|
||||
@@ -58,6 +58,7 @@
|
||||
"damage.MAX_CHARGE": "Maximum gedeeltelijk opgeladen",
|
||||
"damage.TAP_SHOT": "Tik schot",
|
||||
"damage.DISTANCE": "Spatschade",
|
||||
"damage.SPLASH": "Spatschade",
|
||||
"suffix.seconds": "s",
|
||||
"suffix.hp": "hp",
|
||||
"suffix.specialPointsShort": "p",
|
||||
|
||||
@@ -82,6 +82,7 @@
|
||||
"damage.MAX_CHARGE": "Максимальный частичный заряд",
|
||||
"damage.TAP_SHOT": "Тап шот",
|
||||
"damage.DISTANCE": "Разрыв",
|
||||
"damage.SPLASH": "Разрыв",
|
||||
"suffix.seconds": "сек",
|
||||
"suffix.hp": "hp",
|
||||
"suffix.specialPointsShort": "очк.",
|
||||
|
||||
@@ -82,6 +82,7 @@
|
||||
"damage.MAX_CHARGE": "最大不完全蓄力伤害",
|
||||
"damage.TAP_SHOT": "普通攻击",
|
||||
"damage.DISTANCE": "溅射",
|
||||
"damage.SPLASH": "溅射",
|
||||
"suffix.seconds": "s",
|
||||
"suffix.hp": "hp",
|
||||
"suffix.specialPointsShort": "p",
|
||||
|
||||
@@ -142,12 +142,35 @@ function parametersToMainWeaponResult(
|
||||
);
|
||||
};
|
||||
|
||||
const slosherDirectDamage = () => {
|
||||
const DamageParam_ValueDirectMax =
|
||||
params["UnitGroupParam"]?.["Unit"]?.[0]?.["DamageParam"]?.["ValueMax"];
|
||||
const DamageParam_ValueDirectMin =
|
||||
params["UnitGroupParam"]?.["Unit"]?.[0]?.["DamageParam"]?.["ValueMin"];
|
||||
|
||||
if (
|
||||
DamageParam_ValueDirectMax &&
|
||||
DamageParam_ValueDirectMax === DamageParam_ValueDirectMin
|
||||
) {
|
||||
return {
|
||||
DamageParam_ValueDirect: DamageParam_ValueDirectMax,
|
||||
};
|
||||
}
|
||||
|
||||
return {
|
||||
DamageParam_ValueDirectMax,
|
||||
DamageParam_ValueDirectMin,
|
||||
};
|
||||
};
|
||||
|
||||
const KeepChargeFullFrame =
|
||||
params["WeaponKeepChargeParam"]?.["KeepChargeFullFrame"] ??
|
||||
params["spl__WeaponStringerParam"]?.["ChargeKeepParam"]?.[
|
||||
"KeepChargeFullFrame"
|
||||
];
|
||||
|
||||
const isSloshingMachine = weapon.Id === 3020;
|
||||
|
||||
return {
|
||||
SpecialPoint: weapon.SpecialPoint,
|
||||
subWeaponId: resolveSubWeaponId(weapon),
|
||||
@@ -170,7 +193,13 @@ function parametersToMainWeaponResult(
|
||||
? params["DamageParam"]?.["ValueMin"]
|
||||
: undefined,
|
||||
DamageParam_ValueDirect,
|
||||
BlastParam_DistanceDamage: params["BlastParam"]?.["DistanceDamage"],
|
||||
...slosherDirectDamage(),
|
||||
BlastParam_SplashDamage: isSloshingMachine
|
||||
? params["UnitGroupParam"]?.["Unit"]?.[1]?.["DamageParam"]?.["ValueMax"]
|
||||
: undefined,
|
||||
BlastParam_DistanceDamage:
|
||||
params["BlastParam"]?.["DistanceDamage"] ??
|
||||
params["BlastParam"]?.["BlastParam"]?.["DistanceDamage"],
|
||||
DamageParam_ValueFullCharge: params["DamageParam"]?.["ValueFullCharge"],
|
||||
DamageParam_ValueFullChargeMax:
|
||||
params["DamageParam"]?.["ValueFullChargeMax"] !== DamageParam_ValueMax()
|
||||
|
||||
@@ -4,11 +4,13 @@
|
||||
|
||||
### 🟡 analyzer.json
|
||||
|
||||
**107/108**
|
||||
**108/111**
|
||||
|
||||
<details>
|
||||
<summary>Missing</summary>
|
||||
|
||||
- damage.DIRECT_MIN
|
||||
- damage.DIRECT_MAX
|
||||
- torpedoExplanation
|
||||
|
||||
</details>
|
||||
@@ -55,7 +57,7 @@
|
||||
|
||||
### 🟡 analyzer.json
|
||||
|
||||
**94/108**
|
||||
**95/111**
|
||||
|
||||
<details>
|
||||
<summary>Missing</summary>
|
||||
@@ -64,6 +66,8 @@
|
||||
- stat.specialLostSplattedByRP
|
||||
- stat.quickRespawnTimeSplattedByRP
|
||||
- damage.NORMAL_MAX_FULL_CHARGE
|
||||
- damage.DIRECT_MIN
|
||||
- damage.DIRECT_MAX
|
||||
- torpedoExplanation
|
||||
- distanceInline
|
||||
- damageShort
|
||||
@@ -134,7 +138,7 @@
|
||||
|
||||
### 🟡 analyzer.json
|
||||
|
||||
**91/108**
|
||||
**92/111**
|
||||
|
||||
<details>
|
||||
<summary>Missing</summary>
|
||||
@@ -146,6 +150,8 @@
|
||||
- stat.shootingRunSpeedCharging
|
||||
- stat.shootingRunSpeedFullCharge
|
||||
- damage.NORMAL_MAX_FULL_CHARGE
|
||||
- damage.DIRECT_MIN
|
||||
- damage.DIRECT_MAX
|
||||
- torpedoExplanation
|
||||
- distanceInline
|
||||
- damageShort
|
||||
@@ -290,7 +296,7 @@
|
||||
|
||||
### 🟡 analyzer.json
|
||||
|
||||
**91/108**
|
||||
**92/111**
|
||||
|
||||
<details>
|
||||
<summary>Missing</summary>
|
||||
@@ -302,6 +308,8 @@
|
||||
- stat.shootingRunSpeedCharging
|
||||
- stat.shootingRunSpeedFullCharge
|
||||
- damage.NORMAL_MAX_FULL_CHARGE
|
||||
- damage.DIRECT_MIN
|
||||
- damage.DIRECT_MAX
|
||||
- torpedoExplanation
|
||||
- distanceInline
|
||||
- damageShort
|
||||
@@ -458,7 +466,7 @@
|
||||
|
||||
### 🔴 analyzer.json
|
||||
|
||||
**0/108**
|
||||
**0/111**
|
||||
|
||||
### 🔴 badges.json
|
||||
|
||||
@@ -518,11 +526,13 @@
|
||||
|
||||
### 🟡 analyzer.json
|
||||
|
||||
**107/108**
|
||||
**108/111**
|
||||
|
||||
<details>
|
||||
<summary>Missing</summary>
|
||||
|
||||
- damage.DIRECT_MIN
|
||||
- damage.DIRECT_MAX
|
||||
- torpedoExplanation
|
||||
|
||||
</details>
|
||||
@@ -569,7 +579,7 @@
|
||||
|
||||
### 🔴 analyzer.json
|
||||
|
||||
**0/108**
|
||||
**0/111**
|
||||
|
||||
### 🟢 badges.json
|
||||
|
||||
@@ -724,7 +734,7 @@
|
||||
|
||||
### 🟡 analyzer.json
|
||||
|
||||
**94/108**
|
||||
**95/111**
|
||||
|
||||
<details>
|
||||
<summary>Missing</summary>
|
||||
@@ -733,6 +743,8 @@
|
||||
- stat.specialLostSplattedByRP
|
||||
- stat.quickRespawnTimeSplattedByRP
|
||||
- damage.NORMAL_MAX_FULL_CHARGE
|
||||
- damage.DIRECT_MIN
|
||||
- damage.DIRECT_MAX
|
||||
- torpedoExplanation
|
||||
- distanceInline
|
||||
- damageShort
|
||||
@@ -843,7 +855,7 @@
|
||||
|
||||
### 🟡 analyzer.json
|
||||
|
||||
**101/108**
|
||||
**102/111**
|
||||
|
||||
<details>
|
||||
<summary>Missing</summary>
|
||||
@@ -852,6 +864,8 @@
|
||||
- stat.specialLostSplattedByRP
|
||||
- stat.quickRespawnTimeSplattedByRP
|
||||
- damage.NORMAL_MAX_FULL_CHARGE
|
||||
- damage.DIRECT_MIN
|
||||
- damage.DIRECT_MAX
|
||||
- torpedoExplanation
|
||||
- dmgHtdExplanation
|
||||
- noDmgData
|
||||
@@ -938,7 +952,7 @@
|
||||
|
||||
### 🟡 analyzer.json
|
||||
|
||||
**94/108**
|
||||
**95/111**
|
||||
|
||||
<details>
|
||||
<summary>Missing</summary>
|
||||
@@ -947,6 +961,8 @@
|
||||
- stat.specialLostSplattedByRP
|
||||
- stat.quickRespawnTimeSplattedByRP
|
||||
- damage.NORMAL_MAX_FULL_CHARGE
|
||||
- damage.DIRECT_MIN
|
||||
- damage.DIRECT_MAX
|
||||
- torpedoExplanation
|
||||
- distanceInline
|
||||
- damageShort
|
||||
|
||||
Reference in New Issue
Block a user