[英]Angular: directive access to form element
我有一個包含輸入的表單標簽:
<label data-live-email-check="http://www.example-service-uri.com/">
<span class="embedded-label">Email</span>
<input ng-model="formData.email"
type="email"
name="email"
placeholder="Email"
required/>
<span class="message" ng-show="emailValidationMessage">{{emailValidationMessage}}</span>
</label>
我想創建一個指令,該指令采用data-live-email-check屬性提供的URL並將電子郵件發送到該URL,以驗證該電子郵件是否已經存在。
angular.module("App").directive("liveEmailCheck", [function () {
return {
restrict: "A",
scope: {
ngModel: "="
},
link: function (scope, element, attrs) {
scope.$watch(
function(){
return scope.ngModel
},
function(newVal){
console.log(newVal);
}
);
}
}
}]);
我只想查看輸入中的模型,並在更新時發出請求。 由於指令是在標簽元素上定義的,因此ngModel未正確綁定。 我究竟做錯了什么? 我的手表表達式沒有記錄任何內容,因為它從不觸發。
我知道我可以手動獲取輸入,但是好像我要打破我覺得被“束縛”的“角度模式”。 令人沮喪的是,在Angular中似乎有太多的方法可以完成所有工作,我無法確定自己是否正確地解決了問題。
- 編輯 -
為了提供我個人會采取的解決方案(出於對“更好”方法的無知),將是以下內容:
angular.module("App").directive("liveEmailCheck", [function () {
return {
restrict: "A",
require: ["^form"],
link: function (scope, element, attrs, ctrl) {
var formCtrl = ctrl[0];
scope.formEl = formCtrl[element.find("input").attr("name")];
scope.$watch(function(){return scope.formEl.$valid},
function(newVal){
console.log(newVal);
});
}
}
}]);
這種方法有效,但是我感覺它“打破了棱角規則”。
自定義驗證的編寫方式如下:
'use strict';
angular.module('App')
.directive('liveEmailCheck', function (){
return {
require: 'ngModel',
link: function (scope, elem, attr, ngModel){
ngModel.$validators.liveEmailCheck= function (value){
//Your logic here or in a factory
};
}
};
});
然后在您的HTML上
<input type="email" live-email-check="liveEmailCheck>
基本上,您將自己的驗證添加到angular的內置驗證集中。
您需要的是ng模型asyncValidator 。 這是這種指令的簡單實現。
angular.module("App").directive('asyncEmailValidator', function ($http) {
return {
require: 'ngModel',
link: function (scope, element, attrs, ngModel) {
var emailValidationUrl = attrs.asyncEmailValidator;
ngModel.$asyncValidators.emailValidator = function (modelValue, viewValue) {
var value = modelValue || viewValue;
// NOTE: don't forget to correctly add the value to the url
return $http(emailValidationUrl + value).then(function (validationResponse) {
// NOTE: return rejected promise if validation failed else true
});
};
}
};
});
在您的情況下如何使用它:
<label>
<span class="embedded-label">Email</span>
<input ng-model="formData.email"
async-email-validator="http://www.example-service-uri.com/"
type="email"
name="email"
placeholder="Email"
required/>
<span class="message" ng-show="<FormNameHere>.email.$error.emailValidator">
{{emailValidationMessage}}
</span>
</label>
這是正確的解決方案,因為它是通過角度ng模型驗證來實現的,而角度ng模型驗證也考慮了模型的有效性。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.