Trigger an event if there are validation errors?
Asked Answered
B

1

11

I need to add an handle to any circumstance where a form validation fails.

I've read this, that explains that I have to add a handler as follows:

$('form').bind('invalid-form.validate', function () {
  console.log('form is invalid!');
});

But this event only fires when I try to submit the form.

I need to handle an event that's fired ANY time the form is post-validated (i.e. element loses focus etc.).

What I'm trying to achieve is, I have a large form (~50 fields), and it's splitted in Bootstrap tabs.
I want, that when there is any new validation failure or success, set or clear an error class in the tab title of the tab that contains the invalid/valid elements. P.S. my question is not on how to set those classes in the tabs. I only want to know what event(s) to handle in order to be notified upon each validation state change in the entire form.

Beebe answered 25/4, 2015 at 23:57 Comment(6)
There is no such event provided by jQuery or the Validate plugin. You'll have to attach a focusout, blur, keyup, etc to every input element and use the .valid() method to test the form.Condonation
@Condonation is there an event such as onvalidated provided by the unobtrusive validation plugin?Beebe
I am not very familiar with the unobtrusive plugin at all. However within all the thousands of jQuery Validate questions I've seen, I've never seen any custom events described.Condonation
What exactly are you trying to do? Why can't you just use one of the built-in options?Condonation
@Condonation with unobtrusive validation you don't call validate at all. It sets it all up for you. Anyway I've updated my question with the purpose of my requirement.Beebe
Yes, I understand that. However, you can use setDefaults() to get around the inability to call .validate().Condonation
C
8

I need to add a handler to any circumstance where form validation fails.

$('input, textarea, select').on('focusout keyup', function() {
   if ($('form').valid()) {
       // do something
   }
});

I want, that when there is any validation error, set an error class in the tab title that contains the invalid elements.

Well, that's a bit different than what you originally asked about. (Ignore the first half of my answer.)

Use the highlight and unhighlight options along with jQuery DOM traversal to set and unset any class in the DOM you wish. highlight fires when something is invalid and unhighlight fires when it becomes valid. See this answer as an example.

Use the .setDefaults() method to set these options since you're using the unobtrusive-validation plugin and have no direct access to the .validate() method.

Condonation answered 26/4, 2015 at 0:23 Comment(19)
I think the highlight and unhighlight is indeed what I'm looking for. Anyway, Can I call the original highlight function from the highlight function I'm setting up? Here're the original function, do I have to copy and paste it in my override script or it exists anywhere?Beebe
@Shimmy, whatever you put in there will over-ride the default.Condonation
In other words, you'll need to copy the default function into yours if you want to keep the default behavior. Then built upon it to get your new behavior.Condonation
The problem is that I need to set the tabs' titles only after validation has finished for all elements. Otherwise it gets the valid state of its last element validation state. So again, I find myself back with the original question. I believe I'll have to know how and when the unobtrusive validation is triggered.Beebe
@Shimmy, again, review the options. The invalidHandler fires on an invalid form.Condonation
I ended up using the invalid-form.validate event, which is the unobtrusive validation event that is fired out from the under the hood jquery invalidHandler. Unfortunately I missed something in the function that made it not to work. I should haven't asked this question and wasted your time at all. Anyway your answer taught me a lot on how jquery validation works.Beebe
anyway my question is still not answered. That event only stops when submitting form, and doesn't work at all for client validation. Using the proposals in your answer will again trigger an event for each field - I have to get a summary of all invalid fields, and all fields that just became valid (to clear their error state).Beebe
BTW, here's the source code of unobtrusive validation used in ASP.NET MVC.Beebe
@Shimmy, invalidHandler only fires on the submit if any part of the form is invalid. submitHandler only fires on the submit if the entire form is valid. highlight/unhighlight fire on a field-by-field basis as each becomes invalid/valid. The .valid() method can be called programmatically to test a single field or the entire form. That's it. I really don't know what else to tell you.Condonation
there is something else I realize now. The global event only fires for visible elements! Meaning that all the fields in other tabs are not validated, and the real issue is that I have some areas that I hide intentionally and those don't have to be validated... I'm thinking how can I: 1) disable validation skipping for invisible fields 2) unless they disabled.Beebe
ignore: [] will enable validation on hidden fields.Condonation
Please include in your answer for further reference. I'm gonna use ignore: ':disabled'. I hope it's gonna work.Beebe
@Shimmy, I thought you did not want to ignore hidden fields? If you tell it to ignore :disabled, then it's going to ignore the disabled fields. If you tell it to ignore nothing, [], then it will ignore nothing and validate everything.Condonation
I want it to validate :hidden fields, but not :disabled ones.Beebe
@Shimmy, looking at the source code, disabled fields are always going to be ignored no matter what... it's hard coded to bypass the ignore option entirely. So ignore: ':disabled' is effectively the same as ignore: []. See: jsfiddle.net/amy4svenCondonation
I actually changed to ignore: ':disabled' and the event didn't fire at all. I'm gonna try replacing with empty array.Beebe
@Shimmy, I don't think :disabled is a valid selector. Since skipping disabled fields is already built into the plugin, ignore: [] is the best way to go.Condonation
I've found a weird issue in the validator, see this pull request. As a workaround I've used ignore: "input[type='hidden'],fieldset[disabled] *".Beebe
I've found the issue in jQ validation and added a pull request which was committed and will up on next version.Beebe

© 2022 - 2024 — McMap. All rights reserved.