Vue 自適應(yīng)高度表格的實(shí)現(xiàn)方法
前言
示例版本為 Element-ui 2.13.1 + Vue 2.6.11

本人是做后臺(tái)開(kāi)發(fā)的,由于公司業(yè)務(wù)要求需要將前后臺(tái)模塊進(jìn)行分離,兩年前選擇使用vue-element-admin 項(xiàng)目進(jìn)行前臺(tái)的開(kāi)發(fā),該框架集成了很多功能,特別適合對(duì) Vue 很陌生的新手,公司項(xiàng)目組成員接受程度普遍較高。
在使用過(guò)程中 表格 是必不可少的一個(gè)控件,用于展示數(shù)據(jù),單頁(yè)數(shù)據(jù)量過(guò)多就會(huì)導(dǎo)致瀏覽器自動(dòng)生成右側(cè)滾動(dòng)條。

如果頁(yè)面有頭部信息或查詢按鈕,移動(dòng)滾動(dòng)條后會(huì)遮擋住這些操作和信息內(nèi)容。

Element-UI 中的 el-table 提供了設(shè)置高度的選項(xiàng),在代碼中設(shè)置 height 屬性就可以現(xiàn)在表格的高度,數(shù)據(jù)量過(guò)多也只會(huì)在表格內(nèi)部生成滾動(dòng)條,而不是整個(gè)頁(yè)面生成滾動(dòng)條。

但是這個(gè)高度需要固定的數(shù)值,不同的分辨率或者縮放后的瀏覽器使用固定高度后,不能滿足只在 el-table 內(nèi)部生成滾動(dòng)條的條件。

想要滿足上述條件就需要使用 v-adaptive 指令了。
Vue 自定義指令
你可能會(huì)好奇 v-adaptive 是在哪里來(lái)的?它是自定義的指令,設(shè)置表格高度需要對(duì)普通 DOM 元素進(jìn)行底層操作。Vue 除了核心功能默認(rèn)內(nèi)置的指令 ( v-model 和 v-show ),也允許注冊(cè)自定義指令,相關(guān) Api 可以查看 官方文檔 。
v-adaptive
新建包名 src/directive/el-table ,創(chuàng)建 adaptive.js 。頁(yè)面縮放的監(jiān)聽(tīng)是使用的 element-ui 中的 resize-event ,將 addResizeListener 和 removeResizeListener 引入進(jìn)來(lái)。自定義指令要用到的鉤子函數(shù):
- bind:只調(diào)用一次,指令第一次綁定到元素時(shí)調(diào)用。在這里可以進(jìn)行一次性的初始化設(shè)置。
- inserted:被綁定元素插入父節(jié)點(diǎn)時(shí)調(diào)用 (僅保證父節(jié)點(diǎn)存在,但不一定已被插入文檔中)。
- unbind:只調(diào)用一次,指令與元素解綁時(shí)調(diào)用。
import { addResizeListener, removeResizeListener } from 'element-ui/src/utils/resize-event'
// 設(shè)置表格高度
const doResize = async(el, binding, vnode) => {
// 獲取表格Dom對(duì)象
const { componentInstance: $table } = await vnode
// 獲取調(diào)用傳遞過(guò)來(lái)的數(shù)據(jù)
const { value } = binding
if (!$table.height) {
throw new Error(`el-$table must set the height. Such as height='100px'`)
}
// 獲取距底部距離(用于展示頁(yè)碼等信息)
const bottomOffset = (value && value.bottomOffset) || 30
if (!$table) return
// 計(jì)算列表高度并設(shè)置
const height = window.innerHeight - el.getBoundingClientRect().top - bottomOffset
$table.layout.setHeight(height)
$table.doLayout()
}
export default {
// 初始化設(shè)置
bind(el, binding, vnode) {
// 設(shè)置resize監(jiān)聽(tīng)方法
el.resizeListener = async() => {
await doResize(el, binding, vnode)
}
// 綁定監(jiān)聽(tīng)方法到addResizeListener
addResizeListener(window.document.body, el.resizeListener)
},
// 綁定默認(rèn)高度
async inserted(el, binding, vnode) {
await doResize(el, binding, vnode)
},
// 銷毀時(shí)設(shè)置
unbind(el) {
// 移除resize監(jiān)聽(tīng)
removeResizeListener(el, el.resizeListener)
}
}
接下來(lái),需要將寫好的邏輯綁定到 Vue 中,在同一目錄下新建 index.js :
import adaptive from './adaptive'
const install = function(Vue) {
// 綁定v-adaptive指令
Vue.directive('adaptive', adaptive)
}
if (window.Vue) {
window['adaptive'] = adaptive
// eslint-disable-next-line no-undef
Vue.use(install)
}
adaptive.install = install
export default adaptive
在單頁(yè)面使用
指令相關(guān)代碼已經(jīng)寫好了,接下來(lái)就是該如何使用了。找到想要設(shè)置表格自適應(yīng)高度的 vue 文件,在 script 標(biāo)簽下引入自定義的指令并綁定。
import adaptive from '@/directive/el-table'
export default {
name:'Test',
directives: { adaptive },
... ...
}
然后找到表格所在的標(biāo)簽添加指令相關(guān)的代碼:
<el-table
ref="table"
// 自定義指令,bottomOffset 代表距離底部的距離
v-adaptive="{bottomOffset: 85}"
// 高度屬性,100無(wú)具體意義,僅為初始值,不可省略
height="100px"
>
... ...
</table>
全局使用
如果存在多個(gè)頁(yè)面需要設(shè)置自適應(yīng)高度,為了減少使用指令的復(fù)雜度,我們可以在 main.js 中全局引入自定義的指令,上述 script 的內(nèi)容就不需要在每個(gè)頁(yè)面進(jìn)行寫入了。
import adaptive from './directive/el-table' Vue.use(adaptive)
結(jié)尾
源碼放在 GitHub 上了,希望可以幫助到你。
到此這篇關(guān)于Vue 自適應(yīng)高度表格的實(shí)現(xiàn)方法的文章就介紹到這了,更多相關(guān)Vue 自適應(yīng)高度表格內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
基于vue實(shí)現(xiàn)新聞自下往上滾動(dòng)效果(示例代碼)
這篇文章主要介紹了vue新聞自下往上滾動(dòng)效果,當(dāng)鼠標(biāo)鼠標(biāo)放上暫停滾動(dòng),鼠標(biāo)移出繼續(xù)滾動(dòng),本文結(jié)合示例代碼給大家介紹的非常詳細(xì),需要的朋友可以參考下2022-04-04
vue動(dòng)態(tài)子組件的兩種實(shí)現(xiàn)方式
這篇文章主要介紹了vue動(dòng)態(tài)子組件的兩種實(shí)現(xiàn)方式,非常不錯(cuò),具有一定的參考借鑒價(jià)值,需要的朋友可以參考下2019-09-09
vuejs實(shí)現(xiàn)折疊面板展開(kāi)收縮動(dòng)畫(huà)效果
這篇文章主要介紹了vuejs實(shí)現(xiàn)折疊面板展開(kāi)收縮動(dòng)畫(huà)效果,文中通過(guò)代碼給大家分享兩種情況介紹的非常詳細(xì),具有一定的參考借鑒價(jià)值,需要的朋友可以參考下2018-09-09
vue.js聲明式渲染和條件與循環(huán)基礎(chǔ)知識(shí)
這篇文章主要為大家詳細(xì)介紹了vue.js聲明式渲染和條件與循環(huán)的基礎(chǔ)知識(shí),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2017-07-07
詳解Vue組件插槽的使用以及調(diào)用組件內(nèi)的方法
在本篇文章里我們給大家分享了Vue組件插槽的使用以及調(diào)用組件內(nèi)的方法相關(guān)知識(shí)點(diǎn),有需要的朋友們參考下。2018-11-11
vue中的provide/inject的學(xué)習(xí)使用
本篇文章主要介紹了vue中的provide/inject的學(xué)習(xí)使用,小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,也給大家做個(gè)參考。一起跟隨小編過(guò)來(lái)看看吧2018-05-05
Vue3使用ref解決GetElementById為空的問(wèn)題
今天遇到一個(gè)問(wèn)題,就是在Vue3組件中需要獲取template中的元素節(jié)點(diǎn),使用GetElementById返回的卻是null,網(wǎng)上查找了好些資料,才發(fā)需要使用ref,所以本文給大家介紹了Vue3組件中如何使用ref解決GetElementById為空的問(wèn)題,需要的朋友可以參考下2023-12-12
vue項(xiàng)目登錄成功后退出時(shí)清空sessionId和userId的問(wèn)題
這篇文章主要介紹了vue項(xiàng)目登錄成功后退出時(shí)清空sessionId和userId的問(wèn)題,具有很好的參考價(jià)值,希望對(duì)大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2023-12-12
vue手寫<RouterLink/>組件實(shí)現(xiàn)demo詳解
這篇文章主要為大家介紹了vue手寫<RouterLink/>組件實(shí)現(xiàn)demo詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2023-06-06

