Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/javascript/476.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript 如何在每次状态更改时重新渲染组件?_Javascript_Reactjs_Setstate - Fatal编程技术网

Javascript 如何在每次状态更改时重新渲染组件?

Javascript 如何在每次状态更改时重新渲染组件?,javascript,reactjs,setstate,Javascript,Reactjs,Setstate,我仍在学习JS/React,所以很可能我做得完全错误。欢迎任何批评 我有一张画布,上面画着一幅画。我想在按下按钮时多次更改绘图的颜色要清楚:只需单击按钮即可多次更改绘图的颜色 我尝试过几种不同的方法,但它们大多是两种方法的变体: 当按下按钮时,它会调用将多次更改状态的方法,但只会对渲染我设置的最后一个状态产生反应。(这是有道理的) 对每个setState使用setTimeout,但它似乎破坏了方法,并且渲染永远不会更改 下面是一个示例代码: import React from 'reac

我仍在学习JS/React,所以很可能我做得完全错误。欢迎任何批评

我有一张画布,上面画着一幅画。我想在按下按钮时多次更改绘图的颜色要清楚:只需单击按钮即可多次更改绘图的颜色

我尝试过几种不同的方法,但它们大多是两种方法的变体:

  • 当按下按钮时,它会调用将多次更改状态的方法,但只会对渲染我设置的最后一个状态产生反应。(这是有道理的)

  • 对每个
    setState
    使用
    setTimeout
    ,但它似乎破坏了方法,并且渲染永远不会更改

下面是一个示例代码:

import React from 'react';

class App extends React.Component {
 constructor(props) {
      super(props);
      this.state = {
        color: "#000000",
      }
      this.changeColors = this.changeColors.bind(this);
  }
  
  changeColors() {
    let colors = ["#000000", "#0000FF", "#FF0000", "#00FF00"];
    for (let nextColor in colors) {
      console.log(`Color now ${colors[nextColor]}`);
      // This seems to break it
      //setTimeout(function(){ this.setState({color: colors[nextColor]}); }, 3000);

      // This only renders last state
      this.setState({color: colors[nextColor]});
    }
  }

  render() {
    return (
      <div className="App">
        <h1>Change Colors</h1>
        <MyButton changeColor={this.changeColors}/>
        <MyCanvas color={this.state}/>
      </div>
    );
  }
}

class MyButton extends React.Component {
  render() {
    return (
      <button 
        type="button" 
        className="btn btn-secondary" 
        onClick={() => this.props.changeColor()}>
        Color
      </button>
    );
  }
}

class MyCanvas extends React.Component {
  componentDidMount() {
      this.drawOnCanvas(this.props.color)
  }
  
  componentDidUpdate() {
      this.drawOnCanvas(this.props.color)
  }
  
  drawOnCanvas(color) {
    const ctx = this.refs.canvas.getContext('2d');
    ctx.clearRect(0, 0, 300, 300) 
    ctx.fillStyle=color.color;
    ctx.fillRect(10, 10, 100, 100);
  }
  
  render() {
    return (
      <canvas id="canvas" ref="canvas" width={300} height={300}/>
    );
  }
}

export default App;
从“React”导入React;
类应用程序扩展了React.Component{
建造师(道具){
超级(道具);
此.state={
颜色:“000000”,
}
this.changeColors=this.changeColors.bind(this);
}
变色{
让颜色=[“#000000”、“#0000FF”、“#FF0000”、“#00FF00”];
for(让nextColor以颜色显示){
log(`Color now${colors[nextColor]}`);
//这似乎打破了它
//setTimeout(函数(){this.setState({color:colors[nextColor]});},3000);
//这只渲染最后一个状态
this.setState({color:colors[nextColor]});
}
}
render(){
返回(
变色
);
}
}
类MyButton扩展了React.Component{
render(){
返回(
this.props.changeColor()}>
颜色
);
}
}
类MyCanvas扩展了React.Component{
componentDidMount(){
this.drawincanvas(this.props.color)
}
componentDidUpdate(){
this.drawincanvas(this.props.color)
}
drawOnCanvas(彩色){
const ctx=this.refs.canvas.getContext('2d');
ctx.clearRect(0,0,300,300)
ctx.fillStyle=color.color;
ctx.fillRect(10,10100100);
}
render(){
返回(
);
}
}
导出默认应用程序;

我做错了什么?如何使用react实现多个颜色更改?

如果没有
setTimeout
所有渲染基本上都将合并为一个,react就是这样工作的。但是,您可以尝试使用动态超时设置超时

类应用程序扩展了React.Component{
建造师(道具){
超级(道具);
此.state={
颜色:“000000”,
}
}
changeColors=()=>{
让颜色=[“#000000”、“#0000FF”、“#FF0000”、“#00FF00”];
颜色。forEach((颜色,i)=>{
设置超时(()=>{
this.setState({color});
},500*i);
});
}
render(){
返回(
变色
改变
);
}
}
ReactDOM.render(,document.getElementById('root'))


ChangeColor是一个事件处理程序,因此当函数执行时发生的所有setState调用都是批处理的,因此它只会导致一次重新渲染。当您将其置于超时状态时,将在changeColors完成执行后调用setState,并且每个setState都会导致渲染。您应该提供一个箭头函数来设置超时,以便正确设置
this
的值。谢谢。你介意跟进吗?如果
颜色
是由生成器函数定义的,该怎么办?在实际应用中就是这样,在这种情况下,我不能使用
颜色.forEach
。示例:
function*getColors(){let colors=[“#000000”、“#0000FF”、“#00FF00”];for(让c在颜色中)生成颜色[c]}
@ZeCarioca,如果您真的希望它与生成器一起使用的话-