mirror of
https://github.com/Sendouc/sendou.ink.git
synced 2026-04-25 07:32:19 -05:00
generate analyzer jsons script
This commit is contained in:
parent
6fb3c4d89a
commit
d729f409e2
1
.gitignore
vendored
1
.gitignore
vendored
|
|
@ -12,6 +12,7 @@ build
|
|||
# misc
|
||||
xrank_data
|
||||
tourney_maps
|
||||
ability_jsons_output
|
||||
.DS_Store
|
||||
.env
|
||||
.env.local
|
||||
|
|
|
|||
22
frontend-react/src/components/analyzer/BuildAnalyzerPage.tsx
Normal file
22
frontend-react/src/components/analyzer/BuildAnalyzerPage.tsx
Normal file
|
|
@ -0,0 +1,22 @@
|
|||
import React, { useState } from "react"
|
||||
import { RouteComponentProps } from "@reach/router"
|
||||
import PageHeader from "../common/PageHeader"
|
||||
import { Build } from "../../types"
|
||||
import EditableBuild from "./EditableBuild"
|
||||
|
||||
const BuildAnalyzerPage: React.FC<RouteComponentProps> = () => {
|
||||
const [build, setBuild] = useState<Partial<Build>>({
|
||||
headgear: ["UNKNOWN", "UNKNOWN", "UNKNOWN", "UNKNOWN"],
|
||||
clothing: ["UNKNOWN", "UNKNOWN", "UNKNOWN", "UNKNOWN"],
|
||||
shoes: ["UNKNOWN", "UNKNOWN", "UNKNOWN", "UNKNOWN"],
|
||||
})
|
||||
|
||||
return (
|
||||
<>
|
||||
<PageHeader title="Build Analyzer" />
|
||||
<EditableBuild build={build} setBuild={setBuild} />
|
||||
</>
|
||||
)
|
||||
}
|
||||
|
||||
export default BuildAnalyzerPage
|
||||
126
frontend-react/src/components/analyzer/EditableBuild.tsx
Normal file
126
frontend-react/src/components/analyzer/EditableBuild.tsx
Normal file
|
|
@ -0,0 +1,126 @@
|
|||
import React from "react"
|
||||
import AbilityButtons from "../user/AbilityButtons"
|
||||
import ViewSlots from "../builds/ViewSlots"
|
||||
import { Box } from "@chakra-ui/core"
|
||||
import {
|
||||
Build,
|
||||
Ability,
|
||||
HeadOnlyAbility,
|
||||
ClothingOnlyAbility,
|
||||
ShoesOnlyAbility,
|
||||
StackableAbility,
|
||||
} from "../../types"
|
||||
import {
|
||||
headOnlyAbilities,
|
||||
clothingOnlyAbilities,
|
||||
shoesOnlyAbilities,
|
||||
} from "../../utils/lists"
|
||||
|
||||
interface EditableBuildProps {
|
||||
build: Partial<Build>
|
||||
setBuild: React.Dispatch<React.SetStateAction<Partial<Build>>>
|
||||
}
|
||||
|
||||
const EditableBuild: React.FC<EditableBuildProps> = ({ build, setBuild }) => {
|
||||
const handleChange = (value: Object) => setBuild({ ...build, ...value })
|
||||
|
||||
const handleAbilityButtonClick = (ability: Ability) => {
|
||||
if (headOnlyAbilities.indexOf(ability as any) !== -1) {
|
||||
if (build.headgear![0] === "UNKNOWN") {
|
||||
handleChange({
|
||||
headgear: [
|
||||
ability,
|
||||
build.headgear![1],
|
||||
build.headgear![2],
|
||||
build.headgear![3],
|
||||
],
|
||||
})
|
||||
}
|
||||
} else if (clothingOnlyAbilities.indexOf(ability as any) !== -1) {
|
||||
if (build.clothing![0] === "UNKNOWN") {
|
||||
handleChange({
|
||||
clothing: [
|
||||
ability,
|
||||
build.clothing![1],
|
||||
build.clothing![2],
|
||||
build.clothing![3],
|
||||
],
|
||||
})
|
||||
}
|
||||
} else if (shoesOnlyAbilities.indexOf(ability as any) !== -1) {
|
||||
if (build.shoes![0] === "UNKNOWN") {
|
||||
handleChange({
|
||||
shoes: [ability, build.shoes![1], build.shoes![2], build.shoes![3]],
|
||||
})
|
||||
}
|
||||
} else {
|
||||
const headI = build.headgear!.indexOf("UNKNOWN")
|
||||
if (headI !== -1) {
|
||||
const copy = build.headgear!.slice()
|
||||
copy[headI] = ability as HeadOnlyAbility | StackableAbility
|
||||
handleChange({
|
||||
headgear: copy,
|
||||
})
|
||||
return
|
||||
}
|
||||
|
||||
const clothingI = build.clothing!.indexOf("UNKNOWN")
|
||||
if (clothingI !== -1) {
|
||||
const copy = build.clothing!.slice()
|
||||
copy[clothingI] = ability as ClothingOnlyAbility | StackableAbility
|
||||
handleChange({
|
||||
clothing: copy,
|
||||
})
|
||||
return
|
||||
}
|
||||
|
||||
const shoesI = build.shoes!.indexOf("UNKNOWN")
|
||||
if (shoesI !== -1) {
|
||||
const copy = build.shoes!.slice()
|
||||
copy[shoesI] = ability as ShoesOnlyAbility | StackableAbility
|
||||
handleChange({
|
||||
shoes: copy,
|
||||
})
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
const handleClickBuildAbility = (
|
||||
slot: "HEAD" | "CLOTHING" | "SHOES",
|
||||
index: number
|
||||
) => {
|
||||
if (slot === "HEAD") {
|
||||
const copy = build.headgear!.slice()
|
||||
copy[index] = "UNKNOWN"
|
||||
handleChange({
|
||||
headgear: copy,
|
||||
})
|
||||
} else if (slot === "CLOTHING") {
|
||||
const copy = build.clothing!.slice()
|
||||
copy[index] = "UNKNOWN"
|
||||
handleChange({
|
||||
clothing: copy,
|
||||
})
|
||||
} else {
|
||||
const copy = build.shoes!.slice()
|
||||
copy[index] = "UNKNOWN"
|
||||
handleChange({
|
||||
shoes: copy,
|
||||
})
|
||||
}
|
||||
}
|
||||
return (
|
||||
<>
|
||||
<Box mt="1em">
|
||||
<ViewSlots build={build} onAbilityClick={handleClickBuildAbility} />
|
||||
</Box>
|
||||
<Box mt="1em">
|
||||
<AbilityButtons
|
||||
onClick={(ability) => handleAbilityButtonClick(ability)}
|
||||
/>
|
||||
</Box>
|
||||
</>
|
||||
)
|
||||
}
|
||||
|
||||
export default EditableBuild
|
||||
|
|
@ -4,12 +4,14 @@ import Loading from "../common/Loading"
|
|||
import NotFound from "./NotFound"
|
||||
import { ScrollToTop } from "./ScrollToTop"
|
||||
import AdminPage from "../admin/AdminPage"
|
||||
import BuildAnalyzerPage from "../analyzer/BuildAnalyzerPage"
|
||||
|
||||
const HomePage = lazy(() => import("../home/HomePage"))
|
||||
const UserPage = lazy(() => import("../user/UserPage"))
|
||||
const UserSearchPage = lazy(() => import("../usersearch/UserSearchPage"))
|
||||
const MarkdownHelpPage = lazy(() => import("../markdown/MarkdownHelpPage"))
|
||||
const BuildsPage = lazy(() => import("../builds/BuildsPage"))
|
||||
const BuildsAnalyzerPage = lazy(() => import("../analyzer/BuildAnalyzerPage"))
|
||||
const CalendarPage = lazy(() => import("../calendar/CalendarPage"))
|
||||
const TournamentsPage = lazy(() => import("../tournaments/TournamentsPage"))
|
||||
const TournamentsDetailsPage = lazy(() =>
|
||||
|
|
@ -42,6 +44,7 @@ const Routes: React.FC = () => {
|
|||
<MarkdownHelpPage path="/markdown" />
|
||||
<TeamPage path="/t/:name" />
|
||||
<BuildsPage path="/builds" />
|
||||
<BuildAnalyzerPage path="/analyzer" />
|
||||
<MapPlannerPage path="/plans" />
|
||||
<CalendarPage path="/calendar" />
|
||||
<TournamentsPage path="/tournaments" />
|
||||
|
|
|
|||
77
frontend-react/src/hooks/useAbilityEffects.ts
Normal file
77
frontend-react/src/hooks/useAbilityEffects.ts
Normal file
|
|
@ -0,0 +1,77 @@
|
|||
import { Build, Ability } from "../types"
|
||||
import { useEffect, useState } from "react"
|
||||
|
||||
interface Explanation {
|
||||
ability: Ability
|
||||
effect: number
|
||||
explanation: string
|
||||
}
|
||||
|
||||
function buildToAP(build: Partial<Build>) {
|
||||
const AP: Partial<Record<Ability, number>> = {}
|
||||
|
||||
if (build.headgear) {
|
||||
build.headgear.forEach((ability, index) => {
|
||||
if (ability !== "UNKNOWN") {
|
||||
const existing = AP[ability] ?? 0
|
||||
const toAdd = index === 0 ? 10 : 3
|
||||
AP[ability] = existing + toAdd
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
if (build.clothing) {
|
||||
build.clothing.forEach((ability, index) => {
|
||||
if (ability !== "UNKNOWN") {
|
||||
const existing = AP[ability] ?? 0
|
||||
const toAdd = index === 0 ? 10 : 3
|
||||
AP[ability] = existing + toAdd
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
if (build.shoes) {
|
||||
build.shoes.forEach((ability, index) => {
|
||||
if (ability !== "UNKNOWN") {
|
||||
const existing = AP[ability] ?? 0
|
||||
const toAdd = index === 0 ? 10 : 3
|
||||
AP[ability] = existing + toAdd
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
return AP
|
||||
}
|
||||
|
||||
function calculateISM(amount: number) {
|
||||
console.log(amount)
|
||||
return { ability: "ISM" as Ability, effect: 0, explanation: "asd" }
|
||||
}
|
||||
|
||||
const abilityFunctions: Partial<Record<
|
||||
Ability,
|
||||
(amount: number) => Explanation
|
||||
>> = {
|
||||
ISM: calculateISM,
|
||||
} as const
|
||||
|
||||
export default function useAbilityEffects(build: Partial<Build>) {
|
||||
const [explanations, setExplanations] = useState<Explanation[]>([])
|
||||
|
||||
useEffect(() => {
|
||||
const AP = buildToAP(build)
|
||||
|
||||
const newExplanations: Explanation[] = []
|
||||
Object.keys(AP).forEach((ability) => {
|
||||
const func = abilityFunctions[ability as Ability]
|
||||
if (func) {
|
||||
const key = ability as Ability
|
||||
newExplanations.push(func(AP[key]!))
|
||||
}
|
||||
})
|
||||
|
||||
setExplanations(newExplanations)
|
||||
}, [build])
|
||||
|
||||
return explanations
|
||||
}
|
||||
1
frontend-react/src/utils/ability_data.json
Normal file
1
frontend-react/src/utils/ability_data.json
Normal file
File diff suppressed because one or more lines are too long
1
frontend-react/src/utils/weapon_data.json
Normal file
1
frontend-react/src/utils/weapon_data.json
Normal file
File diff suppressed because one or more lines are too long
51
scripts/ability_jsons.py
Normal file
51
scripts/ability_jsons.py
Normal file
|
|
@ -0,0 +1,51 @@
|
|||
import urllib.request, json
|
||||
|
||||
with open("lang_dict_EUen.json") as f:
|
||||
lang_dict = json.load(f)
|
||||
|
||||
inverted_dict = {v: k for k, v in lang_dict.items()} # english -> internal
|
||||
|
||||
ability_jsons = [
|
||||
"BombDamage_Reduction",
|
||||
"BombDistance_Up",
|
||||
"HumanMove_Up",
|
||||
"InkRecovery_Up",
|
||||
"JumpTime_Save",
|
||||
"MainInk_Save",
|
||||
"MarkingTime_Reduction",
|
||||
"OpInkEffect_Reduction",
|
||||
"RespawnSpecialGauge_Save",
|
||||
"RespawnTime_Save",
|
||||
"SpecialIncrease_Up",
|
||||
"SpecialTime_Up",
|
||||
"SquidMove_Up",
|
||||
"SubInk_Save",
|
||||
]
|
||||
|
||||
print_dict = {}
|
||||
|
||||
for code in ability_jsons:
|
||||
with urllib.request.urlopen(
|
||||
f"https://raw.githubusercontent.com/Leanny/leanny.github.io/master/data/Parameter/latest/Player/Player_Spec_{code}.json"
|
||||
) as url:
|
||||
data = json.loads(url.read().decode())
|
||||
print_dict[lang_dict[code]] = data[code]
|
||||
|
||||
print(json.dumps(print_dict, indent=4, sort_keys=True))
|
||||
|
||||
weapon_dict = {}
|
||||
|
||||
with urllib.request.urlopen(
|
||||
"https://raw.githubusercontent.com/Leanny/leanny.github.io/master/data/Mush/latest/WeaponInfo_Main.json"
|
||||
) as url:
|
||||
data = json.loads(url.read().decode())
|
||||
for weapon_obj in data:
|
||||
weapon_dict[lang_dict[weapon_obj["Name"]]] = weapon_obj
|
||||
|
||||
print(json.dumps(weapon_dict, indent=4, sort_keys=True))
|
||||
|
||||
with open("ability_jsons_output/ability_data.json", "w") as fp:
|
||||
json.dump(print_dict, fp)
|
||||
|
||||
with open("ability_jsons_output/weapon_data.json", "w") as fp:
|
||||
json.dump(weapon_dict, fp)
|
||||
Loading…
Reference in New Issue
Block a user