• Empleos
  • Sobre nosotros
  • profesionales
    • Inicio
    • Empleos
    • Cursos y retos
    • Preguntas
    • Profesores
  • empresas
    • Inicio
    • Publicar vacante
    • Nuestro proceso
    • Precios
    • Pruebas Online
    • Nómina
    • Blog
    • Comercial
    • Calculadora de salario

0

96
Vistas
Acceda y cambie el elemento de la matriz de estado en la aplicación React principal desde el nieto

Me disculpo por el título de esta pregunta, pero traté de explicar el problema tanto como pude en una sola línea.

Nuestra tarea escolar requería que creáramos un (tipo de) juego de Tic Tac Toe pero de cierta manera. En lugar de crear nueve elementos Box diferentes a partir de la App principal, se nos solicitó crear una clase Row y una clase Box , por lo que la aplicación principal tendrá tres hijos de clase Row y cada clase Row tendrá tres hijos Box .

Ahora, el problema que encontré es cómo cambiar la matriz de estado de la aplicación principal en un elemento particular que corresponde a ese componente Box exacto.

Soy un principiante y pido disculpas de antemano si no veo algo demasiado obvio. Si tiene alguna pregunta, por favor pregunte, estaré más que feliz de explicar esto tanto como pueda. ¡Gracias!

 import React, { Component } from 'react'; import { render } from 'react-dom'; class App extends Component { constructor(props) { super(props); this.state = { 0 : ['-','-','-'], 1 : ['-','-','-'], 2 : ['-','-','-'] }; this.handleClick = this.handleClick.bind(this) } handleClick(){ // if that particular element is '-' change from '-' to 'X' // else if it is 'X' change to 'O' // else change to 'X' } render() { const rows = [] for (let i = 0; i < 3; i++) { rows.push(<Row key = {i} msg = {this.state[i]} handleClick = {this.handleClick}/>) } return ( <div> <div> <h1>Tic Tac Toe</h1> </div> <div id = 'main'> {rows} </div> </div> ); } } class Row extends Component{ render() { const boxes = [] for (let i = 0; i < 3; i++) { boxes.push(<Box key = {i} msg = {this.props.msg[i]} handleClick = {this.props.handleClick}/>) } return ( <div className = 'row'> {boxes} </div> ) } } class Box extends Component{ render() { return ( <div className = 'box' onClick = {this.props.handleClick}> <p>{this.props.msg}</p> </div> ) } } render(<App />, document.querySelector('#root'));
almost 3 years ago · Juan Pablo Isaza
3 Respuestas
Responde la pregunta

0

Has organizado bien tus componentes. Debe manejar el cambio de jugador después de cada clic y actualizar los valores en el tablero de juego.

  1. Agregue otra variable de estado llamada player (puede ser simplemente un booleano ya que este es un juego de dos jugadores)
 this.state = { 0: ["-", "-", "-"], 1: ["-", "-", "-"], 2: ["-", "-", "-"], player: true };
  1. Puede pasar el índice de fila y columna a la función handleClick como se muestra a continuación.
 handleClick(row, col) { // set the corresponding value (using row and colum index) in the game borad this.setState( { [row]: this.state[row].map((val, colId) => colId === col ? (this.state.player ? "X" : "O") : val ) }, () => { // switch the player (toggle the player boolean value) this.setState({ player: !this.state.player }); } ); }
  1. Pase la row y los col del controlador de clics en el componente Box .
 <Box ... ... handleClick={() => { this.props.handleClick(this.props.row, i); }} />

Zona de pruebas de código

NOTA: cuando desarrolle más para evitar cambiar el mismo cuadro haciendo clic, puede mantener un objeto para almacenar más información como { value: "-", used: false } en lugar de "-" como valores.

almost 3 years ago · Juan Pablo Isaza Denunciar

0

Partiendo de la respuesta de @Amila Senadheera, también podría agregar una verificación en la función handleClick para asegurarse de que un jugador no pueda sobrescribir el movimiento de otro jugador. Algo del estilo de:

 handleClick(row, col) { // set the corresponding value (using row and colum index) in the game board if(this.state[row][col] !== '-') { return // Don't allow the player to overwrite an already-marked square. } this.setState( { [row]: this.state[row].map((val, colId) => colId === col ? (this.state.player ? "X" : "O") : val ) }, () => { // switch the player (toggle the player boolean value) this.setState({ player: !this.state.player }); } ); }

Y si desea agregar un cheque por la victoria, hay una discusión útil aquí: https://codereview.stackexchange.com/questions/24764/tic-tac-toe-victory-check .

almost 3 years ago · Juan Pablo Isaza Denunciar

0

Podrías definir parámetros para handleClick como

 type T = 1 | 2 | 3; function handleClick(row: T, col: T) { const newRow = [ ...this.state[row] ]; this.sign = this.sign === "O" ? "X" : "O"; newRow[col] = this.sign; this.setState({...this.state, [row]: newRow}); }

y luego necesitas nuevos accesorios para Box:

 for (let i = 0; i < 3; i++) { boxes.push( <Box row={props.row} col={i} key={i} msg={this.props.msg[i]} handleClick={this.props.handleClick}/> ) }
almost 3 years ago · Juan Pablo Isaza Denunciar
Responde la pregunta
Encuentra empleos remotos

¡Descubre la nueva forma de encontrar empleo!

Top de empleos
Top categorías de empleo
Empresas
Publicar vacante Precios Nuestro proceso Comercial
Legal
Términos y condiciones Política de privacidad
© 2025 PeakU Inc. All Rights Reserved.

Andres GPT

Recomiéndame algunas ofertas
Necesito ayuda