使用行跨度对数据表进行分页
Paginate datatables with rowspans
我在使用 rowspans 对数据 table 进行分页时遇到了一些问题。我的问题是,在指示“pageLength
”属性时,它会考虑所有 trs。例如,如果我有这样的东西,我需要使用 "pageLength": 3
.
--------------------------------------------
|
tr with rowspan = 2 | tr inside #1
|----------------------
|
| tr inside #2
--------------------------------------------
我的问题是,因此,当沿着 table 的不同页面进行分页时,可能会发生某些 tr 最终成为“孤儿”的情况。例如,如果页面以 tr #1 结尾,则 tr #2 可能会在下一页上“单独”出现(没有 rowspan = 2 的 tr)。有什么方法可以对这些 table 进行分页,只考虑那些“父”行,即带有 rowspan 的行?
我不知道有什么方法可以完全按照您的要求进行操作。话虽如此,我在下面提供了一些注释,以防它们是可以接受的替代方案。
您可以创建一个伪造的 rowspan
效果,无论您在哪个页面,它都会始终在第一列显示相关值:
但即便如此,您仍然可能会在一页底部的跨度中看到一些行,而在下一页的顶部看到跨度中的其余行。我看不出有任何解决办法(除了这个答案末尾提到的一种可能情况)。
作为替代方案,您可能需要查看 row group 扩展。但是,同样不能保证整个组总是只出现在一页上。
如果您对“假行跨度”感兴趣,这里有一个例子。它通过操纵每个页面上的 DOM 节点来工作,以便不显示第一列中的重复值(并且单元格的 border-top
行被删除)。
DataTable 本身的数据没有改变,所以如果您搜索“Edinburgh”,您仍然会找到所有 3 条记录。
var dataSet = {
"data": [
{
"id": "1",
"name": "Tiger Nixon",
"position": "System Architect",
"salary": "0,800",
"start_date": "2011/04/25",
"office": "Edinburgh",
"extn": "5421"
},
{
"id": "2",
"name": "Garrett Winters",
"position": "Accountant",
"salary": "0,750",
"start_date": "2011/07/25",
"office": "Tokyo",
"extn": "8422"
},
{
"id": "3",
"name": "Ashton Cox",
"position": "Junior Technical Author",
"salary": ",000",
"start_date": "2009/01/12",
"office": "Tokyo",
"extn": "1562"
},
{
"id": "4",
"name": "Cedric Kelly",
"position": "Senior Javascript Developer",
"salary": "3,060",
"start_date": "2012/03/29",
"office": "New York",
"extn": "6224"
},
{
"id": "5",
"name": "Airi Satou",
"position": "Accountant",
"salary": "2,700",
"start_date": "2008/11/28",
"office": "Tokyo",
"extn": "5407"
},
{
"id": "6",
"name": "Brielle Williamson",
"position": "Integration Specialist",
"salary": "2,000",
"start_date": "2012/12/02",
"office": "New York",
"extn": "4804"
},
{
"id": "7",
"name": "Herrod Chandler",
"position": "Sales Assistant",
"salary": "7,500",
"start_date": "2012/08/06",
"office": "San Francisco",
"extn": "9608"
},
{
"id": "8",
"name": "Rhona Davidson",
"position": "Integration Specialist",
"salary": "7,900",
"start_date": "2010/10/14",
"office": "Tokyo",
"extn": "6200"
},
{
"id": "9",
"name": "Colleen Hurst",
"position": "Javascript Developer",
"salary": "5,500",
"start_date": "2009/09/15",
"office": "San Francisco",
"extn": "2360"
},
{
"id": "10",
"name": "Sonya Frost",
"position": "Software Engineer",
"salary": "3,600",
"start_date": "2008/12/13",
"office": "Edinburgh",
"extn": "1667"
},
{
"id": "11",
"name": "Jena Gaines",
"position": "Office Manager",
"salary": ",560",
"start_date": "2008/12/19",
"office": "London",
"extn": "3814"
},
{
"id": "12",
"name": "Quinn Flynn",
"position": "Support Lead",
"salary": "2,000",
"start_date": "2013/03/03",
"office": "Edinburgh",
"extn": "9497"
}
]
};
var previous = '';
$(document).ready(function() {
var table = $('#example').DataTable( {
data: dataSet.data,
"order": [[ 0, 'asc' ]],
columns: [
{ title: "Office", data: "office" },
{ title: "Name", data: "name" },
//{ title: "Office2", data: "office" },
{ title: "Position", data: "position" },
{ title: "Start date", data: "start_date" },
{ title: "Salary", data: "salary" }
],
"initComplete": function(settings, json) {
// in case the initial sort order leads to
// cells needing to be altered:
processColumnNodes( $('#example').DataTable() );
}
} );
table.on( 'draw', function () {
processColumnNodes( $('#example').DataTable() );
} );
function processColumnNodes(tbl) {
// see https://datatables.net/reference/type/selector-modifier
var selector_modifier = { order: 'current', page: 'current', search: 'applied' }
var previous = '';
var officeNodes = tbl.column(0, selector_modifier).nodes();
var officeData = tbl.column(0, selector_modifier).data();
for (var i = 0; i < officeData.length; i++) {
var current = officeData[i];
if (current === previous) {
officeNodes[i].textContent = '';
officeNodes[i].setAttribute("style", "border-top:none;");
} else {
officeNodes[i].textContent = current;
}
previous = current;
}
}
} );
<script src="https://code.jquery.com/jquery-3.5.1.js"></script>
<script src="https://cdn.datatables.net/1.10.22/js/jquery.dataTables.js"></script>
<link rel="stylesheet" type="text/css" href="https://cdn.datatables.net/1.10.22/css/jquery.dataTables.css">
<link rel="stylesheet" type="text/css" href="https://datatables.net/media/css/site-examples.css">
<div style="margin: 20px;">
<table id="example" class="cell-border" style="width:100%">
</table>
</div>
当您运行上面的代码片段时,您将在第 1 页末尾的“东京”的 4 行中看到 2 行。您将在第 2 页顶部 - 但您还会看到“东京”标签。
如果您的 rowspan
尺寸始终恰好为“2”,那么您还可以将“页面长度”下拉列表中的值设置为仅使用偶数:
"lengthMenu": [ 10, 20, 50, 100 ]
这样你就不会在不同的页面上出现任何“孤儿”。
我在使用 rowspans 对数据 table 进行分页时遇到了一些问题。我的问题是,在指示“pageLength
”属性时,它会考虑所有 trs。例如,如果我有这样的东西,我需要使用 "pageLength": 3
.
--------------------------------------------
|
tr with rowspan = 2 | tr inside #1
|----------------------
|
| tr inside #2
--------------------------------------------
我的问题是,因此,当沿着 table 的不同页面进行分页时,可能会发生某些 tr 最终成为“孤儿”的情况。例如,如果页面以 tr #1 结尾,则 tr #2 可能会在下一页上“单独”出现(没有 rowspan = 2 的 tr)。有什么方法可以对这些 table 进行分页,只考虑那些“父”行,即带有 rowspan 的行?
我不知道有什么方法可以完全按照您的要求进行操作。话虽如此,我在下面提供了一些注释,以防它们是可以接受的替代方案。
您可以创建一个伪造的 rowspan
效果,无论您在哪个页面,它都会始终在第一列显示相关值:
但即便如此,您仍然可能会在一页底部的跨度中看到一些行,而在下一页的顶部看到跨度中的其余行。我看不出有任何解决办法(除了这个答案末尾提到的一种可能情况)。
作为替代方案,您可能需要查看 row group 扩展。但是,同样不能保证整个组总是只出现在一页上。
如果您对“假行跨度”感兴趣,这里有一个例子。它通过操纵每个页面上的 DOM 节点来工作,以便不显示第一列中的重复值(并且单元格的 border-top
行被删除)。
DataTable 本身的数据没有改变,所以如果您搜索“Edinburgh”,您仍然会找到所有 3 条记录。
var dataSet = {
"data": [
{
"id": "1",
"name": "Tiger Nixon",
"position": "System Architect",
"salary": "0,800",
"start_date": "2011/04/25",
"office": "Edinburgh",
"extn": "5421"
},
{
"id": "2",
"name": "Garrett Winters",
"position": "Accountant",
"salary": "0,750",
"start_date": "2011/07/25",
"office": "Tokyo",
"extn": "8422"
},
{
"id": "3",
"name": "Ashton Cox",
"position": "Junior Technical Author",
"salary": ",000",
"start_date": "2009/01/12",
"office": "Tokyo",
"extn": "1562"
},
{
"id": "4",
"name": "Cedric Kelly",
"position": "Senior Javascript Developer",
"salary": "3,060",
"start_date": "2012/03/29",
"office": "New York",
"extn": "6224"
},
{
"id": "5",
"name": "Airi Satou",
"position": "Accountant",
"salary": "2,700",
"start_date": "2008/11/28",
"office": "Tokyo",
"extn": "5407"
},
{
"id": "6",
"name": "Brielle Williamson",
"position": "Integration Specialist",
"salary": "2,000",
"start_date": "2012/12/02",
"office": "New York",
"extn": "4804"
},
{
"id": "7",
"name": "Herrod Chandler",
"position": "Sales Assistant",
"salary": "7,500",
"start_date": "2012/08/06",
"office": "San Francisco",
"extn": "9608"
},
{
"id": "8",
"name": "Rhona Davidson",
"position": "Integration Specialist",
"salary": "7,900",
"start_date": "2010/10/14",
"office": "Tokyo",
"extn": "6200"
},
{
"id": "9",
"name": "Colleen Hurst",
"position": "Javascript Developer",
"salary": "5,500",
"start_date": "2009/09/15",
"office": "San Francisco",
"extn": "2360"
},
{
"id": "10",
"name": "Sonya Frost",
"position": "Software Engineer",
"salary": "3,600",
"start_date": "2008/12/13",
"office": "Edinburgh",
"extn": "1667"
},
{
"id": "11",
"name": "Jena Gaines",
"position": "Office Manager",
"salary": ",560",
"start_date": "2008/12/19",
"office": "London",
"extn": "3814"
},
{
"id": "12",
"name": "Quinn Flynn",
"position": "Support Lead",
"salary": "2,000",
"start_date": "2013/03/03",
"office": "Edinburgh",
"extn": "9497"
}
]
};
var previous = '';
$(document).ready(function() {
var table = $('#example').DataTable( {
data: dataSet.data,
"order": [[ 0, 'asc' ]],
columns: [
{ title: "Office", data: "office" },
{ title: "Name", data: "name" },
//{ title: "Office2", data: "office" },
{ title: "Position", data: "position" },
{ title: "Start date", data: "start_date" },
{ title: "Salary", data: "salary" }
],
"initComplete": function(settings, json) {
// in case the initial sort order leads to
// cells needing to be altered:
processColumnNodes( $('#example').DataTable() );
}
} );
table.on( 'draw', function () {
processColumnNodes( $('#example').DataTable() );
} );
function processColumnNodes(tbl) {
// see https://datatables.net/reference/type/selector-modifier
var selector_modifier = { order: 'current', page: 'current', search: 'applied' }
var previous = '';
var officeNodes = tbl.column(0, selector_modifier).nodes();
var officeData = tbl.column(0, selector_modifier).data();
for (var i = 0; i < officeData.length; i++) {
var current = officeData[i];
if (current === previous) {
officeNodes[i].textContent = '';
officeNodes[i].setAttribute("style", "border-top:none;");
} else {
officeNodes[i].textContent = current;
}
previous = current;
}
}
} );
<script src="https://code.jquery.com/jquery-3.5.1.js"></script>
<script src="https://cdn.datatables.net/1.10.22/js/jquery.dataTables.js"></script>
<link rel="stylesheet" type="text/css" href="https://cdn.datatables.net/1.10.22/css/jquery.dataTables.css">
<link rel="stylesheet" type="text/css" href="https://datatables.net/media/css/site-examples.css">
<div style="margin: 20px;">
<table id="example" class="cell-border" style="width:100%">
</table>
</div>
当您运行上面的代码片段时,您将在第 1 页末尾的“东京”的 4 行中看到 2 行。您将在第 2 页顶部 - 但您还会看到“东京”标签。
如果您的 rowspan
尺寸始终恰好为“2”,那么您还可以将“页面长度”下拉列表中的值设置为仅使用偶数:
"lengthMenu": [ 10, 20, 50, 100 ]
这样你就不会在不同的页面上出现任何“孤儿”。