Как разрешить директиву ng-disabled с изолированной областью
В последнее время мне нужно сделать элемент ввода работать как с ng-disabled, так и с настраиваемой директивой, которая использует изолированную область для оценки выражения так же, как то, что делает ng-disabled, так как пользовательская директива работает нормально, но ng-disabled doesn ' t, так как он оценивает выражение только в изолированном объеме.
Пользовательская директива довольно проста:
angular
.module('directives', [])
.directive('conditionalAutofocus', function () {
return {
restrict:'A',
scope:{
condition:'&conditionalAutofocus'
},
link:function (scope, element, attrs) {
if (scope.condition()) {
attrs.$set('autofocus','true');
}
}
}
});
в то время как страница выглядит следующим образом:
<input name="pin"
ng-model="pin"
type="password"
required
ng-disabled="names == null"
conditional-autofocus="names != null" />
У кого-нибудь уже есть решение для этой проблемы?
Спасибо заранее!
Янни
Ответы
Ответ 1
У меня была эта же проблема, и самое простое решение imho. заключается в том, чтобы использовать изолированную область для наследования свойства ngDisabled.
angular.module('directives', [])
.directive('conditionalAutofocus', function () {
return {
restrict:'A',
scope:{
condition:'&conditionalAutofocus',
disabled:'=ngDisabled'
},
link:function (scope, element, attrs) {
if (scope.condition()) {
attrs.$set('autofocus','true');
}
if(scope.disabled){
//is disabled
}
}
}
});
Может работать только для ограничения: 'E'. Не проверял других
Ответ 2
В последнее время у меня была аналогичная проблема. Я хотел отключить кнопку в изолированном объеме и использовать эту красивую директиву angular ng-disabled
.
После некоторого копания я пришел к такому решению:
link: function($scope, element, attrs){
$scope.$parent.$watch(attrs.ngDisabled, function(newVal){
element.prop('disabled', newVal);
});
//...
}
Чтобы оценить выражение ng-diabled
вместо $scope
, просто перейдите к $scope.$parent
, и все ваши переменные будут доступны. Несчастливо вручную установить свойство disabled.
Ответ 3
ОК, для моего собственного вопроса над моим решением стоит изменить реализацию директивы, а не использовать изолированную область:
angular.module('directives', [])
.directive('conditionalAutofocus', function () {
return {
restrict:'A',
link:function (scope, element, attrs) {
scope.$watch(attrs.conditionalAutofocus, function(){
if (scope.$eval(attrs.conditionalAutofocus)) {
element.focus();
}else{
element.blur();
}
});
}
}
});
Ответ 4
Вы можете настроить двунаправленную привязку к родительской области в своем изолированном определении области. Затем добавьте часы для изолированного свойства scope. Это просто дублирует код в директиве ngReadonly.
angular.module('directives', [])
.directive('conditionalAutofocus', function () {
return {
restrict:'A',
scope:{
condition: '&conditionalAutofocus',
isReadonly: '=ngReadonly'
},
link:function (scope, element, attrs) {
if (scope.condition()) {
attrs.$set('autofocus','true');
}
scope.$watch('isReadonly', (value) => {
attrs.$set('readonly', !!value);
});
}
}
});
Ответ 5
Вам не нужна какая-либо сложность других ответов. Проблема в том, что ваша директива даже не знает, что wtf ng-Disabled есть. Если вы хотите использовать ng-Disabled в своем шаблоне, вы должны ввести его в объем или требования. Например, этот НЕ будет работать:
.directive('myDirective', function () {
return {
restrict: 'E',
template: '<input type="text" ng-disabled="fieldDisabled" />',
scope:{ something: '=' },
link: function (scope, element, attrs) {
scope.something = attrs.something;
},
controller: function($scope) {
$scope.fieldDisabled = false;
$scope.myAction = function() {
$scope.fieldDisabled = true;
};
}
}
});
Но работает следующая Will:
.directive('myDirective', function () {
return {
restrict: 'E',
template: '<input type="text" ng-disabled="fieldDisabled" />',
scope:{ something: '=', lol: '=ngDisabled' },
link: function (scope, element, attrs) {
scope.something = attrs.something;
},
controller: function($scope) {
$scope.fieldDisabled = false;
$scope.myAction = function() {
$scope.fieldDisabled = true;
};
}
}
});
Обратите внимание, что единственное изменение - lol: '=ngDisabled'
. Это заставляет его работать, потому что теперь ваша директива знает, что такое ngDisabled. Вам не нужно использовать lol
или выполнить любую другую специальную проводку. Вы можете использовать свой контроллер, как и любой другой контроллер, теперь со своими собственными переменными.