微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

vue2.0结合DataTable插件实现表格动态刷新的方法详解

本文实例讲述了vue2.0结合DataTable插件实现表格动态刷新的方法分享给大家供大家参考,具体如下:

产品提出的需求是这样的,很普通的一个统计server端task完成率和状态的表格,要自动刷新其中的数据,并且当单个task完成的时候report给server端,看起来好easy好easy的一个需求啊!且听我说完哈!

我这边使用的是框架是vue,表格自然用v-for渲染,然后我们这边分页搜索神马的都是前端弄,也就是说后端只管把一大坨数据塞到前端,然后前端自己组装分页器和完成模糊搜索,所以啊,我之前用的是DataTable这个插件,组装好的表格效果如下,看着没毛病哈!

可是涉及到自动刷新就有问题了,因为每次获取数据都是全量数据,用dataTable组装表格的话,就必须要组装好的表格destroy掉,然后再v-for再DataTable()组装..页面会一直一直闪!体验好差的说!

我只想出了一个比较笨的方法解决这个局部刷新的问题,大家要是有更好的方法一定要告诉我!!上代码

1.v-for只渲染不变的数据,比如名字备注之类的,一直刷新的字段比如状态和完成率都为空,就这样,只用DataTable首次渲染表格

2.setRefresh是一个定时器,每隔1s就递归调用一次自己,query全量数据,存放到originTableList里

3.updateRefreshStatus是用原生的js去获取每行的dom,然后innerText去改变其值

4.reportTaskComplete是当当前这个task完成率达到100%就汇报给server

5.checkTaskRefresh是递归检查所有的任务,把完成的任务放到completeTaskList,如果全都完成了就把定时器清除掉

6.beforeRouteLeave是vue router的方法,在离开路由之后清除计时器

template

rush:xhtml;">

js

rush:js;"> methods: { initRecordTable: function(){ $('#main-table').DataTable({ "paging": true,// 开启分页 "pageLength": 10,//每页显示数量 "lengthChange": true,//是否允许用户改变表格每页显示的记录数 "searching": true,//搜索 "ordering": true,//排序 "info": true,//左下角 从 1 到 5 /共 23 条数据 "autoWidth": true,// "scrollX": "100%",//表格的宽度 // "scrollY": "200px",//表格的高度 "scrollXInner": "100%",//表格的内容宽度 // "bScrollCollapse":true,//当显示的数据不足以支撑表格的认的高度时,依然显示纵向的滚动条。(认是false) "aaSorting": [ [3,'asc'] ],"language": { "sInfoEmpty": "没有数据","sZeroRecords": "没有查找到满足条件的数据","sInfo": "从 _START_ 到 _END_ /共 _TOTAL_ 条数据","sLengthMenu": "每页显示 _MENU_ 条记录","sInfoFiltered": "(从 _MAX_ 条数据中检索)","oPaginate": { "sFirst": "首页","sPrevIoUs": "前一页","sNext": "后一页","sLast": "尾页" } },}); },initQuery: function(){ // status 和 rate两个字段是实时刷新的 // dataTable摧毁和tableList赋值都砸在promise里完成 // tableList只初始化的时候赋值一次 然后就不动了 用原生js去改变表格内的status字段 let mySelf = this; let callback = function(){ if($('#main-table').DataTable()){ $('#main-table').DataTable().destroy() } mySelf.tableList = util.deepClone(mySelf.originTableList); } let queryTablePromise = mySelf.queryTable(callback); let promiseList = []; mySelf.clearRefresh(); promiseList.push(queryTablePromise); Promise.all(promiseList).then(function (result) { console.log('ajax全部执行完毕:' + JSON.stringify(result)); // ["Hello","World"] //renderTable函数只在首次进入页面调用 1.毁掉dataTable插件 2.加载一次表格更新状态和完成率 3.调用自动刷新 mySelf.renderTable(); mySelf.updateRefreshStatus(); mySelf.setRefresh(); }); },switchRefreshStatus: function(){ let mySelf = this; let status = mySelf.refresh.status; let text = (status==true)?'关闭':'开启'; let confirmCallback = null; if (status==true){ confirmCallback = function(){ mySelf.refresh.status = false; } } else{ confirmCallback = function(){ mySelf.refresh.status = true; mySelf.setRefresh(); } } util.showConfirm('确认要' + text + '自动刷新么?',confirmCallback); },checkTaskRefresh: function(){ let mySelf = this; let originTableList = mySelf.originTableList; let taskAllComplete = true; // console.log(JSON.stringify(mySelf.originTableList)); originTableList.forEach(function(item,index,array){ let completeTaskList = mySelf.refresh.completeTaskList; let completerate = item.completerate; //当前task完成 report给后端 if (Number.parseInt(completerate) == 1){ // 若任务完成列表 没有这个TaskId 则发送请求 if (!completeTaskList.includes(item.id)){ console.log(item.id + "任务完成了!并且不存在于任务完成列表,现在发送完成请求!"); mySelf.reportTaskComplete(item.id); mySelf.refresh.completeTaskList.push(item.id); } } else{ taskAllComplete = false; } }); if(taskAllComplete){ console.log('全部任务都完成了!') return true; } return false; },setRefresh: function(){ let mySelf = this; let status = mySelf.refresh.status; let interval = mySelf.refresh.interval; // 如果所有任务都完成了 则停止发送ajax请求 并更新最后一次 if (mySelf.checkTaskRefresh()){ console.log('更新最后一次表格!') mySelf.updateRefreshStatus(); return false; } // console.log('refresh') if (status){ mySelf.refresh.timer = setTimeout(function(){ let queryTablePromise = mySelf.queryTable(); let promiseList = []; promiseList.push(queryTablePromise); Promise.all(promiseList).then(function (result) { console.log('ajax全部执行完毕:' + JSON.stringify(result)); // ["Hello","World"] mySelf.updateRefreshStatus(); mySelf.setRefresh(); }); },interval); } else{ mySelf.clearRefresh(); } },updateRefreshStatus: function(){ console.log('更新刷新状态') let mySelf = this; let mainTable = document.getElementById("main-table"); let originTableList = mySelf.originTableList; originTableList.forEach(function(item,array){ let trClassName = "id-" + item.id; // console.log(trClassName) // 获取当前页面展示的所有tr let trDom = mainTable.getElementsByClassName(trClassName)[0]; // console.log(trDom) // 局部刷新个别字段 if (trDom){ let tdrate = trDom.getElementsByClassName("rate")[0]; let tdStatus = trDom.getElementsByClassName("status")[0]; tdrate.innerText = item.completerate; tdrate.className = (item.status == "1")?"text-info rate":((item.status == "2")?"text-success rate":"text-danger rate"); tdStatus.innerText = (item.status == "1")?"刷新中":((item.status == "2")?"刷新完成":"刷新失败"); tdStatus.className = (item.status == "1")?"text-info status":((item.status == "2")?"text-success status":"text-danger status"); } }); },clearRefresh: function(){ let mySelf = this; console.log('clear timer'); clearTimeout(mySelf.refresh.timer); },queryTable: function(callback){ let mySelf = this; let promise = new Promise(function (resolve,reject) { let url = pars.domain + "/api.PHP?Action=xxxxxxx&t=" + (new Date).getTime(); $.get(url,function(res) { if (res.code == 0) { let resData = res.list; resData.forEach(function(item,array){ let info = item.info; let completeCount = info.completeCount; let total = info.count; item.completerate = ((completeCount/total)*100).toFixed(2) + "%"; }); // console.log(JSON.stringify(resData)) mySelf.originTableList = resData; if (callback){ callback(); } resolve('queryTable完成!'); } else{ util.showDialog('error',"接口调用失败,报错信息为:" + res.message); } },"json"); }); return promise; },renderTable: function(){ let mySelf = this; mySelf.$nextTick(function(){ mySelf.initRecordTable(); util.hideLoading(); }) } },beforeRouteLeave (to,from,next){ let mySelf = this; mySelf.clearRefresh(); next(); },

整体的效果如下,功能整体是实现了,但是感觉好笨的说,大家要是有好办法一定要告诉我哈!!

希望本文所述对大家vue.js程序设计有所帮助。

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐