React is a library for creating front end views. It has a big ecosystem of libraries that work with it. Also, we can use it to enhance existing apps.
To build single-page apps, we have to have some way to map URLs to the React component to display.
In this article, we’ll look at how to create sidebars with route content only displaying in a portion of the screen with React Router.
Creating Sidebar
We can easily create a fixed sidebar on one side of the screen while displaying route content on the other.
To do this, we just need to add our sidebar on one side with links and the Switch
and Route
components on the other.
For example, we can write the following code to achieve this effect:
import React from "react";
import ReactDOM from "react-dom";
import { BrowserRouter as Router, Switch, Route, Link } from "react-router-dom";
const routes = [
{
path: "/",
exact: true,
sidebar: () => <div>home</div>,
main: () => <h2>Home</h2>
},
{
path: "/foo",
sidebar: () => <div>foo</div>,
main: () => <h2>Bubblegum</h2>
},
{
path: "/shoelbaraces",
sidebar: () => <div>bar</div>,
main: () => <h2>Shoelaces</h2>
}
];
function App() {
return (
<Router>
<div style={{ display: "flex" }}>
<div
style={{
padding: "10px",
width: "40%",
background: "pink"
}}
>
<ul style={{ listStyleType: "none", padding: 0 }}>
<li>
<Link to="/">Home</Link>
</li>
<li>
<Link to="/foo">Foo</Link>
</li>
<li>
<Link to="/bar">Bar</Link>
</li>
</ul> <Switch>
{routes.map((route, index) => (
<Route
key={index}
path={route.path}
exact={route.exact}
children={<route.sidebar />}
/>
))}
</Switch>
</div> <div style={{ flex: 1, padding: "10px" }}>
<Switch>
{routes.map((route, index) => (
<Route
key={index}
path={route.path}
exact={route.exact}
children={<route.main />}
/>
))}
</Switch>
</div>
</div>
</Router>
);
}
const rootElement = document.getElementById("root");
ReactDOM.render(<App />, rootElement);
In the code above, we have the sidebar in the top of App
. And we have the routes
array as follows:
const routes = [
{
path: "/",
exact: true,
sidebar: () => <div>home</div>,
main: () => <h2>Home</h2>
},
{
path: "/foo",
sidebar: () => <div>foo</div>,
main: () => <h2>Bubblegum</h2>
},
{
path: "/shoelbaraces",
sidebar: () => <div>bar</div>,
main: () => <h2>Shoelaces</h2>
}
];
In the outermost div of App
, we have display: 'flex'
style to display the sidebar and the route content side by side, with the sidebar of the left and the route content on the right.
The sidebar is composed of the following code in App
:
<div style={{ padding: "10px", width: "40%", background: "#f0f0f0" }}>
<ul style={{ listStyleType: "none", padding: 0 }}>
<li>
<Link to="/">Home</Link>
</li>
<li>
<Link to="/foo">Foo</Link>
</li>
<li>
<Link to="/bar">Bar</Link>
</li>
</ul>
<Switch>
{routes.map((route, index) => (
<Route key={index} path={route.path} exact={route.exact} children={<route.sidebar />} /> ))}
</Switch>
</div>
In the code above, we have the ul
element to display the Link
s, which we can click on the show the route that we want.
In the Switch
component, we have the routes
array mapped to Route
s that we want to display in the sidebar.
We want to display the component we set as the value of the sidebar
in each entry of routes
. Therefore, we set children
to that.
In the routes
array, we have the route with path
set to '/'
has the exact
property set to true
.
We have to do this so that React Router won’t direct all routes that start with a /
to the ‘home’ route. This is because React Router doesn’t look at the other routes once it found a match.
If the match isn’t exact, then it’ll take anything that starts with a /
as the correct match. In this case, it’ll be the first route.
The right side is composed of the following code:
<div style={{ flex: 1, padding: "10px" }}>
<Switch>
{routes.map((route, index) => (
<Route key={index} path={route.path} exact={route.exact} children={<route.main />} /> ))}
</Switch>
</div>
The code above maps the routes
array again to Route
s, but we set the children
prop to the components set to the main
property instead of sidebar
.
Conclusion
We can create a sidebar easily by using flexbox and the Switch
and Route
components.
As long as we have Switch
and Route
components in only one portion of the screen, the route content will only be displayed on that part of the screen.
Flexbox lets us display items side by side without hassle.