如何使用 Angular jQuery Validate 的 checkForm() 函数
How to use the Angular jQuery Validate's checkForm() function
编辑:
I've added a JsFiddle 这样您就可以轻松排除故障,而不必自己设置环境。正如您所看到的,验证甚至在 input
元素上的 blur
事件之前就已在电子邮件字段上完成,该事件是由 $scope.Email
被更改触发的。如果您注释掉 <p>
元素上的 ng-show="!mainForm.validate()"
,您会发现问题不会发生。
我正在使用 Angular implementation of jQuery Validate,我需要能够在不显示错误消息的情况下检查表单是否有效。我在网上看到的标准方案是使用jQueryValidate的checkForm()
函数,像这样:
$('#myform').validate().checkForm()
但是,我使用的 Angular 包装器目前没有实现 checkForm
功能。我一直在尝试修改源代码以将其引入,但恐怕我已经不知所措了。代码很小很简单,我会把它贴在这里:
(function (angular, $) {
angular.module('ngValidate', [])
.directive('ngValidate', function () {
return {
require: 'form',
restrict: 'A',
scope: {
ngValidate: '='
},
link: function (scope, element, attrs, form) {
var validator = element.validate(scope.ngValidate);
form.validate = function (options) {
var oldSettings = validator.settings;
validator.settings = $.extend(true, {}, validator.settings, options);
var valid = validator.form();
validator.settings = oldSettings; // Reset to old settings
return valid;
};
form.numberOfInvalids = function () {
return validator.numberOfInvalids();
};
//This is the part I've tried adding in.
//It runs, but still shows error messages when executed.
//form.checkForm = function() {
// return validator.checkForm();
//}
}
};
})
.provider('$validator', function () {
$.validator.setDefaults({
onsubmit: false // to prevent validating twice
});
return {
setDefaults: $.validator.setDefaults,
addMethod: $.validator.addMethod,
setDefaultMessages: function (messages) {
angular.extend($.validator.messages, messages);
},
format: $.validator.format,
$get: function () {
return {};
}
};
});
}(angular, jQuery));
我希望能够使用它来显示或隐藏消息,如下所示:
<p class="alert alert-danger" ng-show="!mainForm.checkForm()">Please correct any errors above before saving.</p>
我不只使用 !mainForm.validate()
的原因是因为这会导致错误消息在元素“模糊”之前显示在元素上,这是我试图避免的。谁能帮我在这个 angular 指令中实现 checkForm()
函数?
你可以用ng-show="mainForm.Email.$invalid && mainForm.Email.$touched"
到<p>
标签实现onblur事件
默认情况下 mainForm.Email.$touched
是 false
,在模糊时它会变成 true
为了正确验证,将 <input>
标签类型更改为电子邮件
如果你不想在编辑输入标签时显示错误信息,你可以添加ng-keydown="mainForm.Email.$touched=false"
我没用过angular-validate.js插件
<div ng-app="PageModule" ng-controller="MainController" class="container"><br />
<form method="post" name="mainForm" ng-submit="OnSubmit(mainForm)" >
<label>Email:
<input type="email" name="Email" ng-keydown="mainForm.Email.$touched=false" ng-model="Email" class="email" />
</label><br />
<p class="alert alert-danger" ng-show="mainForm.Email.$invalid && mainForm.Email.$touched">Please correct any errors above before saving.</p>
<button type="submit">Submit</button>
</form>
</div>
更新代码:JSFiddle
More info on Angular validation
更新 2
checkForm 会return判断表单是否有效
// added checForm, also adds valid and invalid to angular
form.checkForm = function (){
var valid = validator.form();
angular.forEach(validator.successList, function(value, key) {
scope.$parent[formName][value.name].$setValidity(value.name,true);
});
angular.forEach(validator.errorMap, function(value, key) {
scope.$parent[formName][key].$setValidity(key,false);
});
return valid
}
要隐藏由 jQuery 验证插件添加的默认消息,请将下面的代码段添加到 $.validator.setDefaults
app.config(function ($validatorProvider) {
$validatorProvider.setDefaults({
errorPlacement: function(error,element) { // to hide default error messages
return true;
}
});
});
这里是修改后的插件样子
(function (angular, $) {
angular.module('ngValidate', [])
.directive('ngValidate', function () {
return {
require: 'form',
restrict: 'A',
scope: {
ngValidate: '='
},
link: function (scope, element, attrs, form) {
var validator = element.validate(scope.ngValidate);
var formName = validator.currentForm.name;
form.validate = function (options) {
var oldSettings = validator.settings;
validator.settings = $.extend(true, {}, validator.settings, options);
var valid = validator.form();
validator.settings = oldSettings; // Reset to old settings
return valid;
};
form.numberOfInvalids = function () {
return validator.numberOfInvalids();
};
// added checkForm
form.checkForm = function (){
var valid = validator.form();
angular.forEach(validator.successList, function(value, key) {
scope.$parent[formName][value.name].$setValidity(value.name,true);
});
angular.forEach(validator.errorMap, function(value, key) {
scope.$parent[formName][key].$setValidity(key,false);
});
return valid
}
}
};
})
.provider('$validator', function () {
$.validator.setDefaults({
onsubmit: false // to prevent validating twice
});
return {
setDefaults: $.validator.setDefaults,
addMethod: $.validator.addMethod,
setDefaultMessages: function (messages) {
angular.extend($.validator.messages, messages);
},
format: $.validator.format,
$get: function () {
return {};
}
};
});
}(angular, jQuery));
控制器
app.controller("MainController", function($scope) {
$scope.Email = "";
$scope.url = "";
$scope.isFormInValid = false; // to hide validation messages
$scope.OnSubmit = function(form) {
// here you can determine
$scope.isFormInValid = !$scope.mainForm.checkForm();
return false;
}
})
每个输入标签都需要跟进(例如电子邮件)
ng-show="isFormInValid && !mainForm.Email.$invalid "
如果表单和电子邮件均无效,则会显示验证消息。
如果我正确理解你的问题,你希望能够在电子邮件地址无效时显示错误消息,并且你决定要显示错误消息。
您可以像这样将输入类型设置为电子邮件来实现此目的<input type=email>
Angular 将 属性 添加到表单 $valid
以便您可以在控制器中检查提交的文本是否有效。所以我们只需要在控制器中访问这个变量并反转它。 (因为我们要在无效时显示错误)
$scope.onSubmit = function() {
// Decide here if you want to show the error message or not
$scope.mainForm.unvalidSubmit = !$scope.mainForm.$valid
}
我还添加了一个在提交时使用浏览器验证的提交按钮。这样 onSubmit
函数甚至不会被调用,浏览器将显示错误。除了 angularjs,这些方法不需要任何东西。
您可以查看更新后的 JSFiddle here
确保打开控制台以查看 onSubmit
函数何时被调用以及按下按钮时发送的值。
尝试使用此代码进行验证这是表单
<form name="userForm" ng-submit="submitForm(userForm.$valid)" novalidate>
<div class="form-group">
<input type="text" ng-class="{ 'has-error' : userForm.name.$invalid && !userForm.name.$pristine }" ng-model="name" name="name" class="form-control" placeholder="{{ 'regName' | translate }}" required>
<p ng-show="userForm.name.$invalid && !userForm.name.$pristine" class="help-block">Your name is required.</p>
</div>
<div class="form-group">
<input type="tel" ng-class="{ 'has-error' : userForm.mob.$invalid && !userForm.mob.$pristine }" ng-model="mob" class="form-control" name="mob" ng-maxlength="11" ng-minlength="11" ng-pattern="/^\d+$/" placeholder="{{ 'regPhone' | translate }}" required>
<p ng-show="userForm.mob.$invalid && !userForm.mob.$pristine" class="help-block">Enter a valid number</p>
</div>
<div class="form-group">
<input type="email" ng-model="email" name="email" class="form-control" placeholder="{{ 'regEmail' | translate }}" required>
<p ng-show="userForm.email.$invalid && !userForm.email.$pristine" class="help-block">Enter a valid email.</p>
</div>
<div class="form-group">
<input type="password" ng-model="pass" name="pass" class="form-control" placeholder="{{ 'regPass' | translate }}" minlength="6" maxlength="16" required>
<p ng-show="userForm.pass.$invalid && !userForm.pass.$pristine" class="help-block"> Too short Min:6 Max:16</p>
<input type="password" ng-model="repass" class="form-control" ng-minlength="6" placeholder="{{ 'regConPass' | translate }}" ng-maxlength="16" required>
</div>
<button class="loginbtntwo" type="submit" id="regbtn2" ng-disabled="userForm.$dirty && userForm.$invalid" translate="signUp" ></button>
</form>
您可以使用 $touched,一旦聚焦然后模糊,这就是正确的。
<p class="alert alert-danger" ng-show="mainForm.Email.$touched && !mainForm.validate()">Please correct any errors above before saving.</p>
您需要稍微修改 Angular 验证插件。这是 JSFiddle 中代码的工作版本。请注意更新后的插件代码以及对原始代码的一对修改。
更新后的插件代码只是将其添加到 validator.SetDefaults 参数中:
errorPlacement: function(error,element) { return true; } // to hide default error message
然后我们使用范围变量来hide/show自定义错误信息:
$scope.OnSubmit = function(form) {
if (form.$dirty) {
if (form.validate()) {
//form submittal code
} else {
$scope.FormInvalid = true;
}
}
您可以按如下方式将 checkForm() 函数添加到插件中。
(function (angular, $) {
angular.module('ngValidate', [])
.directive('ngValidate', function () {
return {
require: 'form',
restrict: 'A',
scope: {
ngValidate: '='
},
link: function (scope, element, attrs, form) {
var validator = element.validate(scope.ngValidate);
form.validate = function (options) {
var oldSettings = validator.settings;
validator.settings = $.extend(true, {}, validator.settings, options);
var valid = validator.form();
validator.settings = oldSettings; // Reset to old settings
return valid;
};
form.checkForm = function (options) {
var oldSettings = validator.settings;
validator.settings = $.extend(true, {}, validator.settings, options);
var valid = validator.checkForm();
validator.submitted = {};
validator.settings = oldSettings; // Reset to old settings
return valid;
};
form.numberOfInvalids = function () {
return validator.numberOfInvalids();
};
}
};
})
.provider('$validator', function () {
$.validator.setDefaults({
onsubmit: false // to prevent validating twice
});
return {
setDefaults: $.validator.setDefaults,
addMethod: $.validator.addMethod,
setDefaultMessages: function (messages) {
angular.extend($.validator.messages, messages);
},
format: $.validator.format,
$get: function () {
return {};
}
};
});
}(angular, jQuery));
请在此处找到更新的 jsFiddle https://jsfiddle.net/b2k4p3aw/
参考:Jquery Validation: Call Valid without displaying errors?
编辑:
I've added a JsFiddle 这样您就可以轻松排除故障,而不必自己设置环境。正如您所看到的,验证甚至在 input
元素上的 blur
事件之前就已在电子邮件字段上完成,该事件是由 $scope.Email
被更改触发的。如果您注释掉 <p>
元素上的 ng-show="!mainForm.validate()"
,您会发现问题不会发生。
我正在使用 Angular implementation of jQuery Validate,我需要能够在不显示错误消息的情况下检查表单是否有效。我在网上看到的标准方案是使用jQueryValidate的checkForm()
函数,像这样:
$('#myform').validate().checkForm()
但是,我使用的 Angular 包装器目前没有实现 checkForm
功能。我一直在尝试修改源代码以将其引入,但恐怕我已经不知所措了。代码很小很简单,我会把它贴在这里:
(function (angular, $) {
angular.module('ngValidate', [])
.directive('ngValidate', function () {
return {
require: 'form',
restrict: 'A',
scope: {
ngValidate: '='
},
link: function (scope, element, attrs, form) {
var validator = element.validate(scope.ngValidate);
form.validate = function (options) {
var oldSettings = validator.settings;
validator.settings = $.extend(true, {}, validator.settings, options);
var valid = validator.form();
validator.settings = oldSettings; // Reset to old settings
return valid;
};
form.numberOfInvalids = function () {
return validator.numberOfInvalids();
};
//This is the part I've tried adding in.
//It runs, but still shows error messages when executed.
//form.checkForm = function() {
// return validator.checkForm();
//}
}
};
})
.provider('$validator', function () {
$.validator.setDefaults({
onsubmit: false // to prevent validating twice
});
return {
setDefaults: $.validator.setDefaults,
addMethod: $.validator.addMethod,
setDefaultMessages: function (messages) {
angular.extend($.validator.messages, messages);
},
format: $.validator.format,
$get: function () {
return {};
}
};
});
}(angular, jQuery));
我希望能够使用它来显示或隐藏消息,如下所示:
<p class="alert alert-danger" ng-show="!mainForm.checkForm()">Please correct any errors above before saving.</p>
我不只使用 !mainForm.validate()
的原因是因为这会导致错误消息在元素“模糊”之前显示在元素上,这是我试图避免的。谁能帮我在这个 angular 指令中实现 checkForm()
函数?
你可以用ng-show="mainForm.Email.$invalid && mainForm.Email.$touched"
到<p>
标签实现onblur事件
默认情况下 mainForm.Email.$touched
是 false
,在模糊时它会变成 true
为了正确验证,将 <input>
标签类型更改为电子邮件
如果你不想在编辑输入标签时显示错误信息,你可以添加ng-keydown="mainForm.Email.$touched=false"
我没用过angular-validate.js插件
<div ng-app="PageModule" ng-controller="MainController" class="container"><br />
<form method="post" name="mainForm" ng-submit="OnSubmit(mainForm)" >
<label>Email:
<input type="email" name="Email" ng-keydown="mainForm.Email.$touched=false" ng-model="Email" class="email" />
</label><br />
<p class="alert alert-danger" ng-show="mainForm.Email.$invalid && mainForm.Email.$touched">Please correct any errors above before saving.</p>
<button type="submit">Submit</button>
</form>
</div>
更新代码:JSFiddle
More info on Angular validation
更新 2
checkForm 会return判断表单是否有效
// added checForm, also adds valid and invalid to angular
form.checkForm = function (){
var valid = validator.form();
angular.forEach(validator.successList, function(value, key) {
scope.$parent[formName][value.name].$setValidity(value.name,true);
});
angular.forEach(validator.errorMap, function(value, key) {
scope.$parent[formName][key].$setValidity(key,false);
});
return valid
}
要隐藏由 jQuery 验证插件添加的默认消息,请将下面的代码段添加到 $.validator.setDefaults
app.config(function ($validatorProvider) {
$validatorProvider.setDefaults({
errorPlacement: function(error,element) { // to hide default error messages
return true;
}
});
});
这里是修改后的插件样子
(function (angular, $) {
angular.module('ngValidate', [])
.directive('ngValidate', function () {
return {
require: 'form',
restrict: 'A',
scope: {
ngValidate: '='
},
link: function (scope, element, attrs, form) {
var validator = element.validate(scope.ngValidate);
var formName = validator.currentForm.name;
form.validate = function (options) {
var oldSettings = validator.settings;
validator.settings = $.extend(true, {}, validator.settings, options);
var valid = validator.form();
validator.settings = oldSettings; // Reset to old settings
return valid;
};
form.numberOfInvalids = function () {
return validator.numberOfInvalids();
};
// added checkForm
form.checkForm = function (){
var valid = validator.form();
angular.forEach(validator.successList, function(value, key) {
scope.$parent[formName][value.name].$setValidity(value.name,true);
});
angular.forEach(validator.errorMap, function(value, key) {
scope.$parent[formName][key].$setValidity(key,false);
});
return valid
}
}
};
})
.provider('$validator', function () {
$.validator.setDefaults({
onsubmit: false // to prevent validating twice
});
return {
setDefaults: $.validator.setDefaults,
addMethod: $.validator.addMethod,
setDefaultMessages: function (messages) {
angular.extend($.validator.messages, messages);
},
format: $.validator.format,
$get: function () {
return {};
}
};
});
}(angular, jQuery));
控制器
app.controller("MainController", function($scope) {
$scope.Email = "";
$scope.url = "";
$scope.isFormInValid = false; // to hide validation messages
$scope.OnSubmit = function(form) {
// here you can determine
$scope.isFormInValid = !$scope.mainForm.checkForm();
return false;
}
})
每个输入标签都需要跟进(例如电子邮件)
ng-show="isFormInValid && !mainForm.Email.$invalid "
如果表单和电子邮件均无效,则会显示验证消息。
如果我正确理解你的问题,你希望能够在电子邮件地址无效时显示错误消息,并且你决定要显示错误消息。
您可以像这样将输入类型设置为电子邮件来实现此目的<input type=email>
Angular 将 属性 添加到表单 $valid
以便您可以在控制器中检查提交的文本是否有效。所以我们只需要在控制器中访问这个变量并反转它。 (因为我们要在无效时显示错误)
$scope.onSubmit = function() {
// Decide here if you want to show the error message or not
$scope.mainForm.unvalidSubmit = !$scope.mainForm.$valid
}
我还添加了一个在提交时使用浏览器验证的提交按钮。这样 onSubmit
函数甚至不会被调用,浏览器将显示错误。除了 angularjs,这些方法不需要任何东西。
您可以查看更新后的 JSFiddle here
确保打开控制台以查看 onSubmit
函数何时被调用以及按下按钮时发送的值。
尝试使用此代码进行验证这是表单
<form name="userForm" ng-submit="submitForm(userForm.$valid)" novalidate>
<div class="form-group">
<input type="text" ng-class="{ 'has-error' : userForm.name.$invalid && !userForm.name.$pristine }" ng-model="name" name="name" class="form-control" placeholder="{{ 'regName' | translate }}" required>
<p ng-show="userForm.name.$invalid && !userForm.name.$pristine" class="help-block">Your name is required.</p>
</div>
<div class="form-group">
<input type="tel" ng-class="{ 'has-error' : userForm.mob.$invalid && !userForm.mob.$pristine }" ng-model="mob" class="form-control" name="mob" ng-maxlength="11" ng-minlength="11" ng-pattern="/^\d+$/" placeholder="{{ 'regPhone' | translate }}" required>
<p ng-show="userForm.mob.$invalid && !userForm.mob.$pristine" class="help-block">Enter a valid number</p>
</div>
<div class="form-group">
<input type="email" ng-model="email" name="email" class="form-control" placeholder="{{ 'regEmail' | translate }}" required>
<p ng-show="userForm.email.$invalid && !userForm.email.$pristine" class="help-block">Enter a valid email.</p>
</div>
<div class="form-group">
<input type="password" ng-model="pass" name="pass" class="form-control" placeholder="{{ 'regPass' | translate }}" minlength="6" maxlength="16" required>
<p ng-show="userForm.pass.$invalid && !userForm.pass.$pristine" class="help-block"> Too short Min:6 Max:16</p>
<input type="password" ng-model="repass" class="form-control" ng-minlength="6" placeholder="{{ 'regConPass' | translate }}" ng-maxlength="16" required>
</div>
<button class="loginbtntwo" type="submit" id="regbtn2" ng-disabled="userForm.$dirty && userForm.$invalid" translate="signUp" ></button>
</form>
您可以使用 $touched,一旦聚焦然后模糊,这就是正确的。
<p class="alert alert-danger" ng-show="mainForm.Email.$touched && !mainForm.validate()">Please correct any errors above before saving.</p>
您需要稍微修改 Angular 验证插件。这是 JSFiddle 中代码的工作版本。请注意更新后的插件代码以及对原始代码的一对修改。
更新后的插件代码只是将其添加到 validator.SetDefaults 参数中:
errorPlacement: function(error,element) { return true; } // to hide default error message
然后我们使用范围变量来hide/show自定义错误信息:
$scope.OnSubmit = function(form) {
if (form.$dirty) {
if (form.validate()) {
//form submittal code
} else {
$scope.FormInvalid = true;
}
}
您可以按如下方式将 checkForm() 函数添加到插件中。
(function (angular, $) {
angular.module('ngValidate', [])
.directive('ngValidate', function () {
return {
require: 'form',
restrict: 'A',
scope: {
ngValidate: '='
},
link: function (scope, element, attrs, form) {
var validator = element.validate(scope.ngValidate);
form.validate = function (options) {
var oldSettings = validator.settings;
validator.settings = $.extend(true, {}, validator.settings, options);
var valid = validator.form();
validator.settings = oldSettings; // Reset to old settings
return valid;
};
form.checkForm = function (options) {
var oldSettings = validator.settings;
validator.settings = $.extend(true, {}, validator.settings, options);
var valid = validator.checkForm();
validator.submitted = {};
validator.settings = oldSettings; // Reset to old settings
return valid;
};
form.numberOfInvalids = function () {
return validator.numberOfInvalids();
};
}
};
})
.provider('$validator', function () {
$.validator.setDefaults({
onsubmit: false // to prevent validating twice
});
return {
setDefaults: $.validator.setDefaults,
addMethod: $.validator.addMethod,
setDefaultMessages: function (messages) {
angular.extend($.validator.messages, messages);
},
format: $.validator.format,
$get: function () {
return {};
}
};
});
}(angular, jQuery));
请在此处找到更新的 jsFiddle https://jsfiddle.net/b2k4p3aw/
参考:Jquery Validation: Call Valid without displaying errors?