Update components dealing with selecting weapons

You can select a weapon and if there is no party, it will create one on the server. It will associate subsequently added weapons to that party.
This commit is contained in:
Justin Edmund 2020-09-16 03:46:56 -07:00
parent b59c92b390
commit 0d862e8085
7 changed files with 194 additions and 72 deletions

View file

@ -9,8 +9,9 @@ import './SearchModal.css'
interface Props {
close: () => void
send: (weapon: Weapon) => void
send: (weapon: Weapon, position: number) => any
placeholderText: string
fromPosition: number
}
interface State {
@ -24,7 +25,7 @@ interface State {
class SearchModal extends React.Component<Props, State> {
searchQuery
constructor(props) {
constructor(props: Props) {
super(props)
this.state = {
query: '',
@ -36,7 +37,7 @@ class SearchModal extends React.Component<Props, State> {
}
fetchResults = (query) => {
fetch(`http://grid-api.ngrok.io/api/v1/search?query=${query}`)
fetch(`http://127.0.0.1:3000/api/v1/search?query=${query}`)
.then(res => res.json())
.then((result) => {
const totalResults = result.length
@ -64,14 +65,19 @@ class SearchModal extends React.Component<Props, State> {
}
}
sendData = (result: Weapon) => {
this.props.send(result, this.props.fromPosition)
this.props.close()
}
renderSearchResults = () => {
const { results } = this.state
if (results.length) {
return (
<ul id="results_container">
{ results.map( result => {
return <WeaponResult key={result.id} data={result} onClick={() => { this.props.send(result) }} />
{ results.map( (result: Weapon) => {
return <WeaponResult key={result.id} data={result} onClick={() => { this.sendData(result) }} />
})}
</ul>
)

View file

@ -4,19 +4,25 @@
justify-content: center;
}
.grid-weapons {
#grid_weapons {
display: flex;
flex-direction: row;
flex-wrap: wrap;
margin: 0;
padding: 0;
width: 528px;
}
.grid-weapons > * {
#grid_weapons > * {
margin-bottom: 72px;
margin-right: 24px;
}
.grid-weapons > *:nth-child(3n+3) {
#grid_weapons > *:nth-child(3n+3) {
margin-right: 0;
}
#grid_weapons > li {
list-style: none;
}

View file

@ -1,28 +1,160 @@
import React from 'react'
import './WeaponGrid.css'
import React, { useEffect, useState } from 'react'
import { withRouter } from 'react-router'
import WeaponGridMainhand from '../WeaponGridMainhand/WeaponGridMainhand'
import WeaponGridUnit from '../WeaponGridUnit/WeaponGridUnit'
class WeaponGrid extends React.Component {
render() {
const numWeapons = 9
let weapons = []
import './WeaponGrid.css'
Array.from(Array(numWeapons)).forEach((x, i) => {
weapons.push(<WeaponGridUnit key={`grid_unit_${i}`} />)
const WeaponGrid = (props: null) => {
const [partyId, setPartyId] = useState<string>()
const [shortcode, setShortcode] = useState<string>()
const [mainhand, setMainhand] = useState<Weapon>()
const [weapons, setWeapons] = useState<{ [key: number]: Weapon }>({})
const numWeapons: number = 9
useEffect(() => {
const shortcode = props.match.params.hash
if (shortcode) {
console.log(shortcode)
} else {
console.log('nothing')
}
}, [])
function fetchGrid(shortcode: string) {
// const body = JSON.stringify({
// 'weapon': {
// 'party_id': pid,
// 'weapon_id': weapon.id,
// 'position': position
// }
// })
// const options = {
// headers: { 'Content-Type': 'application/json' },
// method: 'POST',
// body: body
// }
}
function receiveMainhand(weapon: Weapon, _: number) {
// Store the mainhand weapon
setMainhand(weapon)
if (partyId === undefined) {
let _partyId = ''
createParty().then(data => {
setPartyId(data.party.id)
_partyId = data.party.id
return data.party.shortcode
})
.then((code: string) => {
setShortcode(shortcode)
window.history.replaceState(null, `Grid Tool: ${code}`, `/p/${code}`)
})
.then(() => {
saveMainhand(_partyId, weapon)
})
} else {
saveMainhand(partyId, weapon)
}
}
function receiveWeapon(weapon: Weapon, position: number) {
// Store the grid unit weapon at the correct position
let newWeapons = Object.assign({}, weapons)
newWeapons[position] = weapon
setWeapons(newWeapons)
if (partyId === undefined) {
let _partyId = ''
createParty().then(data => {
setPartyId(data.party.id)
_partyId = data.party.id
return data.party.shortcode
})
.then(() => {
saveWeapon(_partyId, weapon, position)
})
} else {
saveWeapon(partyId, weapon, position)
}
}
function createParty() {
const options = {
headers: { 'Content-Type': 'application/json' },
method: 'POST'
}
return fetch('http://127.0.0.1:3000/api/v1/party', options)
.then(response => response.json())
}
function saveWeapon(pid: string, weapon: Weapon, position: number) {
const body = JSON.stringify({
'weapon': {
'party_id': pid,
'weapon_id': weapon.id,
'position': position,
'mainhand': false
}
})
return (
<div className="WeaponGrid">
<WeaponGridMainhand key="grid_mainhand" />
const options = {
headers: { 'Content-Type': 'application/json' },
method: 'POST',
body: body
}
<div className="grid-weapons">
{weapons}
</div>
</div>
)
fetch('http://127.0.0.1:3000/api/v1/weapons', options)
.then(data => {
console.log(data)
})
}
function saveMainhand(pid: string, weapon: Weapon) {
const body = JSON.stringify({
'weapon': {
'party_id': pid,
'weapon_id': weapon.id,
'mainhand': true
}
})
const options = {
headers: { 'Content-Type': 'application/json' },
method: 'POST',
body: body
}
fetch('http://127.0.0.1:3000/api/v1/weapons', options)
.then(data => {
console.log(data)
})
}
return (
<div className="WeaponGrid">
<WeaponGridMainhand key="grid_mainhand" onReceiveData={receiveMainhand} position={0} weapon={mainhand} />
<ul id="grid_weapons">
{
Array.from(Array(numWeapons)).map((x, i) => {
return <WeaponGridUnit key={`grid_unit_${i}`} onReceiveData={receiveWeapon} position={i} weapon={weapons[i]} />
})
}
</ul>
</div>
)
}
export default WeaponGrid
export default withRouter(WeaponGrid)

View file

@ -1,38 +1,29 @@
import React, { useEffect, useState } from 'react'
import './WeaponGridMainhand.css'
import React, { useEffect } from 'react'
import SearchModal from '../SearchModal/SearchModal'
import { useModal as useModal } from '../../useModal'
import './WeaponGridMainhand.css'
import mainhandImages from '../../images/mainhand/*.jpg'
import Plus from '../../../assets/plus.svg'
function WeaponGridUnit() {
function WeaponGridMainhand(props: WeaponGridProps) {
const { open, openModal, closeModal } = useModal()
const [weapon, setWeapon] = useState<Weapon>({
id: '',
granblue_id: 0,
name: {
en: '',
jp: ''
}
})
function receiveData(data: Weapon) {
setWeapon(data)
closeModal()
}
useEffect(() => {
console.log('Mainhand weapon prop was updated.')
}, [props.weapon])
return (
<div>
<div className="WeaponGridMainhand" onClick={openModal}>
<img className="grid_image" src={mainhandImages[weapon.granblue_id]} />
<img className="grid_image" src={mainhandImages[props.weapon?.granblue_id]} />
<span className='icon'><Plus /></span>
</div>
{open ? (
<SearchModal
close={closeModal}
send={receiveData}
send={props.onReceiveData}
fromPosition={props.position}
placeholderText="Search for a weapon..."
/>
) : null}
@ -40,4 +31,4 @@ function WeaponGridUnit() {
)
}
export default WeaponGridUnit
export default WeaponGridMainhand

View file

@ -1,11 +1,13 @@
.WeaponGridUnit {
display: flex;
align-items: center;
justify-content: center;
background: white;
border: 1px solid rgba(0, 0, 0, 0);
border-radius: 8px;
display: flex;
height: 92px;
justify-content: center;
list-style-type: none;
overflow: hidden;
transition: all 0.18s ease-in-out;
width: 160px;

View file

@ -1,44 +1,30 @@
import React, { useEffect, useState } from 'react'
import './WeaponGridUnit.css'
import React from 'react'
import SearchModal from '../SearchModal/SearchModal'
import { useModal as useModal } from '../../useModal'
import './WeaponGridUnit.css'
import gridImages from '../../images/grid/*.jpg'
import Plus from '../../../assets/plus.svg'
function WeaponGridUnit() {
function WeaponGridUnit(props: WeaponGridProps) {
const { open, openModal, closeModal } = useModal()
const [weapon, setWeapon] = useState<Weapon>({
id: '',
granblue_id: 0,
name: {
en: '',
jp: ''
}
})
function receiveData(data: Weapon) {
setWeapon(data)
closeModal()
}
return (
<div>
<li>
<div className="WeaponGridUnit" onClick={openModal}>
<img className="grid_image" src={gridImages[weapon.granblue_id]} />
<img className="grid_image" src={gridImages[props.weapon?.granblue_id]} />
<span className='icon'><Plus /></span>
</div>
{open ? (
<SearchModal
close={closeModal}
send={receiveData}
send={props.onReceiveData}
fromPosition={props.position}
placeholderText="Search for a weapon..."
/>
) : null}
</div>
</li>
)
}
export default WeaponGridUnit
export default WeaponGridUnit

View file

@ -8,13 +8,12 @@ import gridImages from '../../images/grid/*.jpg'
interface Props {
data: Weapon
onClick: () => Weapon
onClick: () => void
}
const Element = ['null', 'wind', 'fire', 'water', 'earth', 'dark', 'light']
const Proficiency = ['none', 'sword', 'dagger', 'axe', 'spear', 'bow', 'staff', 'fist', 'harp', 'gun', 'katana']
class WeaponResult extends React.Component<Props> {
render() {
const weapon = this.props.data