From 5cdcbf484ad9b693cc3a99eb2aa4f8eedee6cbef Mon Sep 17 00:00:00 2001 From: zq <136432190602163.com> Date: Thu, 29 May 2025 14:42:35 +0800 Subject: [PATCH] =?UTF-8?q?=E4=B8=80=E4=BA=9B=E8=A1=A8=E6=A0=BC=E7=9A=84?= =?UTF-8?q?=E5=B0=9D=E8=AF=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/mixins/tableResizeMixin copy.js | 197 ++++++ src/views/super/Ranking/RankBatchList copy.vue | 806 +++++++++++++++++++++++++ src/views/super/Ranking/RankBatchList.vue | 337 ++--------- 3 files changed, 1061 insertions(+), 279 deletions(-) create mode 100644 src/mixins/tableResizeMixin copy.js create mode 100644 src/views/super/Ranking/RankBatchList copy.vue diff --git a/src/mixins/tableResizeMixin copy.js b/src/mixins/tableResizeMixin copy.js new file mode 100644 index 0000000..c307212 --- /dev/null +++ b/src/mixins/tableResizeMixin copy.js @@ -0,0 +1,197 @@ +// 在有边框,可以进行拖拽的情况下,实现宽度跟随变化(不太行,基本pass) +import ResizeObserver from 'resize-observer-polyfill'; +import { + debounce +} from 'lodash'; + +export default { + data() { + return { + tableResizeObserver: null, + tableWidth: 0, + isDragging: false, // 新增拖拽状态标志 + lastDragTime: 0 // 记录最后一次拖拽时间 + }; + }, + + methods: { + // 销毁观察者 + destroyTableResizeObserver() { + if (this.tableResizeObserver) { + this.tableResizeObserver.disconnect(); + this.tableResizeObserver = null; + } + }, + // 初始化监听 + initTableResizeObserver(tableRef, containerRef) { + this.$nextTick(() => { + const container = containerRef ? this.$refs[containerRef] : this.$el; + if (!container) return; + + this.destroyTableResizeObserver(); + + this.tableResizeObserver = new ResizeObserver( + debounce(entries => { + if (this.isDragging || Date.now() - this.lastDragTime < 300) return; + + const entry = entries[0]; + const newWidth = entry.contentRect.width; + + if (Math.abs(newWidth - this.tableWidth) > 5) { + this.tableWidth = newWidth; + this.forceSyncTableLayout(tableRef); + } + }, 100) + ); + + this.tableResizeObserver.observe(container); + }); + }, + + + // 强制同步表头和表体布局 + forceSyncTableLayout(tableRef) { + const table = this.$refs[tableRef].$refs.guiptable; + if (!table) return; + + // 先获取当前实际宽度 + const currentWidths = this.getCurrentColumnWidths(table); + + // 计算理论宽度 + const calculatedWidths = this.calculateColumnWidths(); + if (!calculatedWidths) return; + + this.$nextTick(() => { + // 1. 设置列定义的宽度 + table.columns.forEach(column => { + const prop = column.property || column.id; + column.width = currentWidths[prop] || calculatedWidths[prop]; + }); + + // 2. 同步DOM宽度 + this.updateDOMWidths(table); + + // 3. 特殊处理固定列 + this.handleFixedColumns(table); + + // 4. 强制重新布局(两次确保生效) + table.doLayout(); + setTimeout(() => table.doLayout(), 50); + }); + }, + + // 获取当前DOM中的实际列宽 + getCurrentColumnWidths(table) { + const widths = {}; + const headerCells = table.$el.querySelectorAll('.el-table__header .cell'); + + headerCells.forEach(cell => { + const col = cell.closest('th'); + if (col && col.style.width) { + const prop = col.getAttribute('data-property') || + col.querySelector('.cell').getAttribute('data-property'); + if (prop) { + widths[prop] = parseInt(col.style.width); + } + } + }); + + return widths; + }, + + // 更新DOM元素宽度 + updateDOMWidths(table) { + const headerCols = table.$el.querySelectorAll('.el-table__header col'); + const bodyCols = table.$el.querySelectorAll('.el-table__body col'); + const headerCells = table.$el.querySelectorAll('.el-table__header th'); + const bodyCells = table.$el.querySelectorAll('.el-table__body td'); + + table.columns.forEach((column, index) => { + const width = column.width; + if (!width) return; + + // 设置colgroup中的宽度 + if (headerCols[index]) { + headerCols[index].width = width; + // headerCols[index].style.width = `${width}px`; + headerCols[index].style.setProperty('width', `${width}px`, 'important'); + + } + if (bodyCols[index]) { + bodyCols[index].width = width; + // bodyCols[index].style.width = `${width}px`; + bodyCols[index].style.setProperty('width', `${width}px`, 'important'); + + } + + // 设置实际单元格宽度 + if (headerCells[index]) { + // headerCells[index].style.width = `${width}px`; + headerCells[index].style.setProperty('width', `${width}px`, 'important'); + headerCells[index].style.minWidth = `${width}px`; + + } + if (bodyCells[index]) { + // bodyCells[index].style.width = `${width}px`; + bodyCells[index].style.setProperty('width', `${width}px`, 'important'); + bodyCells[index].style.minWidth = `${width}px`; + } + + }); + }, + + // 处理固定列 + handleFixedColumns(table) { + const fixedLeft = table.$el.querySelector('.el-table__fixed'); + const fixedRight = table.$el.querySelector('.el-table__fixed-right'); + + if (fixedLeft) fixedLeft.style.height = 'auto'; + if (fixedRight) fixedRight.style.height = 'auto'; + }, + + // 处理拖拽开始 + handleHeaderDragStart() { + this.isDragging = true; + }, + + // 处理拖拽结束 + handleHeaderDragEnd(newWidth, oldWidth, column) { + this.isDragging = false; + this.lastDragTime = Date.now(); + + // 更新列比例配置 + const table = this.$refs[Object.keys(this.$refs).find(k => k.startsWith('myTable'))]; + if (!table || !this.tableWidth) return; + + const availableWidth = this.tableWidth - 20; + const newRatio = newWidth / availableWidth; + + // 更新当前列的ratio + if (this.columnRatios && column.property) { + this.columnRatios[column.property] = newRatio; + } + + // 重新平衡其他列的比例 + this.balanceColumnRatios(column.property); + }, + + // 平衡其他列的比例 + balanceColumnRatios(changedColumnProp) { + if (!this.columnRatios) return; + + const otherColumns = Object.keys(this.columnRatios) + .filter(prop => prop !== changedColumnProp); + + const totalUsedRatio = Object.values(this.columnRatios).reduce((sum, r) => sum + r, 0); + const overflow = totalUsedRatio - 1; + + if (overflow > 0) { + const otherTotalRatio = otherColumns.reduce((sum, prop) => sum + this.columnRatios[prop], 0); + + otherColumns.forEach(prop => { + this.columnRatios[prop] -= (this.columnRatios[prop] / otherTotalRatio) * overflow; + }); + } + } + } +}; \ No newline at end of file diff --git a/src/views/super/Ranking/RankBatchList copy.vue b/src/views/super/Ranking/RankBatchList copy.vue new file mode 100644 index 0000000..19aec9e --- /dev/null +++ b/src/views/super/Ranking/RankBatchList copy.vue @@ -0,0 +1,806 @@ + + + \ No newline at end of file diff --git a/src/views/super/Ranking/RankBatchList.vue b/src/views/super/Ranking/RankBatchList.vue index af80f79..19aec9e 100644 --- a/src/views/super/Ranking/RankBatchList.vue +++ b/src/views/super/Ranking/RankBatchList.vue @@ -31,22 +31,15 @@
- - - - - - - - + ref="elTable" :loading="tableLoading"> +