1

I am half assured that this question is going to be down voted for not having thoroughly researched SO for similar issues. The issue is the following

script.js

'use strict';
angular.module('myApp', [])
.directive('infoDirective', function(){
return {
    scope: { test: '='},
    controller: function($scope){console.log("array-info", $scope); },
};
});

angular.module('myApp')
.controller('myCtrl', function($scope) {

  console.log($scope);
});

index.html

<div class='col-md-12'>

    <h1 >Test</h1>
    <div info-directive test="'alpha'">Variable test = {{ test }}</div>

</div>

output

Test
Variable test =

Even though the log associated with the one marked array-info does show the scope variable having a test variable with value as "alpha", the html expression doesn't evaluate to anything as shown above.

I have tried reading about the scope inheritance - but I don't think I completely understand the difference enough to debug this issue/ I am looking at the wrong topic to debug this.

Any help would be much appreciated! Plunkr

Thanks Sud

  • [read here some changes made in 1.3](http://stackoverflow.com/a/17900556/5409081) – Jorawar Singh Jul 18 '16 at 21:08
  • Thanks for that. I realized that whatever be the scope that gets created by the directive is only applicable within the template. Even in the case of transcluded directives, the variables passed through the directive remain within the directive, and the expressions within the directive that get transcluded look only from the parent's scope! http://teropa.info/blog/2015/06/09/transclusion.html this helped! – Sudharshan Viswanathan Jul 19 '16 at 14:00
  • If any of these answers solved your question you can always mark it as accepted by checking the tick mark next to it – Robin-Hoodie Jul 20 '16 at 11:01
  • Well from the above link, I realized that the transclusion scope prototypically inherits the scope from outside the directive - hence any scope variable initialized through the directive is not available. So the answer that I think is correct is "It can't be done". Also probably it might also be that the pattern that I am expecting to work might not be a good idea for some reason that I can't think of! – Sudharshan Viswanathan Jul 20 '16 at 14:05

2 Answers2

1

What you're trying to do is transclude content into the directive. To do that you need to add a transclude property and an ng-transclude tag into your template.

Also, the {{test}} you're seeing there is in the controller's scope, NOT the directives scope. The directive's scope is in the template|templateUrl property of the directive.

Since the {{test}} is in the controller scope, you need to add an actual test property to the controller scope in order for it to work.

http://plnkr.co/edit/nCZqjHqm9VQqISOnCdNu?p=info

'use strict';

angular.module('myApp', [])
  .directive('infoDirective', function(){
    return {
        scope: { test: '='},
        controller: function($scope){console.log("array-info", $scope); },
        template: '<ng-transclude></ng-transclude>', //infoDirective $scope
        transclude: true
    };
});

angular.module('myApp')
    .controller('myCtrl', function($scope) {
      $scope.test = 'alpha';
      console.log($scope);
    });


<div class='row'>
        <div class='col-md-12'>

          <h1 >Test</h1>
          <div info-directive test="test">
            Variable test = {{ test }} <!-- myCtrl $scope -->
            </div>

        </div>
      </div>

If you'd like to show the test property of the directive scope, move the content between the directive's tag to the template of the directive:

http://plnkr.co/edit/sKCz3OpVPTZP9OJb0U8d?p=preview

'use strict';

angular.module('myApp', [])
  .directive('infoDirective', function(){
    return {
        scope: { test: '='},
        controller: function($scope){console.log("array-info", $scope); },
        template: 'Variable test = {{ test }}'
    };
});

angular.module('myApp')
    .controller('myCtrl', function($scope) {

      console.log($scope);
    });

EDIT: Naturally you can also use combine a directive with a template and transclusion.

http://plnkr.co/edit/QviGc8w2M97ZhU8iyDjj?p=preview

'use strict';

angular.module('myApp', [])
  .directive('infoDirective', function(){
    return {
        scope: { test: '='},
        controller: function($scope){console.log("array-info", $scope); },
        template: '<div>Variable test = {{test}} in infoDirective</div><ng-transclude></ng-transclude>',
        transclude: true
    };
});

angular.module('myApp')
    .controller('myCtrl', function($scope) {
      $scope.test = 'alpha';
      console.log($scope);
    });


<div info-directive test="test">Variable test = {{ test }} from myCtrl</div>
Robin-Hoodie
  • 4,886
  • 4
  • 30
  • 63
  • I am looking along the lines of the 2nd one - but my question is would it be possible to use transclusion on top of it? I tried something along a mix of 1st and 2nd here http://plnkr.co/edit/SKYreniWsY5EjLH7N0vZ?p=preview but that doesn't work still. – Sudharshan Viswanathan Jul 18 '16 at 18:26
  • @SudharshanViswanathan Yes that's possible, I've edited my answer with an example – Robin-Hoodie Jul 20 '16 at 07:00
0

You need to add <div ng-controller="myCtrl"> out of the Html

Something like this :

<div ng-controller="myCtrl">

<h1 >Test</h1>
<div info-directive test="'alpha'">Variable test = {{ test }}</div>

Please check demo: http://jsfiddle.net/Lvc0u55v/7056/

For your Plunkr demo, you need to use the right angular version:

Change

<script data-require="angular.js@1.3.1" data-semver="1.3.1" src="//code.angularjs.org/1.3.1/angular.js"></script>

to

<script data-require="angular.js@1.3.x" src="https://code.angularjs.org/1.3.20/angular.js" data-semver="1.3.20"></script>
Joey Etamity
  • 856
  • 4
  • 9