Category Archives: Uncategorized

Mosh React Tutorial (part 12)

Pagination – Type Checking with Prop Type

What if the user passes something unexpected. Instead of an integer count. It passes a string “abc”.

In Pagination functional component, the string divides by integer. And thus, pagesCount becomes NaN. NaN gets calculated further and nothing comes of it.

npm i prop-types@15.6.2

pagination.jsx

Now let’s put a string, instead of an integer.
movies.jsx

In the console, we’ll get a warning:

Mosh React Tutorial (part 11)

source

Paginating the Data

So the concept is that we should add a property showingArr to our state.
showingArr holds the items to be shown according to what pagination page we’re on.

For example, if we’re on page 1, it should show items 1-4
If its page 2, 5-8
page 3, 9-12, and so on.

What we’re interested in is the first and last item #.
The last item # is always the current page * 4.

So if we’re on page 1, the last item is 4, page 2, last item is 8…etc.

so last item is currentPage * 4

The first item will always be last time – 4

Thus, using them, we paginate the movies array like so:

We create a private function paginateMovies.

In the beginning all the state will be set up when the virtual DOM is being built. When it finishes, it will call render which shows the default state, then in componentDidMount, we will set our state’s showingArr to the correct array. Hence in our componentDidMount():

the setState will trigger a second render, which then will show the paginated items.

full source (movies.jsx)

What are the common folder structures for React?

There are two common practices for React project file structure.

Grouping by features (or routes)

One common way to structure projects is locate CSS, JS, and tests together, grouped by feature or route.


common/
├─ Avatar.js
├─ Avatar.css
├─ APIUtils.js
└─ APIUtils.test.js
feed/
├─ index.js
├─ Feed.js
├─ Feed.css
├─ FeedStory.js
├─ FeedStory.test.js
└─ FeedAPI.js
profile/
├─ index.js
├─ Profile.js
├─ ProfileHeader.js
├─ ProfileHeader.css
└─ ProfileAPI.js

Grouping by file type

Another popular way to structure projects is to group similar files together.

api/
├─ APIUtils.js
├─ APIUtils.test.js
├─ ProfileAPI.js
└─ UserAPI.js
components/
├─ Avatar.js
├─ Avatar.css
├─ Feed.js
├─ Feed.css
├─ FeedStory.js
├─ FeedStory.test.js
├─ Profile.js
├─ ProfileHeader.js
└─ ProfileHeader.css

React Decorators

title is a string that will be set as a document title.
It is a parameter passed in from above (‘Profile’).

WrappedComponent is the Profile component displayed above.

Hence, @setTitle(title)(wrappedComponent) is what’s happening. We want to decorate the class Profile by returning a class
of our own with specific attributes and functionalities.

How do you conditionally render components?

In some cases you want to render different components depending on some state. JSX does not render false or undefined, so you can use conditional short-circuiting to render a given part of your component only if a certain condition is true.

If you need an if-else condition then use ternary operator.

use setState() in componentWillMount() method?

ref – https://stackoverflow.com/questions/52168047/is-setstate-inside-componentdidmount-considered-an-anti-pattern

You may call setState() immediately in componentDidMount(). It will trigger an extra rendering, but it will happen before the browser updates the screen. This guarantees that even though the render() will be called twice in this case, the user won’t see the intermediate state. Use this pattern with caution because it often causes performance issues. In most cases, you should be able to assign the initial state in the constructor() instead. It can, however, be necessary for cases like modals and tooltips when you need to measure a DOM node before rendering something that depends on its size or position.

It is recommended to avoid async initialization in componentWillMount() lifecycle method.

componentWillMount() is invoked immediately before mounting occurs. It is called before render(), therefore setting state in this method will not trigger a re-render. Avoid introducing any side-effects or subscriptions in this method. We need to make sure async calls for component initialization happened in componentDidMount() instead of componentWillMount().

How to use styles in React?

The style attribute accepts a JavaScript object with camelCased properties rather than a CSS string. This is consistent with the DOM style JavaScript property, is more efficient, and prevents XSS security holes.

React state changes, Virtual DOM, reconciliation

Let’s see what happens under the hood.

At this point, we call setState to tell React that the state of this component will change.

React will then schedule an async call to the render method. Whether its five ms, or ten ms, we don’t know when it happens, but it will happen in the future.

The render function will return a new React element. That element comes from the JSX code.

As each render function produces a new React element, when our state changes, the incoming React element will be different than the previous React element. React will diff them, and then apply the change(s) to the real DOM.

For example:

So when we update the count to 1 in our state object, the data we access in formatCount() within the span tag gets updated.

As we know, each element (button, div, span..etc) is an element in our virtual DOM tree. They get their data from the state object.
And when that state object gets updated as the user plays around with the UI, the current virtual DOM gets scheduled (pushed onto a scheduler) to be rendered asynchronously.

React will diff them and see that the incoming virtual DOM have changed compared to the previous virtual DOM. In our case, our span’s data has been modified.

It will notice that our span is modified because that’s where we have used formatCount() to retrieve the updated count property from the state object.
So it will reach out to the real DOM, and update that span, in order to match what we have in the virtual DOM.

Go to the web page, Inspect Elements, and click on the ‘Increment’ button.
You’ll see that as you push the increment button, it calls

which updates the span. It updates the span because it depending on this.state.count it will update the class name to badge-primary or badge-info, and also update the count integer. Thus, in your Inspect Element, nothing else in the DOM is affected. Only that span element.

How does React render Updates?

Explanation
render() function is the point of entry where the tree of React elements are created. When a state or prop within the component is updated, the render() will return a different tree of React elements. If you use setState() within the component, React immediately detects the state change and re-renders the component.

React then figures out how to efficiently update the UI to match the most recent tree changes.
This is when React updates its virtual DOM first and updates only the object that have changed in the real DOM.

Batch Updates

React follows a batch update mechanism to update the real DOM. Hence, leading to increased performance. This means that updates to the real DOM are sent in batches, instead of sending updates for every single change in state.

The repainting of the UI is the most expensive part, and React efficiently ensures that the real DOM receives only batched updates to repaint the UI.

Explanation

When you use React, at a single point in time you can think of the render() function as creating a tree of React elements. On the next state or props update, that render() function will return a different tree of React elements. React then needs to figure out how to efficiently update the UI to match the most recent tree.

There are some generic solutions to this algorithmic problem of generating the minimum number of operations to transform one tree into another. However, the state of the art algorithms have a complexity in the order of O(n3) where n is the number of elements in the tree.

If we used this in React, displaying 1000 elements would require in the order of one billion comparisons. This is far too expensive. Instead, React implements a heuristic O(n) algorithm based on two assumptions:

– Two elements of different types will produce different trees.
– The developer can hint at which child elements may be stable across different renders with a key prop.

The Diffing Algorithm – reconciliation

When diffing two trees, React first compares the two root elements. The behavior is different depending on the types of the root elements.

Elements Of Different Types

Whenever the root elements have different types, React will tear down the old tree and build the new tree from scratch. Going from a tag to img tag or from article tag to Comment tag or from button tag to div tag – any of those will lead to a full rebuild.

When tearing down a tree, old DOM nodes are destroyed. Component instances receive componentWillUnmount(). When building up a new tree, new DOM nodes are inserted into the DOM. Component instances receive componentWillMount() and then componentDidMount(). Any state associated with the old tree is lost.

Any components below the root will also get unmounted and have their state destroyed. For example, when diffing:

This will destroy the old Counter and remount a new one.

DOM Elements Of The Same Type

When comparing two React DOM elements of the same type, React looks at the attributes of both, keeps the same underlying DOM node, and only updates the changed attributes. For example:

By comparing these two elements, React knows to only modify the className on the underlying DOM node.
When updating style, React also knows to update only the properties that changed. For example:

When converting between these two elements, React knows to only modify the color style, not the fontWeight.