I already know how transclusion works ( within first level only I guess) , bUt I have a question about nested transcluded item's scope.
Ok so I have this code :
<body ng-app="docsTabsExample" ng-controller="ctrl">
<my-tabs>
<my-pane title="Hello">
<h4>Hello , The value of "i" is => {{i}}</h4>
</my-pane>
</my-tabs>
</body>
Basically I have a controller
, <my-tabs>
and <my-pane >
.
Looking at myTabs
directive :
.directive('myTabs', function()
{
return {
restrict: 'E',
transclude: true,
scope:
{},
controller: ['$scope', function($scope)
{
$scope.i = 2;
}],
template: '<div ng-transclude></div>'
};
})
I know that the content of the directive will have access to the outer directive's scope
So the yellow part will have access to the outer scope ( which is the main controller scope) :
Here is the code for myPane
directive :
.directive('myPane', function()
{
return {
require: '^myTabs',
restrict: 'E',
transclude: true,
scope:
{
},
controller: function($scope)
{
$scope.i = 4; //different value
},
template: '<div ng-transclude></div>'
};
})
The program starts with :
.controller('ctrl', function($scope)
{
$scope.i = 1000;
})
The output of the program is :
Hello , The value of "i" is => 1000
But
According to the documentation : myPane's
transcluded data should have access to the outer scope of the directive which is myTabs
directive which has the value i=2
.
But myPane
has an isolated scope so it does NOT inherit the scope from myTabs
.
Question
So does it goes one level more higher to the controller's scope in order to get i=1000
?? (Clarification , I'm not asking how can I make i
get another value - I'm asking why/how it has the value of 1000).
I mean how does the hierarchy of scope looks here?
Is it like this?
controller's scope
|
+--------+---------+
| |
myTabs's mypanes's
transcluded transcluded
data's scope data's scope
the docs says :
The transclude option changes the way scopes are nested. It makes it so that the contents of a transcluded directive have whatever scope is outside the directive, rather than whatever scope is on the inside. In doing so, it gives the contents access to the outside scope.
But what scope does the outside of myPAne
directive has ?
In other words , why/how does i=1000
?
FULL PLUNKER
EDIT FROM OP AFTER ANSWER
After installing and configuring PeriScope ( from @MarkRajcok) I can now see it visually :
From the docs on $compile
When you call a transclude function it returns a DOM fragment that is pre-bound to a transclusion scope. This scope is special, in that it is a child of the directive's scope (and so gets destroyed when the directive's scope gets destroyed) but it inherits the properties of the scope from which it was taken.
Parent Hierarchy (from $$childTail) is like:
-1 (root)
--2 (ctrl)
---3 mytab
----4 ($$transcluded = true)
------5 mypane
--------6 ($$transcluded = true)
Prototypical Hierarchy is like (screenshot from AngularJS Batarang)-
Updated plunker with scope id's printed in console should give you a better idea.
Why these are different, I am not very sure. Someone can throw light on this.
Why the value is 1000. Its because i needs to be provided as a bidirectional attribute = so the child scopes can modify it. I have updated the above plunker, you can see now the value responds to change in pane
controller.
More on transcluded scopes -
Confused about Angularjs transcluded and isolate scopes & bindings
https://github.com/angular/angular.js/wiki/Understanding-Scopes
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With