如何获取 kendo 网格中复制单元格的原始值
How to get the original value of a copied cell in kendo grid
如何在 kendo 网格中复制单元格时获取基础值?
我有以下代码
$(document).ready(function () {
$("#cellSelection").kendoGrid({
dataSource: {
data: orders,
pageSize: 6
},
selectable: "multiple cell",
allowCopy: true,
pageable: {
buttonCount: 5
},
scrollable: false,
navigatable: true,
columns: [
{
field: "ShipCountry",
title: "Ship Country",
width: 300
},
{
field: "Freight",
width: 300
},
{
field: "OrderDate",
title: "Order Date",
format: "{0:dd/MM/yyyy}"
}
]
});
//events to capture when Ctrl + C is pressed
$("#cellSelection").bind('copy', function (e) {
var grid = $("#cellSelection").data("kendoGrid");
if (grid != null && grid.areaClipBoard != undefined) {
console.log("copied content is:");
console.log(grid.areaClipBoard.val());
}
});
});
因此,当您复制单元格时,将复制单元格中可见的值。
比如说,如果您从网格中复制的值是 40.65
,那么只有在 kendo 网格中将 allowCopy
设置为 true 时才会复制该值。但根据数据源的原始值是 40.6789
。当按下 ctrl + c 时,我需要将原始值复制到剪贴板。
如你所见,我写了复制事件,它只是输出从网格复制的内容。有没有办法在按下 ctrl + c 时获取基础值?
这里是fiddlelink。 运行 fiddle 并打开开发人员工具和 select 几个单元格并复制它。您应该能够看到复制的内容。
如果您需要使用 40.6789
而不是 40.68
来显示值
我在下面的例子中执行甲酸...可能会帮助你
要获取所选行的数据,请使用:
grid.dataItem(grid.select());
在您的例子中,您使用的是单元格选择和 grid.dataItem
returns null
。
这迫使您进入风景优美的路线。要获取该值,您需要:
- 从选定的单元格中找到选定的行。
- 获取该行的数据。
- 确定所选列。
- 使用列获取字段名称。
- 从行数据和字段名,终于可以找到原始值了。
所以把这些放在一起:
$("#cellSelection").bind('copy', function(e) {
var grid = $("#cellSelection").data("kendoGrid");
if (!grid) {
return;
}
if (grid.areaClipBoard) {
console.log("copied content is:", grid.areaClipBoard.val());
}
var cell = grid.select()[0];
var row = cell.parentNode;
var column = grid.columns[cell.cellIndex];
var data = grid.dataItem(row);
var cellData = data[column.field];
console.log(cellData);
});
关于此的几点注意事项:
- 我不认为我的错误处理是生产就绪的。
- 我只对第一个选定的单元格执行此操作。您实际上使用了
multiple cell
,因此您可能应该迭代 grid.select
的结果并对每个结果执行此操作,通过制表符或其他方式连接。我不知道。您是想要多个单元格并进行复制的人。
- 如果您可以想象隐藏列,那么我认为我获取该列的方法不会奏效。我其实不知道你该怎么做。
感谢@Cobus Kruger 提供的解决方案。这是我的完整解决方案。
- 我们必须遍历网格中的选定项目并获取基础数据源值和 return 结果。
function getTSVFormat(grid) {
var selected = grid.select();
var delimeter = '\t';
var allowCopy = grid.options.allowCopy;
var onlyVisible = true;
if ($.isPlainObject(allowCopy) && allowCopy.delimeter) {
delimeter = allowCopy.delimeter;
}
var text = '';
if (selected.length) {
if (selected.eq(0).is('tr')) {
selected = selected.find('td:not(.k-group-cell)');
}
if (onlyVisible) {
selected.filter(':visible');
}
var result = [];
var cellsOffset = grid.columns.length;
var lockedCols = grid._isLocked() && lockedColumns(grid.columns).length;
var inLockedArea = true;
$.each(selected, function (idx, cell) {
cell = $(cell);
var tr = cell.closest('tr');
var rowIndex = tr.index();
var cellIndex = cell.index();
if (onlyVisible) {
cellIndex -= cell.prevAll(':hidden').length;
}
if (lockedCols && inLockedArea) {
inLockedArea = $.contains(grid.lockedTable[0], cell[0]);
}
if (grid._groups() && inLockedArea) {
cellIndex -= grid._groups();
}
cellIndex = inLockedArea ? cellIndex : cellIndex + lockedCols;
if (cellsOffset > cellIndex) {
cellsOffset = cellIndex;
}
var cellText = cell.text();
var column = grid.columns[cellIndex];
var data = grid.dataItem(tr);
var cellData = data[column.field];
if (!result[rowIndex]) {
result[rowIndex] = [];
}
result[rowIndex][cellIndex] = cellData;
});
var rowsOffset = result.length;
result = $.each(result, function (idx, val) {
if (val) {
result[idx] = val.slice(cellsOffset);
if (rowsOffset > idx) {
rowsOffset = idx;
}
}
});
$.each(result.slice(rowsOffset), function (idx, val) {
if (val) {
text += val.join(delimeter) + '\r\n';
} else {
text += '\r\n';
}
});
}
return text;
}
注意上面的函数不是我自己写的。我查看了 kendo.all.js 文件并对其进行了调试并根据我自己的目的进行了自定义。
- 在您获得复制的文本后,我们必须在复制事件中调用它
$("#cellSelection").bind('copy', function (e) {
var grid = $("#cellSelection").data("kendoGrid");
var text = getTSVFormat(grid);
//add textarea if its not in yet
if (!grid.areaClipBoard) {
grid.areaClipBoard = $('<textarea />').css({
position: 'fixed',
top: '50%',
left: '50%',
opacity: 0,
width: 0,
height: 0
}).appendTo(grid.wrapper);
}
//overwrite the default clipboard content of kendo with our custom data source
grid.areaClipBoard.val(text);
//call copy to clipboard to copy the contents
copyToClipboard(text);
});
- 正如您在复制事件中看到的那样,我们必须覆盖 areaClipBoard 属性 的内容才能获得我们的自定义文本。
- 将内容复制到 areaClipBoard 后,使用要复制到剪贴板的 html 调用 copyToClipBoard。
function copyToClipboard(html) {
var textarea = document.createElement('textarea');
$(textarea).addClass('k-spreadsheet-clipboard').val(html).appendTo(document.body).focus().select();
document.execCommand('copy');
$(textarea).remove();
}
就是这样!您现在可以根据需要粘贴到任何 excel sheet。它将与您在网格中选择的内容具有完全相同的空间。
如何在 kendo 网格中复制单元格时获取基础值?
我有以下代码
$(document).ready(function () {
$("#cellSelection").kendoGrid({
dataSource: {
data: orders,
pageSize: 6
},
selectable: "multiple cell",
allowCopy: true,
pageable: {
buttonCount: 5
},
scrollable: false,
navigatable: true,
columns: [
{
field: "ShipCountry",
title: "Ship Country",
width: 300
},
{
field: "Freight",
width: 300
},
{
field: "OrderDate",
title: "Order Date",
format: "{0:dd/MM/yyyy}"
}
]
});
//events to capture when Ctrl + C is pressed
$("#cellSelection").bind('copy', function (e) {
var grid = $("#cellSelection").data("kendoGrid");
if (grid != null && grid.areaClipBoard != undefined) {
console.log("copied content is:");
console.log(grid.areaClipBoard.val());
}
});
});
因此,当您复制单元格时,将复制单元格中可见的值。
比如说,如果您从网格中复制的值是 40.65
,那么只有在 kendo 网格中将 allowCopy
设置为 true 时才会复制该值。但根据数据源的原始值是 40.6789
。当按下 ctrl + c 时,我需要将原始值复制到剪贴板。
如你所见,我写了复制事件,它只是输出从网格复制的内容。有没有办法在按下 ctrl + c 时获取基础值?
这里是fiddlelink。 运行 fiddle 并打开开发人员工具和 select 几个单元格并复制它。您应该能够看到复制的内容。
如果您需要使用 40.6789
而不是 40.68
来显示值
我在下面的例子中执行甲酸...可能会帮助你
要获取所选行的数据,请使用:
grid.dataItem(grid.select());
在您的例子中,您使用的是单元格选择和 grid.dataItem
returns null
。
这迫使您进入风景优美的路线。要获取该值,您需要:
- 从选定的单元格中找到选定的行。
- 获取该行的数据。
- 确定所选列。
- 使用列获取字段名称。
- 从行数据和字段名,终于可以找到原始值了。
所以把这些放在一起:
$("#cellSelection").bind('copy', function(e) {
var grid = $("#cellSelection").data("kendoGrid");
if (!grid) {
return;
}
if (grid.areaClipBoard) {
console.log("copied content is:", grid.areaClipBoard.val());
}
var cell = grid.select()[0];
var row = cell.parentNode;
var column = grid.columns[cell.cellIndex];
var data = grid.dataItem(row);
var cellData = data[column.field];
console.log(cellData);
});
关于此的几点注意事项:
- 我不认为我的错误处理是生产就绪的。
- 我只对第一个选定的单元格执行此操作。您实际上使用了
multiple cell
,因此您可能应该迭代grid.select
的结果并对每个结果执行此操作,通过制表符或其他方式连接。我不知道。您是想要多个单元格并进行复制的人。 - 如果您可以想象隐藏列,那么我认为我获取该列的方法不会奏效。我其实不知道你该怎么做。
感谢@Cobus Kruger 提供的解决方案。这是我的完整解决方案。
- 我们必须遍历网格中的选定项目并获取基础数据源值和 return 结果。
function getTSVFormat(grid) { var selected = grid.select(); var delimeter = '\t'; var allowCopy = grid.options.allowCopy; var onlyVisible = true; if ($.isPlainObject(allowCopy) && allowCopy.delimeter) { delimeter = allowCopy.delimeter; } var text = ''; if (selected.length) { if (selected.eq(0).is('tr')) { selected = selected.find('td:not(.k-group-cell)'); } if (onlyVisible) { selected.filter(':visible'); } var result = []; var cellsOffset = grid.columns.length; var lockedCols = grid._isLocked() && lockedColumns(grid.columns).length; var inLockedArea = true; $.each(selected, function (idx, cell) { cell = $(cell); var tr = cell.closest('tr'); var rowIndex = tr.index(); var cellIndex = cell.index(); if (onlyVisible) { cellIndex -= cell.prevAll(':hidden').length; } if (lockedCols && inLockedArea) { inLockedArea = $.contains(grid.lockedTable[0], cell[0]); } if (grid._groups() && inLockedArea) { cellIndex -= grid._groups(); } cellIndex = inLockedArea ? cellIndex : cellIndex + lockedCols; if (cellsOffset > cellIndex) { cellsOffset = cellIndex; } var cellText = cell.text(); var column = grid.columns[cellIndex]; var data = grid.dataItem(tr); var cellData = data[column.field]; if (!result[rowIndex]) { result[rowIndex] = []; } result[rowIndex][cellIndex] = cellData; }); var rowsOffset = result.length; result = $.each(result, function (idx, val) { if (val) { result[idx] = val.slice(cellsOffset); if (rowsOffset > idx) { rowsOffset = idx; } } }); $.each(result.slice(rowsOffset), function (idx, val) { if (val) { text += val.join(delimeter) + '\r\n'; } else { text += '\r\n'; } }); } return text; }
注意上面的函数不是我自己写的。我查看了 kendo.all.js 文件并对其进行了调试并根据我自己的目的进行了自定义。
- 在您获得复制的文本后,我们必须在复制事件中调用它
$("#cellSelection").bind('copy', function (e) { var grid = $("#cellSelection").data("kendoGrid"); var text = getTSVFormat(grid); //add textarea if its not in yet if (!grid.areaClipBoard) { grid.areaClipBoard = $('<textarea />').css({ position: 'fixed', top: '50%', left: '50%', opacity: 0, width: 0, height: 0 }).appendTo(grid.wrapper); } //overwrite the default clipboard content of kendo with our custom data source grid.areaClipBoard.val(text); //call copy to clipboard to copy the contents copyToClipboard(text); });
- 正如您在复制事件中看到的那样,我们必须覆盖 areaClipBoard 属性 的内容才能获得我们的自定义文本。
- 将内容复制到 areaClipBoard 后,使用要复制到剪贴板的 html 调用 copyToClipBoard。
function copyToClipboard(html) { var textarea = document.createElement('textarea'); $(textarea).addClass('k-spreadsheet-clipboard').val(html).appendTo(document.body).focus().select(); document.execCommand('copy'); $(textarea).remove(); }
就是这样!您现在可以根据需要粘贴到任何 excel sheet。它将与您在网格中选择的内容具有完全相同的空间。