簡體   English   中英

AngularJS:ng-include和ng-controller

[英]AngularJS : ng-include and ng-controller

我有一個應用程序,我正在構建角度,我有大約8-10個視圖來構建。 所有視圖都有一個共享的頁腳,基於視圖和一組業務規則,我需要有條件地顯示/隱藏頁腳上的一些內容。

所以。 我有每個視圖的控制器,然后一個頁腳。 我使用ng-include包含公共頁腳布局,其中我包含的html引用了ng-controller中的頁腳控制器。

的index.html

<body ng-controller="MainCtrl as vm">
    <p>Message from Main Controller '{{vm.mainMessage}}'</p>
    <div ng-include="'commonFooter.html'"></div>
</body>

commonFooter.html

<div ng-controller="FooterCtrl as vm">
    <p>Message from Footer Controller '{{vm.message}}'</p>
    <p ng-show="vm.showSomthing">Conditional footer Content</p>
</div>

我希望每個視圖控制器確定頁腳的狀態以及是否隱藏特定內容。 (下面的shouldDisplaySomthingInFooter)

app.controller('MainCtrl', function($scope) {
  var vm = this;
  vm.mainMessage= 'HEELO';
  vm.shouldDisplaySomthingInFooter = true;
  window.console.log('Main scope id: ' + $scope.$id);
});

然后我打算在FooterController中返回到父控制器並提取特定設置以根據業務規則啟用/禁用內容。

app.controller('FooterCtrl', function($scope) {
    var vm = this;
  vm.message = 'vm footer';

  window.console.log('Footer scope id: ' + $scope.$id);
  window.console.log('Footer parent scope id: ' + $scope.$parent.$id);
  window.console.log('Footer grandparent scope id: ' + $scope.$parent.$parent.$id);
  window.console.log('Footer grandparent scope name: ' + $scope.$parent.$parent.mainMessage);
  window.console.log('Footer grandparent scope condition: ' + $scope.$parent.$parent.shouldDisplaySomthingInFooter);

  vm.showSomthing = false; //how to pull from parent scope to bind the ng-show to a value set in the parent from within a ng-include?
});

我在這里有這個例子: http//plnkr.co/edit/ucI5Cu4jjPgZNUitY2w0?p = preview

我發現的是,當我進入父作用域以取出它作為未定義的內容時,我不知道為什么。

通過檢查scopeid,我可以看到范圍嵌套到祖父級別,我相信這是因為ng-include在視圖范圍下面添加了一個額外的范圍層。 在附加示例中從控制台輸出

額外點:如果我不能使用$ scope對象並且可以堅持使用var vm = this; 這樣做的方式更可取。 但是乞丐不能選擇:)

app.controller('MainCtrl', function($scope) {
  var vm = this;

非常感謝你提前。

如果將外部控制器作為vm並將內部控制器作為foo ,則可以輕松地將它們分開並引用內部控制器中的vm。

演示

HTML

<body ng-controller="MainCtrl as vm">
    <p>Message from Main Controller '{{vm.mainMessage}}'</p>
    <div ng-include="'commonFooter.html'"></div>
</body>

CommonFooter.html

<div ng-controller="FooterCtrl as footer">
    <p>Message from Footer Controller '{{footer.message}}'</p>
    <p ng-show="vm.shouldDisplaySomethingInFooter">Conditional footer Content</p>
</div>

app.js

var app = angular.module('plunker', []);

app.controller('MainCtrl', function() {
    var self = this;
    self.mainMessage = 'Hello world';
    self.shouldDisplaySomethingInFooter = true;
});

app.controller('FooterCtrl', function() {
    var self = this;
    self.message = 'vm footer';
});

注意:為了清楚起見,我將var vm = this重命名為var self = this ,以減少視圖與控制器之間的混淆。

預期產量:

輸出顯示有條件隱藏\\顯示的項目

你誤解了控制器的語法( 參見文檔 )是用來做什么的。 它只是一種在本地作用域上公開特定控制器的方法,以便您可以從模板訪問其屬性。 當您在父模板和頁腳模板中使用someController as vm時,您不會以某種方式在控制器之間創建連接或類似的東西。 您只是在頁腳范圍內設置vm屬性,因此當您在頁腳模板中使用它時,您正在訪問頁腳的控制器(並且您已阻止前往父控制器的方式)。

對於您要做的事情,您基本上根本不需要控制器作為語法。 只需將數據正確放在$scope ,讓范圍層次結構為您完成剩下的工作。

在您的父控制器中:

$scope.features.rock = true;
$scope.features.roll = false;

在你的頁腳模板中

<p ng-show="features.rock">...</p>
<p ng-show="features.roll">...</p>

您現在還可以查看和更改其他控制器的features (因為它們的范圍是父控制器范圍的后代)。

我擺弄你的羽毛球,但也改變了var vm = this; $scope ,所以我沒有加分:-)

我強烈建議不要使用$scope.$parent ,因為你顯示的原因。 諸如ng-includeng-show等各種指令生成它們自己的范圍。

如果將來某人有意或無意地更改您的HTML並添加范圍,您無法控制。

我建議使用駐留在MainCtrl上的函數,並通過繼承范圍訪問它們。

Plunker

$scope.getShouldShow = function() {
    return $scope.shouldDisplaySomthingInFooter;
  };
  $scope.setShouldShow = function(val) {
    $scope.shouldDisplaySomthingInFooter = val;
  };

  $scope.getMainMessage = function () {
    return $scope.mainMessage;
  }

並打電話給他們:

<p ng-show="getShouldShow();">Conditional footer Content</p>

和:

  window.console.log('Footer grandparent scope name: ' + $scope.getMainMessage());
  window.console.log('Footer grandparent scope condition: ' + $scope.getShouldShow());

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM