Reactでオセロを作成しているのですが、
js
1import React, { useState } from 'react' 2import Square from '../Square' 3import styles from './styles' 4 5const { Status, BoardRow } = styles 6 7const BLACK_PIECE = 'black' 8const WHITE_PIECE = 'white' 9 10let defaultBoard = new Array(8) 11for (let i = 0; i < defaultBoard.length; i++) { 12 defaultBoard[i] = new Array(8) 13} 14 15for (let x = 0; x < 8; x++) { 16 for (let y = 0; y < 8; y++) { 17 defaultBoard[x][y] = null 18 } 19} 20 21// defaultBoard[3][3] = BLACK_PIECE 22// defaultBoard[4][3] = WHITE_PIECE 23// defaultBoard[3][4] = WHITE_PIECE 24// defaultBoard[4][4] = BLACK_PIECE 25 26defaultBoard[0][0] = WHITE_PIECE 27defaultBoard[1][0] = BLACK_PIECE 28defaultBoard[2][0] = WHITE_PIECE 29defaultBoard[3][0] = WHITE_PIECE 30 31defaultBoard[5][0] = WHITE_PIECE 32defaultBoard[6][0] = WHITE_PIECE 33defaultBoard[7][0] = WHITE_PIECE 34 35// defaultBoard[4][1] = WHITE_PIECE 36// defaultBoard[4][2] = WHITE_PIECE 37// defaultBoard[4][3] = WHITE_PIECE 38// defaultBoard[4][4] = WHITE_PIECE 39// defaultBoard[4][5] = WHITE_PIECE 40// defaultBoard[4][6] = BLACK_PIECE 41// defaultBoard[4][7] = WHITE_PIECE 42 43// defaultBoard[3][1] = WHITE_PIECE 44// defaultBoard[2][2] = WHITE_PIECE 45// defaultBoard[1][3] = BLACK_PIECE 46// defaultBoard[0][4] = WHITE_PIECE 47 48// defaultBoard[5][1] = WHITE_PIECE 49// defaultBoard[6][2] = WHITE_PIECE 50// defaultBoard[7][3] = WHITE_PIECE 51 52const Board = () => { 53 const [squares, setSquares] = useState(defaultBoard) 54 const [currentPiece, setCurrentPiece] = useState(BLACK_PIECE) 55 const status = 'Next player: ' + (currentPiece === BLACK_PIECE ? '黒の番' : '白の番'); 56 57 const boardInit = () => { 58 if (!window.confirm('リセットしてもよろしいですか?')) { 59 return false 60 } 61 62 for (let x = 0; x < 8; x++) { 63 for (let y = 0; y < 8; y++) { 64 let newSquares = squares.concat() 65 newSquares[x][y] = null 66 setSquares(newSquares) 67 } 68 } 69 let newSquares = squares.concat() 70 newSquares[3][3] = BLACK_PIECE 71 newSquares[4][3] = WHITE_PIECE 72 newSquares[3][4] = WHITE_PIECE 73 newSquares[4][4] = BLACK_PIECE 74 setCurrentPiece(BLACK_PIECE) 75 setSquares(newSquares) 76 } 77 78 const reversePiece = (currentX, currentY, x, y) => { 79 const nextPiece = currentPiece === BLACK_PIECE ? WHITE_PIECE : BLACK_PIECE 80 let newSquares = squares.concat() 81 let nextYIndex = currentY + y 82 let nextXIndex = currentX + x 83 84 if (newSquares[nextYIndex][nextXIndex] === nextPiece) { 85 newSquares[currentY][currentX] = currentPiece 86 87 while(true) { 88 if (newSquares[nextYIndex][nextXIndex] === currentPiece) { 89 setCurrentPiece(nextPiece) 90 setSquares(newSquares) 91 break 92 } 93 if (newSquares[nextYIndex][nextXIndex] === null) { 94 // breakする前に元の配列に戻す 95 setSquares(squares) 96 break 97 } 98 newSquares[nextYIndex][nextXIndex] = currentPiece 99 nextYIndex = nextYIndex + y 100 nextXIndex = nextXIndex + x 101 if (nextYIndex > 7 || nextYIndex < 0 || nextXIndex > 7 || nextXIndex < 0) { 102 // breakする前に元の配列に戻す 103 setSquares(squares) 104 break 105 } 106 } 107 } 108 } 109 110 const handleClick = (x, y) => { 111 if (squares[y][x] === null) { 112 // reversePiece(x, y, 1, 0) // 右 113 reversePiece(x, y, 0, 1) // 下 114 reversePiece(x, y, 0, -1) // 上 115 // reversePiece(x, y, 1, 1) // 右下 116 // reversePiece(x, y, 1, -1) // 右上 117 // reversePiece(x, y, -1, 0) // 左 118 // reversePiece(x, y, -1, 1) // 左下 119 // reversePiece(x, y, -1, -1) // 左上 120 } 121 } 122 123 // 縦軸y, 横軸x 124 const renderSquare = (boardRow, y) => { 125 return ( 126 boardRow[y].map((square, x) => { 127 return ( 128 <Square 129 square={ square } 130 key={ x } 131 addValue={ () => handleClick(x, y) } 132 /> 133 ) 134 }) 135 ) 136 } 137 138 return ( 139 <> 140 <button 141 onClick={ boardInit } 142 > 143 最初からやり直す 144 </button> 145 <Status>{ status }</Status> 146 <BoardRow> 147 { renderSquare(defaultBoard, 0) } 148 </BoardRow> 149 <BoardRow> 150 { renderSquare(defaultBoard, 1) } 151 </BoardRow> 152 <BoardRow> 153 { renderSquare(defaultBoard, 2) } 154 </BoardRow> 155 <BoardRow> 156 { renderSquare(defaultBoard, 3) } 157 </BoardRow> 158 <BoardRow> 159 { renderSquare(defaultBoard, 4) } 160 </BoardRow> 161 <BoardRow> 162 { renderSquare(defaultBoard, 5) } 163 </BoardRow> 164 <BoardRow> 165 { renderSquare(defaultBoard, 6) } 166 </BoardRow> 167 <BoardRow> 168 { renderSquare(defaultBoard, 7) } 169 </BoardRow> 170 </> 171 ); 172} 173 174export default Board; 175
実際の画面はこちらです。(裏返すことができるかテストするために駒を様々な箇所に設置しています。)
上記の記述のうち、クリックした時に駒を裏返すことができるか1マスずつ判定しつつ、以下の2つの条件に当てはまる場合にはまだ裏返されていない直前のstateを反映させたいのですが、
- 自分のコマと挟み撃ちできていない
- 自分のコマがないままnullである場合
js
1if (newSquares[nextYIndex][nextXIndex] === null) { 2 // breakする前に元の配列に戻す 3 console.log(squares) //これで調べても裏返ったあとのstate(下記画像のような)しか取得できない 4 setSquares(squares) 5 break 6} 7if (nextYIndex > 7 || nextYIndex < 0 || nextXIndex > 7 || nextXIndex < 0) { 8 // breakする前に元の配列に戻す 9 console.log(squares) //これで調べても裏返ったあとのstate(下記画像のような)しか取得できない 10 setSquares(squares) 11 break 12}
と下側の駒まで裏返ってしまいます。
なお、一つずつ方向を記述した場合だと成功するので、裏返なかった結果になっても次のメソッドで一緒に反映されてしまうみたいです。
どのように記述すると直前のstateを取得できるのでしょうか。
よろしくお願いします。
回答1件
あなたの回答
tips
プレビュー
バッドをするには、ログインかつ
こちらの条件を満たす必要があります。
退会済みユーザー
2020/01/29 15:26