3-step Form | Generate Username Dropdown

Form that hides and shows form sections (fieldsets) based on a click event. jQuery validation is also used and proceeding to the next step is not allowed until all required fields are valid. An editable username dropdown is generated with username options.

by Amy Ruddy

HTML

<!-- Bootstrap CSS -->
<link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/4.1.3/css/bootstrap.min.css" integrity="sha384-MCw98/SFnGE8fJT3GXwEOngsV7Zt27NXFoaoApmYm81iuXoPkFOJwJ8ERdknLPMO" crossorigin="anonymous">

<!-- Raleway Font CDN -->
<link href="https://fonts.googleapis.com/css?family=Raleway:400,700" rel="stylesheet">

<!-- Font Awesome CDN for using icons -->
<link rel="stylesheet" href="https://use.fontawesome.com/releases/v5.5.0/css/all.css" integrity="sha384-B4dIYHKNBt8Bc12p+WXckhzcICo0wtJAoU8YZTY5qE0Id1GSseTk6S+L3BlXeVIU" crossorigin="anonymous">
<script src="https://cdn.jsdelivr.net/npm/[email protected]/dist/jquery.validate.min.js"></script>

<div id='mainContent'>
  <div class='container py-5'>
    <h2 class='text-center text-white pb-2'><span class="fas fa-user-plus"></span> Sign Up</h2>
    <div class='mw-md mx-auto bg-white p-3 rounded'>
      <div id="mySteps" class="my-3">
        <ul class="list-unstyled multi-steps">
          <li class='is-active' id="step1"><span></span></li>
          <li id="step2"><span>Your Address</span></li>
          <li id="step3"><span></span></li>
        </ul>
      </div>
      <form id="signUpform" onsubmit='return false;'>
        <!-- Step 1 | First Name, Middle Name, Last Name -->
        <fieldset class='active_fieldset'>
          <div class="form-row">
            <div class="form-group col-sm-4">
              <label for="FirstName">First Name</label>
              <input type="text" class="form-control" id="fname" name="fname">
            </div>
            <div class="form-group col-sm-4">
              <label for="MiddleName">Middle Name</label>
              <input type="text" class="form-control" id="MiddleName">
            </div>
            <div class="form-group col-sm-4">
              <label for="LastName">Last Name</label>
              <input type="text" class="form-control" id="lname" name="lname">
            </div>
          </div>
          <div...

CSS

body {
  font-family: 'Raleway', sans-serif;
}

/* Hide all the steps initially */

fieldset:not(.active_fieldset) {
  display: none;
}

.previous {
  display: none;
}

#mainContent,
html {
  background-color: #095eb9;
}

.mw-md {
  max-width: 500px;
}

hr {
  border-top: 1px solid #095eb9 !important;
}

/* Buttons and text classes*/

.text-navy {
  color: #095eb9;
}

.btn-navy:not(:disabled):not(.disabled) {
  background-color: #095eb9;
  color: #fff;
}

.btn-navy:not(:disabled):not(.disabled):hover {
  opacity: 0.8;
}

.previous:not(:disabled):not(.disabled) {
  background-color: #cfd0d2;
  color: #777;
}

.previous:not(:disabled):not(.disabled):hover {
  opacity: 0.8;
}

/* Styling for the Steps */

#mySteps {
  position: relative;
  z-index: 1;
}

#mySteps span {
  color: #464646;
}

#mySteps .multi-steps>li.is-active:before,
#mySteps .multi-steps>li.is-active~li:before {
  content: counter(stepNum);
  font-family: inherit;
  font-weight: 700;
}

#mySteps .multi-steps>li.is-active:after,
#mySteps .multi-steps>li.is-active~li:after {
  background-color: #f4f4f4 !important;
}

#mySteps .multi-steps {
  display: table;
  table-layout: fixed;
  width: 100%;
}

#mySteps .multi-steps>li {
  counter-increment: stepNum;
  text-align: center;
  display: table-cell;
  position: relative;
  color: #095eb9;
  z-index: 9999;
}

#mySteps .multi-steps>li:before {
  content: '\f00c';
  content: '\2713';
  content: '\10003';
  content: '\10004';
  content: '\2713';
  display: block;
  margin: 0 auto 4px;
  background-color: #1ac635;
  width: 36px;
  height: 36px;
  line-height: 32px;
  text-align: center;
  font-weight: bold;
  border-width: 2px;
  border-style: solid;
  border-color: transparent;
  border-radius: 50%;
}

#mySteps .multi-steps>li:after {
  content: '';
  height: 2px;
  width: 100%;
  background-color: #1ac635;
  position: absolute;
  top: 16px;
  left: 50%;
  z-index: -1;
}

#mySteps .multi-steps>li:last-child:after {
  display: none;
}

#mySteps...

JavaScript

currentIndex = 0;

// steps
var activeStep, nextStep, prevStep;

//fieldsets
var activeFS, nextFS, prevFS;

// Do this when user hits the "next" button
$(".next").click(function() {
  validateForm();

  // propose username by combining first- and lastname
  if ($("#signUpform").valid() === true) {
    if ($('fieldset').is(':visible')) {
      // add is-active class to relevant step
      activeStep = $('#mySteps .is-active');
      nextStep = $('#mySteps .is-active').next('li');
      activeStep.removeClass();
      nextStep.addClass('is-active');

      // Hide/show relevant fieldset
      activeFS = $('fieldset:visible');
      nextFS = $('fieldset:visible').next('fieldset');
      activeFS.hide();
      nextFS.fadeIn('700, swing');

      // Hide/Show correct buttons
      currentIndex += 1;
      getCase();
    }
  }
});

// Do this when the user hits the "Previous" button
$(".previous").click(function() {
  validateForm();

  // add is-active class to relevant step
  activeStep = $('#mySteps .is-active');
  nextStep = $('#mySteps .is-active').prev('li');
  activeStep.removeClass();
  nextStep.addClass('is-active');

  // Hide/show relevant fieldset
  activeFS = $('fieldset:visible');
  nextFS = $('fieldset:visible').prev('fieldset');
  activeFS.hide();
  nextFS.fadeIn('700, swing');

  // Hide/Show correct buttons
  currentIndex -= 1;
  getCase();
});

// Show and hide the relevent buttons
function getCase() {
  switch (currentIndex) {
    case 0:
      $('.previous').hide();
      $('#submit').hide();
      break;
    case 1:
      $('.previous').show();
      $('#submit').hide();
      $('.next').show();

      break;
    case 2:
      $('.previous').show();
      $('.next').hide();
      $('#submit').show();
  }
}

function validateForm() {
  // validate signup form 
  $("#signUpform").validate({
    rules: {
      // fieldset 1
      fname: "required",
      lname: "required",
      phone: {
        required: true,
        minlength: 9
      },
     ...