hensei-web/components/Party/index.tsx

161 lines
No EOL
4.3 KiB
TypeScript

import React, { useEffect, useState } from 'react'
import { useCookies } from 'react-cookie'
import PartyContext from '~context/PartyContext'
import PartySegmentedControl from '~components/PartySegmentedControl'
import WeaponGrid from '~components/WeaponGrid'
import SummonGrid from '~components/SummonGrid'
import CharacterGrid from '~components/CharacterGrid'
import api from '~utils/api'
import { TeamElement } from '~utils/enums'
import './index.scss'
// GridType
enum GridType {
Class,
Character,
Weapon,
Summon
}
// Props
interface Props {
partyId?: string
mainWeapon?: GridWeapon
mainSummon?: GridSummon
friendSummon?: GridSummon
characters?: GridArray<GridCharacter>
weapons?: GridArray<GridWeapon>
summons?: GridArray<GridSummon>
extra: boolean
editable: boolean
pushHistory?: (path: string) => void
}
const Party = (props: Props) => {
// Cookies
const [cookies, _] = useCookies(['user'])
const headers = (cookies.user != null) ? {
headers: {
'Authorization': `Bearer ${cookies.user.access_token}`
}
} : {}
// Set up states
const [extra, setExtra] = useState<boolean>(false)
const [currentTab, setCurrentTab] = useState<GridType>(GridType.Weapon)
const [element, setElement] = useState<TeamElement>(TeamElement.Any)
// Set states from props
useEffect(() => {
setExtra(props.extra || false)
}, [props])
// Methods: Creating a new party
async function createParty() {
let body = {
party: {
...(cookies.user) && { user_id: cookies.user.user_id },
is_extra: extra
}
}
return await api.endpoints.parties.create(body, headers)
}
// Methods: Updating the party's extra flag
// Note: This doesn't save to the server yet.
function checkboxChanged(event: React.ChangeEvent<HTMLInputElement>) {
setExtra(event.target.checked)
}
// Methods: Navigating with segmented control
function segmentClicked(event: React.ChangeEvent<HTMLInputElement>) {
switch(event.target.value) {
case 'class':
setCurrentTab(GridType.Class)
break
case 'characters':
setCurrentTab(GridType.Character)
break
case 'weapons':
setCurrentTab(GridType.Weapon)
break
case 'summons':
setCurrentTab(GridType.Summon)
break
default:
break
}
}
// Render: JSX components
const navigation = (
<PartySegmentedControl
extra={extra}
editable={props.editable}
selectedTab={currentTab}
onClick={segmentClicked}
onCheckboxChange={checkboxChanged}
/>
)
const weaponGrid = (
<WeaponGrid
partyId={props.partyId}
mainhand={props.mainWeapon}
weapons={props.weapons || {}}
extra={extra}
editable={props.editable}
createParty={createParty}
pushHistory={props.pushHistory}
/>
)
const summonGrid = (
<SummonGrid
partyId={props.partyId}
mainSummon={props.mainSummon}
friendSummon={props.friendSummon}
summons={props.summons || {}}
editable={props.editable}
createParty={createParty}
pushHistory={props.pushHistory}
/>
)
const characterGrid = (
<CharacterGrid
partyId={props.partyId}
characters={props.characters || {}}
editable={props.editable}
createParty={createParty}
pushHistory={props.pushHistory}
/>
)
const currentGrid = () => {
switch(currentTab) {
case GridType.Character:
return characterGrid
case GridType.Weapon:
return weaponGrid
case GridType.Summon:
return summonGrid
}
}
return (
<div>
<PartyContext.Provider value={{ element, setElement }}>
{ navigation }
{ currentGrid() }
</PartyContext.Provider>
</div>
)
}
export default Party