Vincent Nabet
Vincent Nabet

Reputation: 128

AngularJS attribute directive. How to add another attribute directive on 'compile'

I would like create an attribute directive which add an icon on a button when it's disabled.

Like this Fiddle

However, I would also add the ng-disabled directive on compile (with the same disabled-button value)

What is the best way ?

If I add the attribute ng-disabled on compile function, it never compile. So, if I re-compile my element on link function, I have to remove ng-tranclude directive due to an error. More, my events, like ng-click, are triggered twice.

Bonus question: Is it possible to restrict my attribute directive to html elements like <a> or <button> ?

Thx

Upvotes: 0

Views: 896

Answers (1)

Nikos Paraskevopoulos
Nikos Paraskevopoulos

Reputation: 40296

I'm afraid you cannot add directives dynamically to the element that contains your directive. The reason is that your compile function will be called after Angular has processed the directive's element and determined what the directives are attached to it. Adding another attribute at this point is too late, discovery has already taken place.

There may be ways to do it that I don't know of (and I would be interested in seeing any stable, non-hackish one).

I can suggest an alternative that may suit you: manually place ng-disabled on the button, but for brevity and consistency let the expression of ng-disabled drive your directive, i.e.:

<button ng-click="ctrl.click()" ng-disabled="ctrl.disabled" disabled-button>

Directive code:

.directive('disabledButton', function($parse) {
    return {
        restrict: 'A',
        transclude: true,
        scope: {
        },
        template: '<span ng-show="disabled">X</span><span ng-transclude></span>',
        link: function (scope, elem, attrs) {
            var disabled = $parse(attrs.ngDisabled);
            scope.disabled = false;
            scope.$watch(
                function() {
                    return disabled(scope.$parent);
                },
                function(newval) {
                    scope.disabled = newval;
                }
            );
        }
    };
})

Fiddle: http://jsfiddle.net/3orwupo5/1/


Or you can manually set the disabled property of the button: http://jsfiddle.net/y5ezvj5L/

Upvotes: 2

Related Questions