在角度控制器中动态创建剑道网格列

Posted

技术标签:

【中文标题】在角度控制器中动态创建剑道网格列【英文标题】:Dynamically creating kendo-grid columns in angular controller 【发布时间】:2013-10-22 05:44:30 【问题描述】:

我正在尝试动态构建剑道角网格的结构。我的问题是在评估 k-options 属性时网格选项是未知的,因此网格绑定到数据源上的所有列。

这是 html

<div kendo-grid k-options="gridModel.options" 
    k-data-source="gridModel.myDataSource">
</div>

这是控制器中的javascript

// this is called after the api call has successfully returned with data
function getSucceeded()
    ...
    $scope.gridModel.options = function()
        // function that properly builds options object with columns, etc.
    
    // this is just shown for example... the data is properly loading
    $scope.gridModel.myDataSource.data(ds.data()); 

数据正在正确加载,但因为 gridModel.options 在被成功方法设置之前在 HTML 中进行了评估,所以它基本上被忽略了,并且正在呈现数据源中的所有列。

gridModel.options 是静态的时,这就像一个冠军。

如何推迟对 k-options 的评估和/或在控制器设置它们后强制重新评估?

【问题讨论】:

这种方法可能对你有帮助***.com/questions/19296500/… 感谢@Chandermani - 这很有帮助,最终成为解决方案的一部分。 【参考方案1】:

我能够弄清楚。我必须做四件事:

    更新我的 angularjs 版本(我在 1.08 上没有 ng-if 指令)。我更新到 1.2.0rc3。 将我的kendo-grid div 包裹在ng-if div 调用我的函数!我只是将$scope.gridModel.options 设置为一个函数 - 我需要实际调用该函数,因此我将变量设置为 from 该函数返回的值。李> 我必须更新我的 angular.module 声明以包含 ngRoute(基于它在 1.2.x 中被分离到它自己的模块中)。

这是更新后的 HTML:

<div data-ng-if="contentAvailable">
    <div kendo-grid k-options="gridModel.options" 
        k-data-source="gridModel.myDataSource">
    </div>
</div>

这是更新后的控制器(未显示:我在控制器的开头设置了$scope.contentAvailable=false;):

// this is called after the api call has successfully returned with data
function getSucceeded()
    ...
    $scope.gridModel.options = function()
        // function that dynamically builds options object with columns, etc.
    (); // <----- NEED to invoke function!!

    // this is just shown for example... the data is properly loading
    $scope.gridModel.myDataSource.data(ds.data()); 

    $scope.contentAvailable=true; // trigger the ng-if

我实际上将函数移到了config 文件中,这样我就不会用太多的配置代码污染控制器。很高兴知道这一点。

【讨论】:

你不必做function()...();,你可以简单地做&lt;div k-options="gridModel.options()"&gt;。注意()【参考方案2】:

这是一个使用“Controller As”语法、动态列和分页的示例。

var app = angular.module("app", ["kendo.directives"]);

function MyCtrl() 
  var colsList = [
    name: "col1"
  , 
    name: "col2"
  , 
    name: "col3"
  , 
    name: "col4"
  ];
  var gridCols = [];
  var iteration = 1;

  var vm = this;
  vm.gridOptions = 
    columns: gridCols,
    dataSource: new kendo.data.DataSource(
      pageSize: 10
    ),
    pageable: true
  ;

  vm.buildGrid = function() 
    var data = ;

    vm.gridOptions.columns = [];
    for (var x = 0; x < colsList.length; x++) 
      if (iteration % 2 === 0 && x === colsList.length - 1) continue;

      var col = ;
      col.field = colsList[x].name;
      col.title = colsList[x].name;
      data[col.field] = "it " + iteration + " " + (1111 * (x + 1));
      vm.gridOptions.columns.push(col);
    
    // add one row to the table
    vm.gridOptions.dataSource.add(data);
    iteration++;
  ;
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
<link rel="stylesheet" href="http://cdn.kendostatic.com/2015.1.318/styles/kendo.common.min.css" />
<link rel="stylesheet" href="http://cdn.kendostatic.com/2015.1.318/styles/kendo.default.min.css" />
<script src="http://cdn.kendostatic.com/2015.1.318/js/kendo.all.min.js"></script>

<body ng-app="app">

  <div ng-controller="MyCtrl as vm">
  <button ng-click="vm.buildGrid()">Build Grid</button>
  <div kendo-grid="grid" k-options="vm.gridOptions" k-rebind="vm.gridOptions"></div>
    </div>

</body>

【讨论】:

【参考方案3】:

我们可以为此使用 k-rebind 指令。来自文档:

Widget Update upon Option Changes

您可以从控制器更新小部件。使用特殊的 k-rebind 属性创建一个小部件,该小部件会在某些范围变量更改时自动更新。此选项将破坏原始小部件并使用更改的选项重新创建它。

除了像往常一样在 GridOptions 中设置列​​数组之外,我们还必须持有对它的引用:

        vm.gridOptions =  ... ;
        vm.gridColumns = [..., ... ,...];
        vm.gridOptions.columns = vm.gridColumns;

然后将该变量传递给 k-rebind 指令:

        <div kendo-grid="vm.grid" options="vm.gridOptions" k-rebind="vm.gridColumns">
        </div>

当您将网格绑定到远程数据(在我的例子中为 OData)时就是这样。现在,您可以在列数组中添加或删除元素。网格重新创建后将再次查询数据。

当将 Grid 绑定到本地数据(对象的本地数组)时,我们必须以某种方式推迟数据的绑定,直到重新创建小部件。对我有用的(也许有更清洁的解决方案)是使用 $timeout 服务:

        vm.gridColumns.push( ... );

        vm.$timeout(function () 
            vm.gridOptions.dataSource.data(vm.myArrayOfObjects);
        , 0);

已使用 AngularJS v1.5.0 和 Kendo UI v2016.1.226 进行了测试。

【讨论】:

以上是关于在角度控制器中动态创建剑道网格列的主要内容,如果未能解决你的问题,请参考以下文章

如何在剑道模板中动态设置列

创建新行时的剑道网格,使用现有行中的值自动填充字段

在网格中为动态列创建过滤器

如何制作可编辑的假剑道网格特定列?

如何动态更改剑道网格的列集

动态绑定剑道网格数据源绑定到指令