Skip to main content

There are two different types of navigation menus in HTML, vertical, and horizontal. This tutorial will take you through creating a stylish CSS 3 vertical menu. I’ll show you how to create a basic menu, all the way through to an animated sliding menu – no Javascript needed.

Vertical menus are very similar to horizontal menus, the main difference being the type of display setting being used. Let’s begin.

Basic HTML 5 Menu

Here’s what we’ll be creating for our basic menu –

See the Pen engFG by lawnch (@lawnch) on CodePen.1507

Default CSS

We need to start by defining some basic CSS styles such as the body, and box-sizing styles. Importantly here we’re defining box-sizing: border-box;. This treats padding and borders differently to the traditional method that would add any values to the standard width. That means if you define a width as 25%, it stays at 25%. Normally that would be 25% + padding + border.

[css]<br />
* {<br />
margin: 0;<br />
padding: 0;<br />
outline: none;</p>
<p> -webkit-box-sizing: border-box;<br />
-moz-box-sizing: border-box;<br />
box-sizing: border-box;<br />
}</p>
<p>body {<br />
background: #eee;<br />
color: #444;<br />
-webkit-font-smoothing: antialiased;<br />
font-family: ‘Helvetica Neue’, sans-serif;<br />
font-size: 20px;<br />
font-weight: 400;<br />
height: auto !important;<br />
height: 100%;<br />
min-height: 100%;<br />
text-rendering: optimizeLegibility;<br />
}</p>
<p>div.wrapper {<br />
margin: 20px auto;<br />
width: 350px;<br />
}<br />
[/css]Most of the styles defined above will be standard and don’t specifically matter for our example. You don’t HAVE to include these when creating the menu for your own website.

Text-rendering allows the browser to choose quality of text over speed of render, making your text look nicer.

The wrapper CSS is also not needed, it simply specifies the width of the menu and makes it sit in the center of the page. By placing the menu in a container element such as a side-bar, you’ll overwrite the need for the wrapper.

Basic Vertical Menu

The first thing to create is our basic list and container element. As we’re using HTML 5 we can use the <nav> element.

Our HTML should look like so –

[html]</p>
<nav class="vertical">
<ul>
<li>
<a href="#">Home</a></li>
<li>
<a href="#">Blog</a></li>
<li>
<a href="#">Work</a></li>
</ul>
</nav>
<p>[/html]And the CSS is as follows –

[css]<br />
nav.vertical {<br />
border-radius: 4px;<br />
box-shadow: 0 0 10px rgba(0,0,0,.15);<br />
overflow: hidden;<br />
text-align: center;<br />
}</p>
<p> nav.vertical > ul {<br />
list-style-type: none;<br />
}</p>
<p> nav.vertical > ul > li {<br />
display: block;<br />
}<br />
[/css]Important style definitions –

  • border-radius – border-radius provides the rounded corners for our element
  • box-shadow – This adds a drop shadow to our element. Format as follows – Y value, X value, shadow size, color.
  • overflow – as our element contains other elements, we need to hide the contents if they extend outside the container. This ensures the rounded corners work as expected.

That gives us our basic HTML 5 vertical menu container. Next we need to style the main nav elements, which can be done by styling the anchor <a> elements –

[css]<br />
nav.vertical > ul > li > a {<br />
background-color: rgb(157, 34, 60);<br />
background-image: -webkit-linear-gradient(135deg, rgb(114, 51, 98), rgb(157, 34, 60));<br />
background-image: -moz-linear-gradient(135deg, rgb(114, 51, 98), rgb(157, 34, 60));<br />
background-image: -o-linear-gradient(135deg, rgb(114, 51, 98), rgb(157, 34, 60));<br />
background-image: linear-gradient(135deg, rgb(114, 51, 98), rgb(157, 34, 60));<br />
border-bottom: 1px solid rgba(255,255,255,.1);<br />
box-shadow: inset 0 1px 1px rgba(0,0,0,.1), 0 1px 1px rgba(0,0,0,.1);<br />
color: rgb(255,255,255);<br />
display: block;<br />
font-size: .85rem;<br />
font-weight: 500;<br />
height: 50px;<br />
letter-spacing: .5rem;<br />
line-height: 50px;<br />
text-shadow: 0 1px 1px rgba(0,0,0,.1);<br />
text-transform: uppercase;<br />
transition: all .1s ease;<br />
text-decoration: none;<br />
}</p>
<p> nav.vertical > ul > li > a:hover {<br />
background-color: rgb(114, 51, 98);<br />
background-image: -webkit-linear-gradient(150deg, rgb(114, 51, 98), rgb(114, 51, 98));<br />
background-image: -moz-linear-gradient(150deg, rgb(114, 51, 98), rgb(114, 51, 98));<br />
background-image: -o-linear-gradient(150deg, rgb(114, 51, 98), rgb(114, 51, 98));<br />
background-image: linear-gradient(150deg, rgb(114, 51, 98), rgb(114, 51, 98));<br />
cursor: pointer;<br />
}<br />
[/css]There’s a lot going on in both of these definitions. First of all let’s go through the basic anchor style –

  • background-color – used as back-up incase the gradient background isn’t supported
  • background-image – prefixed for different browsers, this specifies the CSS 3 gradient effect on each main nav element
  • border-bottom – a simple 1 pixel line at the bottom of the element. Using RGBA makes the white line have 10% opacity, making it blend better
  • box-shadow – an inset box-shadow allows us to have a second border within the element, adding a nicer effect
  • color – white text
  • display – block element fills the whole width. Required when specifying a height
  • font-size – using rem makes the font size relative to the default font-size, allowing for nicer scalability
  • font-weight – 500 is a regular font-weight, not bold, not light.
  • height – specify the height of the element, used with display: block;
  • letter-spacing – increases the space between the letters within the element
  • line-height – setting to the same as the height will place our text in the vertical center of the element – no need for padding
  • text-shadow – add a simple 10% opacity shadow below our text
  • text-transform – make our text all uppercase/capitals
  • transition – used for animation, this makes all changes animated for 100ms using the ease animation
  • text-decoration – remove the underline on our link

The second style definition is using the :hover selector, meaning it’s only active when the use hovers over the specified element. This works well with our transition definition as it will animate the changes.

Sub Navigation Menu

To create the second set of links we simply embed a second list inside our first list. This is very simple and easy to do, just remember to maintain the integrity of the HTML elements.

Let’s take the first menu item and add its sub menu. This is done like so –

[html]</p>
<ul>
<li>
<a href="#">Home</a><br />
<!–START SUB MENU–></p>
<div>
<ul>
<li><a href="#">Index</a></li>
<li><a href="#">About</a></li>
<li><a href="#">Corporate</a></li>
<li><a href="#">Contact</a></li>
</ul>
</div>
<p><!–END SUB MENU–></li>
</ul>
<p>[/html]I’ve commented the embedded list so you can see what’s been added. The containing div isn’t always needed when embedding lists, for this example it is as we’re going to add a background color.

Let’s look at styling the list. As our list is contained within another list, we can use the > CSS selector, making the CSS more specific.

[css]<br />
nav.vertical > ul > li > div {<br />
background-color: rgb(255,255,255);<br />
}</p>
<p> nav.vertical > ul > li > div > ul {<br />
list-style-type: none;<br />
}</p>
<p> nav.vertical > ul > li > div > ul > li > a {<br />
background-color: rgb(255,255,255);<br />
border-bottom: 1px solid rgba(0,0,0,.05);<br />
color: #333331;<br />
display: block;<br />
font-size: 1.1rem;<br />
padding: 10px 0;<br />
text-decoration: none;<br />
transition: all 0.15s linear;<br />
}<br />
[/css]Most of the above code is self explanatory. It can be broken down like so –

  • Set a white background behind our list
  • Turn off HTML bullet points
  • Style our sub-menu list items

Next we want to animate our sub-menu when the user hovers over a list-item. This is combined with our previously defined transition: all 0.15s linear; statement. If you want to change the type, or speed of animation then that’s what you need to change.

[css]<br />
nav.vertical > ul > li > div > ul > li:hover > a {<br />
background-color: lightBlue;<br />
color: rgb(255,255,255);<br />
padding: 10px 0 10px 50px;<br />
}<br />
[/css]To make the text slide to the right we simply add 50px padding to the left. Change the 50px value to suit the amount of sliding you wish to happen.

Simple HTML 5 Vertical Menu Code

We’ve completed the basic menu, here’s the full code so far.

HTML

[html]</p>
<div class="wrapper">
<nav class="vertical">
<ul>
<li>
<a href="#">Home</a></p>
<div>
<ul>
<li><a href="#">Index</a></li>
<li><a href="#">About</a></li>
<li><a href="#">Corporate</a></li>
<li><a href="#">Contact</a></li>
</ul>
</div>
</li>
<li>
<a href="#">Blog</a></p>
<div>
<ul>
<li><a href="#">Articles</a></li>
<li><a href="#">Inspiration</a></li>
<li><a href="#">Tutorials</a></li>
</ul>
</div>
</li>
<li>
<a href="#">Work</a></p>
<div>
<ul>
<li><a href="#">Client Login</a></li>
<li><a href="#">Get Quote</a></li>
<li><a href="#">Portfolio</a></li>
</ul>
</div>
</li>
</ul>
</nav>
</div>
<p>[/html]CSS

[css]<br />
* {<br />
margin: 0;<br />
padding: 0;<br />
outline: none;</p>
<p> -webkit-box-sizing: border-box;<br />
-moz-box-sizing: border-box;<br />
box-sizing: border-box;<br />
}</p>
<p>body {<br />
background: #eee;<br />
color: #444;<br />
-webkit-font-smoothing: antialiased;<br />
font-family: ‘Helvetica Neue’, sans-serif;<br />
font-size: 20px;<br />
font-weight: 400;<br />
height: auto !important;<br />
height: 100%;<br />
min-height: 100%;<br />
text-rendering: optimizeLegibility;<br />
}</p>
<p>div.wrapper {<br />
margin: 20px auto;<br />
width: 350px;<br />
}</p>
<p>nav.vertical {<br />
border-radius: 4px;<br />
box-shadow: 0 0 10px rgba(0,0,0,.15);<br />
overflow: hidden;<br />
text-align: center;<br />
}</p>
<p> nav.vertical > ul {<br />
list-style-type: none;<br />
}</p>
<p> nav.vertical > ul > li {<br />
display: block;<br />
}</p>
<p> nav.vertical > ul > li > a {<br />
background-color: rgb(157, 34, 60);<br />
background-image: -webkit-linear-gradient(135deg, rgb(114, 51, 98), rgb(157, 34, 60));<br />
background-image: -moz-linear-gradient(135deg, rgb(114, 51, 98), rgb(157, 34, 60));<br />
background-image: -o-linear-gradient(135deg, rgb(114, 51, 98), rgb(157, 34, 60));<br />
background-image: linear-gradient(135deg, rgb(114, 51, 98), rgb(157, 34, 60));<br />
border-bottom: 1px solid rgba(255,255,255,.1);<br />
box-shadow: inset 0 1px 1px rgba(0,0,0,.1), 0 1px 1px rgba(0,0,0,.1);<br />
color: rgb(255,255,255);<br />
display: block;<br />
font-size: .85rem;<br />
font-weight: 500;<br />
height: 50px;<br />
letter-spacing: .5rem;<br />
line-height: 50px;<br />
text-shadow: 0 1px 1px rgba(0,0,0,.1);<br />
text-transform: uppercase;<br />
transition: all .1s ease;<br />
text-decoration: none;<br />
}</p>
<p> nav.vertical > ul > li > a:hover {<br />
background-color: rgb(114, 51, 98);<br />
background-image: -webkit-linear-gradient(150deg, rgb(114, 51, 98), rgb(114, 51, 98));<br />
background-image: -moz-linear-gradient(150deg, rgb(114, 51, 98), rgb(114, 51, 98));<br />
background-image: -o-linear-gradient(150deg, rgb(114, 51, 98), rgb(114, 51, 98));<br />
background-image: linear-gradient(150deg, rgb(114, 51, 98), rgb(114, 51, 98));<br />
cursor: pointer;<br />
}</p>
<p> nav.vertical > ul > li > div {<br />
background-color: rgb(255,255,255);<br />
}</p>
<p> nav.vertical > ul > li > div > ul {<br />
list-style-type: none;<br />
}</p>
<p> nav.vertical > ul > li > div > ul > li > a {<br />
background-color: rgb(255,255,255);<br />
border-bottom: 1px solid rgba(0,0,0,.05);<br />
color: #333331;<br />
display: block;<br />
font-size: 1.1rem;<br />
padding: 10px 0;<br />
text-decoration: none;<br />
transition: all 0.15s linear;<br />
}</p>
<p> nav.vertical > ul > li > div > ul > li:hover > a {<br />
background-color: lightBlue;<br />
color: rgb(255,255,255);<br />
padding: 10px 0 10px 50px;<br />
}<br />
[/css]

Animated, Mobile Friendly Vertical Navigation

With our next menu we’re going to build upon the previous example, animating certain elements and tweaking some styles.

Here’s what we’re going to be creating –

See the Pen Animated CSS accoridion menu by lawnch (@lawnch) on CodePen.1507

Most of the HTML is the same as the previous example, the only difference being the use of labels & inputs instead of anchor tags in our main navigation menu. The below code shows the difference between the two –

Before –

[html]</p>
<li>
<a href="#">Home</a></p>
<div>
<ul>
<li><a href="#">Index</a></li>
<li><a href="#">About</a></li>
<li><a href="#">Corporate</a></li>
<li><a href="#">Contact</a></li>
</ul>
</div>
</li>
<p>[/html]After –

[html]</p>
<li>
<label for="home">Home</label><br />
<input type="radio" name="verticalMenu" id="home" /></p>
<div>
<ul>
<li><a href="#">Index</a></li>
<li><a href="#">About</a></li>
<li><a href="#">Corporate</a></li>
<li><a href="#">Contact</a></li>
</ul>
</div>
</li>
<p>[/html]Very little change… but it changes the menu dramatically.

The Theory

Through CSS selectors we can style elements next to / proceeding other elements. By using this we can create a toggle menu using purely HTML and CSS. The theory for this is –

  • Use labels to select radio input buttons
  • Give the radio inputs the same name so only 1 can be selected at any one time
  • When the radio is selected then display the container element that follows
  • When the radio input isn’t selected then hide the container element
  • Use the max-height definition to animate the container, making it expand in size

CSS Styling

First of all we need to change some of our previously used CSS. As we’re using labels and inputs instead of anchor elements we need to modify the CSS rule. Incase you want to also use normal menu items (traditional links), we’ll keep that definition as well.

[css]<br />
nav.vertical > ul > li > label,<br />
nav.vertical > ul > li > a {<br />
background-color: rgb(157, 34, 60);<br />
background-image: -webkit-linear-gradient(135deg, rgb(114, 51, 98), rgb(157, 34, 60));<br />
background-image: -moz-linear-gradient(135deg, rgb(114, 51, 98), rgb(157, 34, 60));<br />
background-image: -o-linear-gradient(135deg, rgb(114, 51, 98), rgb(157, 34, 60));<br />
background-image: linear-gradient(135deg, rgb(114, 51, 98), rgb(157, 34, 60));<br />
border-bottom: 1px solid rgba(255,255,255,.1);<br />
box-shadow: inset 0 1px 1px rgba(0,0,0,.1), 0 1px 1px rgba(0,0,0,.1);<br />
color: rgb(255,255,255);<br />
display: block;<br />
font-size: .85rem;<br />
font-weight: 500;<br />
height: 50px;<br />
letter-spacing: .5rem;<br />
line-height: 50px;<br />
text-shadow: 0 1px 1px rgba(0,0,0,.1);<br />
text-transform: uppercase;<br />
transition: all .1s ease;<br />
}</p>
<p> nav.vertical > ul > li > label:hover,<br />
nav.vertical > ul > li > a:hover {<br />
background-color: rgb(114, 51, 98);<br />
background-image: -webkit-linear-gradient(150deg, rgb(114, 51, 98), rgb(114, 51, 98));<br />
background-image: -moz-linear-gradient(150deg, rgb(114, 51, 98), rgb(114, 51, 98));<br />
background-image: -o-linear-gradient(150deg, rgb(114, 51, 98), rgb(114, 51, 98));<br />
background-image: linear-gradient(150deg, rgb(114, 51, 98), rgb(114, 51, 98));<br />
cursor: pointer;<br />
}<br />
[/css]By seperating definitions with commas we can combine two definitions into one. For that reason there’s no styling differences between the code above and the previous example.

Next we want to style our sub-menu container. First we need to hide the container when the radio isn’t selected, then we need to display, and animate it once it’s selected.

Additionally we want to hide the radio input. As the input works with labels, there’s no need for the user to be able to see the input.

[css]<br />
nav.vertical > ul > li > label + input {<br />
display: none;<br />
visability: hidden;<br />
}</p>
<p> nav.vertical > ul > li > div {<br />
background-color: rgb(255,255,255);<br />
max-height: 0;<br />
overflow: hidden;<br />
transition: all .5s linear;<br />
}</p>
<p> nav.vertical > ul > li > label + input:checked + div {<br />
max-height: 500px;<br />
}<br />
[/css]There are five important rules being used here –

  • + CSS 3 selector – this selector means following, ie.. “label + input” means “label followed by input
  • max-height – setting the max-height to 0 will automatically close all the divs when the page loads
  • Setting the div to overflow hidden will hide the content held inside the containing div
  • transition + max-height – by combining the transition and max-height styles we can give the impression the box is expanding
  • :checked CSS selector – this is for when the radio button is clicked / checked via the label

Full Code

With the above tweaks made the code should now look like the following –

HTML

[html]</p>
<div class="wrapper">
<nav class="vertical">
<ul>
<li>
<label for="home">Home</label><br />
<input type="radio" name="verticalMenu" id="home" /></p>
<div>
<ul>
<li><a href="#">Index</a></li>
<li><a href="#">About</a></li>
<li><a href="#">Corporate</a></li>
<li><a href="#">Contact</a></li>
</ul>
</div>
</li>
<li>
<label for="blog">Blog</label><br />
<input type="radio" name="verticalMenu" id="blog" /></p>
<div>
<ul>
<li><a href="#">Articles</a></li>
<li><a href="#">Inspiration</a></li>
<li><a href="#">Tutorials</a></li>
</ul>
</div>
</li>
<li>
<label for="work">Work</label><br />
<input type="radio" name="verticalMenu" id="work" /></p>
<div>
<ul>
<li><a href="#">Client Login</a></li>
<li><a href="#">Get Quote</a></li>
<li><a href="#">Portfolio</a></li>
</ul>
</div>
</li>
</ul>
</nav>
</div>
<p>[/html]CSS

[css]<br />
* {<br />
margin: 0;<br />
padding: 0;<br />
outline: none;</p>
<p> -webkit-box-sizing: border-box;<br />
-moz-box-sizing: border-box;<br />
box-sizing: border-box;<br />
}</p>
<p>body {<br />
background: #eee;<br />
color: #444;<br />
-webkit-font-smoothing: antialiased;<br />
font-family: ‘Helvetica Neue’, sans-serif;<br />
font-size: 20px;<br />
font-weight: 400;<br />
height: auto !important;<br />
height: 100%;<br />
min-height: 100%;<br />
text-rendering: optimizeLegibility<br />
}</p>
<p>div.wrapper {<br />
margin: 20px auto;<br />
width: 350px;<br />
}</p>
<p>nav.vertical {<br />
border-radius: 4px;<br />
box-shadow: 0 0 10px rgba(0,0,0,.15);<br />
overflow: hidden;<br />
text-align: center;<br />
}</p>
<p> nav.vertical > ul {<br />
list-style-type: none;<br />
}</p>
<p> nav.vertical > ul > li {<br />
display: block;<br />
}</p>
<p> nav.vertical > ul > li > label,<br />
nav.vertical > ul > li > a {<br />
background-color: rgb(157, 34, 60);<br />
background-image: -webkit-linear-gradient(135deg, rgb(114, 51, 98), rgb(157, 34, 60));<br />
background-image: -moz-linear-gradient(135deg, rgb(114, 51, 98), rgb(157, 34, 60));<br />
background-image: -o-linear-gradient(135deg, rgb(114, 51, 98), rgb(157, 34, 60));<br />
background-image: linear-gradient(135deg, rgb(114, 51, 98), rgb(157, 34, 60));<br />
border-bottom: 1px solid rgba(255,255,255,.1);<br />
box-shadow: inset 0 1px 1px rgba(0,0,0,.1), 0 1px 1px rgba(0,0,0,.1);<br />
color: rgb(255,255,255);<br />
display: block;<br />
font-size: .85rem;<br />
font-weight: 500;<br />
height: 50px;<br />
letter-spacing: .5rem;<br />
line-height: 50px;<br />
text-shadow: 0 1px 1px rgba(0,0,0,.1);<br />
text-transform: uppercase;<br />
transition: all .1s ease;<br />
}</p>
<p> nav.vertical > ul > li > label:hover,<br />
nav.vertical > ul > li > a:hover {<br />
background-color: rgb(114, 51, 98);<br />
background-image: -webkit-linear-gradient(150deg, rgb(114, 51, 98), rgb(114, 51, 98));<br />
background-image: -moz-linear-gradient(150deg, rgb(114, 51, 98), rgb(114, 51, 98));<br />
background-image: -o-linear-gradient(150deg, rgb(114, 51, 98), rgb(114, 51, 98));<br />
background-image: linear-gradient(150deg, rgb(114, 51, 98), rgb(114, 51, 98));<br />
cursor: pointer;<br />
}</p>
<p> nav.vertical > ul > li > label + input {<br />
display: none;<br />
visability: hidden;<br />
}</p>
<p> nav.vertical > ul > li > div {<br />
background-color: rgb(255,255,255);<br />
max-height: 0;<br />
overflow: hidden;<br />
transition: all .5s linear;<br />
}</p>
<p> nav.vertical > ul > li > label + input:checked + div {<br />
max-height: 500px;<br />
}</p>
<p> nav.vertical > ul > li > div > ul {<br />
list-style-type: none;<br />
}</p>
<p> nav.vertical > ul > li > div > ul > li > a {<br />
background-color: rgb(255,255,255);<br />
border-bottom: 1px solid rgba(0,0,0,.05);<br />
color: #333331;<br />
display: block;<br />
font-size: 1.1rem;<br />
padding: 10px 0;<br />
text-decoration: none;<br />
transition: all 0.15s linear;<br />
}</p>
<p> nav.vertical > ul > li > div > ul > li:hover > a {<br />
background-color: lightBlue;<br />
color: rgb(255,255,255);<br />
padding: 10px 0 10px 50px;<br />
}<br />
[/css]

Making Changes

Depending on how you want the vertical menu to behave you may decide to make some changes.

First of all you may decide you want the different menus to be independent. That’s easy, change the input types from “radio” to “checkbox”.

Secondly, you could add different groupings of menus by adding multiple radio input names, that way you could have 2/3/4 groupings across 4/6/8 menus.

HTML 5 Content Menu

With the above code you may decide to create an in-content tab box where users can select different data. The changes required are very simple yet again.

Here’s what we can create with some minor tweaks –

See the Pen CSS 3 animated content box by lawnch (@lawnch) on CodePen.1507

Firstly we need to expand our wrapper width. This is done purely through CSS.

[css]<br />
div.wrapper {<br />
margin: 20px auto;<br />
width: 650px;<br />
}<br />
[/css]Next we want to set a default content area, so the box is “open” when users first see it. That’s done by adding checked=”true” to the radio button that controls the area you wish to display.

[html]<br />
<input type="radio" checked="true" name="verticalMenu" id="home" /><br />
[/html]Because the content is slightly different this time, we want to speed up the animation and alter the height of the viewable area.

[css]<br />
nav.vertical > ul > li > div {<br />
background-color: rgb(255,255,255);<br />
height: 0;<br />
overflow: scroll;<br />
transition: all .35s ease;<br />
}</p>
<p> nav.vertical > ul > li > label + input:checked + div {<br />
height: 200px;<br />
}<br />
[/css]Instead of animating the maximum height like before, we’re animating the actual height. If the content inside the container is too big then we’ve set it to scroll, making it look like a traditional HTML frame.

Styling the Scrollbar with CSS

Finally we can style the webkit scrollbar with CSS. That means it works in Chrome and Safari.

The code is as follows –

[css]<br />
nav.vertical ::-webkit-scrollbar {<br />
width: .9rem;<br />
}</p>
<p> nav.vertical ::-webkit-scrollbar-thumb {<br />
background-color: rgb(114, 51, 98);<br />
border: solid rgb(255,255,255);<br />
border-radius: 0 .4rem .4rem 0;<br />
border-width: .4rem .4rem .4rem 0;<br />
}<br />
[/css]Have a play around with the widths and colors to get the look and feel that you want.

Finally you can add whatever content you like into the containing elements.

Code

My final code is included below.

HTML

[html]</p>
<div class="wrapper">
<nav class="vertical">
<ul>
<li>
<label for="home">Home</label><br />
<input type="radio" checked="true" name="verticalMenu" id="home" /></p>
<div>
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Curabitur pretium magna ac nulla laoreet fringilla. Pellentesque pharetra elit feugiat erat ornare eleifend. Morbi lobortis risus quis semper consectetur. Vestibulum vulputate, lorem et tempor luctus, nisi tellus fermentum erat, ut imperdiet nunc justo ac odio. In ac sem erat. Suspendisse euismod faucibus dolor vel sodales. Donec sed placerat erat. Nulla facilisi. In in ipsum nunc. Maecenas at arcu nec justo lobortis vulputate quis a neque.</p>
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Curabitur pretium magna ac nulla laoreet fringilla. Pellentesque pharetra elit feugiat erat ornare eleifend. Morbi lobortis risus quis semper consectetur. Vestibulum vulputate, lorem et tempor luctus, nisi tellus fermentum erat, ut imperdiet nunc justo ac odio. In ac sem erat. Suspendisse euismod faucibus dolor vel sodales. Donec sed placerat erat. Nulla facilisi. In in ipsum nunc. Maecenas at arcu nec justo lobortis vulputate quis a neque.</p>
</div>
</li>
<li>
<label for="blog">Blog</label><br />
<input type="radio" name="verticalMenu" id="blog" /></p>
<div>
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Curabitur pretium magna ac nulla laoreet fringilla. Pellentesque pharetra elit feugiat erat ornare eleifend. Morbi lobortis risus quis semper consectetur. Vestibulum vulputate, lorem et tempor luctus, nisi tellus fermentum erat, ut imperdiet nunc justo ac odio. In ac sem erat. Suspendisse euismod faucibus dolor vel sodales. Donec sed placerat erat. Nulla facilisi. In in ipsum nunc. Maecenas at arcu nec justo lobortis vulputate quis a neque.</p>
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Curabitur pretium magna ac nulla laoreet fringilla. Pellentesque pharetra elit feugiat erat ornare eleifend. Morbi lobortis risus quis semper consectetur. Vestibulum vulputate, lorem et tempor luctus, nisi tellus fermentum erat, ut imperdiet nunc justo ac odio. In ac sem erat. Suspendisse euismod faucibus dolor vel sodales. Donec sed placerat erat. Nulla facilisi. In in ipsum nunc. Maecenas at arcu nec justo lobortis vulputate quis a neque.</p>
</div>
</li>
<li>
<label for="work">Work</label><br />
<input type="radio" name="verticalMenu" id="work" /></p>
<div>
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Curabitur pretium magna ac nulla laoreet fringilla. Pellentesque pharetra elit feugiat erat ornare eleifend. Morbi lobortis risus quis semper consectetur. Vestibulum vulputate, lorem et tempor luctus, nisi tellus fermentum erat, ut imperdiet nunc justo ac odio. In ac sem erat. Suspendisse euismod faucibus dolor vel sodales. Donec sed placerat erat. Nulla facilisi. In in ipsum nunc. Maecenas at arcu nec justo lobortis vulputate quis a neque.</p>
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Curabitur pretium magna ac nulla laoreet fringilla. Pellentesque pharetra elit feugiat erat ornare eleifend. Morbi lobortis risus quis semper consectetur. Vestibulum vulputate, lorem et tempor luctus, nisi tellus fermentum erat, ut imperdiet nunc justo ac odio. In ac sem erat. Suspendisse euismod faucibus dolor vel sodales. Donec sed placerat erat. Nulla facilisi. In in ipsum nunc. Maecenas at arcu nec justo lobortis vulputate quis a neque.</p>
</div>
</li>
</ul>
</nav>
</div>
<p>[/html]CSS

[css]<br />
* {<br />
margin: 0;<br />
padding: 0;<br />
outline: none;</p>
<p> -webkit-box-sizing: border-box;<br />
-moz-box-sizing: border-box;<br />
box-sizing: border-box;<br />
}</p>
<p>body {<br />
background: #eee;<br />
color: #444;<br />
-webkit-font-smoothing: antialiased;<br />
font-family: ‘Helvetica Neue’, sans-serif;<br />
font-size: 20px;<br />
font-weight: 400;<br />
height: auto !important;<br />
height: 100%;<br />
min-height: 100%;<br />
text-rendering: optimizeLegibility<br />
}</p>
<p>div.wrapper {<br />
margin: 20px auto;<br />
width: 650px;<br />
}</p>
<p>nav.vertical {<br />
border-radius: 4px;<br />
box-shadow: 0 0 10px rgba(0,0,0,.15);<br />
overflow: hidden;<br />
text-align: center;<br />
}</p>
<p> nav.vertical > ul {<br />
list-style-type: none;<br />
}</p>
<p> nav.vertical > ul > li {<br />
display: block;<br />
}</p>
<p> nav.vertical > ul > li > label,<br />
nav.vertical > ul > li > a {<br />
background-color: rgb(157, 34, 60);<br />
background-image: -webkit-linear-gradient(135deg, rgb(114, 51, 98), rgb(157, 34, 60));<br />
background-image: -moz-linear-gradient(135deg, rgb(114, 51, 98), rgb(157, 34, 60));<br />
background-image: -o-linear-gradient(135deg, rgb(114, 51, 98), rgb(157, 34, 60));<br />
background-image: linear-gradient(135deg, rgb(114, 51, 98), rgb(157, 34, 60));<br />
border-bottom: 1px solid rgba(255,255,255,.1);<br />
box-shadow: inset 0 1px 1px rgba(0,0,0,.1), 0 1px 1px rgba(0,0,0,.1);<br />
color: rgb(255,255,255);<br />
display: block;<br />
font-size: .85rem;<br />
font-weight: 500;<br />
height: 50px;<br />
letter-spacing: .5rem;<br />
line-height: 50px;<br />
text-shadow: 0 1px 1px rgba(0,0,0,.1);<br />
text-transform: uppercase;<br />
transition: all .1s ease;<br />
}</p>
<p> nav.vertical > ul > li > label:hover,<br />
nav.vertical > ul > li > a:hover {<br />
background-color: rgb(114, 51, 98);<br />
background-image: -webkit-linear-gradient(150deg, rgb(114, 51, 98), rgb(114, 51, 98));<br />
background-image: -moz-linear-gradient(150deg, rgb(114, 51, 98), rgb(114, 51, 98));<br />
background-image: -o-linear-gradient(150deg, rgb(114, 51, 98), rgb(114, 51, 98));<br />
background-image: linear-gradient(150deg, rgb(114, 51, 98), rgb(114, 51, 98));<br />
cursor: pointer;<br />
}</p>
<p> nav.vertical > ul > li > label + input {<br />
display: none;<br />
visability: hidden;<br />
}</p>
<p> nav.vertical > ul > li > div {<br />
background-color: rgb(255,255,255);<br />
height: 0;<br />
overflow: scroll;<br />
transition: all .35s ease;<br />
}</p>
<p> nav.vertical > ul > li > div > p {<br />
margin: 24px;<br />
text-align: left;<br />
}</p>
<p> nav.vertical ::-webkit-scrollbar {<br />
width: .9rem;<br />
}</p>
<p> nav.vertical ::-webkit-scrollbar-thumb {<br />
background-color: rgb(114, 51, 98);<br />
border: solid rgb(255,255,255);<br />
border-width: .4rem .4rem .4rem 0;<br />
border-radius: 0 .4rem .4rem 0;<br />
}</p>
<p> nav.vertical > ul > li > label + input:checked + div {<br />
height: 200px;<br />
}<br />
[/css]

Conclusion

Thanks for reading this tutorial. If you have any questions or want to show where you’ve used any of the examples, please post below.

Subscribe for Updates

Get notified about my latest content first and receive invitations for subscriber only competitions.

7 Comments

  • Hi It’s me again. I found the problem. The css code you’ve pasted in your above example has carried some additional formatting with it. You also posted an on-line code editor link. When I went there, it showed the css code without the extra carried formatting codes. This code can then be pasted directly into a text editor (I used Notepad++) and it works!

  • Julius Nepos says:

    Unfortunately I wasn’t able to get either of the vertical menus: the “simple html5 ” nor the “Animated mobile friendly ” code. The problem appears to be in the css but I’m wondering if other issues interefere with it. I’ll try a simple page with none other than your html, and then a link to the css.

  • Thomas Knudsen says:

    Hi, thanks for at great tutorial 🙂
    I’ve modified the code for private purposes, and i have a question.
    When i load the page, a menu point is already unfolded. How can i keep everything folded up, until i interact with the navigation.

    Kind regards
    Thomas

  • Desiree says:

    Thanks for another great tut!

  • David Luand says:

    Ha ha ah..! so thankx its work

Leave a Reply

This site uses Akismet to reduce spam. Learn how your comment data is processed.