I have a custom attribute directive (i.e., restrict: "A"
) and I want to pass two expressions (using {{...}}
) into the directive as attributes. I want to pass these attributes into the directive's template, which I use to render two nested div
tags -- the outer one containing ng-controller
and the inner containing ng-include
. The ng-controller
will define the controller exclusively used for the template, and the ng-include
will render the template's HTML.
An example showing the relevant snippets is below.
HTML:
<div ng-controller="appController">
<custom-directive ctrl="templateController" tmpl="template.html"></custom-directive>
</div>
JS:
function appController($scope) {
// Main application controller
}
function templateController($scope) {
// Controller (separate from main controller) for exclusive use with template
}
app.directive('customDirective', function() {
return {
restrict: 'A',
scope: {
ctrl: '@',
tmpl: '@'
},
// This will work, but not what I want
// Assigning controller explicitly
template: '<div ng-controller="templateController">\
<div ng-include="tmpl"></div>\
</div>'
// This is what I want, but won't work
// Assigning controller via isolate scope variable from attribute
/*template: '<div ng-controller="ctrl">\
<div ng-include="tmpl"></div>\
</div>'*/
};
});
It appears that explicitly assigning the controller works. However, I want to assign the controller via an isolate scope variable that I obtain from an attribute located inside my custom directive in the HTML.
I've fleshed out the above example a little more in the Plunker below, which names the relevant directive contentDisplay
(instead of customDirective
from above). Let me know in the comments if this example needs more commented clarification:
Plunker
Using an explicit controller assignment (uncommented template code), I achieve the desired functionality. However, when trying to assign the controller via an isolate scope variable (commented template code), it no longer works, throwing an error saying 'ctrl' is not a function, got string
.
The reason why I want to vary the controller (instead of just throwing all the controllers into one "master controller" as I've done in the Plunker) is because I want to make my code more organized to maintain readability.
The following ideas may be relevant:
- Placing the
ng-controller
tags inside the template instead of wrapping it aroundng-include
. - Using one-way binding (
'&'
) to execute functions instead of text binding ('@'
). - Using a link function instead of / in addition to an isolate scope.
- Using an element/class directive instead of attribute directive.
- The priority level of
ng-controller
is lower than that ofng-include
. - The order in which the directives are compiled / instantiated may not be correct.
While I'm looking for direct solutions to this issue, I'm also willing to accept workarounds that accomplish the same functionality and are relatively simple.