Localize WeaponModal and AxSelect

This commit is contained in:
Justin Edmund 2022-03-05 14:30:34 -08:00
parent 5a184ed8aa
commit dfd2bbff19
4 changed files with 88 additions and 17 deletions

View file

@ -1,4 +1,7 @@
import React, { useEffect, useState } from 'react' import React, { useEffect, useState } from 'react'
import { useRouter } from 'next/router'
import { useTranslation } from 'next-i18next'
import classNames from 'classnames' import classNames from 'classnames'
import { axData } from '~utils/axData' import { axData } from '~utils/axData'
@ -19,6 +22,10 @@ interface Props {
} }
const AXSelect = (props: Props) => { const AXSelect = (props: Props) => {
const router = useRouter()
const locale = (router.locale && ['en', 'ja'].includes(router.locale)) ? router.locale : 'en'
const { t } = useTranslation('common')
// Set up form states and error handling // Set up form states and error handling
const [errors, setErrors] = useState<ErrorMap>({ const [errors, setErrors] = useState<ErrorMap>({
axValue1: '', axValue1: '',
@ -84,7 +91,7 @@ const AXSelect = (props: Props) => {
if (modifierSet == 0) { if (modifierSet == 0) {
axOptionElements = axOptions.map((ax, i) => { axOptionElements = axOptions.map((ax, i) => {
return ( return (
<option key={i} value={ax.id}>{ax.name.en}</option> <option key={i} value={ax.id}>{ax.name[locale]}</option>
) )
}) })
} else { } else {
@ -103,14 +110,14 @@ const AXSelect = (props: Props) => {
const secondaryAxOptions = primarySkill.secondary const secondaryAxOptions = primarySkill.secondary
axOptionElements = secondaryAxOptions.map((ax, i) => { axOptionElements = secondaryAxOptions.map((ax, i) => {
return ( return (
<option key={i} value={ax.id}>{ax.name.en}</option> <option key={i} value={ax.id}>{ax.name[locale]}</option>
) )
}) })
} }
} }
} }
axOptionElements?.unshift(<option key={-1} value={-1}>No AX Skill</option>) axOptionElements?.unshift(<option key={-1} value={-1}>{t('ax.no_skill')}</option>)
return axOptionElements return axOptionElements
} }
@ -156,11 +163,19 @@ const AXSelect = (props: Props) => {
let newErrors = {...errors} let newErrors = {...errors}
if (value < primaryAxSkill.minValue) { if (value < primaryAxSkill.minValue) {
newErrors.axValue1 = `${primaryAxSkill.name.en} must be at least ${primaryAxSkill.minValue}${ (primaryAxSkill.suffix) ? primaryAxSkill.suffix : ''}` newErrors.axValue1 = t('ax.errors.value_too_low', {
name: primaryAxSkill.name[locale],
minValue: primaryAxSkill.minValue,
suffix: (primaryAxSkill.suffix) ? primaryAxSkill.suffix : ''
})
} else if (value > primaryAxSkill.maxValue) { } else if (value > primaryAxSkill.maxValue) {
newErrors.axValue1 = `${primaryAxSkill.name.en} cannot be greater than ${primaryAxSkill.maxValue}${ (primaryAxSkill.suffix) ? primaryAxSkill.suffix : ''}` newErrors.axValue1 = t('ax.errors.value_too_high', {
name: primaryAxSkill.name[locale],
maxValue: primaryAxSkill.minValue,
suffix: (primaryAxSkill.suffix) ? primaryAxSkill.suffix : ''
})
} else if (!value || value <= 0) { } else if (!value || value <= 0) {
newErrors.axValue1 = `${primaryAxSkill.name.en} must have a value` newErrors.axValue1 = t('ax.errors.value_empty', { name: primaryAxSkill.name[locale] })
} else { } else {
newErrors.axValue1 = '' newErrors.axValue1 = ''
} }
@ -179,13 +194,21 @@ const AXSelect = (props: Props) => {
if (secondaryAxSkill) { if (secondaryAxSkill) {
if (value < secondaryAxSkill.minValue) { if (value < secondaryAxSkill.minValue) {
newErrors.axValue2 = `${secondaryAxSkill.name.en} must be at least ${secondaryAxSkill.minValue}${ (secondaryAxSkill.suffix) ? secondaryAxSkill.suffix : ''}` newErrors.axValue2 = t('ax.errors.value_too_low', {
name: secondaryAxSkill.name[locale],
minValue: secondaryAxSkill.minValue,
suffix: (secondaryAxSkill.suffix) ? secondaryAxSkill.suffix : ''
})
} else if (value > secondaryAxSkill.maxValue) { } else if (value > secondaryAxSkill.maxValue) {
newErrors.axValue2 = `${secondaryAxSkill.name.en} cannot be greater than ${secondaryAxSkill.maxValue}${ (secondaryAxSkill.suffix) ? secondaryAxSkill.suffix : ''}` newErrors.axValue2 = t('ax.errors.value_too_high', {
name: secondaryAxSkill.name[locale],
maxValue: secondaryAxSkill.minValue,
suffix: (secondaryAxSkill.suffix) ? secondaryAxSkill.suffix : ''
})
} else if (!secondaryAxSkill.suffix && value % 1 !== 0) { } else if (!secondaryAxSkill.suffix && value % 1 !== 0) {
newErrors.axValue2 = `${secondaryAxSkill.name.en} must be a whole number` newErrors.axValue2 = t('ax.errors.value_not_whole', { name: secondaryAxSkill.name[locale] })
} else if (primaryAxValue <= 0) { } else if (primaryAxValue <= 0) {
newErrors.axValue1 = `${primaryAxSkill.name.en} must have a value` newErrors.axValue1 = t('ax.errors.value_empty', { name: primaryAxSkill.name[locale] })
} else { } else {
newErrors.axValue2 = '' newErrors.axValue2 = ''
} }
@ -224,7 +247,7 @@ const AXSelect = (props: Props) => {
<div className="AXSet"> <div className="AXSet">
<div className="fields"> <div className="fields">
<select key="ax1" defaultValue={ (props.currentSkills && props.currentSkills[0]) ? props.currentSkills[0].modifier : -1 } onChange={handleSelectChange} ref={primaryAxModifierSelect}>{ generateOptions(0) }</select> <select key="ax1" defaultValue={ (props.currentSkills && props.currentSkills[0]) ? props.currentSkills[0].modifier : -1 } onChange={handleSelectChange} ref={primaryAxModifierSelect}>{ generateOptions(0) }</select>
<input defaultValue={ (props.currentSkills && props.currentSkills[0]) ? props.currentSkills[0].strength : 0 } className="Input" type="number" onChange={handleInputChange} ref={primaryAxValueInput} disabled /> <input defaultValue={ (props.currentSkills && props.currentSkills[0]) ? props.currentSkills[0].strength : 0 } className="Input" type="number" onChange={handleInputChange} ref={primaryAxValueInput} disabled={primaryAxValue != 0} />
</div> </div>
<p className={primaryErrorClasses}>{errors.axValue1}</p> <p className={primaryErrorClasses}>{errors.axValue1}</p>
</div> </div>
@ -232,7 +255,7 @@ const AXSelect = (props: Props) => {
<div className={secondarySetClasses}> <div className={secondarySetClasses}>
<div className="fields"> <div className="fields">
<select key="ax2" defaultValue={ (props.currentSkills && props.currentSkills[1]) ? props.currentSkills[1].modifier : -1 } onChange={handleSelectChange} ref={secondaryAxModifierSelect}>{ generateOptions(1) }</select> <select key="ax2" defaultValue={ (props.currentSkills && props.currentSkills[1]) ? props.currentSkills[1].modifier : -1 } onChange={handleSelectChange} ref={secondaryAxModifierSelect}>{ generateOptions(1) }</select>
<input defaultValue={ (props.currentSkills && props.currentSkills[1]) ? props.currentSkills[1].strength : 0 } className="Input" type="number" onChange={handleInputChange} ref={secondaryAxValueInput} disabled /> <input defaultValue={ (props.currentSkills && props.currentSkills[1]) ? props.currentSkills[1].strength : 0 } className="Input" type="number" onChange={handleInputChange} ref={secondaryAxValueInput} disabled={secondaryAxValue != 0} />
</div> </div>
<p className={secondaryErrorClasses}>{errors.axValue2}</p> <p className={secondaryErrorClasses}>{errors.axValue2}</p>
</div> </div>

View file

@ -1,6 +1,9 @@
import React, { useState } from 'react' import React, { useState } from 'react'
import { useCookies } from 'react-cookie' import { useCookies } from 'react-cookie'
import { useRouter } from 'next/router'
import { useTranslation } from 'next-i18next'
import { AxiosResponse } from 'axios' import { AxiosResponse } from 'axios'
import * as Dialog from '@radix-ui/react-dialog' import * as Dialog from '@radix-ui/react-dialog'
import AXSelect from '~components/AxSelect' import AXSelect from '~components/AxSelect'
@ -33,6 +36,10 @@ interface Props {
} }
const WeaponModal = (props: Props) => { const WeaponModal = (props: Props) => {
const router = useRouter()
const locale = (router.locale && ['en', 'ja'].includes(router.locale)) ? router.locale : 'en'
const { t } = useTranslation('common')
// Cookies // Cookies
const [cookies] = useCookies(['account']) const [cookies] = useCookies(['account'])
const headers = (cookies.account != null) ? { const headers = (cookies.account != null) ? {
@ -122,7 +129,7 @@ const WeaponModal = (props: Props) => {
const elementSelect = () => { const elementSelect = () => {
return ( return (
<section> <section>
<h3>Element</h3> <h3>{t('modals.weapon.subtitles.element')}</h3>
<ElementToggle <ElementToggle
currentElement={props.gridWeapon.element} currentElement={props.gridWeapon.element}
sendValue={receiveElementValue} sendValue={receiveElementValue}
@ -134,7 +141,7 @@ const WeaponModal = (props: Props) => {
const keySelect = () => { const keySelect = () => {
return ( return (
<section> <section>
<h3>Weapon Keys</h3> <h3>{t('modals.weapon.subtitles.weapon_keys')}</h3>
{ ([2, 3, 17, 22].includes(props.gridWeapon.object.series)) ? { ([2, 3, 17, 22].includes(props.gridWeapon.object.series)) ?
<WeaponKeyDropdown <WeaponKeyDropdown
currentValue={ (props.gridWeapon.weapon_keys) ? props.gridWeapon.weapon_keys[0] : undefined } currentValue={ (props.gridWeapon.weapon_keys) ? props.gridWeapon.weapon_keys[0] : undefined }
@ -165,6 +172,7 @@ const WeaponModal = (props: Props) => {
const axSelect = () => { const axSelect = () => {
return ( return (
<section> <section>
<h3>{t('modals.weapon.subtitles.ax_skills')}</h3>
<AXSelect <AXSelect
axType={props.gridWeapon.object.ax} axType={props.gridWeapon.object.ax}
currentSkills={props.gridWeapon.ax} currentSkills={props.gridWeapon.ax}
@ -189,8 +197,8 @@ const WeaponModal = (props: Props) => {
<Dialog.Content className="Weapon Dialog" onOpenAutoFocus={ (event) => event.preventDefault() }> <Dialog.Content className="Weapon Dialog" onOpenAutoFocus={ (event) => event.preventDefault() }>
<div className="DialogHeader"> <div className="DialogHeader">
<div className="DialogTop"> <div className="DialogTop">
<Dialog.Title className="SubTitle">Modify Weapon</Dialog.Title> <Dialog.Title className="SubTitle">{t('modals.weapon.title')}</Dialog.Title>
<Dialog.Title className="DialogTitle">{props.gridWeapon.object.name.en}</Dialog.Title> <Dialog.Title className="DialogTitle">{props.gridWeapon.object.name[locale]}</Dialog.Title>
</div> </div>
<Dialog.Close className="DialogClose" asChild> <Dialog.Close className="DialogClose" asChild>
<span> <span>
@ -203,7 +211,7 @@ const WeaponModal = (props: Props) => {
{ (props.gridWeapon.object.element == 0) ? elementSelect() : '' } { (props.gridWeapon.object.element == 0) ? elementSelect() : '' }
{ ([2, 3, 17, 24].includes(props.gridWeapon.object.series)) ? keySelect() : '' } { ([2, 3, 17, 24].includes(props.gridWeapon.object.series)) ? keySelect() : '' }
{ (props.gridWeapon.object.ax > 0) ? axSelect() : '' } { (props.gridWeapon.object.ax > 0) ? axSelect() : '' }
<Button onClick={updateWeapon} disabled={props.gridWeapon.object.ax > 0 && !formValid}>Save Weapon</Button> <Button onClick={updateWeapon} disabled={props.gridWeapon.object.ax > 0 && !formValid}>{t('modals.weapon.buttons.confirm')}</Button>
</div> </div>
</Dialog.Content> </Dialog.Content>
<Dialog.Overlay className="Overlay" /> <Dialog.Overlay className="Overlay" />

View file

@ -1,4 +1,13 @@
{ {
"ax": {
"no_skill": "No AX Skill",
"errors": {
"value_too_low": "{{name}} must be at least {{minValue}}{{suffix}}",
"value_too_high": "{{name}} cannot be greater than {{maxValue}}{{suffix}}",
"value_not_whole": "{{name}} must be a whole number",
"value_empty": "{{name}} must have a value"
}
},
"buttons": { "buttons": {
"copy": "Copy link", "copy": "Copy link",
"delete": "Delete team", "delete": "Delete team",
@ -111,6 +120,17 @@
"password": "Password", "password": "Password",
"password_confirm": "Password (again)" "password_confirm": "Password (again)"
} }
},
"weapon": {
"title": "Modify Weapon",
"buttons": {
"confirm": "Save weapon"
},
"subtitles": {
"element": "Element",
"ax_skills": "AX Skills",
"weapon_keys": "Weapon Keys"
}
} }
}, },
"menu": { "menu": {

View file

@ -1,4 +1,13 @@
{ {
"ax": {
"no_skill": "EXスキルなし",
"errors": {
"value_too_low": "{{name}}は最低{{minValue}}{{suffix}}を入力してください",
"value_too_high": "{{name}}は最大{{maxValue}}を入力してください",
"value_not_whole": "{{name}}は整数でなければなりません",
"value_empty": "{{name}}を入力してください"
}
},
"buttons": { "buttons": {
"copy": "リンクをコピー", "copy": "リンクをコピー",
"delete": "編成を削除", "delete": "編成を削除",
@ -112,6 +121,17 @@
"password": "パスワード", "password": "パスワード",
"password_confirm": "パスワード確認" "password_confirm": "パスワード確認"
} }
},
"weapon": {
"title": "武器変更",
"buttons": {
"confirm": "武器を変更する"
},
"subtitles": {
"element": "属性",
"ax_skills": "EXスキル",
"weapon_keys": "武器スキル"
}
} }
}, },
"menu": { "menu": {