问题描述
我创建了一个用于表单验证的角度验证器模块,而无需在表单中包含ngMessages,并且一切都按预期工作.
I created an angular validator module for form validation without the need to include ngMessages in the form and everything is working as expected.
但是,我发现了一个我一直试图修复的错误.它与 $ compile
有关.
However I discovered a bug which I have been trying to fix. It has something to do with $compile
.
所以我有一条指令,可以向表单元素添加属性,这可以通过使用$ compile服务来实现,但是,似乎$ compile服务会导致 ng-click
出现有害行为,因此当 ng-click 会被触发两次;
So I have a directive that adds attributes to form elements and this is achieved by using $compile service however, it seems the $compile service causes an unwanted behaviour to ng-click
so when ng-click
located inside the form is called it fires twice;
这是指令以及我在做什么:
Here is the directive and what I am doing:
angular.module('app',[])
.directive('validateForm',['$compile',
function($compile)
{
var addErrors = function(rules, form, ctrls, scope, config){
//code
};
return {
restrict: 'A',
require: ['^form'],
link: {
post: function(scope, element, attrs, ctrls){
var form = ctrls[0];
var config = scope.validator;
if(typeof config != 'object') return;
var rules = config['rules'];
var errors = [];
//-----
},
pre: function(scope, element, attrs, ctrls){
var elm = element.find('select, input, textarea').attr('validate-field','');
element.removeAttr("validate-form"); //remove the attribute to avoid indefinite loop
element.removeAttr("data-validate-form");
$compile(element.contents())(scope);
}
}
};
}
])
.controller('UserController',['$scope', function($scope){
$scope.title = 'Form Validator';
$scope.clickThings = function(value){
alert(value); //pops up twice means ng-click fires twice
}
}]);
表单标记:
<div ng-controller="UserController">
<form novalidate="" validate-form name="form" role="form">
<div class="form-group">
<input type="text" class="form-control" ng-model="first_name" name="first_name" />
</div>
<div class="form-group">
<input type="text" class="form-control" ng-model="last_name" name="last_name" />
</div>
<div class="form-group">
<input type="text" class="form-control" ng-model="email" name="email" />
</div>
<div class="form-group">
<input type="password" class="form-control" ng-model="password" name="password" />
</div>
<div class="form-group">
<input type="text" class="form-control" ng-model="country" name="country" />
</div>
<a type="button" class="btn btn-success" ng-click="clickThings('Submit Clicked')">Submit</a>
</form>
</div>
我创建了一个塞子: http://embed.plnkr.co/uIid4gczKxKI4rPOHqx7
推荐答案
尝试了不同的方法后,我意识到已经编译的 ng-click
在 $ compile(element.contents())(scope)
被调用.
After trying different things I realized ng-click
which is already compile is compiled a second time when $compile(element.contents())(scope)
is called.
要解决此问题,只需编译更改/受影响的元素,即 elem = element.find('select,input,textarea').attr('validate-field','');
To resolve this issue, only need to compile the altered/affected elements i.eelem = element.find('select, input, textarea').attr('validate-field','');
通过将 $ compile(element.contents())(scope)
替换为 $ compile(elem)(scope);
所以我最终得到了这个
angular.module('app',[])
.directive('validateForm',['$compile',
function($compile)
{
var addErrors = function(rules, form, ctrls, scope, config){
//code
};
return {
restrict: 'A',
require: ['^form'],
link: {
post: function(scope, element, attrs, ctrls){
var form = ctrls[0];
var config = scope.validator;
if(typeof config != 'object') return;
var rules = config['rules'];
var errors = [];
//-----
},
pre: function(scope, element, attrs, ctrls){
var elem = element.find('select, input, textarea').attr('validate-field','');
element.removeAttr("validate-form"); //remove the attribute to avoid indefinite loop
element.removeAttr("data-validate-form");
$compile(elem)(scope);
}
}
};
}
])
.controller('UserController',['$scope', function($scope){
$scope.title = 'Form Validator';
$scope.clickThings = function(value){
alert(value); //pops up twice means ng-click fires twice
}
}]);
在这里工作的打工者:
这篇关于AngularJS指令$ compile导致ng-click触发两次的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!