Building Random Quote Generator in React

Building Random Quote Generator in React
0

#1

Hello,

I am attempting the Random Quote Generator with React, however I may have structured my components wrong because I have hit a bit of a wall.

I have built the random quote machineall in one component but I want to separate the elements to make it more readable and maintainable.

you can see my structure in my pen here

It renders a random quote on load but I am not sure how to get a new quote upon clicking the ‘new quote’ button because the buttons are rendered in a component and the author/text is in another component.

How can use the functions in the buttons component to interact with elements in the author/text component?


#2

You need to assign a state to them, and change the state when the button is clicked. So example is this:

class App extends React.Component {
  state = {
     quote: '',
     author:''
  }

  handleClick = () => {
      this.setState({
         quote: 'new quote',
         author: 'new author'
      }); //new quote
  }

  render(){
    return(
      <div>
        <blockquote>
          {this.state.quote}
          <footer>{this.state.author}</footer>
        </blockquote>
        <button onClick={this.handleClick}>new quote</button>
      </div>
    );
  }
}

the quote is automatically updated because the state watches for changes. i suggest do the react challenges for more info :slight_smile: or check the official react docs

Happy Coding!!


#3

Thanks, but this is what I have already implemented with everything in one component.

In my code here, the buttons are in a separate component than the quote and author elements

class Text extends React.Component {
  
  constructor(props) {
    super(props);
    this.state = {
      content: '',
      author: ''
    }
  }
  
  componentDidMount(){
    let number = (Math.floor(Math.random() * 5));
    
    let quote = quotes[number].content;
    
    this.setState({content: quote})
    
    let author = quotes[number].author;
    this.setState({author: author})
  }
  
  render() {
    return (
      <div>
      <h1>"{this.state.content}"</h1>
      <h2>- {this.state.author}</h2>
        </div>
    )
  }
}

class Buttons extends React.Component {
  constructor(props) {
    super(props);
  
    this.newQuote = this.newQuote.bind(this);
    
    this.tweetQuote = this.tweetQuote.bind(this);
  }
  
  newQuote() {
    alert("new quote");
  }
  
  tweetQuote() {
    alert("tweet quote");
  }
  
  render() {
    return (
      <div>
        <span className="quote-button" onClick={this.newQuote}>New Quote</span>
        <span className="tweet-button" onClick={this.tweetQuote}>Tweet Quote</span>
      </div>
    )
  }
}

#4

That is just an example code but In order for your Text and Buttons Component to interact, you need to lift the state up to its parent, the Quoter Component and pass the state and methods as props… so its like:

class Quoter extends React.Component {
  state = {
     quote: '',
     author: ''
  }

  newQuote() {
    //your new quote logic here
  }

  render() {
    return (
     <div>
        <Text quote={this.state.quote} author={this.state.author} />
        <Buttons handleNewQuote={this.newQuote} />
     </div>
   );
  }
}

and pass them as props.


#5

Nice one Jonathan! i forgot about passing functions to components as props

image


#6

I’m glad you made it. When you feel your question is solved feel free always to mark the post as solved. :smile: thanks!