我遇到过一种情况,我需要根据下拉列表的选定值更改输入框的输入类型。换句话说,如果用户从下拉列表中选择“字符串”,那么输入的类型应该是“文本”等。我决定创建一个指令,因为我还在学习Angular但是我也没有复制块遍布各地的代码(我需要不止一次)。
这是我尝试的内容:
(function () {
"use strict";
angular
.module('app')
.directive('dynamicTypeInput', dynamicTypeInput);
function dynamicTypeInput() {
return {
replace: true,
restrict: 'AE',
require: ['ngModel', '^form'],
scope: {type: '=', placeholder: '@'},
templateUrl: 'app/common/dynamic-type-input/dynamic-type-input.tpl.html',
link : function(scope, element, attrs, ngModel){
//Watch for changes to ngModel, update scope.inputValue
scope.$watch(function(){
return ngModel[0].$modelValue;
}, function (value){
scope.inputValue = value;
});
//Watch inputValue, update the model
scope.$watch('inputValue', function(value){
ngModel[0].$setViewValue(value);
});
//Setup ng-change
if (attrs.ngChange) {
ngModel[0].$viewChangeListeners.push(function () {
scope.$eval(attrs.ngChange);
});
}
}
};
}
})();
注意:模板只是ng-switch
,可根据scope.type
的值选择相应的输入框,输入全部绑定到scope.inputValue
。
我使用this问题的答案来帮助我添加添加ng-change属性并正确触发的功能。根据该答案,我需要从孤立的范围中删除ngModel,我不确定为什么这是必需的,但是,如果有人能够解释它,我将不胜感激。
从隔离范围中删除ngModel使得使用初始值实例化指令变得更加困难,或者在主控制器中更改模型时更新指令,所以现在我看ngModel[0].$modelValue
并更新本地值(如果它)变化。
虽然该指令有效且按照我的预期行事,但这一切看起来有点复杂和低效,难道我无法以更简单的方式实现我想要的目标吗?
答案 0 :(得分:0)
使用second answer引用SO问题我解决了需要从隔离范围中删除ngModel以使ngChange工作的问题。这简化了指令,我可以按原样使用双向绑定。
最终指令:
(function () {
"use strict";
angular
.module('app')
.directive('dynamicTypeInput', dynamicTypeInput);
dynamicTypeInput.$inject = ['$timeout'];
function dynamicTypeInput($timeout) {
return {
replace: true,
restrict: 'AE',
require: ['ngModel', '^form'],
scope: {ngModel: '=', type: '=', placeholder: '@', ngChange: "&"},
templateUrl: 'app/common/dynamic-type-input/dynamic-type-input.tpl.html',
link: function (scope, element, attrs, ngModel) {
scope.$watch('ngModel', function () {
$timeout(scope.ngChange);
});
}
};
}
})();