0

import React from 'react';
import ReactDOM from 'react-dom';

class Car extends React.Component {
  constructor(props) {
    super(props);
    this.state = {
      brand: "Ford",
      model: "Mustang",
      color: "red",
      year: 1964
    };
  }
  changeColor = () => {
    this.setState({color: this.getRandomColor()});
  }
  
  clr = function() {
        var hex = Math.floor(Math.random()*256).toString(16);
        return ("0"+String(hex)).substr(-2); // pad with zero
  }
    
  getRandomColor = function() {
    //return "#"+this.clr()+this.clr()+this.clr();  //referenceError: clr is not defined
    //return "#"+clr()+clr()+clr(); // Failed to compile: 'clr' is not defined
    return "#"+{this.clr}+{this.clr}+{this.clr}; // Failed to compile: Unexpected keyword 'this' 
  }

  render() {
    return (
      <div>
        <h1>My {this.state.brand}</h1>
        <p>It is a {this.state.color} {this.state.model} from {this.state.year}. </p>
        <button
          type="button"
          onClick={this.changeColor}
        >Change color</button>
      </div>
    );
  }
}

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

I'm learning React from a tutorial, and I'm trying to tweak the function to generate a random color for the car. I've tried to call the clr function, and included my failed efforts for review. How do I correctly call the clr function?

Below is the revision I came up with. I will continue with learning Reactjs!

import React from 'react';
import ReactDOM from 'react-dom';

class Car extends React.Component {
  constructor(props) {
    super(props);
    this.state = {
      brand: "Ford",
      model: "Mustang",
      color: "red",
      year: 1964
    };
  }
  changeColor = () => {
    this.setState({color: this.getRandomColor()});
  }
  
  getRandomColor = function() {
        var num = Math.floor(Math.random()*6) + 1;
        switch (num) {
            case 1:
                return ("yellow");
                break;
            case 2:
                return ("purple");
                break;
            case 3:
                return ("orange");
                break;
            case 4:
                return ("blue");
                break;
            case 5:
                return ("black");
                break;
            case 6:
                return ("green");
                break;  
        }
  }  

  render() {
    return (
      <div>
        <h1>My {this.state.brand}</h1>
        <p>It is a {this.state.color} {this.state.model} from {this.state.year}. </p>
        <button
          type="button"
          onClick={this.changeColor}
        >Change color</button>
      </div>
    );
  }
}

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

8
  • Did you mean return "#" + this.clr() + this.clr() + this.clr(); ? Commented Feb 3, 2021 at 22:43
  • { ... } in this context is used to build up objects, like { user: "JuniorDev", question: "JavaScript ..." }. The {this.clr} therefore does not quite work. (There are also so called "template literals" which also use curly brackets, but their syntax is also quite different) Commented Feb 3, 2021 at 22:45
  • Jonas, yes.. I did try return "#" + this.clr() + this.clr() + this.clr(); but I got a reference error for that. It is commented out in my post Commented Feb 3, 2021 at 22:55
  • For debugging purposes, it would be much easier to separate them into three assignment statements. Then perhaps a forth assignment that is a concatenation of them. I would make it easier on you. Commented Feb 3, 2021 at 23:02
  • Ok. I changed changeColor = () => to changeColor = function(), and used return "#"+this.clr()+this.clr()+this.clr(); in the getRandomColor function. However, that results in TypeError: Cannot read property 'setState' of undefined. Commented Feb 3, 2021 at 23:04

2 Answers 2

2

It appears that you have confounded JSX's expression delimiter {} with JavaScript's String literal syntax ${...}.

The fix is quite easy. In your working code,

Change:

return "#"+{this.clr}+{this.clr}+{this.clr};

To:

return `#${this.clr()}${this.clr()}${this.clr()}${this.clr()}`; 

Note the use of backticks, the removal of the + and addition of ().

I also included the fourth pair of hex values as I think you'll have better success if you use the full set.

Here is a working StackBlitz

Sign up to request clarification or add additional context in comments.

Comments

0
  changeColor = () => {
    this.setState({color: this.getRandomColor()});
  }
  clr = function() {
        return Math.floor(Math.random()*256).toString(16);
  }
  getRandomColor = function() {
    return `#${this.clr()}${this.clr()}${this.clr()}`;
  }

  render() {
    return (
      <div>
        <h1>My {this.state.brand}</h1>
        <p>It is a {this.state.color} {this.state.model} from {this.state.year}. </p>
        <button
        style={{color: this.state.color}}
          type="button"
          onClick={this.changeColor}
        >Change color</button>
      </div>
    );
  }

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.