优化 ant-select(下拉数据太多)导致的页面卡顿问题
ant-select 下拉数据加载问题
- 定义混入

import { getSchoolList } from '@/api/basic/school'
export default {
data () {
return {
// 总数据(不会改变)
allDataZ: [],
// 存放前100的数据
frontDataZ: [],
sourceOwnerSystems: [],
valueData: '',
treePageSize: 100,
scrollPage: 1
}
},
methods: {
pkSchoolChange (val) {
// console.log(val, '🫘')
if (!val) {
this.allDataZ = this.schoolOptions
this.frontDataZ = this.schoolOptions.slice(0, 100)
}
},
// 通过接口获取数据
showTabelCiList () {
this.allDataZ = this.schoolOptions // 获取所有的数据赋值给dataZ
this.frontDataZ = this.schoolOptions.slice(0, 100) // 只渲染100条数据
},
// 搜索的时候执行的方法,val就是输入的时候的内容,可以去后端进行查询数据最后赋值给dataZ或者frontDataZ
handleSearch (val) {
this.valueData = val
if (!val) {
this.showTabelCiList()
} else {
this.frontDataZ = []
this.scrollPage = 1
this.allDataZ.forEach(item => {
if (item.label.indexOf(val) >= 0) {
this.frontDataZ.push(item)
}
})
this.allDataZ = this.frontDataZ
this.frontDataZ = this.frontDataZ.slice(0, 100) // 只渲染100条数据
}
},
// 下拉框下滑事件
handlePopupScroll (e) {
const { target } = e
const scrollHeight = target.scrollHeight - target.scrollTop
const clientHeight = target.clientHeight
// 下拉框不下拉的时候
if (scrollHeight === 0 && clientHeight === 0) {
this.scrollPage = 1
// console.log(this.scrollPage)
} else {
// 当下拉框滚动条到达底部的时候
if (scrollHeight < clientHeight + 5) {
this.scrollPage = this.scrollPage + 1
const scrollPage = this.scrollPage// 获取当前页
const treePageSize = this.treePageSize * (scrollPage || 1)// 新增数据量
const newData = [] // 存储新增数据
let max = '' // max 为能展示的数据的最大条数
if (this.allDataZ.length > treePageSize) {
// 如果总数据的条数大于需要展示的数据
max = treePageSize
} else {
// 否则
max = this.allDataZ.length
}
// 判断是否有搜索
if (this.valueData) {
this.allDataZ.forEach((item, index) => {
if (index < max) { // 当data数组的下标小于max时
newData.push(item)
}
})
} else {
this.allDataZ.forEach((item, index) => {
if (index < max) { // 当data数组的下标小于max时
newData.push(item)
}
})
}
this.frontDataZ = newData // 将新增的数据赋值到要显示的数组中
}
}
},
// 回显默认选中数据
setDefaultSchoolOptionsByPkSchool () {
const arr = JSON.parse(JSON.stringify(this.schoolOptions))
this.schoolOptions = []
// console.log('🔪', this.form.pkSchool, this.allDataZ)
// 找到 pkschool对应的索引
// 构建 id 到下标的映射
const schoolMap = new Map()
arr.forEach((school, index) => {
schoolMap.set(school.value, index)
})
// 现在可以很快速地查找元素的下标
const pkschool = this.form.pkSchool
const indexOfSchool = schoolMap.get(pkschool)
// console.log(indexOfSchool) // 输出下标,如果不存在则输出 undefined
const indexOfSchoolWith = 0 // 指定占位(下标位置,应小于下文截取的slice(0, 100)的100)
// 确保下标在数组范围内
if (indexOfSchool !== undefined && indexOfSchoolWith < arr.length) {
// 交换两个元素
[arr[indexOfSchool], arr[indexOfSchoolWith]] = [arr[indexOfSchoolWith], arr[indexOfSchool]]
}
this.$nextTick(() => {
this.schoolOptions = arr
this.allDataZ = this.schoolOptions
this.frontDataZ = this.schoolOptions.slice(0, 100)
})
},
getSchoolList () {
this.schoolOptions = []
return getSchoolList().then(res => {
this.schoolOptions = []
res.filter(item => {
const obj = {}
obj.value = item.id
obj.label = item.schoolName
this.schoolOptions.push(obj)
})
// 进行下一步处理
this.$nextTick(() => {
this.allDataZ = this.schoolOptions
this.frontDataZ = this.schoolOptions.slice(0, 100)
})
})
}
}
}
import schoolSelectMixins from '@/mixins/schoolSelectMixins'
export default {
mixins: [schoolSelectMixins],
......
......
......
<ant-col :span="6">
<ant-form-model-item label="毕业院校" prop="pkSchool">
<ant-select
allowClear
v-model="form.pkSchool"
:filterOption="filterOption"
placeholder="请选择毕业院校"
:disabled="disabled"
@change="pkSchoolChange"
@popupScroll="handlePopupScroll"
showSearch
@search="handleSearch"
>
<!-- //过滤一下数据是否为空 -->
<ant-select-option v-for="frontSelect in frontDataZ.filter(item=>item.label)" :key="frontSelect.value">
{{ frontSelect.label }}
</ant-select-option>
</ant-select>
</ant-form-model-item>
</ant-col>