How To Create A Keypress Navigation Using jQuery

Tutorial Details
  • Difficulty: Beginner
  • Completion Time: 15 Minutes

The key to a succesful website is the ease with which a user finds what they are looking for. Thus, it’s worth spending a lot of time and effort in creating both useful and visually appealing navigation systems. Lately, I have began experimenting with new ways to navigate a website. In this tutorial I’ll show you how to let the user make use of their keyboard to get around your site.

Step 1

The first thing we need to do is create our test page. In this case, I will refer to it as demo.html and it will contain the following:

  1. A link to the jQuery framework.
  2. A link to the script we will work on later. Let’s call it keypress_nav.js
  3. A link to a CSS file called style.css (we will also work on this later).
  4. A header div that will contain our navigation among other things. And
  5. Five unique div elements that will serve as pages for our site.

So, here is what demo.html looks like at this point:

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" 
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html>
	<head>
		<title>KeyPress Navigation Demo</title>
		<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
		<link rel="stylesheet" type="text/css" href="style.css" />
		<script type="text/javascript" src="jquery.js"></script>
		<script type="text/javascript" src="keypress_nav.js"></script>
	</head>
	<body>
		<div id="header">
			<!-- Our navigation will go here -->
		</div>
		<div id="home">
			<h2>Welcome!</h2>
			<p>Some Text</p>
		</div>
		<div id="about">
			<h2>About Me</h2>
			<p>Some Text</p></p>
		</div>
		<div id="contact">
			<h2>No Spam Please</h2>
			<p>Some Text</p>
		</div>
		<div id="awards">
			<h2>Awards, So Many ...</h2>
			<p>Some Text</p>
		</div>
		<div id="links">
			<h2>Cool Sites</h2>
			<p>Some Text</p>
		</div>
	</body>
</html>

Step 2

Now that we have our DIVs in place, we can go ahead and create the navigation for the page. As you may have guessed, we will be using an unordered list <ul> to hold the links and the DIV’s IDs as the targets for these links. Also, we will add the class container to all the DIV “pages.” This class will help us easily refer to these DIVs when we create our script. So, here is what you should have now:

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" 
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html>
	<head>
		<title>KeyPress Navigation Demo</title>
		<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
		<link rel="stylesheet" type="text/css" href="style.css" />
		<script type="text/javascript" src="jquery.js"></script>
		<script type="text/javascript" src="keypress_nav.js"></script>
	</head>
	<body>
		<div id="header">
			<ul id="navigation">
				<li><a href="#home">Home ( a )</a></li>
				<li><a href="#about">About ( s )</a></li>
				<li><a href="#contact">Contact ( d )</a></li>
				<li><a href="#awards">Awards ( f )</a></li>
				<li><a href="#links">Links ( g )</a></li>
			</ul>
		</div>
		<div id="home" class="container">
			<h2>Welcome!</h2>
			<p>Some Text</p>
		</div>
		<div id="about" class="container">
			<h2>About Me</h2>
			<p>Some Text</p></p>
		</div>
		<div id="contact" class="container">
			<h2>No Spam Please</h2>
			<p>Some Text</p>
		</div>
		<div id="awards" class="container">
			<h2>Awards, So Many ...</h2>
			<p>Some Text</p>
		</div>
		<div id="links" class="container">
			<h2>Cool Sites</h2>
			<p>Some Text</p>
		</div>
	</body>
</html>

Note: The letter (key) inside the parenthesis is the key we will later use as navigation for our page.

Step 3

The structure of our test page is now complete but lacking visual appeal. So, let’s add some CSS and jazz it up. One thing to keep in mind before we begin the styling is that our page must look good even if JavaScript is turned off. Scripts, in my opinion, should always be used as a bonus to those users who have JavaScript turned on but should not alienate those who don’t. We are web designers/developers after all, and we care about usability, right?

You can see the look we’re going for in the screenshot above. It’s simple and uses some nice, bold colours to highlight the different sections. So here’s our CSS:

body 
{
	margin: 0;
	padding: 0;
	font-family: "Lucida Grande", "Lucida Sans", sans-serif;
	font-size: 100%;
	background: #333;
}
/* Header
-------------------------------------------------- */

#header
{
	width: 460px;
	margin: 0 auto;
	font-size: .75em;
	font-family: "Helvetica Neue", Helvetica, sans-serif;
}

#header ul 
{
	list-style: none;
	margin: 0;
	padding: 0;
}

#header ul li 
{
	float: left;
	text-align: left;
}

#header ul li a
{
	display: block;
	color: #ffff66;
	text-decoration: none;
	text-transform: uppercase;
	margin-right: 20px;
}

#header ul li a:hover
{
	text-decoration: underline;
	color: #ffcc66;
}
/* Containers
-------------------------------------------------- */

.container
{
	width: 400px;
	height: 300px;
	margin: 30px auto;
	padding: 10px 20px;
	border: 10px solid #fff;
	color: #fff;
	font-size: .75em;
	line-height: 2em;
}

.container h2
{
	padding: 5px 10px;
	width: 200px;
}

#home		{ background: #15add1; }
#home h2	{ background: #007aa5; }
#about		{ background: #fdc700; }
#about h2	{ background: #bd9200; }
#contact	{ background: #f80083; }
#contact h2	{ background: #af005e; }
#awards		{ background: #f18300; }
#awards	h2	{ background: #bb5f00; }
#links		{ background: #98c313; }
#links h2	{ background: #6f9a00; }
/* Self-Clearing Rules 
-------------------------------------------------- */

ul#navigation:after 
{
    content: ".";
    display: block;
    visibility: hidden;
    clear: both;
    height: 0;
}

* html ul#navigation 	{ height: 1px; }
ul#navigation 			{ min-height: 1px; }

Note: I have added some self-clearing rules to the navigation in order to work around its lack of height due to its inner floated elements. In other words, margin rules from the upper most container will now have the proper effect on the navigation <ul>.

Step 5

At this point in the tutorial you should have a page looking something like this:

Test Page Preview

It is a functional page and it works properly without the need for JavaScript to be turned on. However, as I said before, let’s give a little bonus to those users who do have JavaScript turned on on their browsers. We will do this in two steps. Firstly, we will create two functions that will hide and display the pages appropiately. And secondy, we will add some some code to determine the keys pressed by the user. Let’s now create a file called keypress_nav.js and get to work on our functions.

Step 6

We are going to need two functions for our script to work as desired. One of the functions will be called when the user presses one of our predetermined navigation keys (The letters in parenthesis from Step 2) and will hide all other containers displaying only the DIV associated to this key. This is what our first function looks like:

function showViaKeypress(element_id)
{
	$(".container").css("display","none");
	$(element_id).slideDown("slow");
}

Now, our second function will take an array of links and assign them on click target functions. In other words the function will get our navigation links, retrieve the “href” attribute and display the appropiate DIV upon clicking it. So, here is what the second function looks like:

function showViaLink(array)
{
	array.each(function(i)
	{	
		$(this).click(function()
		{
			var target = $(this).attr("href");
			$(".container").css("display","none");
			$(target).slideDown("slow");
		});
	});
}

Step 7

Now that we have our functions coded, we need to call them appropiately when the page loads. The first thing we need to do is hide all the elements that have class container with the exception of the DIV that has the ID home. Next, we need to call the showViaLink() function with the links inside of our navigation <ul> as its parameter. Last but not least, we have to listen for the user keypress and call the showViaPress() function with the appropiate ID as its parameter. This can be accomplished by using a switch on the key pressed.

The switch will have 5 cases (one for every link) and its number corresponds to the ASCII number for the keypress. For example, if the “a” key is pressed, switch will use case 97. So, here is what the code looks like:

$(document).ready(function()
{
	// hides all DIVs with the CLASS container
	// and displays the one with the ID 'home' only
	$(".container").css("display","none");
	$("#home").css("display","block");
	
	// makes the navigation work after all containers have bee hidden 
	showViaLink($("ul#navigation li a"));
	
	// listens for any navigation keypress activity
	$(document).keypress(function(e)
	{
		switch(e.which)
		{
			// user presses the "a"
			case 97:	showViaKeypress("#home");
						break;	
						
			// user presses the "s" key
			case 115:	showViaKeypress("#about");
						break;
						
			// user presses the "d" key
			case 100:	showViaKeypress("#contact");
						break;
						
			// user presses the "f" key
			case 102:	showViaKeypress("#awards");
						break;
						
			// user presses the "g" key 
			case 103:	showViaKeypress("#links");
		}
	});
});

Step 8

Now that we have all the pieces of the puzzle, we can put it together. Here is what the final iteration of our script should look like:

$(document).ready(function()
{
	// hides all DIVs with the CLASS container
	// and displays the one with the ID 'home' only
	$(".container").css("display","none");
	$("#home").css("display","block");
	
	// makes the navigation work after all containers have bee hidden 
	showViaLink($("ul#navigation li a"));
	
	// listens for any navigation keypress activity
	$(document).keypress(function(e)
	{
		switch(e.which)
		{
			// user presses the "a"
			case 97:	showViaKeypress("#home");
						break;	
						
			// user presses the "s" key
			case 115:	showViaKeypress("#about");
						break;
						
			// user presses the "d" key
			case 100:	showViaKeypress("#contact");
						break;
						
			// user presses the "f" key
			case 102:	showViaKeypress("#awards");
						break;
						
			// user presses the "g" key 
			case 103:	showViaKeypress("#links");
		}
	});
});

// shows a given element and hides all others
function showViaKeypress(element_id)
{
	$(".container").css("display","none");
	$(element_id).slideDown("slow");
}

// shows proper DIV depending on link 'href'
function showViaLink(array)
{
	array.each(function(i)
	{	
		$(this).click(function()
		{
			var target = $(this).attr("href");
			$(".container").css("display","none");
			$(target).slideDown("slow");
		});
	});
}

Demo

Take a look at the script in action on this demo page.
The pattern used in this demo was made by Taylor Satula.

Tags: jQuery
Note: Want to add some source code? Type <pre><code> before it and </code></pre> after it. Find out more
  • http://www.anotherblog.co.uk/ Andrew Pryde

    Very nice idea but I cant think of many websites if any that utilize this.

    Andrew Pryde

    • http://www.omikrosys.com Puneet

      Gmail utilizes a lot of keyboard shortcuts. For example, to navigate emails in the inbox.

  • James

    “Very nice idea but I cant think of many websites if any that utilize this. ”

    ??? I thought that would make it better and more impressive….

    My only reservation is that outside the hardcore geek community used to working at the CLI, I don’t know many people who are that concerned about keeping their hands off the mouse.

    But a good idea well implemented. Thank you.

  • s0sed

    Great tut! Thnx a lot. Best wishes from Russia/.

  • http://monument70.no Tor Løvskogen

    Andrew, first – why include your name and URL? It’s already in your comment. Shameless. Anyway, I think keypress navigation will get more popular as the distinction between desktop and web applications vanishes.

  • Mitch

    Cool tutorial, I like it if I will use the mouse only.

    When it comes to navigation online, most of users prefer to use mice and no keyboards. Keyboards only for filling forms and we usually (developers) try to minimize that by making forms short and easy.

  • http://www.showpage.it freddie

    Thanks for this post and this site!

  • Daniel

    very useful and nice technique. thanks a lot Bedrich!

  • http://www.ben-griffiths.com Ben Griffiths

    Good tutorial, thanks :)

  • Mark Bowen

    Nice tutorial,

    Perhaps you should also add in accesskey support too?

    Best wishes,

    Mark

  • k.en

    Great tutorial! Very useful.
    I also like the sliding on this one.
    Thanks Bedrich! Your tutorials are the best!

  • http://www.giackop.com giackop

    Cool tut.. thanx

  • http://www.joecritchley.com/ Joe Critchley

    Very smooth. One thing though, if you press one link and then another one before the other has finished loading, they will both appear on the screen at the same time. (Mac OS X – Firefox RC1).

    If you can solve this, it will be interesting to see how you’ve done it, because I have a jQuery technique that is suffering from a similar issue. Is there an “animating” event or something?

  • Johan Munk

    Hey there, i like the tutorial, although i might not getting around to using it.
    Anyway, i ran into a problem. The script won’t work in ff if you’ve got quick find turned on (searching for text, as i type), while it will change pages on the first click, but not on the second and so forth.

  • http://www.swaymedia.com Ali

    very nice tutorial, the frequency of publication is increasing, very nice

  • http://www.freshclickmedia.com Shane

    Good to see another tutorial on jQuery – one of my favourite things at the moment.

    Whilst it’s all very interesting, practically speaking I can’t say it’s something that I can see myself using, but thanks for posting nonetheless.

  • http://inretro.com Niels

    Great tutorial, thanks. I’ve been looking for this quite some time.

    Is there a possibility to add in support for the browser’s back button? When a user presses ‘Back’, the previous div is being loaded… Such an addition would rock!

  • http://desert-lion.blogspot.com Rijalul Fikri

    wow, nice effect. When I saw this, I remember the way gmail works ^^

  • Peter

    Great tutorial and effect, but I’m afraid the behaviour of the browsers back-button will confuse many normal surfers.
    Anyway, nice!

  • Peter

    Great tutorial and effect, but I’m afraid the behaviour of the browsers back-button will confuse many normal surfers. Anyway, nice!

  • http://mcarthurgfx.com/ Sean

    You mean you guys don’t know the benefit of keyboard shortcuts? Any developer loves shortcuts. Pressing a key for an action is much faster and more efficient than clicking things with the mouse. I know I love learning shortcuts in all the programs I use.

  • http://gabediaz.com gdiaz

    Pretty cool, to use within a section of your site. You might want to check it, as it does break and displays 2 elements if you toggle quick enough with the mouse. Best way to test something is to try and break it, and it seems that this technique breaks when using the mouse(displays your last 2 choices). When using only the keys it will display only the last key you pressed but if you toggle quick enough you can see the all the pressed elements for a small moment.

  • J.C.

    It would be nice to have a link at the TOP of the tutorial so that we can have a better idea of what it’s all about.

  • http://pickysurfer.com Danny

    Hey this could be an awesome new concept in online surfing… who knows huh. Great article!

  • http://davidcarreira.com D. Carreira

    Great idea!

    This is a great tutorial! Thanks.

    David Carreira

  • http://im.mindtripping.net Andrei Constantin

    hmm, not half bad

  • http://www.joelwsmith.com Joel Smith

    Great idea, but won’t work if a user has “Search when I start typing” enabled on a browser (ie. Firefox 3). I agree with Mitch that most users (non-developers, which makes up about 99.9% of users) don’t use shortcuts when browsing.

    Good looking, none the less.

  • http://laminbarrow.com Lamin Barrow

    I have been using this concept to make a link appear appear as the default button in a form for a while now. Thanks for posting this here and am sure a lot of my fellow web developers will learn from this. :)

  • InLikeALion

    I second the idea that all nettuts.com posts should have a demo link at the top. That’s just better user experience, and common sense. I hate having to scroll to the bottom to find out what I’m going to be reading about.

    Other than that nitpick, I’m glad you guys have been showcasing some simple jQuery stuff in easy to understand tutorials. I’ve been reading nettuts for only a few weeks now, but have been really impressed with the write-ups, subjects, and frequency of interesting information. Thanks a lot!

  • http://www.crysfel.com stock

    Well, nice article, but you’re missing something, when the user press the same key over and over again….

  • http://www.bootstrappingblog.com Mike Smith – Bootstrapping Blog

    Nice tutorial. Even without the key shortcuts, the effect is something I’m going to be using on a new site. thanks for keeping this site with fresh content that is actually worth something :)

  • Mike

    Thanks for the clarity of execution in your tut.

    One thing: I wish the links changed state to show where you are in the navigation. When they stay perpetually normal (even when active) I think it’s easy for a user to get lost.

    What’s the easiest way to remedy that, if indeed one wanted to?

    Thanks!!

  • http://webshopinabox.peter-tashjian.com/WebShopInABox.htm Peter T – Webshop

    I had seen this on a website a while back but forgot all about it. This is a great sample and there are huge positive implications in using this…I gotta run but might come back and write more…thanks.

  • http://talkingtofu2.iblogger.org Taylor Satula

    Hey Thats My Background Pattern Why Did I Get No Credit!!!!!
    Somebody ANSWER WHY!!!

  • http://bedrichrios.com Bedrich Rios
    Author

    @Taylor

    Sorry for giving you no credit for the pattern. I will do so right now. A friend of mine gave me a set of patterns not so long ago and I thought they were all royalty free, obviously I was wrong. Sorry.

  • http://talkingtofu2.iblogger.org Taylor Satula

    Links being posted no prob

  • http://flickr.com/photos/parapet Nima

    Cute but doesn’t work on FireFox!

  • http://flickr.com/photos/parapet Nima

    I mean the keypress part

  • http://flickr.com/photos/parapet Nima

    Oops I was wrong! if u want u can delete my other comments!
    Its workin on FF too! but I think there is a bug when u click on second link just after 1st one… it shows both of them!

  • http://im.mindtripping.net Andrei Constantin

    Of course it’s running on Firefox, even better than on any other browser

  • http://www.freshclickmedia.com Shane

    Just a small thing here – but it’s Firefox.

    It doesn’t have a capital F in the middle. :)

  • http://ooyes.net seo

    Thanks for the information.

  • http://totalabyss.com totalabyss

    nice tutorial, this breaks though when using the mouse. when clicking instead of using the keys you will be able to see the last 2 elements that were clicked on.

  • Bill

    Very nice. I can see this coming in very handy for some apps I do that require some heavy data entry.

  • http://roshanbh.com.np/ Roshan Bhattarai

    If you click the links very fast the other’s div doesn’t gets hidden in firefox…please fix this..

  • http://www.designXmachina.com Christian Mejia

    Very useful tutorial. Thank you

  • http://www.mcarthurgfx.com Sean

    Firefox renders almost everything correctly. I’m in love with Firefox, but it burns me when I code a site, I’m like “Sweet, all done, looks rad and everything. Oh hey, let’s not forget to check IE.”

    Starts IE. Loads web-site.

    “^!@%$^%!@$.”

  • http://www.goldenthunder.com Nico

    Very nice. This will be nice if I get a client that needs a hyper-super-accessible site!

  • http://www.bevosports.com/ Brian

    If you’ve got “find as you type” turned on in Firefox (which everyone should) it breaks on the second attempt. The first keypress works but the second doesn’t as FF tries to do a find rather than registering the keypress. Not really a fault of the code but more of a limitation of keypress navigation.

  • http://www.pliggs.com Geoserv

    Very nice tutorial, I love jquery, but find it hard to use at times.

  • http://inspirationup.com Joefrey Mahusay

    Really nice. Thanks