web-dev-qa-db-fra.com

React supprimer un élément lorsque onClick

J'essaie de supprimer un div quand onClick est pressé. Le div existe sur mon composant parent où j'ai

 render() {
    const listPlayers = players.map(player => (
      <Counter
        key={player.id}
        player={player}
        name={player.name}
        sortableGroupDecorator={this.sortableGroupDecorator}
        decrementCountTotal={this.decrementCountTotal}
        incrementCountTotal={this.incrementCountTotal}
        removePlayer={this.removePlayer}
        handleClick={player}
      />
    ));

    return (
      <ContainLeft style={{ alignItems: 'center' }}>
        <ProjectTitle>Score Keeper</ProjectTitle>
        <Copy>
          A sortable list of players that with adjustable scores.  Warning, don't go negative!
        </Copy>
        <div>
          <Stats totalScore={this.state.totalScore} players={players} />
          {listPlayers}
        </div>
      </ContainLeft>
    );
  }

Il passe les accessoires au composant enfant où le bouton pour supprimer la div, ici

    return (
      <div
        style={{ display: this.state.displayInfo }}
        className="group-list"
        ref={sortableGroupDecorator}
        id="cell"
      >
        <CountCell style={{ background: this.state.color }}>
          <Row style={{ alignItems: 'center', marginLeft: '-42px' }}>
            <Col>
              <DeleteButton onClick={removePlayer}>
                <Icon name="delete" className="delete-adjust fa-minus-circle" />
              </DeleteButton>
            </Col>

(J'ai coupé le reste du code car il était long et pas utile ici)

Le tableau (un fichier séparé) est importé dans le composant parent et se lit comme ceci

const players = [
  {
    name: 'Jabba',
    score: 10,
    id: 11
  },
  {
    name: 'Han',
    score: 10,
    id: 1
  },
  {
    name: 'Rey',
    score: 30,
    id: 10
  }
];

export default players;

Donc, ce que j'essaie de faire, c'est d'écrire une fonction sur le parent principal que lorsque l'on clique à l'intérieur de l'enfant, le div est supprimé, supprimé, disparu (quel que soit le meilleur terme) un peu comme "supprimer le lecteur, ajouter un lecteur"

Sur mon composant parent, j'ai écrit une fonction où le console.log fonctionne quand il est cliqué dans l'enfant, mais tout ce que j'écris dans la fonction ne semble pas vouloir fonctionner.

La fonction que je construis (en cours, je suis encore un peu perdue ici) est:

  removePlayer() {
    console.log('this was removed');
    players.splice(2, 0, 'Luke', 'Vader');
  }

qui est cartographié ici comme accessoire

const listPlayers = players.map(player => (
  <Counter
    key={player.id}
    player={player}
    name={player.name}
    sortableGroupDecorator={this.sortableGroupDecorator}
    decrementCountTotal={this.decrementCountTotal}
    incrementCountTotal={this.incrementCountTotal}
    removePlayer={this.removePlayer}
    handleClick={player}
  />
));

Et passé dans l'enfant ici:

render() {
const {
  name,
  sortableGroupDecorator,
  decrementCountTotal,
  incrementCountTotal,
  removePlayer
} = this.props;

return (
  <div
    style={{ display: this.state.displayInfo }}
    className="group-list"
    ref={sortableGroupDecorator}
    id="cell"
  >
    <CountCell style={{ background: this.state.color }}>
      <Row style={{ alignItems: 'center', marginLeft: '-42px' }}>
        <Col>
          <DeleteButton onClick={removePlayer}>
            <Icon name="delete" className="delete-adjust fa-minus-circle" />
          </DeleteButton>

Je sais que tout cela est long et je voulais fournir autant de détails que possible parce que React est encore nouveau pour moi et je me confond avec certains des verbiages. Merci d'avoir aidé à l'avance

7
sthig

Nous l'avons trié dans le chat. Comme prévu, c'était un problème avec l'État.

J'ai fait un petit extrait semi-pseudo avec des commentaires comme explication:

import React, { Component } from 'react';

// Your player constant, outside the scope of any React component
// This pretty much just lives in your browser as a plain object.
const players = [
  {
    name: 'Jabba',
    score: 10,
    id: 11
  },
  {
    name: 'Han',
    score: 10,
    id: 1
  },
  {
    name: 'Rey',
    score: 30,
    id: 10
  }
];

class App extends Component {

  constructor() {
    super();

    this.state = {
      players, // ES6 Syntax, same as players: players
      // Add all your other stuff here
    };
  }

  removePlayer(id) {
    const newState = this.state;
    const index = newState.players.findIndex(a => a.id === id);

    if (index === -1) return;
    newState.players.splice(index, 1);

    this.setState(newState); // This will update the state and trigger a rerender of the components
  }

  render() {

   const listPlayers = this.state.players.map(player => { // Note the this.state, this is important for React to see changes in the data and thus rerender the Component
      <Counter
        ..

        removePlayer={this.removePlayer.bind(this)} //bind this to stay in the context of the parent component
      />
    });

    return (
      <div>
        {listPlayers}
      </div>
    );
  }
}





//////////////////////////////////////// Child component

....

<DeleteButton onClick={() => this.props.removePlayer(this.props.player.id)}>

....
7
Cynigo

Peu confondre le fonctionnement de l'ensemble de l'application, mais je vais essayer de vous aider.

Pour faire réagir les modifications du dom, vous devez mettre players dans le state. Donc, dans le removePlayer vous faites une copie de this.state.players Dans une variable locale (juste pour ne pas changer le tableau directement dans state, c'est une bonne pratique), puis vous faites le fractionnement de cette variable locale et enfin vous setState({ players: localPlayers}).

De cette façon, le "div" sera supprimé.