Building a Responsive Navigation Bar with React & CSS
CSS is hard. As a newer developer say you finally get all the styling just as you wanted to on a project, only to go to the developer tools and check it out on mobile-view and it looks like a truck just ran through your application! This has definitely happened to me before until I found out about media queries! With media queries, we can change up our styling based on the dimensions of the screen so that no matter what type of device the user is on you will have a nice responsive application. I’d like to go over with you how to build a responsive navigation bar that on smaller screens displays a hamburger menu and on larger screens your typical navigation bar with all your links lined up along the same row. For this code-along, I’ll be skipping the step to getting our react starter template and we’ll also be using React hooks. If you are unfamiliar with these subjects, refer to the resources at the bottom for the documentation.
Once we initiate our app, first thing to do is get rid of all the unnecessary code we’re provided in our App.js, and have it only contain a Header component that we will be building next.
Building our Navigation Bar
Before we start writing any code, let’s grab some of the icons we’re going to need for our mobile-view hamburger menu. You can use any icon providers you like, but for this example i’m going to be using the icons from Heroicons. The icons we’ll be using are “Menu”, “X”, and “Cube-transparent” and i’ll be storing these icons as SVGs in an assets folder.
Next is to create a Header component as well as a css file for our component, to keep things simple i’ll be naming mine Header.jsx and header.css. Within our header component we’ll need to import our SVGs and make it a functional component
The current state of our application should look like this:
As it is, not a whole lot going on here. So let’s start with adding in our logo, some menu options, and I want to have a separate section along the nav-bar for signin/up.
Now i’m sure you’re looking at this code and asking yourself “Wait a second, why is there two Signin/up links?” we’ll touch on a little bit later as to why! The next item to address adding the code for mobile-view hamburger menu and it’s functionality so that when it clicked, we want to set the dropdown menu to be open or closed.
New things added here are we are using React hooks to create a clicked or unclicked state as a boolean. We’re also creating two functions, handleClick is going to toggle our clicked state on and off, while the closeMobileMenu function is just setting our clicked state to false as when a user clicks on a menu-item in mobile view we want to close the menu. Looking at line 21 we are setting conditional that if clicked is set to true then the class will include an additional class name of active, if false, just have the class just be regular nav-options. If you haven’t guessed by the class name already, this conditional is going to be what toggles is the display of our dropdown menu. The rest is adding some class names to other elements which we’ll be using to style. Now let’s take a look at our stylesheet:
I’m not going to go over all of the stylings, but the part I really want to highlight is lines 30–35. We are setting these displays to none as these are mobile-only options we don’t want to display. But the problem we have now is that no matter what screen size we have the mobile options are never going to display at all! That is where media queries come into play.
From line 62 and on we are stating that if the width of the screen goes below 649px then add these stylings. Biggest ones being at this screen size we are displaying the previously hidden mobile-menu items, and hiding the other signin/up container we had from before.
For the full code & demo, check out codesandbox below:
Resources:
Icons used(Heroicons): https://heroicons.com/
Create-react-app: https://reactjs.org/docs/create-a-new-react-app.html
React Hooks: https://reactjs.org/docs/hooks-intro.html