Fix being able to open multiple selects at once
This was miserable
This commit is contained in:
parent
4c73ebf294
commit
45f1bd291e
11 changed files with 215 additions and 76 deletions
|
|
@ -80,6 +80,10 @@ const AccountModal = (props: Props) => {
|
||||||
// const [privateProfile, setPrivateProfile] = useState(false)
|
// const [privateProfile, setPrivateProfile] = useState(false)
|
||||||
|
|
||||||
// Setup
|
// Setup
|
||||||
|
const [pictureOpen, setPictureOpen] = useState(false)
|
||||||
|
const [genderOpen, setGenderOpen] = useState(false)
|
||||||
|
const [languageOpen, setLanguageOpen] = useState(false)
|
||||||
|
const [themeOpen, setThemeOpen] = useState(false)
|
||||||
|
|
||||||
// UI management
|
// UI management
|
||||||
function openChange(open: boolean) {
|
function openChange(open: boolean) {
|
||||||
|
|
@ -87,16 +91,10 @@ const AccountModal = (props: Props) => {
|
||||||
}
|
}
|
||||||
|
|
||||||
function openSelect(name: 'picture' | 'gender' | 'language' | 'theme') {
|
function openSelect(name: 'picture' | 'gender' | 'language' | 'theme') {
|
||||||
const stateVars = selectOpenState
|
setPictureOpen(name === 'picture' ? !pictureOpen : false)
|
||||||
Object.keys(stateVars).forEach((key) => {
|
setGenderOpen(name === 'gender' ? !genderOpen : false)
|
||||||
if (key === name) {
|
setLanguageOpen(name === 'language' ? !languageOpen : false)
|
||||||
stateVars[name] = true
|
setThemeOpen(name === 'theme' ? !themeOpen : false)
|
||||||
} else {
|
|
||||||
stateVars[key] = false
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
setSelectOpenState(stateVars)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Event handlers
|
// Event handlers
|
||||||
|
|
@ -117,6 +115,14 @@ const AccountModal = (props: Props) => {
|
||||||
setAppTheme(value)
|
setAppTheme(value)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function onEscapeKeyDown(event: KeyboardEvent) {
|
||||||
|
if (pictureOpen || genderOpen || languageOpen || themeOpen) {
|
||||||
|
return event.preventDefault()
|
||||||
|
} else {
|
||||||
|
setOpen(false)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// API calls
|
// API calls
|
||||||
function update(event: React.FormEvent<HTMLFormElement>) {
|
function update(event: React.FormEvent<HTMLFormElement>) {
|
||||||
event.preventDefault()
|
event.preventDefault()
|
||||||
|
|
@ -189,9 +195,10 @@ const AccountModal = (props: Props) => {
|
||||||
description={t('modals.settings.descriptions.picture')}
|
description={t('modals.settings.descriptions.picture')}
|
||||||
className="Image"
|
className="Image"
|
||||||
label={t('modals.settings.labels.picture')}
|
label={t('modals.settings.labels.picture')}
|
||||||
open={selectOpenState.picture}
|
open={pictureOpen}
|
||||||
onClick={() => openSelect('picture')}
|
onOpenChange={() => openSelect('picture')}
|
||||||
onChange={handlePictureChange}
|
onChange={handlePictureChange}
|
||||||
|
onClose={() => setPictureOpen(false)}
|
||||||
imageAlt={t('modals.settings.labels.image_alt')}
|
imageAlt={t('modals.settings.labels.image_alt')}
|
||||||
imageClass={pictureData.find((i) => i.filename === picture)?.element}
|
imageClass={pictureData.find((i) => i.filename === picture)?.element}
|
||||||
imageSrc={[`/profile/${picture}.png`, `/profile/${picture}@2x.png 2x`]}
|
imageSrc={[`/profile/${picture}.png`, `/profile/${picture}@2x.png 2x`]}
|
||||||
|
|
@ -206,9 +213,10 @@ const AccountModal = (props: Props) => {
|
||||||
name="gender"
|
name="gender"
|
||||||
description={t('modals.settings.descriptions.gender')}
|
description={t('modals.settings.descriptions.gender')}
|
||||||
label={t('modals.settings.labels.gender')}
|
label={t('modals.settings.labels.gender')}
|
||||||
open={selectOpenState.gender}
|
open={genderOpen}
|
||||||
onClick={() => openSelect('gender')}
|
onOpenChange={() => openSelect('gender')}
|
||||||
onChange={handleGenderChange}
|
onChange={handleGenderChange}
|
||||||
|
onClose={() => setGenderOpen(false)}
|
||||||
value={`${gender}`}
|
value={`${gender}`}
|
||||||
>
|
>
|
||||||
<SelectItem key="gran" value="0">
|
<SelectItem key="gran" value="0">
|
||||||
|
|
@ -224,9 +232,10 @@ const AccountModal = (props: Props) => {
|
||||||
<SelectTableField
|
<SelectTableField
|
||||||
name="language"
|
name="language"
|
||||||
label={t('modals.settings.labels.language')}
|
label={t('modals.settings.labels.language')}
|
||||||
open={selectOpenState.language}
|
open={languageOpen}
|
||||||
onClick={() => openSelect('language')}
|
onOpenChange={() => openSelect('language')}
|
||||||
onChange={handleLanguageChange}
|
onChange={handleLanguageChange}
|
||||||
|
onClose={() => setLanguageOpen(false)}
|
||||||
value={language}
|
value={language}
|
||||||
>
|
>
|
||||||
<SelectItem key="en" value="en">
|
<SelectItem key="en" value="en">
|
||||||
|
|
@ -242,9 +251,10 @@ const AccountModal = (props: Props) => {
|
||||||
<SelectTableField
|
<SelectTableField
|
||||||
name="theme"
|
name="theme"
|
||||||
label={t('modals.settings.labels.theme')}
|
label={t('modals.settings.labels.theme')}
|
||||||
open={selectOpenState.theme}
|
open={themeOpen}
|
||||||
onClick={() => openSelect('theme')}
|
onOpenChange={() => openSelect('theme')}
|
||||||
onChange={handleThemeChange}
|
onChange={handleThemeChange}
|
||||||
|
onClose={() => setThemeOpen(false)}
|
||||||
value={theme}
|
value={theme}
|
||||||
>
|
>
|
||||||
<SelectItem key="system" value="system">
|
<SelectItem key="system" value="system">
|
||||||
|
|
@ -274,7 +284,11 @@ const AccountModal = (props: Props) => {
|
||||||
<span>{t('menu.settings')}</span>
|
<span>{t('menu.settings')}</span>
|
||||||
</li>
|
</li>
|
||||||
</DialogTrigger>
|
</DialogTrigger>
|
||||||
<DialogContent className="Account Dialog">
|
<DialogContent
|
||||||
|
className="Account Dialog"
|
||||||
|
onOpenAutoFocus={(event: Event) => {}}
|
||||||
|
onEscapeKeyDown={onEscapeKeyDown}
|
||||||
|
>
|
||||||
<div className="DialogHeader">
|
<div className="DialogHeader">
|
||||||
<div className="DialogTop">
|
<div className="DialogTop">
|
||||||
<DialogTitle className="SubTitle">
|
<DialogTitle className="SubTitle">
|
||||||
|
|
|
||||||
|
|
@ -17,6 +17,7 @@ interface Props {
|
||||||
object: 'character' | 'weapon'
|
object: 'character' | 'weapon'
|
||||||
awakeningType?: number
|
awakeningType?: number
|
||||||
awakeningLevel?: number
|
awakeningLevel?: number
|
||||||
|
onOpenChange: (open: boolean) => void
|
||||||
sendValidity: (isValid: boolean) => void
|
sendValidity: (isValid: boolean) => void
|
||||||
sendValues: (type: number, level: number) => void
|
sendValues: (type: number, level: number) => void
|
||||||
}
|
}
|
||||||
|
|
@ -81,6 +82,11 @@ const AwakeningSelect = (props: Props) => {
|
||||||
// Classes
|
// Classes
|
||||||
function changeOpen() {
|
function changeOpen() {
|
||||||
setOpen(!open)
|
setOpen(!open)
|
||||||
|
props.onOpenChange(!open)
|
||||||
|
}
|
||||||
|
|
||||||
|
function onClose() {
|
||||||
|
props.onOpenChange(false)
|
||||||
}
|
}
|
||||||
|
|
||||||
function generateOptions(object: 'character' | 'weapon') {
|
function generateOptions(object: 'character' | 'weapon') {
|
||||||
|
|
@ -165,7 +171,8 @@ const AwakeningSelect = (props: Props) => {
|
||||||
value={`${awakeningType}`}
|
value={`${awakeningType}`}
|
||||||
open={open}
|
open={open}
|
||||||
onValueChange={handleSelectChange}
|
onValueChange={handleSelectChange}
|
||||||
onClick={() => changeOpen()}
|
onOpenChange={() => changeOpen()}
|
||||||
|
onClose={onClose}
|
||||||
triggerClass="modal"
|
triggerClass="modal"
|
||||||
>
|
>
|
||||||
{generateOptions(props.object)}
|
{generateOptions(props.object)}
|
||||||
|
|
|
||||||
|
|
@ -20,6 +20,7 @@ interface ErrorMap {
|
||||||
interface Props {
|
interface Props {
|
||||||
axType: number
|
axType: number
|
||||||
currentSkills?: SimpleAxSkill[]
|
currentSkills?: SimpleAxSkill[]
|
||||||
|
onOpenChange: (index: 1 | 2, open: boolean) => void
|
||||||
sendValidity: (isValid: boolean) => void
|
sendValidity: (isValid: boolean) => void
|
||||||
sendValues: (
|
sendValues: (
|
||||||
primaryAxModifier: number,
|
primaryAxModifier: number,
|
||||||
|
|
@ -193,9 +194,22 @@ const AXSelect = (props: Props) => {
|
||||||
: undefined
|
: undefined
|
||||||
}
|
}
|
||||||
|
|
||||||
function openSelect(ref: ForwardedRef<HTMLButtonElement>) {
|
function openSelect(index: 1 | 2) {
|
||||||
if (ref === primaryAxModifierSelect) setOpenAX1(!openAX1)
|
if (index === 1) {
|
||||||
if (ref === secondaryAxModifierSelect) setOpenAX2(!openAX2)
|
setOpenAX1(!openAX1)
|
||||||
|
setOpenAX2(false)
|
||||||
|
props.onOpenChange(1, !openAX1)
|
||||||
|
props.onOpenChange(2, false)
|
||||||
|
} else if (index === 2) {
|
||||||
|
setOpenAX2(!openAX2)
|
||||||
|
setOpenAX1(false)
|
||||||
|
props.onOpenChange(2, !openAX2)
|
||||||
|
props.onOpenChange(1, false)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function onClose(index: 1 | 2) {
|
||||||
|
props.onOpenChange(index, false)
|
||||||
}
|
}
|
||||||
|
|
||||||
function generateOptions(modifierSet: number) {
|
function generateOptions(modifierSet: number) {
|
||||||
|
|
@ -392,8 +406,9 @@ const AXSelect = (props: Props) => {
|
||||||
key="ax1"
|
key="ax1"
|
||||||
value={`${primaryAxModifier}`}
|
value={`${primaryAxModifier}`}
|
||||||
open={openAX1}
|
open={openAX1}
|
||||||
|
onClose={() => onClose(1)}
|
||||||
|
onOpenChange={() => openSelect(1)}
|
||||||
onValueChange={handleAX1SelectChange}
|
onValueChange={handleAX1SelectChange}
|
||||||
onClick={() => openSelect(primaryAxModifierSelect)}
|
|
||||||
triggerClass="modal"
|
triggerClass="modal"
|
||||||
>
|
>
|
||||||
{generateOptions(0)}
|
{generateOptions(0)}
|
||||||
|
|
@ -419,8 +434,9 @@ const AXSelect = (props: Props) => {
|
||||||
key="ax2"
|
key="ax2"
|
||||||
value={`${secondaryAxModifier}`}
|
value={`${secondaryAxModifier}`}
|
||||||
open={openAX2}
|
open={openAX2}
|
||||||
|
onClose={() => onClose(2)}
|
||||||
|
onOpenChange={() => openSelect(2)}
|
||||||
onValueChange={handleAX2SelectChange}
|
onValueChange={handleAX2SelectChange}
|
||||||
onClick={() => openSelect(secondaryAxModifierSelect)}
|
|
||||||
triggerClass="modal"
|
triggerClass="modal"
|
||||||
ref={secondaryAxModifierSelect}
|
ref={secondaryAxModifierSelect}
|
||||||
>
|
>
|
||||||
|
|
|
||||||
|
|
@ -8,7 +8,10 @@ interface Props
|
||||||
extends React.DetailedHTMLProps<
|
extends React.DetailedHTMLProps<
|
||||||
React.DialogHTMLAttributes<HTMLDivElement>,
|
React.DialogHTMLAttributes<HTMLDivElement>,
|
||||||
HTMLDivElement
|
HTMLDivElement
|
||||||
> {}
|
> {
|
||||||
|
onEscapeKeyDown: (event: KeyboardEvent) => void
|
||||||
|
onOpenAutoFocus: (event: Event) => void
|
||||||
|
}
|
||||||
|
|
||||||
export const DialogContent = React.forwardRef<HTMLDivElement, Props>(
|
export const DialogContent = React.forwardRef<HTMLDivElement, Props>(
|
||||||
function dialog({ children, ...props }, forwardedRef) {
|
function dialog({ children, ...props }, forwardedRef) {
|
||||||
|
|
@ -25,6 +28,8 @@ export const DialogContent = React.forwardRef<HTMLDivElement, Props>(
|
||||||
<DialogPrimitive.Content
|
<DialogPrimitive.Content
|
||||||
className={classes}
|
className={classes}
|
||||||
{...props}
|
{...props}
|
||||||
|
onOpenAutoFocus={props.onOpenAutoFocus}
|
||||||
|
onEscapeKeyDown={props.onEscapeKeyDown}
|
||||||
ref={forwardedRef}
|
ref={forwardedRef}
|
||||||
>
|
>
|
||||||
{children}
|
{children}
|
||||||
|
|
|
||||||
|
|
@ -60,12 +60,18 @@ const FilterBar = (props: Props) => {
|
||||||
props.onFilter({ raidSlug: slug })
|
props.onFilter({ raidSlug: slug })
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function onSelectChange(name: 'element' | 'recency') {
|
||||||
|
setElementOpen(name === 'element' ? !elementOpen : false)
|
||||||
|
setRecencyOpen(name === 'recency' ? !recencyOpen : false)
|
||||||
|
}
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div className={classes}>
|
<div className={classes}>
|
||||||
{props.children}
|
{props.children}
|
||||||
<Select
|
<Select
|
||||||
value={`${props.element}`}
|
value={`${props.element}`}
|
||||||
open={elementOpen}
|
open={elementOpen}
|
||||||
|
onOpenChange={() => onSelectChange('element')}
|
||||||
onValueChange={elementSelectChanged}
|
onValueChange={elementSelectChanged}
|
||||||
onClick={openElementSelect}
|
onClick={openElementSelect}
|
||||||
>
|
>
|
||||||
|
|
@ -106,6 +112,7 @@ const FilterBar = (props: Props) => {
|
||||||
value={`${props.recency}`}
|
value={`${props.recency}`}
|
||||||
trigger={'All time'}
|
trigger={'All time'}
|
||||||
open={recencyOpen}
|
open={recencyOpen}
|
||||||
|
onOpenChange={() => onSelectChange('recency')}
|
||||||
onValueChange={recencySelectChanged}
|
onValueChange={recencySelectChanged}
|
||||||
onClick={openRecencySelect}
|
onClick={openRecencySelect}
|
||||||
>
|
>
|
||||||
|
|
|
||||||
|
|
@ -106,6 +106,7 @@ const JobDropdown = React.forwardRef<HTMLSelectElement, Props>(
|
||||||
placeholder={'Select a class...'}
|
placeholder={'Select a class...'}
|
||||||
open={open}
|
open={open}
|
||||||
onClick={openJobSelect}
|
onClick={openJobSelect}
|
||||||
|
onOpenChange={() => setOpen(!open)}
|
||||||
onValueChange={handleChange}
|
onValueChange={handleChange}
|
||||||
triggerClass="Job"
|
triggerClass="Job"
|
||||||
>
|
>
|
||||||
|
|
|
||||||
|
|
@ -123,6 +123,7 @@ const RaidDropdown = React.forwardRef<HTMLSelectElement, Props>(
|
||||||
value={props.currentRaid}
|
value={props.currentRaid}
|
||||||
placeholder={'Select a raid...'}
|
placeholder={'Select a raid...'}
|
||||||
open={open}
|
open={open}
|
||||||
|
onOpenChange={() => setOpen(!open)}
|
||||||
onClick={openRaidSelect}
|
onClick={openRaidSelect}
|
||||||
onValueChange={handleChange}
|
onValueChange={handleChange}
|
||||||
>
|
>
|
||||||
|
|
|
||||||
|
|
@ -15,8 +15,9 @@ interface Props
|
||||||
open: boolean
|
open: boolean
|
||||||
trigger?: React.ReactNode
|
trigger?: React.ReactNode
|
||||||
children?: React.ReactNode
|
children?: React.ReactNode
|
||||||
onClick?: () => void
|
onOpenChange?: () => void
|
||||||
onValueChange?: (value: string) => void
|
onValueChange?: (value: string) => void
|
||||||
|
onClose?: () => void
|
||||||
triggerClass?: string
|
triggerClass?: string
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -24,8 +25,13 @@ const Select = React.forwardRef<HTMLButtonElement, Props>(function Select(
|
||||||
props: Props,
|
props: Props,
|
||||||
forwardedRef
|
forwardedRef
|
||||||
) {
|
) {
|
||||||
|
const [open, setOpen] = useState(false)
|
||||||
const [value, setValue] = useState('')
|
const [value, setValue] = useState('')
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
setOpen(props.open)
|
||||||
|
}, [props.open])
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
if (props.value && props.value !== '') setValue(`${props.value}`)
|
if (props.value && props.value !== '') setValue(`${props.value}`)
|
||||||
else setValue('')
|
else setValue('')
|
||||||
|
|
@ -36,10 +42,27 @@ const Select = React.forwardRef<HTMLButtonElement, Props>(function Select(
|
||||||
if (props.onValueChange) props.onValueChange(newValue)
|
if (props.onValueChange) props.onValueChange(newValue)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function onCloseAutoFocus() {
|
||||||
|
setOpen(false)
|
||||||
|
if (props.onClose) props.onClose()
|
||||||
|
}
|
||||||
|
|
||||||
|
function onEscapeKeyDown() {
|
||||||
|
setOpen(false)
|
||||||
|
if (props.onClose) props.onClose()
|
||||||
|
}
|
||||||
|
|
||||||
|
function onPointerDownOutside() {
|
||||||
|
setOpen(false)
|
||||||
|
if (props.onClose) props.onClose()
|
||||||
|
}
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<RadixSelect.Root
|
<RadixSelect.Root
|
||||||
|
open={open}
|
||||||
value={value !== '' ? value : undefined}
|
value={value !== '' ? value : undefined}
|
||||||
onValueChange={onValueChange}
|
onValueChange={onValueChange}
|
||||||
|
onOpenChange={props.onOpenChange}
|
||||||
>
|
>
|
||||||
<RadixSelect.Trigger
|
<RadixSelect.Trigger
|
||||||
className={classNames('SelectTrigger', props.triggerClass)}
|
className={classNames('SelectTrigger', props.triggerClass)}
|
||||||
|
|
@ -53,7 +76,11 @@ const Select = React.forwardRef<HTMLButtonElement, Props>(function Select(
|
||||||
</RadixSelect.Trigger>
|
</RadixSelect.Trigger>
|
||||||
|
|
||||||
<RadixSelect.Portal className="Select">
|
<RadixSelect.Portal className="Select">
|
||||||
<RadixSelect.Content>
|
<RadixSelect.Content
|
||||||
|
onCloseAutoFocus={onCloseAutoFocus}
|
||||||
|
onEscapeKeyDown={onEscapeKeyDown}
|
||||||
|
onPointerDownOutside={onPointerDownOutside}
|
||||||
|
>
|
||||||
<RadixSelect.ScrollUpButton className="Scroll Up">
|
<RadixSelect.ScrollUpButton className="Scroll Up">
|
||||||
<ArrowIcon />
|
<ArrowIcon />
|
||||||
</RadixSelect.ScrollUpButton>
|
</RadixSelect.ScrollUpButton>
|
||||||
|
|
|
||||||
|
|
@ -15,8 +15,9 @@ interface Props {
|
||||||
imageClass?: string
|
imageClass?: string
|
||||||
imageSrc?: string[]
|
imageSrc?: string[]
|
||||||
children: React.ReactNode
|
children: React.ReactNode
|
||||||
onClick: () => void
|
onOpenChange: () => void
|
||||||
onChange: (value: string) => void
|
onChange: (value: string) => void
|
||||||
|
onClose: () => void
|
||||||
}
|
}
|
||||||
|
|
||||||
const SelectTableField = (props: Props) => {
|
const SelectTableField = (props: Props) => {
|
||||||
|
|
@ -53,8 +54,9 @@ const SelectTableField = (props: Props) => {
|
||||||
<Select
|
<Select
|
||||||
name={props.name}
|
name={props.name}
|
||||||
open={props.open}
|
open={props.open}
|
||||||
onClick={props.onClick}
|
onOpenChange={props.onOpenChange}
|
||||||
onValueChange={props.onChange}
|
onValueChange={props.onChange}
|
||||||
|
onClose={props.onClose}
|
||||||
triggerClass={classNames({ Bound: true, Table: true })}
|
triggerClass={classNames({ Bound: true, Table: true })}
|
||||||
value={value}
|
value={value}
|
||||||
>
|
>
|
||||||
|
|
|
||||||
|
|
@ -9,10 +9,13 @@ import './index.scss'
|
||||||
|
|
||||||
// Props
|
// Props
|
||||||
interface Props {
|
interface Props {
|
||||||
|
open: boolean
|
||||||
currentValue?: WeaponKey
|
currentValue?: WeaponKey
|
||||||
series: number
|
series: number
|
||||||
slot: number
|
slot: number
|
||||||
onChange?: (value: string, slot: number) => void
|
onChange?: (value: string, slot: number) => void
|
||||||
|
onOpenChange: () => void
|
||||||
|
onClose?: () => void
|
||||||
}
|
}
|
||||||
|
|
||||||
const WeaponKeySelect = React.forwardRef<HTMLButtonElement, Props>(
|
const WeaponKeySelect = React.forwardRef<HTMLButtonElement, Props>(
|
||||||
|
|
@ -64,10 +67,6 @@ const WeaponKeySelect = React.forwardRef<HTMLButtonElement, Props>(
|
||||||
fetchWeaponKeys()
|
fetchWeaponKeys()
|
||||||
}, [props.series, props.slot])
|
}, [props.series, props.slot])
|
||||||
|
|
||||||
function openSelect() {
|
|
||||||
setOpen(!open)
|
|
||||||
}
|
|
||||||
|
|
||||||
function weaponKeyGroup(index: number) {
|
function weaponKeyGroup(index: number) {
|
||||||
;['α', 'β', 'γ', 'Δ'].sort((a, b) => a.localeCompare(b, 'el'))
|
;['α', 'β', 'γ', 'Δ'].sort((a, b) => a.localeCompare(b, 'el'))
|
||||||
|
|
||||||
|
|
@ -125,9 +124,10 @@ const WeaponKeySelect = React.forwardRef<HTMLButtonElement, Props>(
|
||||||
<Select
|
<Select
|
||||||
key={`weapon-key-${props.slot}`}
|
key={`weapon-key-${props.slot}`}
|
||||||
value={props.currentValue ? props.currentValue.id : 'no-key'}
|
value={props.currentValue ? props.currentValue.id : 'no-key'}
|
||||||
open={open}
|
open={props.open}
|
||||||
|
onClose={props.onClose}
|
||||||
|
onOpenChange={props.onOpenChange}
|
||||||
onValueChange={handleChange}
|
onValueChange={handleChange}
|
||||||
onClick={openSelect}
|
|
||||||
ref={ref}
|
ref={ref}
|
||||||
triggerClass="modal"
|
triggerClass="modal"
|
||||||
>
|
>
|
||||||
|
|
|
||||||
|
|
@ -4,7 +4,13 @@ import { useRouter } from 'next/router'
|
||||||
import { useTranslation } from 'next-i18next'
|
import { useTranslation } from 'next-i18next'
|
||||||
import { AxiosResponse } from 'axios'
|
import { AxiosResponse } from 'axios'
|
||||||
|
|
||||||
import * as Dialog from '@radix-ui/react-dialog'
|
import {
|
||||||
|
Dialog,
|
||||||
|
DialogClose,
|
||||||
|
DialogContent,
|
||||||
|
DialogTitle,
|
||||||
|
DialogTrigger,
|
||||||
|
} from '~components/Dialog'
|
||||||
|
|
||||||
import AXSelect from '~components/AxSelect'
|
import AXSelect from '~components/AxSelect'
|
||||||
import AwakeningSelect from '~components/AwakeningSelect'
|
import AwakeningSelect from '~components/AwakeningSelect'
|
||||||
|
|
@ -74,6 +80,14 @@ const WeaponModal = (props: Props) => {
|
||||||
const [weaponKey2Id, setWeaponKey2Id] = useState('')
|
const [weaponKey2Id, setWeaponKey2Id] = useState('')
|
||||||
const [weaponKey3Id, setWeaponKey3Id] = useState('')
|
const [weaponKey3Id, setWeaponKey3Id] = useState('')
|
||||||
|
|
||||||
|
const [weaponKey1Open, setWeaponKey1Open] = useState(false)
|
||||||
|
const [weaponKey2Open, setWeaponKey2Open] = useState(false)
|
||||||
|
const [weaponKey3Open, setWeaponKey3Open] = useState(false)
|
||||||
|
const [weaponKey4Open, setWeaponKey4Open] = useState(false)
|
||||||
|
const [ax1Open, setAx1Open] = useState(false)
|
||||||
|
const [ax2Open, setAx2Open] = useState(false)
|
||||||
|
const [awakeningOpen, setAwakeningOpen] = useState(false)
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
setElement(props.gridWeapon.element)
|
setElement(props.gridWeapon.element)
|
||||||
|
|
||||||
|
|
@ -188,16 +202,35 @@ const WeaponModal = (props: Props) => {
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function openSelect(index: 1 | 2 | 3 | 4) {
|
||||||
|
setWeaponKey1Open(index === 1 ? !weaponKey1Open : false)
|
||||||
|
setWeaponKey2Open(index === 2 ? !weaponKey2Open : false)
|
||||||
|
setWeaponKey3Open(index === 3 ? !weaponKey3Open : false)
|
||||||
|
setWeaponKey4Open(index === 4 ? !weaponKey4Open : false)
|
||||||
|
}
|
||||||
|
|
||||||
|
function receiveAxOpen(index: 1 | 2, isOpen: boolean) {
|
||||||
|
if (index === 1) setAx1Open(isOpen)
|
||||||
|
if (index === 2) setAx2Open(isOpen)
|
||||||
|
}
|
||||||
|
|
||||||
|
function receiveAwakeningOpen(isOpen: boolean) {
|
||||||
|
setAwakeningOpen(isOpen)
|
||||||
|
}
|
||||||
|
|
||||||
const keySelect = () => {
|
const keySelect = () => {
|
||||||
return (
|
return (
|
||||||
<section>
|
<section>
|
||||||
<h3>{t('modals.weapon.subtitles.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) ? (
|
||||||
<WeaponKeySelect
|
<WeaponKeySelect
|
||||||
|
open={weaponKey1Open}
|
||||||
currentValue={weaponKey1 != null ? weaponKey1 : undefined}
|
currentValue={weaponKey1 != null ? weaponKey1 : undefined}
|
||||||
series={props.gridWeapon.object.series}
|
series={props.gridWeapon.object.series}
|
||||||
slot={0}
|
slot={0}
|
||||||
|
onOpenChange={() => openSelect(1)}
|
||||||
onChange={receiveWeaponKey}
|
onChange={receiveWeaponKey}
|
||||||
|
onClose={() => setWeaponKey1Open(false)}
|
||||||
/>
|
/>
|
||||||
) : (
|
) : (
|
||||||
''
|
''
|
||||||
|
|
@ -205,10 +238,13 @@ const WeaponModal = (props: Props) => {
|
||||||
|
|
||||||
{[2, 3, 17].includes(props.gridWeapon.object.series) ? (
|
{[2, 3, 17].includes(props.gridWeapon.object.series) ? (
|
||||||
<WeaponKeySelect
|
<WeaponKeySelect
|
||||||
|
open={weaponKey2Open}
|
||||||
currentValue={weaponKey2 != null ? weaponKey2 : undefined}
|
currentValue={weaponKey2 != null ? weaponKey2 : undefined}
|
||||||
series={props.gridWeapon.object.series}
|
series={props.gridWeapon.object.series}
|
||||||
slot={1}
|
slot={1}
|
||||||
|
onOpenChange={() => openSelect(2)}
|
||||||
onChange={receiveWeaponKey}
|
onChange={receiveWeaponKey}
|
||||||
|
onClose={() => setWeaponKey2Open(false)}
|
||||||
/>
|
/>
|
||||||
) : (
|
) : (
|
||||||
''
|
''
|
||||||
|
|
@ -216,10 +252,13 @@ const WeaponModal = (props: Props) => {
|
||||||
|
|
||||||
{props.gridWeapon.object.series == 17 ? (
|
{props.gridWeapon.object.series == 17 ? (
|
||||||
<WeaponKeySelect
|
<WeaponKeySelect
|
||||||
|
open={weaponKey3Open}
|
||||||
currentValue={weaponKey3 != null ? weaponKey3 : undefined}
|
currentValue={weaponKey3 != null ? weaponKey3 : undefined}
|
||||||
series={props.gridWeapon.object.series}
|
series={props.gridWeapon.object.series}
|
||||||
slot={2}
|
slot={2}
|
||||||
|
onOpenChange={() => openSelect(3)}
|
||||||
onChange={receiveWeaponKey}
|
onChange={receiveWeaponKey}
|
||||||
|
onClose={() => setWeaponKey3Open(false)}
|
||||||
/>
|
/>
|
||||||
) : (
|
) : (
|
||||||
''
|
''
|
||||||
|
|
@ -228,10 +267,13 @@ const WeaponModal = (props: Props) => {
|
||||||
{props.gridWeapon.object.series == 24 &&
|
{props.gridWeapon.object.series == 24 &&
|
||||||
props.gridWeapon.object.uncap.ulb ? (
|
props.gridWeapon.object.uncap.ulb ? (
|
||||||
<WeaponKeySelect
|
<WeaponKeySelect
|
||||||
|
open={weaponKey4Open}
|
||||||
currentValue={weaponKey1 != null ? weaponKey1 : undefined}
|
currentValue={weaponKey1 != null ? weaponKey1 : undefined}
|
||||||
series={props.gridWeapon.object.series}
|
series={props.gridWeapon.object.series}
|
||||||
slot={0}
|
slot={0}
|
||||||
|
onOpenChange={() => openSelect(4)}
|
||||||
onChange={receiveWeaponKey}
|
onChange={receiveWeaponKey}
|
||||||
|
onClose={() => setWeaponKey4Open(false)}
|
||||||
/>
|
/>
|
||||||
) : (
|
) : (
|
||||||
''
|
''
|
||||||
|
|
@ -247,6 +289,7 @@ const WeaponModal = (props: Props) => {
|
||||||
<AXSelect
|
<AXSelect
|
||||||
axType={props.gridWeapon.object.ax}
|
axType={props.gridWeapon.object.ax}
|
||||||
currentSkills={props.gridWeapon.ax}
|
currentSkills={props.gridWeapon.ax}
|
||||||
|
onOpenChange={receiveAxOpen}
|
||||||
sendValidity={receiveValidity}
|
sendValidity={receiveValidity}
|
||||||
sendValues={receiveAxValues}
|
sendValues={receiveAxValues}
|
||||||
/>
|
/>
|
||||||
|
|
@ -262,6 +305,7 @@ const WeaponModal = (props: Props) => {
|
||||||
object="weapon"
|
object="weapon"
|
||||||
awakeningType={props.gridWeapon.awakening?.type}
|
awakeningType={props.gridWeapon.awakening?.type}
|
||||||
awakeningLevel={props.gridWeapon.awakening?.level}
|
awakeningLevel={props.gridWeapon.awakening?.level}
|
||||||
|
onOpenChange={receiveAwakeningOpen}
|
||||||
sendValidity={receiveValidity}
|
sendValidity={receiveValidity}
|
||||||
sendValues={receiveAwakeningValues}
|
sendValues={receiveAwakeningValues}
|
||||||
/>
|
/>
|
||||||
|
|
@ -278,29 +322,46 @@ const WeaponModal = (props: Props) => {
|
||||||
setOpen(open)
|
setOpen(open)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const anySelectOpen =
|
||||||
|
weaponKey1Open ||
|
||||||
|
weaponKey2Open ||
|
||||||
|
weaponKey3Open ||
|
||||||
|
weaponKey4Open ||
|
||||||
|
ax1Open ||
|
||||||
|
ax2Open ||
|
||||||
|
awakeningOpen
|
||||||
|
|
||||||
|
function onEscapeKeyDown(event: KeyboardEvent) {
|
||||||
|
if (anySelectOpen) {
|
||||||
|
return event.preventDefault()
|
||||||
|
} else {
|
||||||
|
setOpen(false)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return (
|
return (
|
||||||
// TODO: Refactor into Dialog component
|
// TODO: Refactor into Dialog component
|
||||||
<Dialog.Root open={open} onOpenChange={openChange}>
|
<Dialog open={open} onOpenChange={openChange}>
|
||||||
<Dialog.Trigger asChild>{props.children}</Dialog.Trigger>
|
<DialogTrigger asChild>{props.children}</DialogTrigger>
|
||||||
<Dialog.Portal>
|
<DialogContent
|
||||||
<Dialog.Content
|
|
||||||
className="Weapon Dialog"
|
className="Weapon Dialog"
|
||||||
onOpenAutoFocus={(event) => event.preventDefault()}
|
onOpenAutoFocus={(event) => event.preventDefault()}
|
||||||
|
onEscapeKeyDown={onEscapeKeyDown}
|
||||||
>
|
>
|
||||||
<div className="DialogHeader">
|
<div className="DialogHeader">
|
||||||
<div className="DialogTop">
|
<div className="DialogTop">
|
||||||
<Dialog.Title className="SubTitle">
|
<DialogTitle className="SubTitle">
|
||||||
{t('modals.weapon.title')}
|
{t('modals.weapon.title')}
|
||||||
</Dialog.Title>
|
</DialogTitle>
|
||||||
<Dialog.Title className="DialogTitle">
|
<DialogTitle className="DialogTitle">
|
||||||
{props.gridWeapon.object.name[locale]}
|
{props.gridWeapon.object.name[locale]}
|
||||||
</Dialog.Title>
|
</DialogTitle>
|
||||||
</div>
|
</div>
|
||||||
<Dialog.Close className="DialogClose" asChild>
|
<DialogClose className="DialogClose" asChild>
|
||||||
<span>
|
<span>
|
||||||
<CrossIcon />
|
<CrossIcon />
|
||||||
</span>
|
</span>
|
||||||
</Dialog.Close>
|
</DialogClose>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div className="mods">
|
<div className="mods">
|
||||||
|
|
@ -317,10 +378,8 @@ const WeaponModal = (props: Props) => {
|
||||||
text={t('modals.weapon.buttons.confirm')}
|
text={t('modals.weapon.buttons.confirm')}
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
</Dialog.Content>
|
</DialogContent>
|
||||||
<Dialog.Overlay className="Overlay" />
|
</Dialog>
|
||||||
</Dialog.Portal>
|
|
||||||
</Dialog.Root>
|
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue