Created
March 22, 2017 07:52
-
-
Save saitoxu/70aa7204b3b3fb4e82b749fa55115a1b to your computer and use it in GitHub Desktop.
2017-03-22
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import React, { Component, PropTypes } from 'react'; | |
import Knight from './Knight'; | |
import BoardSquare from './BoardSquare'; | |
import { canMoveKnight, moveKnight } from './Game'; | |
import { DragDropContext } from 'react-dnd'; | |
import HTML5Backend from 'react-dnd-html5-backend'; | |
class Board extends Component { | |
renderSquare(i) { | |
const x = i % 8; | |
const y = Math.floor(i / 8); | |
return ( | |
<div key={i} | |
style={{ width: '12.5%', height: '12.5%' }} | |
onClick={() => this.handleSquareClick(x, y)}> | |
<BoardSquare x={x} | |
y={y}> | |
{this.renderPiece(x, y)} | |
</BoardSquare> | |
</div> | |
); | |
} | |
renderPiece(x, y) { | |
const [knightX, knightY] = this.props.knightPosition; | |
if (x === knightX && y === knightY) { | |
return <Knight />; | |
} | |
} | |
handleSquareClick(toX, toY) { | |
if (canMoveKnight(toX, toY)) { | |
moveKnight(toX, toY); | |
} | |
} | |
render() { | |
const squares = []; | |
for (let i = 0; i < 64; i++) { | |
squares.push(this.renderSquare(i)); | |
} | |
return ( | |
<div style={{ | |
width: '100%', | |
height: '100%', | |
display: 'flex', | |
flexWrap: 'wrap' | |
}}> | |
{squares} | |
</div> | |
) | |
} | |
} | |
Board.propTypes = { | |
knightPosition: PropTypes.arrayOf( | |
PropTypes.number.isRequired | |
).isRequired | |
}; | |
export default DragDropContext(HTML5Backend)(Board); |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import React, { Component, PropTypes } from 'react'; | |
import Square from './Square'; | |
import { canMoveKnight, moveKnight } from './Game'; | |
import { ItemTypes } from './Constants'; | |
import { DropTarget } from 'react-dnd'; | |
const squareTarget = { | |
drop(props, monitor) { | |
moveKnight(props.x, props.y); | |
}, | |
canDrop(props) { | |
return canMoveKnight(props.x, props.y); | |
} | |
}; | |
function collect(connect, monitor) { | |
return { | |
connectDropTarget: connect.dropTarget(), | |
isOver: monitor.isOver(), | |
canDrop: monitor.canDrop() | |
}; | |
} | |
class BoardSquare extends Component { | |
renderOverlay(color) { | |
return ( | |
<div style={{ | |
position: 'absolute', | |
top: 0, | |
left: 0, | |
height: '100%', | |
width: '100%', | |
zIndex: 1, | |
opacity: 0.5, | |
backgroundColor: color | |
}} /> | |
) | |
} | |
render() { | |
const { x, y, connectDropTarget, isOver, canDrop } = this.props; | |
const black = (x + y) % 2 === 1; | |
return connectDropTarget( | |
<div style={{ | |
position: 'relative', | |
width: '100%', | |
height: '100%' | |
}}> | |
<Square black={black}> | |
{this.props.children} | |
</Square> | |
{isOver && !canDrop && this.renderOverlay('red')} | |
{!isOver && canDrop && this.renderOverlay('yellow')} | |
{isOver && canDrop && this.renderOverlay('green')} | |
</div> | |
); | |
} | |
} | |
BoardSquare.propTypes = { | |
x: PropTypes.number.isRequired, | |
y: PropTypes.number.isRequired, | |
isOver: PropTypes.bool.isRequired, | |
canDrop: PropTypes.bool.isRequired | |
} | |
export default DropTarget(ItemTypes.KNIGHT, squareTarget, collect)(BoardSquare); |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
export const ItemTypes = { | |
KNIGHT: 'knight' | |
}; |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
let knightPosition = [1, 7]; | |
let observer = null; | |
function emitChange() { | |
observer(knightPosition); | |
} | |
export function observe(o) { | |
if (observer) { | |
throw new Error('Multiple observers not implemented.'); | |
} | |
observer = o; | |
emitChange(); | |
} | |
export function moveKnight(toX, toY) { | |
knightPosition = [toX, toY]; | |
emitChange(); | |
} | |
export function canMoveKnight(toX, toY) { | |
const [x, y] = knightPosition; | |
const dx = toX - x; | |
const dy = toY - y; | |
return (Math.abs(dx) === 2 && Math.abs(dy) === 1) || | |
(Math.abs(dx) === 1 && Math.abs(dy) === 2); | |
} |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import React from 'react'; | |
import ReactDOM from 'react-dom'; | |
import Board from './Board'; | |
import { observe } from './Game'; | |
const rootEl = document.getElementById('root'); | |
observe(knightPosition => | |
ReactDOM.render( | |
<Board knightPosition={knightPosition} />, | |
rootEl | |
) | |
); |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import React, { Component, PropTypes } from 'react'; | |
import { ItemTypes } from './Constants'; | |
import { DragSource } from 'react-dnd'; | |
const knightSource = { | |
beginDrag(props) { | |
return {}; | |
} | |
}; | |
function collect(connect, monitor) { | |
return { | |
connectDragSource: connect.dragSource(), | |
connectDragPreview: connect.dragPreview(), | |
isDragging: monitor.isDragging() | |
} | |
} | |
class Knight extends Component { | |
componentDidMount() { | |
const img = new Image(); | |
img.src = 'data:image/png;base64,iVBORw0KGgoAAAA...'; // svg全体はチュートリアルを確認してください | |
img.onload = () => this.props.connectDragPreview(img); | |
} | |
render() { | |
const { connectDragSource, isDragging } = this.props; | |
return connectDragSource( | |
<div style={% raw %}{{ | |
opacity: isDragging ? 0.5 : 1, | |
fontSize: 25, | |
fontWeight: 'bold', | |
cursor: 'move' | |
}}{% endraw %}> | |
♘ | |
</div> | |
) | |
} | |
} | |
Knight.propTypes = { | |
connectDragSource: PropTypes.func.isRequired, | |
connectDragPreview: PropTypes.func.isRequired, | |
isDragging: PropTypes.bool.isRequired | |
} | |
export default DragSource(ItemTypes.KNIGHT, knightSource, collect)(Knight); |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import React, { Component, PropTypes } from 'react'; | |
export default class Square extends Component { | |
render() { | |
const { black } = this.props; | |
const fill = black? 'black' : 'white'; | |
const stroke = black? 'white' : 'black'; | |
return <div style={{ | |
backgroundColor: fill, | |
color: stroke, | |
width: '100%', | |
height: '100%', | |
}}> | |
{this.props.children} | |
</div>; | |
} | |
} | |
Square.propTypes = { | |
black: PropTypes.bool | |
}; |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment