Repeating over transition in Angular - best practice for accessing current element?

I wrote the following directive:

transclude: true, scope: { items: '=' } ... <div class="row" ng-repeat="item in items"> <div class="col-xs-9"> <ng-transclude></ng-transclude> </div> </div> 

Is it legal / good practice to do the following when using this directive?

 cakes = [ { name: 'blueberry cheesecake', color: 'blue' }, { name: 'rocky road', color: 'mostly brown' } ] ... <custom-list items="cakes"> <h5>{{$parent.item.name}}</h5> </custom-list> 

I specifically talk about the $parent. aspect $parent. .

+5
source share
2 answers

Angular recognized that a more flexible ng-transclude would be useful:

https://github.com/angular/angular.js/issues/5489

One suggested workaround is to define your own override for ng-transclude , which allows you to do the following:

 <div ng-transclude="sibling"></div> <!-- Original behaviour --> <div ng-transclude="parent"></div> <!-- Takes from where transclusion happens --> <div ng-transclude="child"></div> <!-- Takes from where transclusion happens, but creates a new child scope --> 

Source for custom ng-transclude :

 .config(function($provide){ $provide.decorator('ngTranscludeDirective', ['$delegate', function($delegate) { // Remove the original directive $delegate.shift(); return $delegate; }]); }) .directive( 'ngTransclude', function() { return { restrict: 'EAC', link: function( $scope, $element, $attrs, controller, $transclude ) { if (!$transclude) { throw minErr('ngTransclude')('orphan', 'Illegal use of ngTransclude directive in the template! ' + 'No parent directive that requires a transclusion found. ' + 'Element: {0}', startingTag($element)); } var iScopeType = $attrs['ngTransclude'] || 'sibling'; switch ( iScopeType ) { case 'sibling': $transclude( function( clone ) { $element.empty(); $element.append( clone ); }); break; case 'parent': $transclude( $scope, function( clone ) { $element.empty(); $element.append( clone ); }); break; case 'child': var iChildScope = $scope.$new(); $transclude( iChildScope, function( clone ) { $element.empty(); $element.append( clone ); $element.on( '$destroy', function() { iChildScope.$destroy(); }); }); break; } } } }) 
+2
source

If I wanted to summarize the problem you are trying to solve, I would say that you are trying to create a customList directive that allows the user to specify a template for each element.

transclude does not look like it was intended for this - it was intended for broadcasting content from the outer scope - not for reverse access to the inner scope of the directive.

So conceptually you can do something like the following:

 .directive("customList", function() { return { scope: { items: "=" }, templateUrl: function(element){ element.data("customListTemplate", element.find("item-template")); return "customList.html"; }, compile: function(tElement, tAttrs) { var template = element.data("customListTemplate"); tElement.find("item-placeholder").replaceWith(template.contents()); } }; }); 

customList.html :

 <div ng-repeat="item in items"> <item-placeholder></item-placeholder> </div> 

And the following is used:

 <custom-list items="cakes"> <item-template> {{$index}} | {{item.name}} <hr> </item-template> </custom-list> 

plunker

+1
source

Source: https://habr.com/ru/post/1213554/


All Articles