【问题标题】:View is getting initialized again and again视图一次又一次地被初始化
【发布时间】:2015-10-22 07:28:44
【问题描述】:

我正在构建一个类似于Admin Dashboard Theme的仪表板

我正在实现右侧边栏,如屏幕截图中所示

我的 App 代码结构是这样的:

index.html:
<div ui-view=""></div> 

main.html
<div ui-view=""></div> 
<div ng-include='"app/dashboard/sidebar.html"'></div> 

我在 main.html 中完成了视图的嵌套,我在其中注入了不同的视图。此外,由于我的右侧边栏是固定的,我希望它在所有主要视图中都是通用的。所以,我刚刚将它包含在我的 main.html 中。

现在,无论我向下滚动页面还是在侧边栏中执行任何操作,问题都以某种方式一次又一次地初始化我的 sidebar.html。我已经通过为 sidebar.html 视图中使用的每个控制器功能打印控制台日志来验证它。

这个问题与我的post有关:之前,我无法弄清楚实际问题。

以下是我的控制器和玉代码:

angular.module('myApp')
  .controller('SidebarCtrl', function($scope, $rootScope) {
    $scope.message = {};

    $scope.addSideBarToggleClass = function() {
      console.log("addSideBarToggleClass");
      return true;
    }

    $scope.getStatusClass = function(status) {
      console.log("getStatusClass");
      return 'is-online';
    }

    $scope.openChat = function(receiver) {
      console.log("openChat");
    }

    // etc...

  });
<aside ng-class="{ 'control-sidebar-open' : addSideBarToggleClass()}" 
       ng-controller="SidebarCtrl">
  <ul>
    <li ng-class="{active: isTabSelected('chat')}">
      <a data-toggle="tab" ng-click="updateCurrenTab('chat')"></a>
    </li>
    <li ng-class="{active: isTabSelected('home')}">
      <a data-toggle="tab" ng-click="updateCurrenTab('home')"></a>
    </li>
  </ul>
  <div>
    <div ng-class="{active: isTabSelected('home')}">
      <h3>Recent Activity</h3>
    </div>
    <div ng-class="{active: isTabSelected('chat')}">
      <div>
        <h4>Chat {{noOfUsersOnline}}</h4>
        <div>Friends
          <a href="#" ng-repeat="user in users" ng-click="openChat(user)"> 
           <span ng-class="getStatusClass(user.status)"></span>
           {{user.name}}</a>
        </div>
      </div>
    </div>
  </div>
</aside>

我看到很多"addSideBarToggleClass""getStatusClass" 的日志,每次点击openChat,我都会看到"openChat" 的日志,然后又看到"addSideBarToggleClass""getStatusClass" 的日志

谁能指出这种行为可能存在的问题?

【问题讨论】:

  • 代码太多,无法浏览。削减它以摆脱所有无关紧要的东西,这似乎是其中的大部分。如果人们不必阅读太多内容甚至可以查明问题所在,他们会更快地尝试找出答案。
  • @sethflowers:好的...我正在删除我认为不应该成为问题的代码。
  • @sethflowers:我已经更新了代码。如果还有什么需要做的,请告诉我
  • @dark_shadow,还是 waaay 太多了。您应该能够自己减少问题。我们需要所有样式标记吗?我们是否需要所有这些特定于应用程序的功能?除了在视图中显示console.log 之外,我们还需要任何 功能吗?
  • @NewDev:我已经重新迭代了代码以减少它。请看一下,如果还需要改进,请告诉我?

标签: javascript html css angularjs angular-ui-router


【解决方案1】:

您需要熟悉 Angular 中 digest loop 的概念。

简而言之,每次摘要循环运行时,所有表达式,例如{{name}}ng-show="isActive &amp;&amp; isEnabled",被 Angular “$watched”评估(有时不止一次)。这意味着如果您在表达式中调用函数:

<div ng-show="isShown()">
$scope.isShown = function(){
   console.log("expect to see this text a lot of times");
   return true;
};

该函数将在每个摘要循环上执行。

在 Angular 中调用 $scope.$digest 的任何时候都会运行摘要循环,默认情况下会发生在 ng-clickng-change$http.then 等事物上。

【讨论】:

  • 首先,非常感谢。您向我展示了如何仅发布问题的相关代码。一个快速的问题,正如您提到的,在 ng-click 或 ng-change 之类的事情上会发生摘要循环,那么这也应该在其他视图中体验到吗?我的网络应用程序中有很多视图,但这个特殊的东西只在这个嵌套视图中被注意到。是否仅在嵌套视图中发生某些事情?此外,由于我的实际事件(如滚动)发生在页面上,为什么它再次更改侧边栏视图?有什么办法可以解决这个问题吗?
  • @dark_shadow,也许其他视图没有 $watched 功能,例如{{someFunction()}},就像您在此视图中所做的那样,因此您看不到它们被调用。我不确定我得到你的最后一个问题
  • 但是有什么我可以解决的吗?我最后一个问题的意思是如何抑制这种行为?此外,我应该尝试抑制这个还是 angularjs 的预期行为?此外,如果这种预期行为不应该会导致性能下降,因为您每次观看函数?
  • @dark_shadow,这就是 Angular 的工作方式——它执行“脏检查”来跟踪 $watched 表达式改变了返回值的内容。 Angular 应用程序中最重要的性能因素是 $digest 周期,它取决于 $watched 表达式的数量和执行一个所需的时间。所以,$watched 函数必须非常快——几乎是 getter——并且绝对不做任何循环或异步调用
  • 非常感谢您的帮助。现在我知道了。这就是为什么我没有看到 ng-click() 函数的任何日志的原因。我认为 $watched 表达式不包括 ng-click()/ng-submit() 事件。如果我错了,请纠正我。此外,如果您能指出一些提高 Angular 应用程序性能的好技巧以及如何避免使用 $watched 表达式,那将是非常棒的。另外,我们可以增加 $digest 事件发生的时间吗?也许它可以包括一些优化?
猜你喜欢
  • 1970-01-01
  • 2015-05-06
  • 1970-01-01
  • 2019-09-05
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-11-04
  • 2012-09-02
相关资源
最近更新 更多