开发者问题收集

React 防止组件在点击事件上重新渲染

2019-08-20
7257

我花了很多时间试图弄清楚如何阻止我的组件在 render() 方法中重新渲染 this.createColorBlocks() 。我读过一些关于纯组件和 shouldComponentUpdate 方法的帖子,但我仍然无法找出一种方法,让我能够将生成的数组添加到状态,然后在更新后将其映射到该状态。

我走在正确的轨道上吗?在 render 方法中触发 createColorMethod 方法是否会导致整个组件重新渲染?我该如何避免这种情况?

import React, { Component } from "react";
import ColorScheme from "color-scheme";
import uuidv1 from "uuid/v1";
import ColorBar from "../ColorBar/ColorBar";
import "./PalettePicker.css";

export default class PalettePicker extends Component {
  state = {
    hue: null,
    colorScheme: null,
    variation: "pastel",
    colors: [],
    editable: false
  };

  // shouldComponentUpdate(nextProps) {
  //   return this.props.color !== nextProps.color;
  // }

  toggleEditable = () => {
    const toggle = this.state.editable;
    this.setState({ editable: !toggle });
  };

  generateRandomHue = () => {
    return Math.floor(Math.random() * (360 + 1));
  };

  generateColors = () => {
    // The possible values are 'mono', 'contrast', 'triade', 'tetrade', and 'analogic'
    const { hue, colorScheme, variation } = this.state;
    const { pColorScheme = "mono" } = this.props;
    const scheme = new ColorScheme();
    scheme
      .from_hue(hue || this.generateRandomHue())
      .scheme(colorScheme || pColorScheme)
      .variation(variation);
    // return scheme.colors();
    const colors = scheme.colors().map(color => {
      return "#" + color;
    });
    return colors;
  };

  createColorBlocks = () => {
    const generatedColors = this.generateColors();
    const colors = generatedColors.splice(0, this.props.totalColors);
    console.log(colors);
    return colors.map((color, i) => {
      const uuid = uuidv1();
      return (
        <ColorBar
          color={color}
          vRotate={this.props.vRotate}
          number={i}
          key={uuid}
        />
      );
    });
  };

  render() {
    const editBlockStyles = {
      transform: "translateY(-15px)"
    };
    const colors = this.createColorBlocks();
    return (
      <section className="PalettePicker">
        <div className="colors-section">{colors}</div>
        <div className="button-bar">
// I believe this onClick event is causing the rerender.
          <button className="primary-btn" onClick={this.toggleEditable}>
            Edit Colors
          </button>
          <button className="primary-btn">Save</button>
        </div>
      </section>
    );
  }
}
1个回答

React 中的每个状态更新都会导致重新渲染,并且由于您的 onClick 切换 editable 标志,因此组件将在每次单击按钮时重新渲染。如果您不希望每次都重新生成颜色,则需要将该函数移出 render() (例如,移至 componentDidMount() ,正如 John Ruddell 建议 )。

ngranko
2019-08-20