React

Introduction

React is a Javascript library for building user interfaces created and maintained by Facebook. React was first released publicly in July 2013. You can check out the Official React Documents or stick with us for a simpler version.


Why React?

One of the main reasons why people are using React is its ability to reflect changes in the browser DOM when some states changed in just a split second. Developers just need to keep track of changes in states and React will do all the jobs under the hood. Instead of manipulating the browser's DOM directly, React creates a VIRTUAL DOM in memory, where it does all the necessary manipulating, before making the changes in the browser DOM.

Another cool thing about React is that React only changes what needs to be changed. When something changes, React will then compare new states with the previous states and only make changes if they are different.

React is also component-based. This means when developing with React you need to split your UI into smaller components. The advantage of this approach is that the components will encapsulate all the logic inside, you will then have the ability to reuse these components with all of their logic in different places without duplicating your code.


Basic Concepts & Syntax

Hello World

The smallest React example looks like this:

import ReactDOM from "react-dom/client";

const root = ReactDOM.createRoot(document.getElementById("root"));
root.render(<h1>Hello, world!</h1>);

The example above will display a heading saying "Hello, world!" on the page.

JSX

First, let's take a look at this simple example below:

const element = <h1>Hello, world</h1>

The funny tag syntax is neither a string nor HTML.

It is called JSX, and it is a syntax extension to JavaScript. We will use it in React to describe what the UI should look like. JSX may remind you of a template language, but it comes with the full power of JavaScript.

Let's checkout another example to see what JSX can do

function formatName(user) {
  return user.firstName + " " + user.lastName
}

function getGreeting(user) {
  const stranger = "Stranger"
  if (user) {
    return <h1>Hello, {formatName(user)}!</h1>
  }
  return <h1>Hello, {stranger}.</h1>
}

const user = {
  firstName: "Harper",
  lastName: "Perez"
}

const element = getGreeting(user)

You can put any valid Javascript expression inside the curly braces {} in JSX. For example, formatName(user) or stranger variable are all valid Javascript expressions. Take note that all the expressions will be executed before React renders JSX into browser DOM.

JSX is also an expression, so you can use JSX inside if statements or for loops, assign to variables, accept it as arguments, and return it from functions

Curly braces {} can also be used to embed a Javascript expression in an HTML tag attribute

const element = <img className={classnames} src={user.avatarUrl}></img>

Warning

Since JSX is closer to JavaScript than to HTML, React DOM uses camelCase property naming convention instead of HTML attribute names.

For example, class becomes className in JSX, and tabindex becomes tabIndex.

Components

There are 2 ways to define a React Component

  • The first one is to create a function that takes in props and returns a JSX (Functional components).
  • The second method is to create a Class that extends from React.Component, also takes in props from the constructor and has a special method called render() to return a JSX (Class components).

You should know!

Because Functional components are too powerful right now and can do most of the things Class components can, so for the beginners, in this documentation, we will only talk about developing React with Functional components.

export default function Welcome(props) {
  const { username } = props;

  return (
    <h1>Hello, {username}</h1>
  )
}

To use the created component in other places, you can import it and use it as an HTML tag like this

import Welcome from "components/Welcome"

function Container(props) {
  return (
    <div>
      <Welcome />
    </div>
  )
}

Note

Always start component names with a capital letter.

React treats components starting with lowercase letters as DOM tags. For example, <div /> represents an HTML div tag, but <Welcome /> represents a component and requires Welcome to be in scope.

Props and States

As mentioned in the previous section, components' input parameters are called props, then what exactly are Props?

Props are unique ways to allow communication between components in React. You can get variables from other components through props, or even a callback function to return data back to them. To pass a variable to a component, you will need to pass the variable through an HTML Tag attribute, like this

function Welcome(props) {
  const { username } = props;

  return (
    <h1>Hello, {username}</h1>
  )
}

function Container(props) {
  const username = "World"

  return (
    <div>
      <Welcome username={username} />
    </div>
  )
}

Warning

Props are Read-Only

If Props are variables from parent components, then States are special local/encapsulated variables inside a component that React will keep track of changes to decide whether it should rerender the DOM or not. Since they are special variables, you need to define them using a different way, through a useState hook. We will discuss more about React Hooks in the next section, but for now, just check out the example below for how to define a state

import { useState } from "react"

function Welcome(props) {
  const [username, setUserName] = useState()

  const handleChangeInput = (event) => {
    setUserName(event.target.value)
  }

  return (
    <div>
      <h1>Hello, {username}</h1>
      <input onChange={handleChangeInput} />
    </div>
  )
}

username is the state, and to change its value, you need to call setUserName function and pass in the new value. React will then check if the new value and the current value are different and then trigger a rerender process if they are.

Warning

Do not modify State directly. You must use the setState function.

State updates are Asynchronous. After calling setState, the state value will remain unchanged until React completes its rerender process.

In the example above, you might notice that normal HTML tags also have their own props that after rendered will be remapped to the corresponding DOM element props, like onChange will be remapped to element.onchange, which allows you to add event listeners and do more many things.


Advanced Techniques

High Order Component

HOC is an advanced technique in React for reusing component logic. HOCs are not React API. They are a pattern that emerges from React's compositional nature.

Concretely, a higher-order component (HOC) is a function that takes a component and returns a new component.

HOCs are usually used when you want to apply common styles or inject common props, and logic into multiple different components. Check out the example below

(() => {
function Input(props) {
const handleChange = (e) => { console.log(e.target.value) }
return <input onChange={handleChange} />
}
function Select(props) {
const handleChange = (e) => { console.log(e.target.value) }
return (
<select onChange={handleChange}>
<option value="option1">Option 1</option>
<option value="option2">Option 2</option>
</select>
)
}
const withLabel = (OriginalComponent) => {
function WrappedComponent(props) {
const { label, ...passThroughProps } = props
return (
<div>
<label>{label}</label><br />
<OriginalComponent {...passThroughProps} />
</div>
)
}
return WrappedComponent
}
const InputWithLabel = withLabel(Input)
const SelectWithLabel = withLabel(Select)
function App() {
return (
<div>
<InputWithLabel label="Input" />
<SelectWithLabel label="Select" />
</div>
)
}
return App
})()

Context

When coding React, you will sometimes have to pass data down to children at very deep levels, but the middle components don't need to use that data at all. Or your app has some global variables and you want to use them everywhere you want. That's what Context was born for.

To use Context you just need have to define 3 things:

  • React.createContext: this function will take in a defaultValue and create a Context object to be used later.
  • Context.Provider: a special component that you can use to wrap any other components, other components will be in the scope of the context and can access the context's values.
  • useContext: a React Hook that lets you get the current context's values from any wrapped components.
// Signatures
const MyContext = React.createContext(defaultValue);

<MyContext.Provider value={/* some value */}>
  <WrappedComponent />
</MyContext.Provider>

Example

const themes = {
  light: {
    foreground: "#000000",
    background: "#eeeeee"
  },
  dark: {
    foreground: "#ffffff",
    background: "#222222"
  }
};

const ThemeContext = React.createContext(themes.light);

function ThemedButton() {
  const theme = useContext(ThemeContext);
  return (
    <button style={{ background: theme.background, color: theme.foreground }}>
      I am styled by theme context!
    </button>
  );
}

function Toolbar(props) {
  return (
    <div>
      <ThemedButton />
    </div>
  );
}

function App() {
  return (
    <ThemeContext.Provider value={themes.dark}>
      <Toolbar />
    </ThemeContext.Provider>
  );
}

That's it. That's all about React that you need to know. Once you can understand deeply and master all of these fundamental concepts, you will be coding React like a pro. In the next section, we will talk more about React Hooks, what are they and what are their functions in the React world.

Previous
Installation