Skip to content

Instantly share code, notes, and snippets.

@leahgarrett
Last active June 25, 2019 01:09
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save leahgarrett/241eea3f2e5b6e8f7aed52fd8a1ad275 to your computer and use it in GitHub Desktop.
Save leahgarrett/241eea3f2e5b6e8f7aed52fd8a1ad275 to your computer and use it in GitHub Desktop.
Functional Component and Props

Function components and props

Today we will continue with the example we started yesterday. Sample solutions and code to create a create-react-app are here:
https://gist.github.com/leahgarrett/02f600f408c4f97e944890f3dd954300

Function components

What if we wanted to add social links sections to our page multiple times:
/src/App.js

function App() {
  const name = 'Universe'

  return (
    <div className="App">

      <header className="App-header">
      <nav>
        <a href="https://www.facebook.com/">facebook</a>
        <a href="https://www.instagram.com/">instagram</a>
        <a href="https://www.twitter.com/">twitter</a>
      </nav>
        <img src={logo} className="App-logo" alt="logo" />
        <p>
          Greetings {name}!
        </p>
        <nav>
          <a href="https://www.facebook.com/">facebook</a>
          <a href="https://www.instagram.com/">instagram</a>
          <a href="https://www.twitter.com/">twitter</a>
      </nav>
      </header>
    </div>
  );
}

We can refactor this into a reusable component. /src/App.js

function SocialLinks() {
  return <nav>
          <a href="https://www.facebook.com/">facebook</a>
          <a href="https://www.instagram.com/">instagram</a>
          <a href="https://www.twitter.com/">twitter</a>
        </nav>
}

function App() {
  const name = 'Universe'

  return (
    <div className="App">

      <header className="App-header">
        <SocialLinks />
        <img src={logo} className="App-logo" alt="logo" />
        <p>
          Greetings {name}!
        </p>
        <SocialLinks />
      </header>
    </div>
  );
}

It’s just a function which returns a React element.

We can also convert our greeting into a function component.

/src/App.js

function Greetings() {
  return <h1>Hello, World</h1>;
}

function App() {
  const name = 'Universe'

  return (
    <div className="App">

      <header className="App-header">
        <SocialLinks />
        <img src={logo} className="App-logo" alt="logo" />
        <Greetings />
        <SocialLinks />
      </header>
    </div>
  );
}

Props

This function components accepts a single “props” (which stands for properties) object argument with data and returns a React element. We call such components “function components” because they are literally JavaScript functions.

By default all React components get passed props.

/src/App.js

function Greetings(props) {
  console.log(props)
  return <h3>Hello, World</h3>;
}

Using data passed by props.

/src/App.js

function Greetings(props) {
  console.log(props)
  return <h3>Hello, {props.name}</h3>;
}

function App() {
  const name = 'Universe'

  return (
    <div className="App">

      <header className="App-header">
        <SocialLinks />
        <img src={logo} className="App-logo" alt="logo" />
        <Greetings name="Sara" />
        <Greetings name="Cahal" />
        <Greetings name="Edite" />
        <SocialLinks />
      </header>
    </div>
  );
}

What if we had an array of names and wanted to display multiple Greetings?
Note: We need to provide a unique key for repeated elements.
/src/App.js

function App() {
  const people = ['Sara','Cahal','Edite']

  let items = [];
    
  for (let i = 0; i < people.length; i++) {
    items.push(<Greetings key={i} name={people[i]} />);
  }

  return (
    <div className="App">

      <header className="App-header">
        <SocialLinks />
        <img src={logo} className="App-logo" alt="logo" />
        {items}
        <SocialLinks />
      </header>
    </div>
  );
}

A more concise (and common way) is to use map.
/src/App.js

function App() {
  const people = ['Sara','Cahal','Edite']

  return (
    <div className="App">

      <header className="App-header">
        <img src={logo} className="App-logo" alt="logo" />
        {people.map((item, index) => (
          <Greetings key={index} name={item} />
        ))}
      </header>
    </div>
  );
}

Challenge

  1. Update the code above to use the more detailed people array below. Update the Greetings component so it will display: Hello, Sara Hegdal from Hawaii
  const people = [
    {
      firstName: 'Sara',
      lastName: 'Hegdal',
      city: 'Hawaii',
    },
    {
      firstName: 'Cahal',
      lastName: 'Louis',
      city: 'Jakarta',
    },  
    {
      firstName: 'Edite',
      lastName: 'Williams',
      city: 'Perth',
    }
  ]

1.5 Refactor components into separate files; place all newly created files in a components folder which will be a subdirectory off src. There should be a js and a css files for each component.


  1. Create a Notification status message component. It will have a prop called message and will check the status code to display a background color for each of the different types of notifications:
  • Alert
  • Info
  • Error
  • Success

Use the starter code below.

/src/App.js

function getRandomInt(max) {
  return Math.floor(Math.random() * Math.floor(max));
}
function getStatus()
{
  return getRandomInt(4);
}
function App() {
  const status = getStatus();
  const text = 'This is a status message'; 

  return (
    <div>
      <header className="App-header">
        <img src={logo} className="App-logo" alt="logo" />
      </header>
      <Notification message={text} />
    </div>
  );
}

Beast

  1. For this part we will display stats for each of people in the array (used by Greeting above). Use and the getRandomInt to generate a stat and the PercentageStat component to display each person's name and the stat.

/src/App.js

function PercentageStat({ label, score = 0, total = Math.max(1, score) }) {
  return (
    <div>
      <h6>{ label }</h6>
      <span>{ Math.round(score / total * 100) }%</span>
    </div>
  )
}

from https://reactjs.org/docs/components-and-props.html


References

Jon's intro to React - starts without create react app and shows how Babel works


Further Reading

https://www.robinwieruch.de/conditional-rendering-react/

Common use of conditional display is for a Loading component. https://disjoint.ca/til/2017/09/21/how-to-delay-the-display-of-loading-animations-in-react/

React File Structure
https://medium.com/@Charles_Stover/optimal-file-structure-for-react-applications-f3e35ad0a145 https://blog.bitsrc.io/structuring-a-react-project-a-definitive-guide-ac9a754df5eb

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment