JQuery Validation and Bootstrap 3 for same form-group - error and success classes for each field

11,174

Both of your inputs are placed inside separate <div class="col-sm-4"> elements. So you can just replace these lines :

$(element).closest('.form-group').removeClass('has-success').addClass('has-error');
// ...
$(element).closest('.form-group').removeClass('has-error').addClass('has-success');

with these:

$(element).parent().removeClass('has-success').addClass('has-error');
// ...
$(element).parent().removeClass('has-error').addClass('has-success');

.. or these (the same as above but class related):

$(element).closest('.col-sm-4').removeClass('has-success').addClass('has-error');
// ...
$(element).closest('.col-sm-4').removeClass('has-error').addClass('has-success');

Fiddle


Alternatively, if you can't affect classes on input parents for some reason, or you can't base on parent element (f.ex. your project is under development, or gets frequent updates), you can make sure that error/success class is applied properly to the fields using .wrap(). Your fields gets wrapped into dynamically created <span> element with proper (error/success) class:

highlight: function(element) {
    $(element).parent().is('.has-success, .has-error') ? 
        $(element).parent().removeClass('has-success').addClass('has-error') : 
        $(element).wrap('<span class="has-error"></span>');
},
unhighlight: function(element) {
    $(element).parent().is('.has-success, .has-error') ? 
        $(element).parent().removeClass('has-error').addClass('has-success') : 
        $(element).wrap('<span class="has-success"></span>');
}

Fiddle

Share:
11,174
gamehendgeVA
Author by

gamehendgeVA

Updated on June 05, 2022

Comments

  • gamehendgeVA
    gamehendgeVA almost 2 years

    I have a Bootstrap 3 form where I have 2 fields side-by-side (e.g., First Name and Last Name), and in order to achieve this with BS3, I am putting both fields in the same form-group div, which works great.

    However, with the jQuery Validate script that I am using (v1.13.1), it adds has-error and has-success styling to the fields based on form-group, so if one of the fields is has-error (e.g., First Name), then both of the fields show the has-error styling (both First Name and Last Name) when it is only one of the fields that should have the class.

    I found a solution that seems like it's on the right track, but it still doesn't solve the issue: JQuery Validation and Bootstrap 3 for same form-group This code does not work, but you can see that it's on the right path to what I'm trying to do... basically, separate out the has-error and has-success styling (highlight vs unhighlight) for 2 different fields within the same form-group.

    Here is my simplified form HTML:

    <form class="form-horizontal" name="paymentInformation" id="paymentInformation" action="verifyOrder.cfm" method="post" role="form">
    <div class="form-group">
      <label for="firstname" class="col-sm-2 control-label">First Name</label>  
      <div class="col-sm-4">
      <input id="firstname" name="firstname" placeholder="First Name" class="form-control input-md" type="text" autofocus>
      </div>
      <label for="lastname" class="col-sm-2 control-label">Last Name</label>  
      <div class="col-sm-4">
      <input id="lastname" name="lastname" placeholder="Last Name" class="form-control input-md" type="text">
      </div>
    </div>
    <input type="submit" value="PROCEED TO THE NEXT STEP &#xf054;" class="blueButton">
    </form>
    

    And, here is the simplified JS (adapted from comments here Bootstrap 3 with jQuery Validation Plugin ):

    <script>
    $.validator.setDefaults({
        errorElement: "span",
        errorClass: "help-block",
        highlight: function(element) {
            $(element).closest('.form-group').removeClass('has-success').addClass('has-error');
        },
        unhighlight: function(element) {
            $(element).closest('.form-group').removeClass('has-error').addClass('has-success');
        },
        errorPlacement: function (error, element) {
            if (element.parent('.input-group').length || element.prop('type') === 'checkbox' || element.prop('type') === 'radio') {
            error.insertAfter(element.parent());
            } else {
                error.insertAfter(element);
            }
        }
    });
    $("#paymentInformation").validate({
        rules: {
            'firstname': {
                required: true,
                maxlength: 200
            },
            'lastname': {
                required: true,
                maxlength: 200
            }
        },
       messages: {
            'firstname': {
                required: "Enter your First Name.",
                maxlength: "Your First Name cannot exceed 200 characters"
            },
            'lastname': {
                required: "Enter your Last Name.",
                maxlength: "Your Last Name cannot exceed 200 characters"
            }
        }
    });
    </script>
    

    The error can be found in that if either the First Name OR the Last Name field is validated or not, then the other fields shows that it's validated or not (like an all-or-neither with the green and red for both fields).

    Here is a Fiddle showing the issue: http://jsfiddle.net/gamehendgeVA/m2o6c2vj/

    Any help is greatly appreciated!

    thanks!

  • gamehendgeVA
    gamehendgeVA about 9 years
    WOW, perfect!!! the "parent" one works perfectly, and I can see how the class one would too. Thank you so much for the help and for teaching me this! :)
  • gamehendgeVA
    gamehendgeVA about 9 years
    Awesome, you are too kind!! I like that solution even better, works great! Thanks so much for helping me! :)