2012-09-19 16 views
5

ディレクティブの属性は、スコープが更新されたときに変更されず、初期値を保持します。私はここで何が欠けていますか?angularjsの動的ディレクティブ

HTML

<ul class="nav nav-pills nav-stacked" navlist> 
    <navelem href="#!/notworking/{{foo}}"></navelem> 
    <navelem href="#!/working">works great</navelem> 
</ul> 

<p>works: {{foo}}</p> 

Javascriptを (フロントページ上の角度タブの例に基づいて)

angular.module('myApp.directives', []). 
directive('navlist', function() { 
    return { 
     scope: {}, 
     controller: function ($scope) { 
      var panes = $scope.panes = []; 

      this.select = function(pane) { 
       angular.forEach(panes, function(pane) { 
        pane.selected = false; 
       }); 
       pane.selected = true; 
      } 

      this.addPane = function(pane) { 
       if (panes.length == 0) 
        this.select(pane); 
       panes.push(pane); 
      } 

     } 
    } 
}). 
directive('navelem', function() { 
    return { 
     require: '^navlist', 
     restrict: 'E', 
     replace: true, 
     transclude: true, 
     scope: { href: '@href' }, 
     link: function(scope, element, attrs, tabsCtrl) { 
      tabsCtrl.addPane(scope); 
      scope.select = tabsCtrl.select; 
     }, 
     template: 
      '<li ng-class="{active: selected}" ng-click="select(this)"><a href="{{href}}" ng-transclude></a></li>' 
    }; 
}); 

答えて

8

あなたのディレクティブでscope: {}を定義することで、それはisolated scopeを作成しています。 親スコープがディレクティブから見えなくなりました。

親スコープを参照したい場合は、共有の スコープ(同一のディレクティブ内)にscope: trueを置き、通常のスコープのネストだけのスコープ宣言を省略することができます。 親の$scope.fooを参照したい場合は、子ディレクティブのように明示的なスコープ変数 を定義することができます。

8

は、ディレクティブのスコープの継承の3つのタイプがあります

  1. いいえ「スコープ:...」または明示scope: false - 新しいスコープが作成されません。ディレクティブは、親と同じスコープを使用します。これはシンプルで便利ですが、再利用可能なコンポーネントを構築する場合は、親スコープにそのスコーププロパティがある場合にのみ、ディレクティブを使用/使用する必要があると定義されているため、使用できません。
  2. scope: true - 親スコープの通常のプロトタイプ継承を使用して、同じ要素のすべてのディレクティブによって共有される新しいスコープを作成します。再利用可能なコンポーネントの最適な選択肢ではないでしょう。おそらく、ディレクティブは親スコープのプロパティにアクセスしてはいけません。親のスコープのプロパティを誤って変更する可能性があるからです。
  3. scope: { ... } - 新しい「隔離された」スコープを作成します。プロトタイプ的に親スコープを継承しません。しかし、オブジェクトハッシュ(すなわち、{...})は、親スコープから派生したローカルディレクティブスコープのプロパティを定義することができるので、共有するプロパティとその方法を制御できます。
    1. 親スコーププロパティとディレクティブスコーププロパティ間の強力な双方向バインディングには '='を使用します。どちらのスコーププロパティへの変更も他方のスコーププロパティに影響します。
    2. 親の属性値をディレクティブスコーププロパティにバインドする場合は、 '@'を使用します。これは本質的に一方向結合です。親スコープの変更のみがディレクティブスコープに影響します。
    3. '&'を使用して親スコープの式/関数にバインドします。あなたの特定の問題については

、あなたはスコープのプロパティを使用すると、2ウェイ結合したいオブジェクトのハッシュで指定する必要があります。(写真を含む)よりおよそディレクティブのスコープの

は、ここにセクションディレクティブを参照してください:What are the nuances of scope prototypal/prototypical inheritance in AngularJS?

+0

このおそらく最良の説明。ありがとうございました。 – user2734679

0

マークRajcokが言ったように - 範囲:{}は、親からプロパティを継承しない新しい孤立スコープを作成します。しかし、$ parentプロパティを使ってこれらのプロパティにアクセスすることはできます。

コントローラー:

app.controller('indexController', function($scope) { 
    $scope.test="Hello world!"; 
}); 

指令

app.directive("test", function() { 
    return{ 
     restrict: "A", 
     scope: {}, 
     controller: function($scope){ 
      console.log("directiv $scope.$parent.test: " + $scope.$parent.test); 
      console.log("directiv $scope.test: " + $scope.test); 
     } 
    }; 
}); 

出力:私が読んだディレクティブのスコープの

directiv $scope.$parent.test: Hello world! 
directiv $scope.test: undefined 
関連する問題