web-dev-qa-db-fra.com

Modèles dynamiques de directive AngularJS

J'essaie de faire directive avec différents modèles basés sur la valeur de la portée.

C’est ce que j’ai fait jusqu’à présent et dont je ne sais pas pourquoi ne fonctionne pas http://jsbin.com/mibeyotu/1/edit

Élément HTML:

<data-type content-attr="test1"></data-type>

Directif:

var app = angular.module('myApp', []);

app.directive('dataType', function ($compile) {

    var testTemplate1 = '<h1>Test1</h1>';
    var testTemplate2 = '<h1>Test2</h1>';
    var testTemplate3 = '<h1>Test3</h1>';

    var getTemplate = function(contentType){

        var template = '';

        switch(contentType){
            case 'test1':
                template = testTemplate1;
                break;
            case 'test2':
                template = testTemplate2;
                break;
            case 'test3':
                template = testTemplate3;
                break;
        }

        return template;
    }; 

    var linker = function(scope, element, attrs){
        element.html(getTemplate(scope.content)).show();
        $compile(element.contents())(scope);
    };

    return {
        restrict: "E",
        replace: true,
        link: linker,
        scope: {
            content:'='
        }
    };
});
62
Jack

1) Vous passez le contenu en tant qu'attribut dans votre code HTML. Essaye ça:

element.html(getTemplate(attrs.content)).show();

au lieu de:

element.html(getTemplate(scope.content)).show();

2) La partie données de la directive est en cours de compilation, vous devez donc utiliser autre chose. Au lieu de type de données, par ex. type de datan.

Voici le lien:

http://jsbin.com/mibeyotu/6/edit

15
Slaven Tomac

Vous pouvez définir la propriété template de votre objet de définition de directive sur une fonction qui renverra votre modèle dynamique:

restrict: "E",
replace: true,
template: function(tElement, tAttrs) {
    return getTemplate(tAttrs.content);
}

Notez que vous n'avez pas accès à la portée à ce stade, mais que vous pouvez accéder aux attributs via tAttrs.

Votre modèle est maintenant déterminé avant la phase de compilation et vous n'avez pas besoin de le compiler manuellement.

114
DRiFTy

Vous pouvez aussi le faire très simplement comme ceci:

appDirectives.directive('contextualMenu', function($state) {
    return {
      restrict: 'E',
      replace: true,
      templateUrl: function(){
        var tpl = $state.current.name;
        return '/app/templates/contextual-menu/'+tpl+'.html';
      }
    };
});
20
eloone

Si vous devez charger votre modèle basé sur $scope variables que vous pouvez faire en utilisant ng-include:

.directive('profile', function() {
  return {
    template: '<ng-include src="getTemplateUrl()"/>',
    scope: {
      user: '=data'
    },
    restrict: 'E',
    controller: function($scope) {
      //function used on the ng-include to resolve the template
      $scope.getTemplateUrl = function() {
        //basic handling
        if ($scope.user.type == 'Twitter') {
          return 'Twitter.tpl.html';
        }
        if ($scope.user.type == 'facebook') {
          return 'facebook.tpl.html';
        }
      }
    }
  };
});

Référence: https://coderwall.com/p/onjxng/angular-directives-using-a-dynamic-template

10