Welcome

首页 / 脚本样式 / JavaScript / Vue 固定头 固定列 点击表头可排序的表格组件

原理是将原table的指定行,指定列clone一份放在其上
实现代码如下:
<template><div> <div id="divBox1" :style="{height:height}"><table id="tbTest1" cellpadding="0" cellspacing="0" style="text-align:center;background:rgba(244,249,255,0.4);"> <tr><th v-for="item in thead" @click="sortBy(item)"> {{item}}<img style="width:0.16rem;height:0.20rem;margin-left:4px;" :src="filterUrl" alt="" v-if="$index!=0" data-img="{{filterUrl}}"></th> </tr> <tr v-for="row in tableRows | orderBy sortBykey sortOrders[sortKey]"><td style="overflow:hidden;white-space:nowrap;" v-for="item in gridColumns" v-html="row[item] | numberFilter" :id="$parent.$index"></td> </tr></table> </div></div> </template> <script>/*eslint-disable*/var ofixed_table_st = window.setTimeout;var hasLeft = "";var hasHead = "";window.setTimeout = function(fRef, mDelay) { if(typeof fRef == "function") {var argu = Array.prototype.slice.call(arguments, 2);var f = (function() { fRef.apply(null, argu);});return ofixed_table_st(f, mDelay); } return ofixed_table_st(fRef, mDelay);};function oFixedTable(id, obj, _cfg) { this.id = id; this.obj = obj; this.box = this.obj.parentNode; this.config = {fixHead: _cfg.fixHead || true,rows: _cfg.rows || 1,cols: _cfg.cols || 0,background: _cfg.background || "#ffffff",zindex: _cfg.zindex || 10 }; window.setTimeout(this._fixTable, 100, this);}oFixedTable.prototype._fixTable = function(_) { if(_.obj.rows.length <= 0) {return false; } var hasLeft = _.buildLeft(); var hasHead = _.buildHead(); _.box.onscroll = function() {if(_.divHead != null) { _.divHead.scrollLeft = this.scrollLeft;}if(_.divLeft != null) { _.divLeft.scrollTop = this.scrollTop;} }; if(hasHead && hasLeft) {_.buildTopLeft(); }};oFixedTable.prototype.buildHead = function() { console.log(2222222222222222222) var _ = this; var strDivId = _.id + "_div_head"; var strTbId = _.id + "_tb_header"; var div = document.createElement("div"); div.id = strDivId; div.style.cssText = "position:absolute;overflow:hidden;z-index:" + (_.config.zindex + 1) + ";"; div.innerHTML = "<table id="" + strTbId + "" cellpadding="0" cellspacing="0" style="background:" + _.config.background + ";"></table>"; _.box.insertBefore(div, _.obj); _.divHead = div; _.tbHead = document.getElementById(strTbId); //判断是否出现纵向滚动条,若出现,高度减去滚动条宽度 16px var sw = _.obj.offsetHeight > _.box.offsetHeight ? 0 : 0; _.divHead.style.width = (_.box.offsetWidth - sw) + "px"; _.tbHead.style.textAlign = _.obj.style.textAlign; _.tbHead.style.width = _.obj.offsetWidth + "px"; var hasHead = false; if(_.config.fixHead && _.obj.tHead != null) {var tHead = _.obj.tHead;_.tbHead.appendChild(tHead.cloneNode(true));hasHead = true; } else {for(var i = 0; i < _.config.rows; i++) { var row = _.obj.rows[i]; if(row != null) {_.tbHead.appendChild(row.cloneNode(true));hasHead = true; }} } return hasHead;};oFixedTable.prototype.buildLeft = function() { var _ = this; if(_.config.cols <= 0) {return false; } var strDivId = _.id + "_div_left"; var strTbId = _.id + "_tb_left"; var div = document.createElement("div"); div.id = strDivId; div.style.cssText = "position:absolute;overflow:hidden;z-index:" + _.config.zindex + ";box-shadow: #dddddd 2px 0px 2px;width: 2rem;"; div.innerHTML = "<table id=" + strTbId + " cellpadding="0" cellspacing="0" style="background:" + _.config.background + ";width: 2rem;"></table>"; _.box.insertBefore(div, _.obj); _.divLeft = div; _.tbLeft = document.getElementById(strTbId); _.tbLeft.style.textAlign = _.obj.style.textAlign; //判断是否出现横向滚动条,若出现,高度减去滚动条高度 16px var sw = _.obj.offsetWidth > _.box.offsetWidth ? 0 : 0; _.divLeft.style.height = (_.box.offsetHeight - sw) + "px"; var hasLeft = false; for(var i = 0, rows = _.obj.rows.length; i < rows; i++) {var row = _.tbLeft.insertRow(_.tbLeft.rows.length);row.style.cssText = _.obj.rows[i].style.cssText;for(var j = 0; j < _.config.cols; j++) { var cell = _.obj.rows[i].cells[j]; if(cell != null) {row.appendChild(cell.cloneNode(true));cell.style.cssText = _.obj.rows[i].cells[j].style.cssText;hasLeft = true; }} } return hasLeft;};oFixedTable.prototype.buildTopLeft = function() { var _ = this; var strDivId = _.id + "_div_top_left"; var strTbId = _.id + "_tb_top_left"; var div = document.createElement("div"); div.id = strDivId; div.style.cssText = "position:absolute;overflow:hidden;z-index:" + (_.config.zindex + 2) + ";box-shadow: #dddddd 2px 0px 2px;width: 2rem;"; div.innerHTML = "<table id="" + strTbId + "" cellpadding="0" cellspacing="0" style="background:" + _.config.background + ";"></table>"; _.box.insertBefore(div, _.obj); var tbTopLeft = document.getElementById(strTbId); tbTopLeft.style.textAlign = _.obj.style.textAlign; for(var i = 0; i < _.config.rows; i++) {var row = tbTopLeft.insertRow(tbTopLeft.rows.length);row.style.cssText = _.obj.rows[i].style.cssText;for(var j = 0; j < _.config.cols; j++) { var cell = _.obj.rows[i].cells[j]; if(cell != null) {row.appendChild(cell.cloneNode(true));cell.style.cssText = _.obj.rows[i].cells[j].style.cssText;hasLeft = true; }} }};export default{ // 接收父组件传过来的参数 props: ["tableRows", "gridColumns", "thead", "store", "height", "singleData"], // 监控 watch: {"tableRows": function (val) { var self = this // 明星店铺页面时动态调整店铺名所在列的宽度s if (self.store) {document.querySelectorAll("table td:nth-child(3)")[0].style.width = 3 + "rem"document.querySelectorAll("table th:nth-child(3)")[0].style.width = 3 + "rem" } var length = self.gridColumns.length document.getElementById("tbTest1").style.width = 2 * length + "rem" setTimeout(function () {if (self.singleData) { document.getElementById("ofix1_tb_left").classList.add("ofix1_tb_left")}document.querySelectorAll("#ofix1_tb_left td")[0].style.width = 2 + "rem"var tbObj = document.getElementById("ofix1_tb_header")tbObj.addEventListener("click",function (event) { if(event.target.tagName === "TH"){self.sortBy(event.target.innerText, event) }}) }, 101)} }, data: function() {var sortOrders = {}this.gridColumns.forEach(function (key) { sortOrders[key] = 1})return { sortKey: "", filterUrl: "./static/img/indus/filter1.png", sortOrders: sortOrders} }, methods: {sortBykey: function (a, b) { return parseFloat(a[this.sortKey]) - parseFloat(b[this.sortKey]) console.log("11111111111")},sortBy: function (key, event) { // 每一次排序之前所有的图片重置 var imgDom = document.querySelectorAll("#ofix1_tb_header th img") for (var x = 0; x < imgDom.length; x++) {imgDom[x].setAttribute("src", "./static/img/indus/filter1.png") } // 排序 var activeTheadIndex = 0 for (var i = 0; i < this.thead.length; i++) {if (this.thead[i] === key) { activeTheadIndex = i} } this.sortKey = this.gridColumns[activeTheadIndex] this.sortOrders[this.gridColumns[activeTheadIndex]] = this.sortOrders[this.gridColumns[activeTheadIndex]] * -1 // 排序时同步改变标识图片 if (this.sortOrders[this.gridColumns[activeTheadIndex]] > 0) {event.target.getElementsByTagName("img")[0].setAttribute("src", "./static/img/indus/filter2.png") } else {event.target.getElementsByTagName("img")[0].setAttribute("src", "./static/img/indus/filter3.png") } // 排序时同步改变左边第一列的内容 setTimeout(function(){var tdDom = document.querySelectorAll("#tbTest1 tr td:nth-child(1)")var tdDomLeft = document.querySelectorAll("#ofix1_tb_left td")for (var y = 0; y < tdDom.length; y++) { tdDomLeft[y].innerHTML = tdDom[y].innerHTML} },0)} }, filters: {numberFilter: function (value) { if (value == 0) {return "0" } else if (!value) {return "/" } else {return value }} }, components: { }, ready: function() {var ofix1 = new oFixedTable("ofix1", document.getElementById("tbTest1"), { rows: 1, cols: 1}) }, created () { }} </script> <style lang="scss" scoped>#divBox1{ overflow:auto; width:100%; font-size: 0.28rem;}#ofix1_div_left{ box-shadow: #dddddd 2px 0px 2px; width: 2rem;}table { table-layout : fixed;}table td,table th { width: 2rem; line-height: 1rem; height: 1rem; padding: 0; color: #999999; overflow: hidden; white-space: nowrap; /*vertical-align: middle;*/}table th{ background: rgba(188,219,255,0.4); color: #999; font-size: .28rem; font-weight: normal;}table th:nth-child(1){ box-shadow: #dddddd 2px 0px 0px;}.ofix1_tb_left tr td:nth-child(1){ /*display: inline-block;*/ text-align: left;}#ofix1_div_top_left{ box-shadow: #dddddd 2px 0px 2px;}#tbTest1 tr td:nth-child(1){ box-shadow: #dddddd 2px 0px 0px;}#tbheader td { background: #fff;} </style> 
父组件调用实例:
<template><table-locked :table-rows="tableData" :grid-columns="gridColumns" :thead="thead" :height="height"></table-locked> </template> import TableLocked from "../../common/TableLocked.vue" export default{ components: {TableLocked}, data () { data.gridColumns = ["brand", "product_count", "averagePrice", "sales", "huang_sale_per", "sale_per", "sales_amount", "huang_sale_amount_per", "sales_amount_per", "score_num", "scort_good_per"]data.thead = ["品类", "产品种类", "均价", "销量", "销量环比", "销量占比", "销额(万元)", "销额环比", "销额占比", "评论总数", "好评率"] } }
以上所述是小编给大家介绍的Vue 固定头 固定列 点击表头可排序的表格组件,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对脚本之家网站的支持!