vue,elementui 冻结列希望得到同样的滚动效果

今天一个奇葩的需求,假设冻结列属于A类数据,其他滚动列属于B类数据。

产品还有老板不断的增加A类是数据的列,已经严重挤到B类数据的生存了,如下示例截图,哈哈哈,实际情况我已经抠了很多边距字体了

 

上主菜

<template>
    <div class="table-2t" :style="{'padding-left':(leftWidth+rightOffset)+'px'}">

        <!-- 左边表格 -->
        <div class="table-2t-left" :style="{width:leftWidth+'px'}">
            <el-table :data="tableData" border :height="tabHeight">
                <el-table-column prop="date" label="日期" width="150">
                </el-table-column>
                <el-table-column prop="name" label="姓名" width="120">
                </el-table-column>
                <el-table-column prop="province" label="省份" width="120">
                </el-table-column>
                <el-table-column prop="city" label="市区" width="120">
                </el-table-column>
                <el-table-column prop="address" label="地址" width="300">
                </el-table-column>
                <el-table-column prop="address" label="地址1" width="300">
                </el-table-column>
                <el-table-column prop="address" label="地址2" width="300">
                </el-table-column>
                <el-table-column prop="address" label="地址3" width="300">
                </el-table-column>
                <el-table-column prop="zip" label="邮编4" width="120">
                </el-table-column>
            </el-table>
        </div>

        <!-- 中间阴影线 -->
        <div :style="{height:tabHeight+'px',left:(leftWidth+rightOffset-3)+'px'}" class="table-2t-shadow"></div>

        <!-- 右边表格 -->
        <div class="table-2t-right">
            <el-table :data="tableData" border :height="tabHeight">
                <el-table-column prop="date" label="日期youbian" width="150">
                </el-table-column>
                <el-table-column prop="name" label="姓名" width="120">
                </el-table-column>
                <el-table-column prop="province" label="省份" width="120">
                </el-table-column>
                <el-table-column prop="city" label="市区" width="120">
                </el-table-column>
                <el-table-column prop="address" label="地址" width="300">
                </el-table-column>
                <el-table-column prop="address" label="地址1" width="300">
                </el-table-column>
                <el-table-column prop="address" label="地址2" width="300">
                </el-table-column>
                <el-table-column prop="address" label="地址3" width="300">
                </el-table-column>
                <el-table-column prop="zip" label="邮编4" width="120">
                </el-table-column>
            </el-table>
        </div>
    </div>
</template>



<script lang="ts">
import { Component, Prop, Vue } from 'vue-property-decorator';
/**
 * 后台登录后的首页
 */
@Component
export default class Home extends Vue {
    private tableData: any[] = [];

    /**
     * 左边宽度
     */
    private leftWidth: number = 700;
    /**
     * 右边表,的左边距补偿
     */
    private rightOffset: number = 0;

    /**
     * 表格高度
     */
    private tabHeight: number = 700;

    getScrollbarWidth() {
        var odiv = document.createElement('div'), //创建一个div
            styles = {
                width: '100px',
                height: '100px',
                overflowY: 'scroll' //让他有滚动条
            },
            i,
            scrollbarWidth;
        for (i in styles) odiv.style[i] = styles[i];
        document.body.appendChild(odiv); //把div添加到body中
        scrollbarWidth = odiv.offsetWidth - odiv.clientWidth; //相减
        odiv.remove(); //移除创建的div
        return scrollbarWidth; //返回滚动条宽度
    }

    scrollLock() {
        const leftWrapper = this.$el.querySelectorAll(
            '.table-2t-left .el-table__body-wrapper'
        )[0] as Element;
        const rightWrapper = this.$el.querySelectorAll(
            '.table-2t-right .el-table__body-wrapper'
        )[0] as Element;

        let scrollInfo: any = {
            scrollStar: '',
            timeFlag: 0,
            // 操作时间
            operTime: 0
        };

        const timeStar = () => {
            // 保险代码
            clearInterval(scrollInfo.timeFlag);
            scrollInfo.timeFlag = setInterval(() => {
                if (scrollInfo.operTime + 200 < new Date().getTime()) {
                    clearInterval(scrollInfo.timeFlag);
                    if (scrollInfo.scrollStar === 'left') {
                        rightWrapper.addEventListener('scroll', rh);
                    } else if (scrollInfo.scrollStar === 'right') {
                        leftWrapper.addEventListener('scroll', lh);
                    }
                    scrollInfo.scrollStar = '';
                    console.log('解锁');
                }
            }, 202);
        };

        const lh = e => {
            console.log('lh');
            scrollInfo.operTime = new Date().getTime();
            if (scrollInfo.scrollStar != 'left') {
                scrollInfo.scrollStar = 'left';
                rightWrapper.removeEventListener('scroll', rh);
                timeStar();
            }
            if (rightWrapper.scrollTop != leftWrapper.scrollTop) {
                rightWrapper.scrollTop = leftWrapper.scrollTop;
            }
        };
        const rh = e => {
            console.log('rh');
            scrollInfo.operTime = new Date().getTime();
            if (scrollInfo.scrollStar != 'right') {
                scrollInfo.scrollStar = 'right';
                leftWrapper.removeEventListener('scroll', lh);
                timeStar();
            }
            if (leftWrapper.scrollTop !== rightWrapper.scrollTop) {
                leftWrapper.scrollTop = rightWrapper.scrollTop;
            }
        };

        leftWrapper.addEventListener('scroll', lh);
        rightWrapper.addEventListener('scroll', rh);
    }

    mounted() {
        this.rightOffset = this.getScrollbarWidth() * -1 - 1;
        var arr = [];
        for (let i = 0; i < 200; i++) {
            arr.push({
                date: '2016-05-03',
                name: '王小虎',
                province: '上海',
                city: '普陀区',
                address: `上海市普陀区金沙江路 ${i + 1} 弄`,
                zip: 200333
            });
        }
        this.tableData = arr;

        this.scrollLock();
    }
}
</script>

<style lang="scss" scoped>
.table-2t {
    // display: flex;
    min-height: 500px;
    max-height: 700px;
    position: relative;
    .table-2t-left {
        z-index: 1;
        overflow: hidden;
        position: absolute;
        top: 0px;
        left: 0px;
    }
    .table-2t-right {
        z-index: 2;
        position: relative;
    }
}
.table-2t-shadow {
    position: absolute;
    // box-shadow: 0 0 10px rgba(0, 0, 0, 0.12);
    width: 3px;
    -webkit-box-shadow: 0 0 6px rgba(0, 0, 0, 0.4);
    box-shadow: 6px 0 6px rgba(0, 0, 0, 0.12);
    z-index: 3;
}
</style> 

element UI冻结列的写法其实使用了两个表格,主表格和冻结列表格,冻结列表格容器大小,在层叠上面的,最好的作用就是行的高度撑开不会 影响布局(以前改过一个jqgrid,那个坑多的很)

最开始我想在这个基础上做处理,但奈何发现冻结列的高度,直接减去了横向滚动条的高度,怕坑多就没尝试了

最后转到使用这种双表格的做法,只需要通过两个容器的滚动调进行锁定即可。

1.尝试过掩藏左边滚动条,发现不触发scroll事件

2.左边滚动使用mouseover,奈何发现滚动顺畅度不够,难受

3.增加左侧滚动条,浏览器自带的滚动效果自然好玩,但是遇到了另外几个问题

4.mac版本上有一个设置,让浏览器滚动条像移动设备手机一样,是悬浮在上边,导致滚动的时候出现,使用css对滚动条进行处理,找了一个简单的发现element UI表头没有帮我算计滚动条的位置,但表格主要内容有,找到一个详细的时候解决了这个问题

5.增加左侧滚动条之后发现不能使用单纯的margin-right 负值减去,这也是自己的技术不过关导致的。最后用右边div负值叠上去

 

细节处理。

6.仔细看element UI冻结列,在移动的时候左边其实有阴影的,哈哈哈,坑又来了

7.由于是右边叠在左边,导致左边的阴影不生效,好,很好,真的是心累,弄一个div来处理吧

.......不补了,想不起之前烦恼的事情了

浏览器滚动条的css


// 滚动条
::-webkit-scrollbar {
    height: 8px;
    width: 8px;
}
::-webkit-scrollbar-button {
    height: 0;
    width: 0;
}
::-webkit-scrollbar-button:start:decrement,
::-webkit-scrollbar-button:end:increment {
    display: block;
}
::-webkit-scrollbar-button:vertical:start:increment,
::-webkit-scrollbar-button:vertical:end:decrement {
    display: none;
}
::-webkit-scrollbar-track:vertical,
::-webkit-scrollbar-track:horizontal,
::-webkit-scrollbar-thumb:vertical,
::-webkit-scrollbar-thumb:horizontal,
::-webkit-scrollbar-track:vertical,
::-webkit-scrollbar-track:horizontal,
::-webkit-scrollbar-thumb:vertical,
::-webkit-scrollbar-thumb:horizontal {
    border-style: solid;
    border-color: transparent;
}
::-webkit-scrollbar-track:vertical::-webkit-scrollbar-track:horizontal {
    background-clip: padding-box;
    background-color: #fff;
}
::-webkit-scrollbar-thumb {
    box-shadow: inset 1px 1px 0 rgba(0, 0, 0, 0.1),
        inset 0 -1px 0 rgba(0, 0, 0, 0.07);
    background-clip: padding-box;
    background-color: rgba(0, 0, 0, 0.2);
    min-height: 28px;
    padding-top: 100;
}
::-webkit-scrollbar-thumb:hover {
    box-shadow: inset 1px 1px 1px rgba(0, 0, 0, 0.25);
    background-color: rgba(0, 0, 0, 0.4);
}
::-webkit-scrollbar-thumb:active {
    box-shadow: inset 1px 1px 3px rgba(0, 0, 0, 0.35);
    background-color: rgba(0, 0, 0, 0.5);
}
::-webkit-scrollbar-track:vertical,
::-webkit-scrollbar-track:horizontal,
::-webkit-scrollbar-thumb:vertical,
::-webkit-scrollbar-thumb:horizontal {
    border-width: 0;
}
::-webkit-scrollbar-track:hover {
    box-shadow: inset 1px 0 0 rgba(0, 0, 0, 0.1);
    background-color: rgba(0, 0, 0, 0.05);
}
::-webkit-scrollbar-track:active {
    box-shadow: inset 1px 0 0 rgba(0, 0, 0, 0.14),
        inset -1px -1px 0 rgba(0, 0, 0, 0.07);
    background-color: rgba(0, 0, 0, 0.05);
}

忘记说了,哈哈哈,我公司被我说服,只考虑谷歌浏览器,所以其他的兼容性并没有测试过

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值