美文网首页
2018-03-12DND

2018-03-12DND

作者: NOTEBOOK2 | 来源:发表于2018-03-12 16:53 被阅读0次

可以点击跳到任意位置


click3.png click2.png click1.png

添加L形规则

屏幕快照 2018-03-12 16.51.53.png

DragSource

屏幕快照 2018-03-12 16.52.00.png 屏幕快照 2018-03-12 16.51.36.png

DropTarget
新建一个文件,为什么需要新建??

drop1.png drop2.png

最后显示完整源码:

// index.js  
import React from 'react';
import ReactDOM from 'react-dom';
import Board from './Board'
import Knight from './Knight'
import { observe } from './Game'

observe(knightPosition =>
  ReactDOM.render(
    <Board knightPosition={knightPosition}/>,
  document.getElementById('root')
))

从Game.js 里导入observe,可以看到observe方法里,将参数赋值给observer,再调用emitChange方法。
参数是 knightPosition,也就是骑士的位置,【1,7】
knightPosition是Board的一个属性

// Game.js   
let knightPosition = [1,7]
let observer = null

function emitChange() {
  observer(knightPosition)
}

export function observe(o) {
  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);
}
// Knight.js  
import React, { Component } from 'react';
import { ItemTypes } from './Constants'
import { DragSource } from 'react-dnd'

const knightSource = {
  beginDrag(props) {
    return {}
  }
}

function collect(connect, monitor) {
  return {
    connectDragSource: connect.dragSource(),
    isDragging: monitor.isDragging(),
  }
}


class Knight extends Component {
  render() {
    const { connectDragSource, isDragging } = this.props
    return connectDragSource(
      <div style={{
        opacity: isDragging ? 0.5 : 1,
        fontSize: 25,
        fontWeight: 'bold',
        cursor: 'move'
      }}>
        ♘
      </div>
    )
  }
}

export default DragSource(ItemTypes.KNIGHT, knightSource, collect)(Knight)
// Square.js  
import React, { Component } 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: '30px',
      height: '30px'
    }}>
      {this.props.children}
    </div>
    )
  }
}
// Board.js  
import React, { Component } from 'react'
import PropTypes from 'prop-types'
import Knight from './Knight'
import Square from './Square'
import { canMoveKnight, moveKnight } from './Game'
import { DragDropContext } from 'react-dnd'
import HTML5Backend from 'react-dnd-html5-backend'
import BoardSquare from './BoardSquare'
class Board extends Component {

  handleSquareClick(toX, toY) {
    if (canMoveKnight(toX, toY)) {
      moveKnight(toX, toY);
    }
  }

  renderSquare(i) {
    const x = i % 8;
    const y = Math.floor(i / 8);

    return (
      <div key={i}
           style={{width: '30px', height: '30px'}}>
        <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 />
  }
}

  render(){
    const squares = [];
    for (let i = 0; i < 64; i++){
      squares.push(this.renderSquare(i));
    }
    return (
      <div style={{width: '240px',height: '240px',display:'flex',flexWrap:'wrap'}}>
        {squares}
      </div>
    )
  }
}

export default DragDropContext(HTML5Backend)(Board)
// BoardSquare.js   
import React, {Component} from 'react'
import Square from './Square'
import { canMoveKnight, moveKnight } from './Game'
import { ItemTypes } from './Constants'
import { DropTarget } from 'react-dnd'

const squareTarget = {
  drop(props) {
    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>
    )
  }
}

export default DropTarget(ItemTypes.KNIGHT, squareTarget, collect)(BoardSquare)   
// Constants.js  
export const ItemTypes = {
  KNIGHT: 'knight'
}  

相关文章

  • 2018-03-12DND

    可以点击跳到任意位置 添加L形规则 DragSource DropTarget新建一个文件,为什么需要新建?? 最...

网友评论

      本文标题:2018-03-12DND

      本文链接:https://www.haomeiwen.com/subject/iwtofftx.html