2014-11-06 139 views
15

我有一個父指令,我想在鏈接函數中動態添加子指令。 子指令^要求父指令。 我能夠添加任何HTML元素,但只要我試圖$編譯我的子指令我收到以下錯誤,它無法找到所需的控制器。如果我手動添加子指令,它完美的作品。在父指令中附加子指令

錯誤:

Error: [$compile:ctreq] Controller 'myInput', required by directive 'myKey', can't be found! 

我的模板應該是這樣的添加元素後:

<myInput> 
<myKey></myKey> <-- added dynamically 
<myKey></myKey> <-- added dynamically 
<myKey></myKey> <-- added dynamically 
    .... 
</myInput> 

myInput指令:

angular.module('myModule').directive('myInput', ['$log', '$templateCache', '$compile', function($log, $templateCache, $compile) { 
    return { 
    restrict: 'E', 
    transclude: true, 
    scope: { 
     service: '=',   // expects a stimulus object provided by the tatoolStimulusService 
     onkeydown: '&'   // method called on key press 
    }, 
    controller: ['$scope', function($scope) { 
     this.addKey = function(keyCode, value) { 
     $scope.service.addInputKey(keyCode, { givenResponse: value }); 
     }; 
    }], 
    link: function (scope, element, attr) { 

     // add keys directives 
     angular.forEach(scope.service.registeredKeyInputs, function(value, key) { 
     var keyEl = angular.element(
      $compile('<myKey code="'+ key +'" response="'+ value.response +'"></myKey >')($rootScope)); 
     element.children(":first").append(keyEl); 
     }); 

    }, 
    template: '<div ng-transclude></div>' 
    }; 
}]); 

的myKey指令:

angular.module('myModule').directive('myKey', ['$log', '$sce', function($log, $sce) { 
    return { 
    restrict: 'E', 
    scope: {}, 
    require: '^myInput', 
    link: function (scope, element, attr, myCtrl) { 
     myCtrl.addKey(attr.code, attr.response); 

     // ... 
    }, 
    template: '<div class="key"><span ng-bind-html="key"></span></div>' 
    }; 
}]); 

回答

22

更改編譯追加的操作順序追加編譯:

var keyEl = angular.element('<myKey code="'+ key +'" response="'+ value.response +'"></myKey>'); 
element.append(keyEl); 
$compile(keyEl)(scope); 

顯然,這是在這種情況下(定位父元素指令)重要的是,新的元素被編譯爲已經在DOM。

除非將DOM元素附加到DOM,否則它沒有父項(其parentNode屬性爲null)。當Angular查找^myInput時,它會遍歷DOM樹,直到找到具有所需指令的節點。如果該元素不在DOM中,則該搜索立即失敗,因爲元素沒有單個parentNode。因此你得到的錯誤。

此外,我建議從駝峯改變你的指令名蛇情況:

<my-input> 
    <my-key></my-key> 
</my-input> 

然後編譯部分也將發生變化:

angular.element('<my-key code="'+ key +'" response="'+ value.response +'"></my-key >'); 
+0

完美的作品,並沒有甚至意義(儘管關於此的文檔將有所幫助)。我只是在帖子中使用虛擬名稱,但你當然對蛇的情況是正確的。再次感謝。 – jimmy 2014-11-07 00:16:17

+1

我不瞭解文檔,但很容易理解。在DOM元素附加到DOM樹之前,它不會有**父項(它的'parentNode'屬性是'null')。當Angular查找'^ myInput'時,它會遍歷DOM樹,直到找到具有所需指令的節點。在我們的例子中,它立即失敗,因爲元素沒有單個父節點。 – dfsq 2014-11-07 07:04:07

相關問題