kirilv kirilv - 2 months ago 9
AngularJS Question

How can I control dynamically inserted content inside a directive from within the controller in AngularJS 1?

I have the following problem.
I have a custom directive with some content.
There is a spacial place inside this directive that should be dynamic (some custom functionality).

The directive looks something like this:

var app = angular.module('plunker', []);
app.directive('mydirective', mydirective);
function mydirective() {
return {
restrict : "E",
scope : {
customContent: '@'
},
template : "<div>Some common directive stuff in here! <div id='customContent'></div></div>",
compile: function(element, attr) {
return {
post: function($scope, element, attr) {
console.log("POST");
},
pre: function($scope, element, attr) {
console.log("PRE: " + $scope.customContent);
if($scope.customContent) {
var customContent = (angular.element(document.getElementById('customContent')));
customContent.append($scope.customContent);
}
}
};
}
}
}


As you can see there is a div tag with id='customContent'

Now whenever I use this directive from a controller, I would like to be able not only to inject special custom content inside this directive, but also to provide the scoping functionality.

The required result should be:

controller

app.controller('MainCtrl', function($scope) {
$scope.func = function() { // THIS DOESN'T WORK
alert(1);
}
});


html

<mydirective custom-content="<button ng-controller='MainCtrl' ng-click='func()'>Test</button>"></mydirective>


As you can see I am injecting the passed custom-content as parameter in the PRE linking function. Unfortunately I was not able to hook the func() function into the controller's scope, because that's the place that I would like to be able to control the things from.

Thank you in advance for any help!

This is the plunker: https://plnkr.co/edit/I4WAQ20ugeDiackxXqUz?p=preview

Answer

This should do what you want:

var app = angular.module('plunker', []);

app.controller('MainCtrl', function($scope) {
  $scope.func = function() {
    alert(1);
  }
});

app.directive('mydirective', mydirective);

function mydirective() {
        return {
            restrict : "E",
            transclude: true,
            scope : {

            },
            template : "<div>Some base directive stuff in here!   <ng-transclude></ng-transclude></div>",

        }
    }

and

<!DOCTYPE html>
<html ng-app="plunker">

  <head>
    <meta charset="utf-8" />
    <title>AngularJS Plunker</title>
    <script>document.write('<base href="' + document.location + '" />');</script>
    <link rel="stylesheet" href="style.css" />
    <script data-require="angular.js@1.5.x" src="https://code.angularjs.org/1.5.8/angular.js" data-semver="1.5.8"></script>
    <script src="app.js"></script>
  </head>

  <body ng-controller="MainCtrl">

      <mydirective><button ng-controller='MainCtrl' ng-click='func()'>Test</button></mydirective>

  </body>

</html>

Working plunker