Search code examples
javascriptangularjstabsscopes

AngularJS Scope and tab directive


I just can't get how AngularJS scope works.

I have an ui-tabs Directive, with a tab controller. This is supposed to handle tabbed content.

This tab directive can contains 2 others directive, heading-template Directive, which is the template for the tab heading, and tab-pane Directive, which is the panes to show/hide.

The tab directive can have 2 behaviors : if the attr templated is on the element, then we use an empty template, and we will use later the heading-template Directive to generate tabs heading.

Else, we use a template which generates ul list with each panes title.

The problem is the heading-template Directive : this Directive simply binds the ng-repeat Directive to the template and compiles it.

But I can't have access to the scope.panes, which are located in Tab Directive's controller scope. The directive simply don't find them, and I don't understand why.

Here's the JSFiddle : http://jsfiddle.net/whitep4nther/mwk9gp9x/

Thank you for your help, I'm turning crazy


Solution

  • Lately, I found a lot of people have problems with the same root cause:

    The ng-transclude doesn't work in a way that you are expecting.

    It's by design that content added via ng-transclude will be binded with an outer (original) scope, not a scope of the current element that ng-transclude is on.

    In your case the content added via ng-transclude in templated-heading.tpl.html will be binded with the $rootScope, not the isolate scope of uiTabs directive.

    If you want the transcluded content to be binded with the isolate scope, you could use a modified version of ng-tranclude like this:

    .directive('myTransclude', function () {
      return {
        restrict: 'EAC',
        link: function(scope, element, attrs, controllers, transcludeFn) {
          transcludeFn(scope, function(nodes) {
            element.empty();
            element.append(nodes);
          });
        }
      };
    });
    

    And use it in the template:

    <script type="text/ng-template" id="/templated-heading.tpl.html">
      <div class="ui-tabs" my-transclude>
      </div>
    </script>
    

    Example JSFiddle: http://jsfiddle.net/a7fjb9sr/1/