4

我開發了一個經典的遞歸菜單,它自身很好。問題在於ngClick永遠不會從遞歸指令的元素中被觸發。 我知道這是一個範圍問題,我嘗試了很多配置,但沒有運氣。ngClick不會在遞歸模板中觸發

這是一個小提琴看到它:http://jsfiddle.net/PM2dy/2/

要調用的函數是retrieveFiles(路徑)

,代碼:

app.directive("mediaTree", function ($compile) { 
    return { 
     restrict: "E", 
     scope: { folder: '=', retrieveFiles: '=' }, 
     template: 
      '<ul>' + 
       '<li data-ng-repeat="child in folder.Children">' + 
        '<a href="#" data-ng-click="retrieveFiles(child.Path)">{{child.Name}}</a>' + 
        '<media-tree folder="child"></media-tree>' + 
       '</li>' + 
      '</ul>', 
     compile: function (tElement, tAttr) { 
      var contents = tElement.contents().remove(); 
      var compiledContents; 
      return function (scope, iElement, iAttr) { 
       if (!compiledContents) { 
        compiledContents = $compile(contents); 
       } 
       compiledContents(scope, function (clone, scope) { 
        iElement.append(clone); 
       }); 
      }; 
     } 
    }; 
}); 


app.directive('mediaPanel', function ($compile) { 
    return { 
     restrict: 'E', 
     replace: true, 
     template: '<div></div>', 
     link: function (scope, elem, attrs) { 
      scope.retrieveFiles = function (me) { 
       console.log("thanks for calling " + me); 
      } 
      scope.folder = { 
       Name: 'Media', 
       Path: '/', 
       Children: [ 
        { 
         Name: 'Child1', 
         Path: '/Child1', 
         Children: [ 
          { 
           Name: 'GrandChild1', 
           Path: '/Child1/GrandChild1', 
           Children: [] 
          } 
         ] 
        }, 
        { 
         Name: 'Child2', 
         Path: '/Child2', 
         Children: [ 
          { 
           Name: 'GrandChild2', 
           Path: '/Child1/GrandChild2', 
           Children: [] 
          } 
         ] 
        } 
       ] 
      }; 

      elem.append($compile("<media-tree class='media-tree' folder='folder'></media-tree>")(scope));    
     } 
    } 
}); 

回答

3

我在這種情況下使用的方法是「父母指令的要求控制者」。在mediaTree指令,添加:

require: "^mediaPanel" 

現在所有的mediaTree節點訪問的mediaPanel控制器。寫一個,露出你想要的功能被稱爲(注:使用this,不$scope):

app.directive('mediaPanel', function ($compile) { 
    ... 
    controller: function($scope) { 
     this.retrieveFiles = function(me) { 
      console.log("thanks for calling " + me); 
     }; 
    } 
}); 

然後mediaTree的鏈接功能訪問該控制器及其retrieveFiles成員:

compile: function (tElement, tAttr) { 
    ... 
    return function (scope, iElement, iAttr, mediaPanel) { 
     // call mediaPanel.retrieveFiles(x) from here, or put it in scope 
    }; 
} 

我花了一些自由,重新安排了一下你的代碼。有些編譯並不是真的需要,我將數據定義移到了頂層控制器等。請參閱重新安排和工作案例的小提琴:http://jsfiddle.net/KRDEf/

+0

哇,它的工作,謝謝! –