Mam bardzo spartaczoną wersję tego, co robię, przez co problem się pojawia.
Mam prosty directive
. Każde kliknięcie elementu powoduje dodanie kolejnego. Jednak najpierw trzeba go skompilować, aby poprawnie wyrenderować.
Doprowadziły mnie moje badania $compile
. Ale wszystkie przykłady wykorzystują skomplikowaną strukturę, której tak naprawdę nie wiem, jak się tutaj zastosować.
Fiddles są tutaj: http://jsfiddle.net/paulocoelho/fBjbP/1/
A JS jest tutaj:
var module = angular.module('testApp', [])
.directive('test', function () {
return {
restrict: 'E',
template: '<p>{{text}}</p>',
scope: {
text: '@text'
},
link:function(scope,element){
$( element ).click(function(){
// TODO: This does not do what it's supposed to :(
$(this).parent().append("<test text='n'></test>");
});
}
};
});
Rozwiązanie Josh David Miller: http://jsfiddle.net/paulocoelho/fBjbP/2/
$compile
? Nawiasem mówiąc, dziękuję za odpowiedź!$compile
usługa jest tym, co drąży dyrektywy i zaczepia je w cyklu zdarzeń. W$compile
takiej sytuacji nie można obejść tego problemu, ale w większości przypadków inna dyrektywa, taka jak ngRepeat, może wykonać to samo zadanie (więc ngRepeat wykonuje dla nas kompilację). Czy masz konkretny przypadek użycia?Oprócz idealnego przykładu Riceball LEE dodania nowej dyrektywy elementowej
Dodanie nowej dyrektywy atrybutowej do istniejącego elementu można wykonać w następujący sposób:
Powiedzmy, że chcesz dodać on-the-fly
my-directive
dospan
elementu.Mam nadzieję, że to pomaga.
źródło
Maximum call stack size exceeded
Błąd zawsze się dzieje z powodu nieskończonej rekurencji. Nigdy nie widziałem przypadku, w którym zwiększenie rozmiaru stosu rozwiązałoby to.Dynamiczne dodawanie dyrektyw do angularjs ma dwa style:
Dodaj dyrektywę angularjs do innej dyrektywy
wstawianie nowego elementu (dyrektywy)
To proste. I możesz użyć w „link” lub „kompilacji”.
wstawianie nowego atrybutu do elementu
To trudne i sprawia mi ból głowy w ciągu dwóch dni.
Użycie „$ compile” spowoduje krytyczny błąd rekursywny !! Może powinien zignorować obecną dyrektywę podczas ponownej kompilacji elementu.
Muszę więc znaleźć sposób na wywołanie funkcji „link” dyrektywy. Bardzo trudno jest znaleźć przydatne metody ukryte głęboko w zamknięciach.
Teraz działa dobrze.
źródło
źródło
Odpowiedź zaakceptowana przez Josha Davida Millera działa świetnie, jeśli próbujesz dynamicznie dodać dyrektywę, która używa wbudowanego
template
. Jednak jeśli Twoja dyrektywa skorzysta ztemplateUrl
jego odpowiedzi, nie zadziała. Oto, co zadziałało dla mnie:źródło
Josh David Miller ma rację.
PCoelho, jeśli zastanawiasz się, co
$compile
dzieje się za kulisami i jak generowany jest wynik HTML z dyrektywy, spójrz poniżej$compile
Serwis kompiluje fragment HTML ("< test text='n' >< / test >"
), który zawiera dyrektywy ( „test” jako element) i wywołuje funkcję. Tę funkcję można następnie wykonać z zakresem, aby uzyskać „wynik HTML z dyrektywy”.Więcej szczegółów z pełnymi przykładami kodu tutaj: http://www.learn-angularjs-apps-projects.com/AngularJs/dynamically-add-directives-in-angularjs
źródło
Zainspirowany wieloma wcześniejszymi odpowiedziami wymyśliłem następującą dyrektywę „stroman”, która zastąpi się innymi dyrektywami.
Ważne: Zarejestruj dyrektywy, których chcesz używać
restrict: 'C'
. Lubię to:Możesz użyć w ten sposób:
Aby uzyskać to:
Protip Jeśli nie chcesz używać dyrektyw opartych na klasach, możesz zmienić
'<div></div>'
na coś, co lubisz. Np. Mają stały atrybut, który zawiera nazwę żądanej dyrektywy zamiastclass
.źródło