3

I am trying to display the details of items in a list. This should be done by lazy loading the template (DOM for the details), because the template is very large and i've got many items in the list so a ng-show with ng-include is not working, since it is compiled into the DOM and makes the performance very bad.

After experimenting I figured out a solution, only working with a inline template. I am using a click handler to render the HTML with the detail-view directive to the DOM.

HTML

<div ng-controller="Ctrl">
    {{item.name}} <button show-on-click item="item">Show Details</button>  

    <div class="detailView"></div>

    <div ng-include="'include.html'"></div>
</div>

<!-- detailView Template -->
<script type="text/ng-template" id="detailView.html">
    <p>With external template: <span>{{details.description}}</span></p>
</script>

Show On Click Directive

myApp.directive("showOnClick", ['$compile', '$parse', function($compile, $parse) {

  return {
    restrict: 'A',
    scope: {
      item: "=item"
    },
    link: function (scope, element, attrs) {
        // Bind the click handler
        element.bind('click', function() {
            // Parse the item
            var item = $parse(attrs.item)(scope);

            // Find the element to include the details
            var next = $(element).next('div.detailView');

            // Include and Compile new html with directiv
            next.replaceWith($compile('<detail-view details="item"></detail-view>')(scope));

        });
     }
   };
}]); 

Detail View Directive:

myApp.directive("detailView", ['$parse', '$templateCache', '$http', function($parse, $templateCache, $http) {    
  return {
    restrict: 'E',
    replace: true,
    templateUrl: 'detailView.html', // this is not working
    // template: "<div>With template in directive: <span>{{details.description}}</span></div>", // uncomment this line to make it work
    link: function (scope, element, attrs) {
        var item = $parse(attrs.details)(scope);
        scope.$apply(function() {
          scope.details = item.details;
        });
    }        
  };
}]); 

Here is the full example on Plunker

Is there a way to improve my solution, or what am I missing to load the external template? Thanks beforehand!

2 Answers 2

1

You can also look at ng-if directive in Angular version 1.1.5 . ng-if would only render the html if condition is true. So this becomes

<div ng-controller="Ctrl">
    {{item.name}} <button ng-if="showDetails" item="item" ng-click='showDetails=true'>Show Details</button>  

    <div class="detailView"></div>

    <div ng-include="'include.html'"></div>
</div>
Sign up to request clarification or add additional context in comments.

Comments

0

By just using ng-include:

<div ng-controller="Ctrl" ng-init="detailsViewTemplateSource='';">
    {{item.name}} 
    <button ng-click="detailsViewTemplateSource = 'detailView.html'">
        Show Details
    </button>       
    <div ng-include="detailsViewTemplateSource"></div>
</div>

<!-- detailView Template -->
<script type="text/ng-template" id="detailView.html">
    <p>With external template: <span>{{details.description}}</span></p>
</script>

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.