React is a popular library for creating web apps and mobile apps.
In this article, we’ll look at how to compose React components.
Higher-order components are components that accept other components as arguments and return them after modifying them.
A higher-order component looks like the following:
const HoC = Component => EnhancedComponent
We take in a component and return an enhanced one.
For instance, we can write:
const withClassName = Component => props => (
<Component {...props} className="foo" />
)
Then we can return a component that has a class name prop added to it.
Instead of using it directly, we write:
const ComponentWithClassName = withClassName(Component)
We always start our higher-order component with with
so that we can tell them apart.
With higher-order components, we can create different ones that are similar to each other, but mostly the same.
The Recompose package has various high-order components that we can use individually or in combination.
To install it, we can run:
npm install recompose --save
Then we can use it by writing:
import React from "react";
import { withState } from "recompose";
const enhance = withState("count", "setCount", 0);
const Counter = enhance(({ count, setCount }) => (
<div>
Count: {count}
<button onClick={() => setCount(n => n + 1)}>Increment</button>
</div>
));
export default function App() {
return <Counter />;
}
We created a Counter
component with the withState
function to hold the state instead of using the useState
hook.
Then we pass our component into the enhance
function so that we can get the props we need.
The state and function to set it are available as props.
This lets our state be used in multiple components.
There are many other functions we can use.
For instance, we can write:
import React from "react";
import { withProps, flattenProp, compose } from "recompose";
const enhance = compose(
withProps({
obj: { a: "a", b: "b" },
c: "c"
}),
flattenProp("obj")
);
const Foo = enhance(({ a, b, c }) => (
<div>
{a} {b} {c}
</div>
));
export default function App() {
return <Foo />;
}
We called compose
to combine multiple higher-order components into one.
We have withProps
to pass in some props.
And we called flattenProp
to flatten the nested obj
prop.
Then to create Foo
we pass in a component into the enhance
function and show the values of the props.
Then we display Foo
in App
.
Functions can be passed in as a child prop of another component.
For instance, we write:
const FunctionAsChild = ({ children }) => children()
To use it, we can write:
import React from "react";
const FunctionAsChild = ({ children }) => children();
export default function App() {
return <FunctionAsChild>{() => <div>hello/div>}</FunctionAsChild>;
}
We passed in a function in between the tags so that it can be called in FunctionAsChild
.
Also, we can pass in parameters. For instance, we can write:
import React from "react";
const Greeting = ({ children }) => children("james");
export default function App() {
return <Greeting>{name => <div>Hello, {name}!</div>}</Greeting>;
}
We have a Greeting
component, we call children
, which is what’s between the tags.
Then in App
, we pass in a function that we call in Greeting
.
This makes our function much more flexible
#javascript #web-development #programming #react