Skip to content

ENGINEERING LEADER

WordPress Developer

Speaker

Unapologetic Punk

Mitch Canter

  • Threads
  • Instagram
  • Bluesky
  • LinkedIn
  • GitHub
  • YouTube
Development, WordPress

A Responsive Menu Solution for WordPress

Mitch Canter

Reading time: 3 minutes

Edited 01/14/14 to work with WordPress 3.8

A few months ago I modified a really cool WordPress template and started using it for my own clients.  As part of the overhaul, I realized that there was no really good way (included) to turn a WordPress unordered list into a menu that would work on a mobile device.  I tried a few different solutions, but in the end went for the simple one.  A selection (drop-down) menu works well, allows for an infinite number of parent and child categories, and is easily done with a simple jQuery script.

I’ve since modified that script, and wanted to share it as a snippit with you.  Make sure you have jQuery loaded somewhere before this script:

<script>
// Create the dropdown base
jQuery(".menu-main-container li a").addClass("top-level");
jQuery(".menu-main-container .sub-menu li a").addClass("second-level");
jQuery("<select class='main-drop' />").appendTo(".menu-main-container");

// Create default option "Go to..."
jQuery("<option />", {
"selected": "selected",
"value" : "",
"text" : "Main Navigation"
}).appendTo(".menu-main-container select");

// Populate dropdown with menu items
jQuery(".menu-main-container li a").each(function() {
var el = jQuery(this);
jQuery("<option />", {
"value" : el.attr("href"),
"text" : el.text(),
"class" : el.attr("class")
}).appendTo(".menu-main-container select");
});

// Allows user to automatically "submit" selection and travel to page
jQuery(".menu-main-container select").change(function() {
window.location = jQuery(this).find("option:selected").val();
});

// adds a dash to second-level classes
jQuery('<p>- </p>').prependTo('option.second-level');

</script>

There’s one bit of code you need to include in your stylesheet (or responsive stylesheet):

.main-drop{
display: none;
}

/* All Mobile Sizes (devices and browser) */
@media only screen and (max-width: 767px) {

.main-drop{
display: block;
width: 94%;
margin: 10px 3% 10px;
}

}

This should work on most themes with a dynamic menu system.  There’s a bit of margin included with the drop downs, but you can adjust as needed.

So, what’s actually going on?

// Create the dropdown base
jQuery(".menu-main-container li a").addClass("top-level");
jQuery(".menu-main-container .sub-menu li a").addClass("second-level");
jQuery("<select class='main-drop' />").appendTo(".menu-main-container");

This code is adding classes to the links of the menu.  Typically, only the list items have a class attached to them, and this will allow us to differentiate between top level and second level navigation.  It also creates the base for the drop-downs (a “select” input) that we’ll soon populate with links.

// Create default option "Go to..."
jQuery("<option />", {
"selected": "selected",
"value" : "",
"text" : "Main Navigation"
}).appendTo(".menu-main-container select");

This creates a default option.  You can change the “text” value to whatever you want.  It becomes the default option.

// Populate dropdown with menu items
jQuery(".menu-main-container li a").each(function() {
var el = jQuery(this);
jQuery("<option />", {
"value" : el.attr("href"),
"text" : el.text(),
"class" : el.attr("class")
}).appendTo(".menu-main-container select");
});

This code searches each list item in the menu container and creates an option in the select box for each.  It pulls the link (href), the text, and the class we assigned earlier.

// Allows user to automatically "submit" selection and travel to page
jQuery(".menu-main-container select").change(function() {
window.location = jQuery(this).find("option:selected").val();
});

// adds a dash to second-level classes
jQuery('<p>- </p>').prependTo('option.second-level');

Since there’s no form element, selecting the drop-down options by themselves would do nothing.  This causes the browser to automatically go to whichever link in the drop-down is selected.  The second bit adds a dash to all second level classes – that will allow you to have a differentiates multi-level navigation.

This snippit has proven useful time and time again, and even though it’s built for WordPress, it can be adapted to any content management system that uses some sort of a semantic menu structure.

jQuery, menu, responsive design
  • A Field Guide to Speculative Loading in WordPress

    A Field Guide to Speculative Loading in WordPress

    Reading time: 3 minutes

    Here’s a fun one: your WordPress site might already be reading your mind a little. Not in a creepy way – well, maybe a little in a creepy way – but in a “hey, I bet you’re about to click that” kind of way. If you’re running WordPress 6.8 or later, there’s a decent chance…

    WordPress
  • State of the Word 2023 Recap

    State of the Word 2023 Recap

    Reading time: 2 minutes

    The WordPress community was abuzz with excitement as Matt Mullenweg, WordPress’ illustrious co-founder, took to the international stage to deliver the first non-North-American “State of the Word”, live from Spain. While there was some retrospection, the theme of the event was definitively looking forward as Matt (and Matias ventura, WordPress’ lead architect) teased new features…

    WordPress
  • Home
  • About
  • Speaking
  • Articles
  • Contact