jquery-validation.js在前端验证中使用起来非常方便,提供的功能基本上能满足大部分验证需求,例如:1、内置了很多常用的验证方法;2、可以自定义错误显示信息;3、可以自定义错误显示位置;4、可以自定义验证方法;5、ajax提交验证,等等
但是有时候,我们在做项目的时候总会遇到一些特殊需求,例如,在单个控件验证结束后,根据验证的成功与否,需要调用一些自己定义的方法,这个需求貌似该插件没有提供(可能有只是我没发现),没办法, 只能看源码(这就是开源的好处啊),通过对源码的分析,找到了一种可以给指定控件添加验证回调函数的方法,虽然需要修改一部分源码,但是丝毫不影响对其之前的使用,该方法可以批量添加多个控件的验证回调函数,添加方式与添加自定义规则、自定义错误信息等类似,在阅读源码的过程中,还发现了如何控制控件验证的事件触发,以及如何解决与My97DatePicker日期插件的冲突等问题,所以建议大家多看源码,有时候会有意外收获哦。
因此,本文包括三个方面:
添加控件的验证回调函数
控制控件验证的事件触发
解决与My97DatePicker日期插件的冲突问题
下面我们来一步步分析:
给指定控件添加自定义回调函数
首先,要添加回调函数必须找到该插件的验证方法。其实在使用该插件的时候,从直观的操作上我们就可以发现,控件验证的触发有多种方式,包括:控件焦点的失去,控件内容的改变(其实是keyup),以及点击提交按钮等,相信大家都知道,这些只是表象。经查看源码,能触发验证的方法有很多,如:validate、form、checkForm和element等,但这依旧是表象,以我们程序员的嗅觉,真正的验证函数肯定只有一个,经过深入勘察,前面每个方法都调用了check方法,在check方法中发现一句话:
var result = $.validator.methods[method].call(this, element.value.replace(/\r/g, ""), element, rule.parameters);
可见,这句代码就是真正调用验证逻辑的地方,因此,我们需要将自定义的验证回调函数,放置在check方法中,修改后的代码如下(黄色部分为添加的代码):
check: function(element) {
element = this.validationTargetFor(this.clean(element));
var rules = $(element).rules();
var dependencyMismatch = false;
for (var method in rules) {
var rule = { method: method, parameters: rules[method] };
try {
var result = $.validator.methods[method].call(this, element.value.replace(/\r/g, ""), element, rule.parameters);
// if a method indicates that the field is optional and therefore valid,
// don't mark it as valid when there are no other rules
if (result == "dependency-mismatch") {
dependencyMismatch = true;
continue;
}
dependencyMismatch = false;
if (result == "pending") {
this.toHide = this.toHide.not(this.errorsFor(element));
return;
}
if (!result) {
this.formatAndAdd(element, rule);
//验证失败回调函数
if ("invalidEventForElement" in this.settings) { if (element.id in this.settings.validCallbackForElement) {
this.settings.validCallbackForElement[element.id].fail();
}
} return false;
}
} catch (e) {
this.settings.debug && window.console && console.log("exception occured when checking element " + element.id
+ ", check the '" + rule.method + "' method", e);
throw e;
}
}
if (dependencyMismatch)
return;
if (this.objectLength(rules))
this.successList.push(element);
//验证成功回调函数 if ("invalidEventForElement" in this.settings) { if (element.id in this.settings.validCallbackForElement) {
this.settings.validCallbackForElement[element.id].success();
} }
return true;
},
在这里,为了和插件的其他自定义属性保持一致,我们定义了一个对象,结构如下:
validCallbackForElement:{
yourControlId1:{
success:function(){
//验证成功回调
},
fail:function(){
//验证失败回调
}
},
yourControlId2:{
success:function(){
//验证成功回调
},
fail:function(){
//验证失败回调
}
},
}
然后将其放入validate方法的参数中,示例如下(修改的时候将"yourControlId1"和"yourControlId2"更换成你自己的控件id):
$("#form1").validate({
rules: {
yourControlId1: {
required: true
},
yourControlId2: {
required: true,
maxlength: 500
}
}, //end rule
messages: {
yourControlId1: {
required: "不能为空"
},
yourControlId2: {
required: "不能为空",
maxlength: "内容过长"
}
},
errorPlacement: function(error, element) {
if (element.context.name == "yourControlId1") {
error.appendTo(document.getElementById("yourControlId1_error"));
}
else if (element.context.name == "yourControlId2")
error.appendTo(document.getElementById("yourControlId2_error"));
},
submitHandler: function(form) {
ajaxSubmit();
},
validCallbackForElement: {
yourControlId1: {
success: function() {
//控件yourControlId1的验证成功回调
},
fail: function() {
//控件yourControlId1的验证失败回调
}
},
yourControlId2: {
success: function() {
//控件yourControlId2的验证成功回调
},
fail: function() {
//控件yourControlId2的验证失败回调
}
}
}
}); //end validate function
在构造函数中,会将validCallbackForElement对象合并多this.settings对象中,因此,在调用的时候需要写成:this.settings.validCallbackForElement[element.id].success();
因为我们不一定给所有的验证控件都添加回调函数,因此,在调用的时候需要首先判断该控件有没有对应的毁掉函数,这样,调用代码就改为
但是有时候,我们在做项目的时候总会遇到一些特殊需求,例如,在单个控件验证结束后,根据验证的成功与否,需要调用一些自己定义的方法,这个需求貌似该插件没有提供(可能有只是我没发现),没办法, 只能看源码(这就是开源的好处啊),通过对源码的分析,找到了一种可以给指定控件添加验证回调函数的方法,虽然需要修改一部分源码,但是丝毫不影响对其之前的使用,该方法可以批量添加多个控件的验证回调函数,添加方式与添加自定义规则、自定义错误信息等类似,在阅读源码的过程中,还发现了如何控制控件验证的事件触发,以及如何解决与My97DatePicker日期插件的冲突等问题,所以建议大家多看源码,有时候会有意外收获哦。
因此,本文包括三个方面:
添加控件的验证回调函数
控制控件验证的事件触发
解决与My97DatePicker日期插件的冲突问题
下面我们来一步步分析:
给指定控件添加自定义回调函数
首先,要添加回调函数必须找到该插件的验证方法。其实在使用该插件的时候,从直观的操作上我们就可以发现,控件验证的触发有多种方式,包括:控件焦点的失去,控件内容的改变(其实是keyup),以及点击提交按钮等,相信大家都知道,这些只是表象。经查看源码,能触发验证的方法有很多,如:validate、form、checkForm和element等,但这依旧是表象,以我们程序员的嗅觉,真正的验证函数肯定只有一个,经过深入勘察,前面每个方法都调用了check方法,在check方法中发现一句话:
var result = $.validator.methods[method].call(this, element.value.replace(/\r/g, ""), element, rule.parameters);
可见,这句代码就是真正调用验证逻辑的地方,因此,我们需要将自定义的验证回调函数,放置在check方法中,修改后的代码如下(黄色部分为添加的代码):
check: function(element) {
element = this.validationTargetFor(this.clean(element));
var rules = $(element).rules();
var dependencyMismatch = false;
for (var method in rules) {
var rule = { method: method, parameters: rules[method] };
try {
var result = $.validator.methods[method].call(this, element.value.replace(/\r/g, ""), element, rule.parameters);
// if a method indicates that the field is optional and therefore valid,
// don't mark it as valid when there are no other rules
if (result == "dependency-mismatch") {
dependencyMismatch = true;
continue;
}
dependencyMismatch = false;
if (result == "pending") {
this.toHide = this.toHide.not(this.errorsFor(element));
return;
}
if (!result) {
this.formatAndAdd(element, rule);
//验证失败回调函数
if ("invalidEventForElement" in this.settings) { if (element.id in this.settings.validCallbackForElement) {
this.settings.validCallbackForElement[element.id].fail();
}
} return false;
}
} catch (e) {
this.settings.debug && window.console && console.log("exception occured when checking element " + element.id
+ ", check the '" + rule.method + "' method", e);
throw e;
}
}
if (dependencyMismatch)
return;
if (this.objectLength(rules))
this.successList.push(element);
//验证成功回调函数 if ("invalidEventForElement" in this.settings) { if (element.id in this.settings.validCallbackForElement) {
this.settings.validCallbackForElement[element.id].success();
} }
return true;
},
在这里,为了和插件的其他自定义属性保持一致,我们定义了一个对象,结构如下:
validCallbackForElement:{
yourControlId1:{
success:function(){
//验证成功回调
},
fail:function(){
//验证失败回调
}
},
yourControlId2:{
success:function(){
//验证成功回调
},
fail:function(){
//验证失败回调
}
},
}
然后将其放入validate方法的参数中,示例如下(修改的时候将"yourControlId1"和"yourControlId2"更换成你自己的控件id):
$("#form1").validate({
rules: {
yourControlId1: {
required: true
},
yourControlId2: {
required: true,
maxlength: 500
}
}, //end rule
messages: {
yourControlId1: {
required: "不能为空"
},
yourControlId2: {
required: "不能为空",
maxlength: "内容过长"
}
},
errorPlacement: function(error, element) {
if (element.context.name == "yourControlId1") {
error.appendTo(document.getElementById("yourControlId1_error"));
}
else if (element.context.name == "yourControlId2")
error.appendTo(document.getElementById("yourControlId2_error"));
},
submitHandler: function(form) {
ajaxSubmit();
},
validCallbackForElement: {
yourControlId1: {
success: function() {
//控件yourControlId1的验证成功回调
},
fail: function() {
//控件yourControlId1的验证失败回调
}
},
yourControlId2: {
success: function() {
//控件yourControlId2的验证成功回调
},
fail: function() {
//控件yourControlId2的验证失败回调
}
}
}
}); //end validate function
在构造函数中,会将validCallbackForElement对象合并多this.settings对象中,因此,在调用的时候需要写成:this.settings.validCallbackForElement[element.id].success();
因为我们不一定给所有的验证控件都添加回调函数,因此,在调用的时候需要首先判断该控件有没有对应的毁掉函数,这样,调用代码就改为