如何在AngularJs中重新加载/重新编译/刷新指令?

时间:2016-01-06 11:24:31

标签: angularjs angularjs-directive angular-module

我已经安装了malhar-angular-dashboard模块以便使用小部件。配置选项后,信息中心布局指令正常工作,并在视图中显示我的小部件。如果我在编译指令后更改控制器中的选项,则会出现此错误:

  

找不到小部件fromTimeout。未定义

HTML

 <div ng-controller="widgetCtrl">
  <div class="row">
    <div class="col-md-12" style="background:#B8B7C9;">
      <div ng-if="layoutOptions"
           dashboard-layouts="layoutOptions"
           class="dashboard-container"
           template-url="views/dashboards/widget-area/customDashboardLayout.tmpl.html">
      </div>
    </div>
  </div>

选择小部件 - 按钮

 <div class="btn-group" ng-if="!options.widgetButtons">
        <span class="dropdown" on-toggle="toggled(open)">
          <button type="button" class="btn btn-primary dropdown-toggle" data-toggle="dropdown">
            <span class="fa fa-bars"></span> Chose widget
          </button>
          <ul class="dropdown-menu" role="menu">
            <li ng-repeat="widget in layoutOptions.widgetDefinitions"> <!-- initial was : widget in widgetDefs -->
              <a href="#" ng-click="addWidgetInternal($event, widget);" class="dropdown-toggle"><span class="label label-primary">{{widget.name}}</span></a>
            </li>
          </ul>
        </span>
</div>

JavaScript控制器

// layout with explicit save
$scope.layoutOptions = { 
        storageId: 'demo-layouts-explicit-save',
        storage: localStorage,
        storageHash: 'fs4df4d51',
        widgetDefinitions: $scope.myWidgets, // to be changed
        layoutDefinitions:widgetDefs.REQUEST_ATTRIBUTES.layouts, // to be changed
        defaultWidgets: [], 
        explicitSave: true,
        defaultLayouts: [
          {title: 'Layout 1', active: true, defaultWidgets: []}
        ]
      };

 $scope.newChanges = function(){
     $scope.layoutOptions = { 
        storageId: 'demo-layouts-explicit-save',
        storage: localStorage,
        storageHash: 'fs4df4d51',
        widgetDefinitions:[{name:"fromTimeout"}], //changed
        layoutDefinitions:[],                     //changed
        defaultWidgets: [], 
        explicitSave: true,
        defaultLayouts: [
          {title: 'Layout 1', active: true, defaultWidgets: []}
        ]
      };
 };

运行应用程序

  1. 首次加载(加载 layoutOptions

    works

  2. 调用 newChanges()函数

    enter image description here

  3. 结论

    当我从选择小部件触发点击事件时,执行了 addWidgetInternal($ event,widget),这导致我在信息中心中遇到此问题 - 布局指令代码:

     scope.widgetDefs = new WidgetDefCollection(scope.options.widgetDefinitions);
      scope.addWidget = function (widgetToInstantiate, doNotSave) {
    
          if (typeof widgetToInstantiate === 'string') {
            widgetToInstantiate = {
              name: widgetToInstantiate
            };
          }
    
          var defaultWidgetDefinition = scope.widgetDefs.getByName(widgetToInstantiate.name); // is undefined
          if (!defaultWidgetDefinition) {
            throw 'Widget ' + widgetToInstantiate.name + ' is not found.';
          }
    
          // Determine the title for the new widget
          var title;
          if (!widgetToInstantiate.title && !defaultWidgetDefinition.title) {
            widgetToInstantiate.title = 'Widget ' + count++;
          }
    
          // Instantiation
          var widget = new WidgetModel(defaultWidgetDefinition, widgetToInstantiate);
    
          // Add to the widgets array
          scope.widgets.push(widget);
          if (!doNotSave) {
            scope.saveDashboard();
          }
    
          return widget;
        };
    

    我想我需要重新编译该指令才能访问我从控制器中进行的新更改。有什么建议吗?

1 个答案:

答案 0 :(得分:1)

我没有使用layout-dashboard指令,但我正在使用dashboardwidget指令。关于Kendo UI库的使用,我一直在努力解决这个问题,并发现了一个强制重新编译小部件的黑客攻击。

当我在widget指令代码中发现scope.compileTemplate()函数调用时,它开始了。

就我而言,我搜索了Kendo网格类.k-grid,并在角度范围对象上找到了这个方法:$angular_scope.compileTemplate();

所以在我的刷新代码中,我首先在DOM中查找任何Kendo网格(另一个hack):

   var grids = $(angular.element(document.getElementById('dash'))).find('.k-grid');
然后我使用_.each()来迭代DOM元素:

  _.each(grids, function (elem) {
         var grid = $(elem).parent().find('.k-grid').data('kendoGrid');  
         // add'l code omitted...
         if (grid) {                    
             grid.$angular_scope.compileTemplate();          // *** COMPILE TEMPLATE ***
          }
    });

它不是很优雅,但是当我动态交换小部件定义的templateURL属性时,它会重新编译我的HTML代码。

祝你好运, 鲍勃