I tested Redux with creating a little RPG game.
(我通过创建一个小的RPG游戏测试了Redux。)
I have a component called Monster who move on the map.
(我有一个叫做Monster的组件,它在地图上移动。)
The position, the direction and the spriteLocation are controlled by the store. (位置,方向和spriteLocation由商店控制。)
The monster Reducer look like this: (怪物Reducer看起来像这样:)
const intialState = {
position: [0,360],
spriteLocation: '0px 80px',
direction: 'EAST',
walkIndex : 0
}
const monsterReducer = (state = intialState, action) => {
switch(action.type){
case 'MOVE_MONSTER':
return {
...action.payload
}
default:
return state
}
}
export default monsterReducer
The moves are dispatched like that:
(动作的调度是这样的:)
import store from '../../config/store'
import {SPRITE_SIZE, MAP_WIDTH, MAP_HEIGHT} from '../../config/constants'
export default function handleMovement(monster){
//APPEL AU DEPLACEMENT TOUTES LES X secondes
// setInterval(handleMove(store.getState().monster.direction), 500);
setInterval(() => {
handleMove(store.getState().monster.direction)
}, 300);
function handleMove(direction){
switch(direction){
case 'WEST':
return attemptMove('WEST')
case 'EAST':
return attemptMove('EAST')
case 'NORTH':
return attemptMove('NORTH')
case 'SOUTH':
return attemptMove('SOUTH')
default:
}
}
function attemptMove(direction){
const oldPos = store.getState().monster.position
const newPos = getNewPosition(oldPos,direction)
if(observeBoundaries(newPos) && observeImpassable(newPos)){
dispatchMove(direction, newPos)
}else{
switch(direction){
case 'WEST':
return attemptMove('EAST')
case 'EAST':
return attemptMove('WEST')
case 'NORTH':
return attemptMove('SOUTH')
case 'SOUTH':
return attemptMove('NORTH')
default:
}
}
}
//UPDATE DE LA POSITION
function getNewPosition(oldPos, direction){
switch(direction){
case 'WEST':
return [oldPos[0]-SPRITE_SIZE, oldPos[1]]
case 'EAST':
return [oldPos[0]+SPRITE_SIZE, oldPos[1]]
case 'NORTH':
return [oldPos[0], oldPos[1]-SPRITE_SIZE]
case 'SOUTH':
return [oldPos[0], oldPos[1]+SPRITE_SIZE]
default:
}
}
function observeBoundaries(newPos){
//SI ON EST DANS LA MAP ON RETOURNE TRUE SINON FALSE
return (newPos[0] >= 0 && newPos[0] <= MAP_WIDTH-SPRITE_SIZE) &&
(newPos[1] >= 0 && newPos[1] <= MAP_HEIGHT-SPRITE_SIZE)
}
function observeImpassable(newPos){
//TEST DES OBSTACLES
const tiles = store.getState().map.tiles
const y = newPos[1] / SPRITE_SIZE
const x = newPos[0] / SPRITE_SIZE
const nextTile = tiles[y][x]
return nextTile < 5
}
function getWalkIndex(){
const walkIndex = store.getState().monster.walkIndex
return walkIndex >= 4 ? 0 : walkIndex+1
}
function getSpriteLocation(direction, walkIndex){
switch (direction){
case 'EAST' :
return `${SPRITE_SIZE*walkIndex}px ${SPRITE_SIZE*2}px`
case 'SOUTH' :
return `${SPRITE_SIZE*walkIndex}px ${SPRITE_SIZE*0}px`
case 'WEST' :
return `${SPRITE_SIZE*walkIndex}px ${SPRITE_SIZE*3}px`
case 'NORTH' :
return `${SPRITE_SIZE*walkIndex}px ${SPRITE_SIZE*1}px`
default:
}
}
//DISPATCH DE LA NOUVELLE POSITION ET DIRECTION POUR ANIMATION DU PERSO AU STORE
function dispatchMove(direction, newPos){
const walkIndex = getWalkIndex()
store.dispatch({
type: 'MOVE_MONSTER',
payload: {
position: newPos,
direction,
walkIndex,
spriteLocation : getSpriteLocation(direction, walkIndex)
}
})
}
return monster
}
I would like to create another Monster component but with different initial state but who works with the same reducer.
(我想创建另一个Monster组件,但是初始状态不同,但是谁使用相同的reducer。)
Maybe it's not the good solution to use reducer for that?
(也许使用reducer并不是一个好的解决方案?)
ask by Yann SAINTY translate from so 与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…