0

I am looking to specify the controller that a directive should use via an attribute on the element - i.e. dynamically:

HTML

<div data-mydirective data-ctrl="DynController"></div>

Angular

angular.module('app', [])
    .controller('MainController', [function() { ... }])

    .controller('DynController', [function() { ... }])

    .directive('mydirective', [function() {
        return {
            controller: 'DynController', // <- make this dynamic

            ...
        }
    }]);

3 Answers 3

2

You can do the following:

.directive('mydirective', [function() {
    return {        
        controller: function($scope, $element, $attrs){
              //Make decision based on attributes or $scope members
              if($scope.$attrs.caseA == 'true'){
                   return new ControllerA($scope, $element, $attrs);
               } else {
                   return new ControllerDefault($scope, $element, $attrs);
               }
         },
        ...
    }
}]);

Taking it a step farther, you can use $controller

.directive('mydirective', ['$controller',function($controller) {
        return {   
            controller: function($scope, $element, $attrs){
                  return $controller($attrs.dynamicCtrlName, {$scope: $scope,$element:$element,$attrs:$attrs});
             },
             ...
        }
}

In both cases, make sure you provide all the specific injectable dependencies (particular $scope, $attrs, transclude function etc...) your controllers expect. More details on controller injectables here $compile under the controller section - ideally, outer controller function should receive them all pass as locals.

Sign up to request clarification or add additional context in comments.

Comments

1

Nothing in the docs about this, but you can do the following. From my understanding this stuff is used under the hood to make ng-controller work.

.directive('mydirective', [function() {
    return {
        controller: '@',
        name: 'ctrl', // <- attribute that specifies the controller to use

        ...
    }
}]);

Comments

0

I think a better approach is just use scope since scope is already bound to controller, i.e. put what you want to call on controller scope and simple handle it in directive link

1 Comment

Yeah, I'm not sure if there's any benefit of putting the controllers contents on the scope over accessing them via scope.$parent (should probably say this is an isolated scope that I'm accessing via a React component [externally to Angular]).

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.