jqGrid - bindkeys 改变箭头和制表键的行为

jqGrid - bindkeys change arrow and tab keys behavior

我想在我的 jqGrid 上提供 bindKeys 功能。这意味着在 Enter 上,数据应该被保存(工作正常),在 left 箭头上,光标应该移动到左边的可编辑单元格等等.

这意味着当光标位于文本框中最左侧的位置(如图所示)并按下 箭头键时,光标应移动到上一个可编辑的位置单元格(在本例中为 项目编号)。如果光标位于文本中间的某个位置,那么应该会发生正常行为。

箭头键类似,如果光标位于最右侧,它应该移动到右侧的可编辑单元格。同样,如果光标位于文本中间的某个位置,则应该会发生正常行为。

向上向下方向键,可编辑行分别切换到上行和下行。

我已经尝试实施 bindKeys 但它似乎不起作用。我在这里错过了什么?

电网代码: jsFiddle

我建议您修改演示 https://jsfiddle.net/kapv1qjy/26/ to something like https://jsfiddle.net/OlegKi/kapv1qjy/28/,它使用修改后的 keydown 事件处理程序:

list.keydown(function(e) {
  switch (e.which) {
    case 40: // down
      var $grid = $(this),
        $td = $(e.target).closest("tr.jqgrow>td"),
        $tr = $td.closest("tr.jqgrow"),//$td.parent()
        rowid = $tr.attr("id"),
        $trNext = $tr.next("tr.jqgrow"),
        p = $grid.jqGrid("getGridParam"),
        cm = $td.length > 0 ? p.colModel[$td[0].cellIndex] : null;
      var cmName = cm !== null && cm.editable ? cm.name : 'PackCartonNo';
      var selectedRowId = $grid.jqGrid('getGridParam', 'selrow');
      if (selectedRowId == null || rowid !== selectedRowId) { return; }

      // this is the DOM of table and $tr[0] is DOM of tr
      if ($trNext.length < 1) { return; }

      var rowidNext = $trNext.attr("id");
      $grid.jqGrid('saveRow', rowid, {
        aftersavefunc: function () {
          $(this).jqGrid("setSelection", rowidNext, false)
            .jqGrid("editRow", rowidNext, {
              keys: true,
              focusField: cmName
            });
        }
      });

      e.preventDefault();
      break;

    default:
      return;
  }
});

我通常建议您在事件处理程序中使用 相对 寻址元素。 e.target 是事件的目标 DOM,通常位于某些 <td> 元素内部的某处。通过使用 var $td = $(e.target).closest("tr.jqgrow>td")var $tr = $td.closest("tr.jqgrow"),您可以 "travel" 到 <td><tr> 元素,其中包含 e.target。以同样的方式,您可以使用 var $trNext = $tr.next("tr.jqgrow") 获取下一个数据行(使用 $tr.prev("tr.jqgrow") 获取前一个数据行)。 jQuery 方法的实现使用原生的 DOM 方法,运行速度非常快。另一方面,list.getDataIDs() 遍历网格的 所有 元素,并将所有元素的 id 属性值保存在一个数组中。它运行得更慢。

最后,只有在上一行成功保存后,您才应该在下一行调用setSelectioneditRow。例如,如果出现任何服务器端错误(例如,由于验证错误),您应该继续编辑当前行。此外,将方法调用放在 aftersavefunc 内可以确保我们不会同时编辑多行。