Well hello web developer world. Starting with this tutorial, we are going to start investigating React.js – a ridiculously popular open source JavaScript library. Before embarking on our React.js journey, it will help to brush up a bit on ES6 and various JavaScript concepts like variables, objects, and arrays. React.js of course uses functions and classes in JavaScript. In addition we’ll be learning about the declarative nature of using React. Declarative means that you describe what you want to happen, and the tool does the work for you. The SQL language is the most popular example of the declarative style. Let’s get started with React.js now!
Why Is React.js So Popular?
Certainly you have heard of React.js before checking out this tutorial. In fact, WordPress now leverages the React.js library in its own Gutenberg editor. React focuses on building user interfaces. The UI is of course is what end users are presented with to interact with an application, be it web-based or mobile based. React.js uses JavaScript, so it is perfect for both web and mobile user interfaces. In React.js, the developer describes the user interface. This is a key aspect of React.js that makes it popular. The designer can tell React.js what she wants, and React.js does the heavy lifting for us. React.js allows developers to build complex user interfaces without doing everything from scratch using JavaScript and native APIs. This is what it means to be declarative. In other words, we tell the tool what we want, not how to do it. Working directly with the DOM API is difficult. React.js instead uses a virtual dom that is more friendly than the real one. Having React.js skills is great for iOS and Android mobile applications as well as Desktop browsers. Additionally, React.js is fairly small so once you have the basic API down, your knowledge of JavaScript will enable you to do very productive things with the library.
3 Basic React.js Concepts
In React.js, there are three basic concepts to understand. The first is components.
1. Components
User interfaces in React are described using Components. Think of a component as a simple JavaScript function. Just like in other programming languages, functions are invoked with some input and hopefully we get some output returned. In React.js, this works a little differently. A React.js component is not really invoked. You simply write it out in a similar fashion as to how you would write standard html.
Components are:
- Like functions
- Input: props, state | Output: UI
- Reusable and composable
- <Component />
- Can manage a private state
2. Reactive Updates
The second big concept with React.js is that of Reactive Updates. When the state of a React component, this can be thought of as the input to that component, changes, then the user interface it represents, the output, will change as well. Any time this changes happens the html in the dom tree needs to be regenerated. When using React.js, it will simply react to the changes in a component’s state and automatically update the parts of the DOM that need to be updated.
For Reactive Updates:
- React will react
- Take updates to the browser
3. The Virtual DOM
The third important concept we need to be aware of concerning React.js is the Virtual DOM. What is the Virtual DOM? It can be thought of as a virtual representation of views in memory. In React.js, you generate your html markup using JavaScript. When a web application receives data from the server via AJAX, you need something more than HTML to work with that data. This is where React.js uses a virtual representation of HTML views in memory, also known as the tree reconciliation algorithm. React uses the virtual DOM to compare versions of the UI in memory before it acts on them. You can learn more about the Virtual DOM here.
For The Virtual DOM:
- Generate HTML using JavaScript
- No HTML template language.
- Tree reconciliation
Let’s Build A React Component
Ok enough with the blah blah, let’s build a simple React.js component to see how this works.
function Helloreact() {
return <div>Hello React!</div>;
}
ReactDOM.render(
<Helloreact />,
document.getElementById('mountIt'),
);
<div id="mountIt"></div>
Output:
In the code above is a simple React function component named Helloreact
. This component returns a div has no input. To display a React component in the browser, we need to tell the ReactDOM library how to do that. We can use the ReactDOM.render() function, which takes in two arguments. The first argument is the component to render. In this example, it is the Helloreact component. The second argument to the ReactDOM.render() function is the DOM element in the browser where we wish the React component to show up. This is where the component will be mounted.
Installing Create React App
The easiest way to get working with some React.js code on your local machine is to use the Create React App available by installing it using NPM. As long as you have Node installed already, you can run a few simple commands such as these.
npm i create-react-app
npx create-react-app hello-react
cd hello-react
npm start
Then visit http://localhost:3000/ and witness a new React.js application in all of its glory!
You can open your application folder in an editor like Visual Studio Code and it will appear similar to this.
Now, to be sure we understand what’s going on here we can get rid of everything in App.js and replace with this code here.
import ReactDOM from 'react-dom'
import React from 'react';
function Button() {
return <button>Stateless Button!</button>;
}
ReactDOM.render(
<Button />,
document.getElementById('root'),
);
export default Button;
This gives us a simple button that does nothing when we click it!
How To Use A React Hook
Now we are going to get a little more fancy with our button. We want to make use of some kind of state. Let’s update the code to this found here.
import ReactDOM from 'react-dom'
import React, { useState } from 'react';
function Button() {
const [counter, setCounter] = useState(1);
return <button onClick={() => setCounter(counter+1)}>{counter}</button>;
}
ReactDOM.render(
<Button />,
document.getElementById('root'),
);
export default Button;
The code above makes use of a special function in React.js named useState. If you were to follow that link, you would see that this function is actually a State Hook in React.js. The useState function returns two items when called. The first item is a state object, and the second is a function to change that state object. The state object can be of any type such as a string, a number, or an array or something else. In this example it is a number. The state object has a name of counter
while the name of its updater function is setCounter
. In the code we are using JavaScript destructuring to capture these two variables in one line. The rest of the code pretty much shows us what is happening. When the button is clicked, the counter is incremented by one. We can see that here!
One Way Data Flow In React
In React data moves from component to component. Let’s see that in action here.
import ReactDOM from 'react-dom'
import React, { useState } from 'react';
function Button(props) {
return (
<button onClick={props.onClickFunction}>
"Click To Increment!"
</button>
);
}
function Presentation(props) {
return (
<li>{props.message}</li>
);
}
function App() {
const [counter, setCounter] = useState(0);
const incrementCounter = () => setCounter(counter+1);
return (
<div>
<Button onClickFunction={incrementCounter} increment={1} />
<Presentation message={counter}/>
</div>
);
}
ReactDOM.render(
<App />,
document.getElementById('root'),
);
export default App;
In the code above, we are now using one way data flow between components. The state in a React component can only be accessed by that component itself. To make the counter state accessible to both components, we need to create a parent component. That is what the new App
component is for. Therefore useState is now part of the App component. With the counter state now in the App component, which is the parent of the Presentation
component, data can now flow from the parent to the child. Our goal is to make the value of counter
flow to the Presentation
component. This is done with the props object. To pass a prop to a component, you specify an attribute similar to how you do in HTML. The Presentation
component receives a prop named message
, and the value of that message is the counter variable that’s coming from the useState Hook. The Presentation component can now use its props object. All function components receive this object, even when they have no attributes. That means the Button
component is currently receiving its props object, and that object so far has been empty. Since a component can receive several attributes, the props object will have a key-value pair for each attribute. This means in order to access the message prop and place its value within the Presentation div we use {props.message}
.
In the App
component is a new function named incrementCounter
. This function updates the App
component’s counter state to increment the counter value using the previous counter value. To enable the Button
component to be able to invoke the incrementCounter
function in the App
component, we can pass a reference to incrementCounter
to the Button
component as a prop. Functions are just objects in JavaScript, and since you can pass any object value as a prop, this works just fine. The onClickFunction
gets a value of incrementCounter, which is a reference to the function defined in the App component. We can use this new passed-down behavior directly in the onClick value. It will be a prop on this component, so we can access it with props.onClickFunction
. The onClick function property allowed the Button to invoke the App component’s incrementCounter function. It’s as if when clicking that button, the Button component is reaching out to the App component and says “Hey, invoke that incrementCounter function!” So that gives us a basic idea of how data flows in one direction in React using props.