使用带有引导选项卡的固定列的数据表问题
Posted
技术标签:
【中文标题】使用带有引导选项卡的固定列的数据表问题【英文标题】:Datatables issue using fixedColumns with Bootstrap tabs 【发布时间】:2019-07-28 14:39:07 【问题描述】:我有一个包含两个引导选项卡的页面,每个选项卡包含一个数据表。只有在我将 fixedColumns 集成到两个数据表中之后,才开始出现以下行为。
在页面加载时,第一个表格正确显示,并且 fixedColumns 正常工作。当我单击表 2 的选项卡时,会显示该表,但是应该在表下方的页面内容显示在表的顶部,并且 fixedColumns 不起作用。
表 1:
表 2:
Link to the snippet,虽然我很难让它渲染任何东西。
Javascript:
$(function ()
dataRetrievalpromise()
.then(function (result)
generateTabsPromise(result)
.then(function (result)
console.log(result);
createTablehtmlPromise(result)
.then(function (result)
createTableColumnsAndDataPromise(result);
);
);
);
//Below works only when debugging/using breakpoints
$('a[data-toggle="tab"]').on('shown.bs.tab', function (e)
//$('.dTable:visible').each(function (e)
// $(this).DataTable().columns.adjust().responsive.recalc();
//);
$.fn.dataTable.tables( visible: true, api: true )
.columns.adjust()
.fixedColumns().relayout()
.responsive.recalc();
//.fixedHeader.adjust();
//.columns.adjust().redraw()
);
);
var generateTabsPromise = function (trainerJson)
var promise = new Promise(function (resolve, reject)
var result = ;
var tabInfo = [];
var allMonthsFromJson = Object.getOwnPropertyNames(trainerJson);
var tabHTML = '';
for (var i = 0; i < allMonthsFromJson.length; i++)
tabInfo.push(allMonthsFromJson[i]);
for (var i = 0; i < tabInfo.length; i++)
//Make first tab active
if (i == 0)
tabHTML += '<li class="active"><a href="' + '#tab-' + tabInfo[i] + '" data-toggle="tab"> ' + tabInfo[i] + '</a></li>';
else
tabHTML += '<li><a href="' + '#tab-' + tabInfo[i] + '" data-toggle="tab"> ' + tabInfo[i] + '</a></li>';
$(".nav-tabs").html(tabHTML);
result = firstTab: tabInfo[0], jsonData: trainerJson, allMonthsInJson: allMonthsFromJson ;
resolve(result);
);
return promise;
;
function createTableHTMLPromise(generateTabsResult)
var promise = new Promise(function (resolve, reject)
var tableHTML = '';
for (var i = 0; i < generateTabsResult.allMonthsInJson.length; i++)
if (i === 0)
tableHTML += '<div class="tab-pane active" id="' + 'tab-' + generateTabsResult.allMonthsInJson[i] + '">';
tableHTML += '<table class="table dTable" id="' + 'table-' + generateTabsResult.allMonthsInJson[i] + '" cellspacing="0" >' + '</table>';
tableHTML += '</div>';
else
tableHTML += '<div class="tab-pane" id="' + 'tab-' + generateTabsResult.allMonthsInJson[i] + '">';
tableHTML += '<table class="table dTable" id="' + 'table-' + generateTabsResult.allMonthsInJson[i] + '" cellspacing="0" >' + '</table>';
tableHTML += '</div>';
$(".tab-content").html(tableHTML);
result = allMonthsInJson: generateTabsResult.allMonthsInJson, jsonData: generateTabsResult.jsonData ;
resolve(result);
);
return promise;
function createTableColumnsAndDataPromise(createTableHTMLResult)
var promise = new Promise(function (resolve, reject)
var result = ;
var columnResult = [];
for (var i = 0; i < createTableHTMLResult.allMonthsInJson.length; i++)
var month = createTableHTMLResult.jsonData[createTableHTMLResult.allMonthsInJson[i]].metaData.month;
var numDays = createTableHTMLResult.jsonData[createTableHTMLResult.allMonthsInJson[i]].metaData.numDays;
var year = createTableHTMLResult.jsonData[createTableHTMLResult.allMonthsInJson[i]].metaData.year;
var tabName = createTableHTMLResult.allMonthsInJson[i];
columnResult.push( "data": "managerName", title: "managerName", "name": "managerName", "defaultContent": "" );
columnResult.push( "data": "employeeName", title: "employeeName", "name": "employeeName", "defaultContent": "" );
for (var j = 0; j < numDays; j++)
if (j + 1 < 10)
columnResult.push( "data": month + "-0" + String(j + 1) + "-" + year, title: month + "-" + String(j + 1) + "-" + year, "name": month + "-" + String(j + 1) + "-" + year, "defaultContent": "" );
else
columnResult.push( "data": month + "-" + String(j + 1) + "-" + year, title: month + "-" + String(j + 1) + "-" + year, "name": month + "-" + String(j + 1) + "-" + year, "defaultContent": "" );
initiateTable(columnResult, createTableHTMLResult.jsonData[tabName].data, tabName);
columnResult = [];
tabName = "";
resolve(result);
);
return promise;
function initiateTable(columnArray, tableData, tab)
//console.log("initiateTable called: " + tab);
var table = $("#table-" + tab).DataTable(
data: tableData,
"columns": columnArray,
"scrollX": true,
scrollCollapse: true,
"paging": false,
"searching": false,
"fixedColumns":
leftColumns: 2
);
var dataRetrievalpromise = function ()
var jsonData = ;
var promise = new Promise(function (resolve, reject)
//console.log('first method completed ');
resolve(jsonData =
"Jan-2019":
"metaData":
"month": "Jan",
"numDays": 31,
"year": "2019"
,
"data": [
"managerName": "Person 1",
"employeeName": "Employee 1",
"Jan-01-2019": "<span style='background-color:green;'>Event 1</span>",
"Jan-03-2019": "Event #3"
,
"managerName": "Person 1",
"employeeName": "Employee 2",
"Jan-02-2019": "Event #2"
,
"managerName": "Person 1",
"employeeName": "Employee 3",
"Jan-01-2019": "Event #1"
]
,
"Feb-2019":
"metaData":
"month": "Feb",
"numDays": 28,
"year": "2019"
,
"data": [
"managerName": "Person 1",
"employeeName": "Employee 1",
"Feb-01-2019": "<span style='background-color:green;'>Event 1</span>",
"Feb-03-2019": "Event #3"
,
"managerName": "Person 1",
"employeeName": "Employee 2",
"Feb-06-2019": "Event #2"
,
"managerName": "Person 1",
"employeeName": "Employee 3",
"Feb-01-2019": "Event #1"
]
);
);
return promise;
;
HTML:
<link href="~/Content/bootstrap.css" rel="stylesheet" />
<link href="~/Content/dataTables.bootstrap.css" rel="stylesheet" />
<link href="~/Content/fixedColumns.bootstrap.css" rel="stylesheet" />
<script src="~/Scripts/jquery-3.3.1.min.js"></script>
<div class="container">
<div role="tabpanel">
<ul class="nav nav-tabs"></ul>
<div class="tab-content"></div>
</div>
</div>
<script src="~/Scripts/bootstrap337.min.js"></script>
<script src="~/Scripts/jquery.dataTables.js"></script>
<script src="~/Scripts/dataTables.bootstrap.js"></script>
<script src="~/Scripts/dataTables.responsive.js"></script>
<script src="~/Scripts/dataTables.fixedColumns.js"></script>
<script src="~/Scripts/test2.js"></script>
【问题讨论】:
【参考方案1】:一切似乎都很好。唯一的问题是,选项卡更改的以下事件侦听器不像您在评论中提到的那样工作。
//Below works only when debugging/using breakpoints
$('a[data-toggle="tab"]').on('shown.bs.tab', function (e)
$.fn.dataTable.tables( visible: true, api: true )
.columns.adjust()
.fixedColumns().relayout()
.responsive.recalc();
);
);
这是因为您正在动态呈现 html 内容,而此时 a[data-toggle="tab"]
元素不可用。最好在渲染选项卡和表格后放置该代码。
dataRetrievalpromise().then(function (result)
generateTabsPromise(result).then(function (result)
createTableHTMLPromise(result).then(function (result)
createTableColumnsAndDataPromise(result);
$('a[data-toggle="tab"]').on('shown.bs.tab', function (e)
$.fn.dataTable.tables( visible: true, api: true )
.columns.adjust()
.fixedColumns().relayout()
.responsive.recalc();
);
);
);
);
Demo
【讨论】:
非常感谢 Prashant 的解释,它奏效了。问题已解决。以上是关于使用带有引导选项卡的固定列的数据表问题的主要内容,如果未能解决你的问题,请参考以下文章
Jinja2 和 Flask:引导选项卡仅显示第一个选项卡的内容,而不显示其余选项卡的内容