How to Code a Sliding Registration Form Panel with jQuery

There are many different user interface techniques for building a login/signup layout. One of my favorite approaches is to include both the forms on a single page and offer some navigation between the two. A large dropdown or popup modal window could work, and sliding panels are another example.

In this tutorial I want to demonstrate how we can build two sliding forms which rotate into a single page using jQuery. The effect doesn't require very much code, and it's mostly repetitive in nature. This should also work on smartphones and other mobile browsers with JavaScript enabled. The direct improvement to user experience is phenomenal and definitely worth considering to implement in your own website.

Live Demo - Download Source Code

Let's get started by creating a single HTML page named index.html. I'm going to build on a simple HTML5 template which I use in most of my projects. I've copied this code over below:

<meta content="text/html; charset=utf-8">
<meta content="Jake Rocheleau">
<link rel="shortcut icon" href="">
<link rel="icon" href="">
<link rel="stylesheet" href="styles.css">
<link rel="stylesheet" href=",400italic">

In the header you may notice I've included references to a couple local files. First is a stylesheet styles.css which will hold all our page designs. And then I am also referencing an external Google Web Fonts stylesheet for some custom page text. Aside from the HTML5shiv and jQuery libraries, the only other reference is to a script named formslider.js.

I will go into all our jQuery code which is stored within this file later on in greater detail. For now let's take a look over what needs to go inside the webpage body and how we should style these items using CSS.

HTML Body Elements

So the ultimate goal is to place two forms inside a single wrapper container. The first is a login form and that is displayed right when the page loads. Then we will click a link and the registration form should slide in from the right side as the login form is pushed out of view to the left.

<div id="w">
<h1>jQuery Sliding Login/Registration Form</h1>
<div id="page">
<div id="content-login">
<h2>Login to the Site</h2>
<div class="content"><a id="showregister" class="slidelink" href="#">Don't Have An Account? →</a><form id="login" action="#" method="post" name="login"><label for="email">Email Address</label> <input id="email" class="txtfield" tabindex="1" autocomplete="off" name="email" type="email"> <label for="password">Password</label> <input id="password" class="txtfield" tabindex="2" autocomplete="off" name="password" type="password"> <input id="loginbtn" class="btn" tabindex="3" name="loginbtn" type="submit" value="Login"></form></div>
<!-- /end #content-login -->
<div id="content-register">
<h2>Register a New Account</h2>
<div class="content"><a id="showlogin" class="leftsidelink" href="#">← Already Have an Account? Login Now!</a><form id="register" action="#" method="post" name="register"><label for="fname">First Name</label> <input id="fname" class="txtfield" tabindex="4" autocomplete="off" name="fname" type="text"> <label for="lname">Last Name</label> <input id="lname" class="txtfield" tabindex="5" autocomplete="off" name="lname" type="text"> <label for="newemail">Email Address</label> <input id="newemail" class="txtfield" tabindex="6" autocomplete="off" name="newemail" type="email"> <label for="password1">Password</label> <input id="password1" class="txtfield" tabindex="7" autocomplete="off" name="password1" type="password"> <label for="password2">Confirm Password</label> <input id="password2" class="txtfield" tabindex="8" autocomplete="off" name="password2" type="password"> <input id="registerbtn" class="btn" tabindex="9" name="registerbtn" type="submit" value="Sign Up"></form></div>
<!-- /end #content-register --></div>
<!-- /end #page --></div>

The whole wrapper container is centered on the page with an internal #page div. Inside I've split both the forms into #content-login and #content-register. What I'm going to do is give the outer page container a position: relative; and then put the two inner content wrappers with absolute positions.

First we want the login form to be in the top left corner and displaying immediately when the page loads. The registration div will be out of view by the exact width of the page wrapper (880px). Here are the CSS code styles I'm using:

/* page structure */
#w { width: 880px; margin: 0 auto; padding-top: 25px; }

#page { 
  display: block;
  position: relative;
  overflow: hidden;
  height: auto;
  background: #fff; 
  box-sizing: border-box;
  -webkit-box-shadow: 0 0 12px 0 rgba(150, 180, 210, .9);
  -moz-box-shadow: 0 0 12px 0 rgba(150, 180, 210, .9);
  box-shadow: 0 0 12px 0 rgba(150, 180, 210, .9);
.content {
  box-sizing: border-box;
  width: 600px;
  margin: 0 auto;
  padding-bottom: 30px;
  padding: 5px 15px;
  padding-top: 25px;

/* inner page layouts */
#content-login { display: block; position: relative; width: 100%; }

#content-register { display: none; width: 100%; position: absolute; top: 0; left: 880px; }

The current plan is to work with jQuery's .animate() method to update these values and animate them over a couple seconds. Using absolute positioning means we don't need to mess with floats or having content overflow the original wrapper.

html, body, div, span, applet, object, iframe, h1, h2, h3, h4, h5, h6, p, blockquote, pre, a, abbr, acronym, address, big, cite, code, del, dfn, em, img, ins, kbd, q, s, samp, small, strike, strong, sub, sup, tt, var, b, u, i, center, dl, dt, dd, ol, ul, li, fieldset, form, label, legend, table, caption, tbody, tfoot, thead, tr, th, td, article, aside, canvas, details, embed, figure, figcaption, footer, header, hgroup, menu, nav, output, ruby, section, summary, time, mark, audio, video {
  margin: 0;
  padding: 0;
  border: 0;
  font-size: 100%;
  font: inherit;
  vertical-align: baseline;
  outline: none;
html { height: 101%; }
body { background: #e8eff7; font-size: 62.5%; line-height: 1; padding-bottom: 55px; font-family: Arial, Geneva, sans-serif; }

article, aside, details, figcaption, figure, footer, header, hgroup, menu, nav, section { display: block; }
ol, ul { list-style: none; }

blockquote, q { quotes: none; }
blockquote:before, blockquote:after, q:before, q:after { content: ''; content: none; }
strong { font-weight: bold; } 

a { text-decoration: none; color: #4983bd; }
a:hover { text-decoration: underline; }

table { border-collapse: collapse; border-spacing: 0; }
img { border: 0; max-width: 100%; }
input { outline: none; }

Also just one more thing to note are the CSS resets I'm using in my document. I have added a couple extra properties to build my own custom template off Eric Meyer's CSS resets. This is a very quick way for the browser to render default conditions with all modern brands including Firefox, IE9, Chrome, Opera, and Safari. Grab the codes above if you're interested to try them out in a webpage.

Dynamic JQuery Animations

And now to build the final effects of our animated forms. We should first create the new file formslider.js and setup a typical $(document).ready() clause. This will keep all the JavaScript code inactive until the DOM finishes rendering.

  $("form").submit(function(e) {

  var clogin = $("#content-login");
  var cregister = $("#content-register");


The first block of code inside our function is checking against any form which is submitted on the page. For my demo example we do not have any backend script to load so I've set the action attribute to a hash(#) for no defined value.

But instead of loading that hash symbol into the URL we can stop the form action altogether. Understand that if you want to have your form submit properly you will need to remove all 3 lines of code related to the e.preventDefault() method. It's a great solution for my demo example but will not work if you need the forms to actually function correctly!

The other two variables are merely quick references to the login and registration form container divs. This keeps the code shorter since we can use jQuery variable selectors and save a lot of space typing.

Building the On/Off Functions

Now the rest of our jQuery code will be centered around these two animations. The first function will call whenever the user clicks our registration link with the ID #showregister.

/* display the register page */
$("#showregister").on("click", function(e){
  var newheight = cregister.height();
  $(cregister).css("display", "block");

    "left": "-880px"
  }, 800, function(){ /* callback */ });

    "left": "0px"
  }, 800, function(){ $(clogin).css("display", "none"); });

    "height": newheight+"px"
  }, 550, function(){ /* callback */ });

Once the user clicks on this link we pass that click event into a new function and yet again call e.preventDefault(); to stop the href value from loading. This line of code you can leave in the script since your anchor links shouldn't load a new page anyways - but as a fallback method you can setup the href value to load a new registration page. Then users without JavaScript enabled will be redirected to the signup form either way.

Another problem not yet addressed is the container height. Obviously the registration form will be much longer in height than the login form. We need the page container to adjust for this as the animation is moving into view.

The first two animations move the login div out -880px to the left and positions the registration form at the top left of our container. Also in the callback method after the registration panel finishes sliding, we change the login div to display: none;. Now the 3rd animation is the page height which actually animates a bit quicker at 550 milliseconds.

If you're familiar with everything being done in this single function then you definitely have a solid grasp on the JS code! In order to achieve the login form sliding back into place we can use very similar code with some numbers and variables switched. This time we are targeting the link #showlogin which only appears once the registration page is in view.

/* display the login page */
$("#showlogin").on("click", function(e){
  var newheight = clogin.height();
  $(clogin).css("display", "block");

    "left": "0px"
  }, 800, function() { /* callback */ });
    "left": "880px"
  }, 800, function() { $(cregister).css("display", "none"); });

    "height": newheight+"px"
  }, 550, function(){ /* callback */ });

Live Demo - Download Source Code

Wrapping Up

I hope this tutorial can offer some design insight towards building user registration pages. With the modern advancements of web development HTML5/CSS3 can be a huge time saver. And the jQuery library is also an amazing resource if you can learn the basics.

Be sure to check out my live demo example to see this script in action. You can also download a copy of my source code and work with something similar on your own website. If you have any further suggestions or questions on the tutorial feel free to share with us in the post discussion area.

Jake Rocheleau

First it was design, then writing, and now affiliate marketing. Over a period of 6-7 years he wrote a lot of content for many websites. You can reach Jake on Twitter.

Get more to your email

Subscribe to our newsletter and access exclusive content and offers available only to MonsterPost subscribers.

From was successfully send!
Server error. Please, try again later.

Leave a Reply