React onClick event; updating the color (SOLVED)

Hey there,

for learning purposes I wrote this class component. User should change the color everytime the buttons are clicked. The number hsl is gettig updated in the DOM, but the color is not changing. What did I do wrong?

class ColorShifter extends React.Component {
  constructor(props) {
    super(props)
    this.state = {hsl: 0};
    this.addHsl =this.addHsl.bind(this);
    this.reduceHsl=this.reduceHsl.bind(this);
    this.divStyle = {
      backgroundColor: `hsl(${this.state.hsl}, 100%, 50%)`
      } 
      this.addHsl = this.addHsl.bind(this);
      this.reduceHsl=this.reduceHsl.bind(this);    
  }
  addHsl() {
    this.setState({hsl: this.state.hsl +15})
  }
  reduceHsl() {
    this.setState({hsl: this.state.hsl -15})
  }
  render() {
    return (
      <div>
        <button onClick={this.addHsl}>Add HSL</button>        
        <button onClick={this.reduceHsl}>Reduce HSL</button>
        <p>{this.state.hsl}</p>
        <div id="square" style={this.divStyle}></div>
      </div>
    )
  }  
}

ReactDOM.render(<ColorShifter />, document.getElementById('root'));

I would try binding this inside the render function instead.

<button onClick={this.reduceHsl.bind(this)}>

I have used that before to avoid binding in the constructor

Also perhaps using ( ) around your setState object like so:

    this.setState({hsl: (this.state.hsl -15) })
1 Like

setState is asynchronous, so you can’t trust you’ll have the right value for this.state for it. You have to use the callback method in order to access the correct state.

1 Like

@camperextraordinaire thanks so much. I added this.divStyle to addHsl and reduceHsl and it works now!

addHsl() {
    this.setState({hsl: (this.state.hsl +15) })
    this.divStyle = {
      backgroundColor: `hsl(${this.state.hsl}, 100%, 50%)`
      } 
  }
  reduceHsl() {
    this.setState({hsl: (this.state.hsl -15) })
    this.divStyle = {
      backgroundColor: `hsl(${this.state.hsl}, 100%, 50%)`
      } 
  }