实现的功能简介
自定义的table表格实现无限滚动
上代码(子组件定义)
<template>
<div
class="container"
:id="id"
>
<!-- 容器 -->
<div>
<!-- 表头 -->
<div class="header">
<div
:style="{ width: IndexWidth }"
v-if="config.isRequiredIndex"
>
#
</div>
<div
class="header_item"
v-for="(item, index) in headerList"
:key="item"
:style="{ width: otherWidth + 'px', height: '40px' }"
>
{{ item }}
</div>
</div>
<div class="inner">
<!-- base-scroll-list-text -->
<!-- <div class="row_area"> -->
<div
v-for="(item, index) in currentInnerList"
:key="item.rowIndex"
class="inner_container base-scroll-list-text"
:style="{
height: rowHeights[index] + 'px',
lineHeight: rowHeights[index] + 'px',
backgroundColor: item.rowIndex % 2 === 0 ? oddBc[0] : oddBc[1]
}"
>
<div
class="inner_column"
v-for="(item2, index2) in item.data"
:key="index2"
:style="{
width: otherWidth + 'px',
color: index2 === 0 ? config.columuCorlo : ''
}"
>
{{ item2 }}
</div>
</div>
<!-- </div> -->
</div>
</div>
</div>
</template>
<script>
//import dom from './index'
import { v4 as uuidv4 } from 'uuid'
import cloneDeep from 'lodash/cloneDeep'
export default {
name: 'MyTable',
components: {},
props: {
config: {
type: Object,
default: () => ({
headerList: [],
isRequiredIndex: false,
row: [],
columuCorlo: '',
openOddSty: false
})
// headerList: []
}
},
data() {
return {
headerList: [],
innerList: [],
// 容器的宽高
style: {
width: '',
height: ''
},
// id: uuidv4(),
id: '',
//序号列的宽度
IndexWidth: '80px',
otherWidth: 0,
row: [],
// columnHeight: 0,
//假设一页10条
pagesize: 5,
//当前界面实际要展示的数量(滚动动画)
currentInnerList: [],
//指针
currentIndex: 0,
//步进器指数
moveNum: 1,
// 所有行高的数组
rowHeights: 0
// newRowList:[]
}
},
created() {
this.id = `base-scroll-list-${uuidv4()}`
},
mounted() {
console.log('mytable')
this.getStyle()
const { config } = this
this.headerList = config.headerList
this.row = config.row.map((v, index) => ({
data: v,
rowIndex: index
}))
// 其它列的宽度
const _IndexWidth = +this.IndexWidth.replace('px', '')
this.otherWidth =
(this.style.width - (this.config.isRequiredIndex ? _IndexWidth : 0)) /
this.headerList.length
this.animationStart()
},
computed: {
// 行高
columnHeight() {
const result = (this.style.height - 40) / this.pagesize
return result
},
// 奇偶列样式
oddBc() {
if (this.config.openOddSty) {
return ['blue', 'orange']
} else {
// 相当于没设置
return ['white', 'white']
}
}
},
methods: {
getStyle() {
const dom = window.document.getElementById(this.id)
this.style.width = dom.clientWidth
this.style.height = dom.clientHeight
},
// 动画开始
async animationStart() {
// { currentIndex, moveNum } = this
// 指针
// currentIndex = 0
// 每次向下移动几个
// moveNum = 1
//当前实际传了几个数据过来
let totalLength = this.row.length
if (totalLength < this.pagesize) {
return
}
// 克隆一份row数据
const _row = cloneDeep(this.row)
// 实际要显示的数据
const rows = _row.slice(this.currentIndex)
rows.push(..._row.slice(0, this.currentIndex))
// console.log(this.currentIndex, 'currentIndex')
this.currentInnerList = rows
// debugger
// 把所有的高度以数组的形式展示
this.rowHeights = new Array(totalLength).fill(this.columnHeight)
//[72, 72, 72, 72, 72, 72, 72, 72, 72, 72, __ob__: Observer]
// console.log(this.rowHeights, ' this.rowHeights')
const waitTime = 300
await new Promise((res) => setTimeout(res, waitTime))
this.rowHeights.splice(
0,
this.moveNum,
...new Array(this.moveNum).fill(0)
)
// console.log(this.rowHeights, ' this.rowHeights')
this.currentIndex += this.moveNum
// 是否到达最后一组数据
const isLast = this.currentIndex - totalLength
if (isLast >= 0) {
this.currentIndex = isLast
}
await new Promise((resolve) => setTimeout(resolve, 2000 - waitTime))
await this.animationStart()
}
}
}
</script>
<style lang="scss">
.container {
// width: 800px;
position: relative;
height: 100%;
width: 100%;
overflow: hidden;
.header {
background-color: #ccc;
display: flex;
align-items: center;
.header_item {
height: 40px;
line-height: 40px;
font-size: 15px;
color: white;
}
}
.inner {
height: 360px;
overflow: hidden;
.base-scroll-list-text {
// padding: 0 10px;
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
box-sizing: border-box;
}
.inner_container {
display: flex;
color: white;
transition: all 0.3s linear;
// text-align: center;
}
// height: 320px;
// background-color: #ccc;
}
}
</style>
如何让列表滚动起来?
每隔一定时间删除数组最前面一个值,然后把这个值再push到数组的最后面去,接着定义一个数组,这个数组的值是所有高度区间组成的数组,接着每次让这个数组的第一项的值变成0就可以了,加上transtion,就会让我们肉眼看见那种卷去头部第一项的效果,后面的逻辑就比较简单了
一些小细节
const arr = [72, 72, 72, 72, 72, 72, 72, 72, 72, 72]
arr.splice(0, 1, ...new Array(1).fill(0))
// [0, 72, 72, 72, 72, 72, 72, 72, 72, 72]
console.log(arr)
父组件使用
<template>
<div
class="container"
style="width: 500px; height: 400px"
>
<my-table v-bind:config="config"></my-table>
</div>
</template>
<script>
export default {
components: {},
data() {
return {
headerList: [],
innerList: [],
config: {
headerList: [],
isRequiredIndex: false,
row: [],
columuCorlo: 'red',
//是否开始奇偶列样式
openOddSty: true
}
}
},
created() {
this.config.headerList = ['姓名', '年龄', '收入']
const data = []
for (let index = 0; index < 10; index++) {
data.push([
'同学' + (index + 1),
Math.floor(Math.random() * 10 + 20),
Math.floor(Math.random() * 10000 + 20000)
])
}
this.config.row = data
},
mounted() {
//this.headerList.push({})
},
methods: {}
}
</script>
<style scoped>
.container {
width: 500px;
height: 400px;
}
</style>