为什么排序在React组件中不起作用

时间:2019-10-09 12:50:37

标签: javascript reactjs

我有这个行数组,我尝试使用sortByTitle()函数按字母顺序排序。我很确定的sort方法是可以的,但是我在调​​用它的地方一定有东西使它无法工作,并且它根本不会改变数组。可能是因为反应的生命周期所致。

getRows()上的排序工作正常。

  getHistory() {
    if (this.state.historyUser && this.state.historyUser.length) {
      return this.state.historyUser.map(x => {
        x.state = x.finishDate ? 'closed' : 'open';
        return x;
      });
    } else {
      return [];
    }
  }

  getRows() {
    let rows = this.state.rows || this.getHistory();
    rows.sort((a, b) => b.creationDate - a.creationDate)
    return rows.map((x, j) => {
      return (
        <div key={j} className={`testTable__row testTable__test testTable__test--${x.state}`}>
          {this.allTypes.map((type, i) => {
            let value = type.className !== 'checks' ? x[type.prop] : x.checked;
            if (type.className === 'name') {
              value = (
                <a href={`/test/${x._id}#1`}>{x[type.prop]}</a>
              );
            }
            return (
              <CellUser
                key={i}
                id={x._id}
                value={value}
                className={type.className}
                changeChecked={this.changeChecked}
                isSimulacro={x.isSimulacro}
                score={x.scoreProMIR}
              />
            );
          })}
        </div>
      );
    });
  }

  handleInputChange(e) {
    let rows = this.state.historyUser;
    const selector = e.target.getAttribute("label")
    rows = rows.filter(elm => elm[selector].toLowerCase().includes(e.target.value.toLowerCase()));
    this.setState({ inputValue: e.target.value, rows: rows});
  }

  sortByTitle() {
    let rows = this.state.rows || this.getHistory();
    rows.sort((a, b) => a.title.localeCompare(b.title));
    this.setState({ rows: row });
  }

  render() {
    return (
      <div style={{ height: '100%', width: '100%' }}>
        <div className="testTable">
          <div className="testTable__row testTable__header">
            <div className="testTable__column testTable__column--name"> 
              Nombre 
              <input type="text" label="title" onChange={this.handleInputChange} />
              <button onClick={this.sortByTitle}> Ordenar </button>
            </div>
            <div className="testTable__column testTable__column--score"> Nota </div>
            <div className="testTable__column testTable__column--type"> Tipo </div>
            <div className="testTable__column testTable__column--date"> Fecha </div>
            <div className="testTable__column testTable__column--state"> Estado </div>
            <div className="testTable__column testTable__column--checks">
              <label>
                Abiertos <Checkbox selected={this.state.checkOpen} onClick={this.allOpened} />
              </label>
              <label>
                Cerrados <Checkbox selected={this.state.checkClose} onClick={this.allClosed} />
              </label>
              <label>
                Todos <Checkbox selected={this.state.selectedAllRows} onClick={this.allRows} />
              </label>
            </div>
          </div>
          <div className="testTable__body">
            <Scrollbars {...scrollbarsProps()}>{this.getRows()}</Scrollbars>
          </div>

          <div
            className={`testTable__row testTable__footer${
              this.state.btnClose || this.state.btnReset || this.state.btnReopen ? ' active' : ''
            }`}
          >
            <ReactCSSTransitionGroup
              component="div"
              transitionName="topBottom"
              transitionEnterTimeout={0}
              transitionLeaveTimeout={0}
            >
              {this.state.btnClose ? (
                <button className="button button--close" onClick={this.requestAction} name="close">
                  Cerrar seleccionados
                </button>
              ) : null}
              {this.state.btnReset ? (
                <button className="button button--reset" onClick={this.requestAction} name="reset">
                  Resetear seleccionados
                </button>
              ) : null}
              {this.state.btnReopen ? (
                <button className="button button--open" onClick={this.requestAction} name="open">
                  Reabrir seleccionados
                </button>
              ) : null}
              {this.state.btnAddToStats ? (
                <button className="button button--add" onClick={this.requestAction} name="add">
                  Añadir a estadísticas
                </button>
              ) : null}
            </ReactCSSTransitionGroup>
          </div>
        </div>
        <ReactCSSTransitionGroup
            component="div"
            transitionName="topBottom"
            className={`superCoverMsg${this.state.confirmAction ? '' : ' none'}`}
            transitionEnterTimeout={0}
            transitionLeaveTimeout={0}
          >
            {this.state.confirmAction ? (
              <div className="coverMsg confirmPopUp" key="0">
                <p>{this.state.textAction}</p>
                <div className="coverLabelInput coverLabelInput__botones columnWidth">
                  <ul className="cien">
                    <li className="cincuenta cancelar">
                      <a onClick={this.removeConfirmAction} href="#" title="Cancelar">
                        Cancelar
                      </a>
                    </li>
                    <li className="cincuenta aceptar">
                      <a onClick={this.aceptAction} href="#" title="Aceptar">
                        Aceptar
                      </a>
                    </li>
                  </ul>
                </div>
              </div>
            ) : null}
          </ReactCSSTransitionGroup>
      </div>
    );
  }
}

2 个答案:

答案 0 :(得分:0)

看起来您的设置行等于row,我没有看到定义。也许可以更改

this.setState({ rows: row });

this.setState({ rows: rows });

我也认为从状态修改数组的反应友好方法是使用散布运算符,以免直接改变状态对象,就像这样:

let rows = [...this.state.rows] || this.getHistory();

答案 1 :(得分:0)

sortByTitle() {
    let rows = this.state.rows || this.getHistory();
    rows.sort((a, b) => a.title.localeCompare(b.title));
    this.setState({ rows: row });
}

您正在改变状态。而是将内容复制到单独的新数组中,对其进行排序并在.setState中使用该新变量。