Kendo UI Grid 可编辑手动 dataItem.set() 慢/延迟

Posted

技术标签:

【中文标题】Kendo UI Grid 可编辑手动 dataItem.set() 慢/延迟【英文标题】:Kendo UI Grid editable manual dataItem.set() slow/delay 【发布时间】:2013-11-08 13:56:44 【问题描述】:

我有一个可编辑的剑道网格,它可能有一个带有复选框的列来更改布尔值。我使用了 OnaBai 提出的this solution,效果很好!

唯一的问题是复选框值变化太慢。当用户点击它时,大约需要 1 秒的时间来改变。我意识到 dataItem.set() 方法是造成这种延迟的原因。

我的网格有大量数据。大约 30-40 列和 300 多行。定义如下:

$("#mainGrid").kendoGrid(
    dataSource: dataSource,

    pageable: false,
    sortable: true,

    scrollable: true,
    editable: true,
    autoBind: false,
    columnMenu: true, // Cria o menu de exibição de colunas
    height: getGridHeight(),

    toolbar: [/* hide for brevity */],
    columns: [/* hide for brevity */],
    dataBound: function()  /* hide for brevity. */,
    edit: function()  /* hide for brevity. */
);

另一个细节是,当dataItem.set() 被调用时,它会调用dataBound() 事件,但这不会导致延迟。 Grid 的edit() 方法没有在这个过程中被调用。我不知道是否值得发布dataSource 代码。

【问题讨论】:

【参考方案1】:

在使用复选框时,我建议使用 this 代码库文章中的方法。它不使用模型的 set 方法,并且仍然以相同的方式工作。即使单页上有 2000 条记录,CheckAll 也能完美运行。

【讨论】:

对不起,但这似乎与我使用的方法相同。查看文件 Index.cshtml 第 30 行。与我引用的答案中使用的 sn-p 相同。 是的,我引用了 CheckAll 函数中使用的方法,您可以看到 IsAdmin 属性是直接分配的(不使用 set 方法),然后手动刷新 Grid。 我明白了——我想。在我的情况下,分配不是由set() 分配的,值是由数据源解析的。这很好用。我只在click 事件上调用的代码上使用set() 方法。 请看我的回答,如果你同意,请告诉我。【参考方案2】:

我找到了一种替代方法来执行 OnaBai 提出的建议,并且效果更好。

// This is the grid
var grid = $("#mainGrid").data("kendoGrid");

// .flag is a class that is used on the checkboxes
grid.tbody.on("change", ".flag", function (e) 

    // Get the record uid
    var uid = grid.dataItem($(e.target).closest("tr")).uid;

    // Find the current cell
    var td = $(e.target).parent().parent();

    // This opens the cell to edit(edit mode)
    grid.editCell(td);

    // This ones changes the value of the Kendo's checkbox, that is quickly shown, 
    // changed and then hidden again. This marks the cell as 'dirty' too.
    $(td.find("input")[0]).prop("checked", $(e.target).is(":checked") ? "checked" : null).trigger("change").trigger("blur");

【讨论】:

对我不起作用。我收到“模板”为空或不是对象的错误。如果您不将其用于任何用途,为什么还要获取 uid?此外,prop 特定于 jQuery 的更高版本,早期的 IE 版本不支持它,而“attr”是通用的。但是 $(e.target) 只有在像这样的操作函数中使用它时才有效,而不是在 IE (javascripter.net/faq/eventtargetsrcelement.htm) 中使用。设置像.setAttribute('id',id) 这样使用$Id 传入的属性,然后可以用于通过jQuery 抓取对象并且是通用的。 另外,在我的回答中,当我尝试将.trigger("change").blur() 混合时,它不喜欢它。我不得不把它们放在不同的行上。 @vapcguy 但是我没有在这里问任何关于 .NET 的问题。我什至不使用它,只有javascript。因此,您在 my 案例中的回答没有进一步帮助。 呃,它是否在 .NET/MVC/HTML 中并不重要——我们在上面讨论的是 javascript。如果您不将 uid 用于任何事情,那么获取它没有任何意义。 attr 与早期版本的 jQuery 向后兼容,而 prop 则不兼容。 $(e.target) 与 IE 不兼容。你可以做.setAttribute('id',id) 并在函数中从e.id 传入id。将.trigger("change").trigger("blur") 放在同一行对我来说不起作用——不知道它对你有什么影响。所有这些都是关于 javascript 的,而我所说的并没有针对任何类型的案例。【参考方案3】:

应该尝试这样的事情:

我将使用“编辑”按钮设置列如下所示:

columns.Command(command => command.Edit().HtmlAttributes(new  id = "btnEdit_" + "$Id" ); ).Width(100).Hidden(true);

点击第一列(我有一个带有超链接的图像)使用 onclick 函数以编程方式单击“编辑”按钮,单击复选框,然后单击“更新”按钮。可能更“老派”,但我喜欢知道它遵循我自己更新时的顺序。

我传入对象(“t​​his”),所以当它出现时我可以获取行和复选框,新状态为 0 或 1(我有一些使用它的代码,但对于这个演示来说并不是必需的,所以为了简单起见,我将这部分从我的函数中删除),以及该项目的 ID:

columns.Bound(p => p.IsActive).Title("Active").Width(100).ClientTemplate("# if (IsActive == true ) # <a href=javascript:void(0) id=btnActive_$Id onclick=changeCheckbox(this, '0', $Id) class='k-button k-button-icontext k-grid-update'><img style='border:1px solid black' id=imgActive src=../../Images/active_1.png /></a> # else # <a href=javascript:void(0) id=btnActive_$Id onclick=changeCheckbox(this, '1', $Id) class='k-button k-button-icontext k-grid-update'><img style='border:1px solid black' id=imgActive src=../../Images/active_0.png /></a> ##");

function changeCheckbox(obj, status, id) 
    var parentTr = obj.parentNode.parentNode;
    $('[id="btnEdit_' + id + '"]').click();

    parentTr.childNodes[5].childNodes[0].setAttribute("id", "btnUpdate_" + id); // my Update button is in the 6th column over
    parentTr.childNodes[0].childNodes[0].setAttribute("id", "chkbox_" + id);
    $('[id=chkbox_' + id + ']').click().trigger("change");
    $('[id=chkbox_' + id + ']').blur();

    var btnUpdate = $('[id="btnUpdate_' + id + '"]');
    $('[id="btnUpdate_' + id + '"]').click();


当然,上面的代码假定复选框位于第一列。否则,将 chkbox setAttribute 行上的第一个 childNodes[0] 调整为它所在的列,减一,因为它从零开始计数。

【讨论】:

【参考方案4】:

我做了一个很像@DontVoteMeDown 的解决方案。但是我有一个嵌套网格(主/详细信息),所以我从事件参数中获取父网格。我也只是在复选框上触发一个点击事件。

$("#grid .k-grid-content").on("change", "input.chkbx", function (e) 
    // Get the parent grid of the checkbox. This can either be the master grid or the detail grid.
    var parentGrid = $(e.target).closest('div[data-role="grid"]').data("kendoGrid");
    // Get the clicked cell.
    var td = $(e.target).closest("td");
    // Enter the cell's edit mode.
    parentGrid.editCell(td);
    // Find the checkbox in the cell (which now is in "edit-mode").
    var checkbox = td.children("input[type=checkbox]");
    // Trigger a click (which will toggle check/uncheck).
    checkbox.trigger("click");
);

【讨论】:

以上是关于Kendo UI Grid 可编辑手动 dataItem.set() 慢/延迟的主要内容,如果未能解决你的问题,请参考以下文章

Kendo UI Grid:如果有任何未决更改,则无法拦截和取消排序事件

kendo ui grid 动态控制某属性

Kendo UI Grid 条件编辑

Kendo UI Grid 内联编辑发布的数据为空

如何使用 MVC Razor 在编辑器模板中将 Kendo UI Grid 绑定到我的模型集合

kendo ui AngularJS Grid CRUD操作