Angular ディレクティブの再帰 Angular ディレクティブの再帰は多くの議論を引き起こし、解決策は 2 つのカテゴリに分類されます: 手動 HTML コンパイル このアプローチには、実行時のスコープの状態に基づいて HTML を段階的に構築することが含まれます。ただし、コンパイルされたコードを削除できないことと、コンパイル プロセスを手動で管理するのが複雑であるという問題があります。 スクリプト テンプレート このメソッドは を使用します。テンプレート自体を参照するため、ディレクティブの制限を効果的に回避できます。ただし、パラメータ化が犠牲になり、新しいコントローラー インスタンスにバインドされます。</p> <h3>洗練されたソリューション: 再帰ヘルパー サービス</h3> <p>既存のソリューションからインスピレーションを得た、より洗練されたアプローチには、抽象化する再帰ヘルパー サービスの作成が含まれます。再帰機能。その仕組みは次のとおりです:</p> <div class="code" style="position:relative; padding:0px; margin:0px;"><pre>module.factory('RecursionHelper', ['$compile', function($compile){ return { compile: function(element, link){ var contents = element.contents().remove(); var compiledContents; return { pre: link && link.pre ? link.pre : null, post: function(scope, element){ if (!compiledContents) { compiledContents = $compile(contents); } compiledContents(scope, function(clone){ element.append(clone); }); if (link && link.post) { link.post.apply(null, arguments); } } }; } }; }]);</pre><div class="contentsignin">ログイン後にコピー</div></div> <p>このヘルパー サービスにより、要素の手動コンパイルが可能になり、再帰ループが中断されます。要素とリンク関数をパラメータとして受け取り、コンパイル前およびコンパイル後のリンク関数を返します。</p> <h3>使用法</h3> <p>再帰ヘルパー サービスは、次のようにディレクティブで使用できます。</p> <div class="code" style="position:relative; padding:0px; margin:0px;"><pre>module.directive("tree", ["RecursionHelper", function(RecursionHelper) { return { restrict: "E", scope: {family: '='}, template: '<p>{{ family.name }}</p>'+ '<ul>' + '<li ng-repeat="child in family.children">' + '<tree family="child"></tree>' + '</li>' + '</ul>', compile: function(element) { return RecursionHelper.compile(element); } }; }]);</pre><div class="contentsignin">ログイン後にコピー</div></div> <h3>利点</h3> <p>このソリューションは優れていますその理由:</p> <ul> <li>特殊なディレクティブが不要になり、HTML の複雑さが軽減されます。</li> <li>再帰ロジックは再帰ヘルパー サービスにカプセル化され、よりクリーンなディレクティブになります。</li> </ul> <h3>アップデート</h3> <p>Angular 1.5.x 以降の場合、再帰的ディレクティブは、テンプレートを使用するときにそのまま使用できます。ただし、テンプレート URL を使用する場合は、依然として Recursion Helper サービスが必要です。</p>