hook函数封装
export const useTableColumnWidth = _this => {
const { refTable } = _this
const columnWidthObj = ref ( )
const getTableColumnWidth = cb => {
nextTick ( ( ) => {
columnWidthObj. value = { }
const tableEle = refTable?. refBaseTable?. $el
if ( ! tableEle) return
const rows = tableEle. querySelectorAll (
'.el-table__body-wrapper .el-table__row'
)
if ( ! rows. length) return
const hideRows = tableEle. querySelectorAll ( '.hidden-columns div' )
const cells = rows[ 0 ] . cells
Array. from ( cells) . forEach ( ( cell, i ) => {
let maxVal = 0
const prop = hideRows[ i] . getAttribute ( 'data-prop' )
if ( ! prop) return
Array. from ( rows) . forEach ( row => {
const cellsEle = row. cells[ i]
cellsEle. style. display = 'inline-block'
cellsEle. style. width = '100vw'
const cellEle = cellsEle. querySelector ( '.cell' )
cellEle. style. display = 'inline-block'
maxVal = Math. max (
cellEle. getBoundingClientRect ( ) . width + 1 ,
maxVal
)
cellsEle. style. display = 'table-cell'
cellsEle. style. width = 'auto'
cellEle. style. display = 'block'
} )
columnWidthObj. value[ prop] = Math. ceil ( maxVal)
} )
cb ( columnWidthObj. value)
} )
}
return {
columnWidthObj,
getTableColumnWidth
}
}
自定义组件封装
BaseTable
< template>
< el-table
ref = " refBaseTable"
class = " dy-list-table"
element-loading-background = " rgba(0, 0, 0, 0.8)"
:stripe = " stripe"
border
:height = " height"
: = " $attrs"
>
< slot />
</ el-table>
</ template>
< script setup >
defineProps ( {
height : {
type : String,
default : '100%'
} ,
stripe : {
type : Boolean,
default : true
}
} )
const refBaseTable = ref ( null )
defineExpose ( {
refBaseTable
} )
</ script>
TableColumn
< template>
< el-table-column
v-if = " hasDefaultSlot"
:min-width = " getMinWidth()"
:width = " cWidth"
:data-prop = " dataProp"
: = " $attrs"
>
< template #default = " scope" >
< slot v-bind = " scope" />
</ template>
</ el-table-column>
< el-table-column
v-else
:min-width = " getMinWidth()"
:width = " cWidth"
:data-prop = " dataProp"
: = " $attrs"
/>
</ template>
< script setup >
const props = defineProps ( {
dataProp : {
type : String,
default : ''
} ,
width : {
type : [ String, Number] ,
default : ''
}
} )
const $attrs = useAttrs ( )
const slots = useSlots ( )
const cWidth = ref ( props. width)
const hasDefaultSlot = computed ( ( ) => ! ! slots. default)
const getMinWidth = ( ) => {
const minWidth = g_utils. calcTextWidth ( $attrs. label)
let actualWidth = $attrs[ 'column-width' ]
? Math. max ( minWidth, $attrs[ 'column-width' ] )
: minWidth
if ( $attrs[ 'show-overflow-tooltip' ] !== undefined ) {
actualWidth += 2
}
if ( $attrs[ 'column-type' ] === 'width' ) {
cWidth. value = actualWidth + 10
return ''
} else {
if ( $attrs. sortable !== undefined ) actualWidth += 24
return actualWidth
}
}
</ script>
动态计算文本的宽度
export const calcTextWidth = (
str = '' ,
style = {
fontSize : '16px' ,
fontWeight : 'bold'
}
) => {
const span = document. createElement ( 'span' )
span. innerText = str
span. style. fontSize = style. fontSize
span. style. fontWeight = style. fontWeight
document. body. appendChild ( span)
const width = span. getBoundingClientRect ( ) . width + 25
document. body. removeChild ( span)
return Math. ceil ( width)
}
使用教程
< BaseTable
ref = " refContentTable"
v-loading = " loading"
:data = " tableData"
row-key = " imei"
style = " margin-top : 10px"
>
< TableColumn
align = " center"
prop = " imei"
data-prop = " imei"
:label = " $t('public.IMEI')"
:column-width = " columnWidthObj.imei"
/>
</ BaseTable>
< script setup >
const loading = ref ( false )
const refContentTable = ref ( null )
const tableData = ref ( [ ] )
const columnWidthObj = ref ( { } )
const getDeviceList = ( ) => {
loading. value = true
apiDeviceList ( {
pageNum : pageNum. value,
pageSize : pageSize. value,
... listParams. value
} )
. then ( ( { code, data} ) => {
if ( code === '200' && data) {
tableData. value = data. items
useTableColumnWidth ( {
refTable : refContentTable. value
} ) . getTableColumnWidth ( data => {
columnWidthObj. value = data
} )
}
} )
. finally ( ( ) => {
loading. value = false
} )
}
onMounted ( ( ) => {
getDeviceList ( )
} )
</ script>
最终效果图