JS虚拟滚动
HTML
<div class="list_scroll">
<div class="list">
<div class="item">1</div>
</div>
</div>
CSS
.list_scroll {
width: 500px;
height: 800px;
border: 1px solid #f80c0c;
overflow: auto;
background-color: antiquewhite;
}
.list {
width: 90%;
margin: auto;
}
.item {
width: 100%;
border: 1px solid #000;
box-sizing: border-box;
display: flex;
justify-content: center;
align-items: center;
}
Javascrip
const listScroll = document.querySelector('.list_scroll')
const list = document.querySelector('.list')
const dataSource = []
let renderData = []
const itemHeight = 50
const maxCount = Math.floor(listScroll.clientHeight / itemHeight) + 2
let startIndex = 0
let endIndex = 0
function GetData() {
for (let i = 0; i < 30; i++) {
dataSource.push(i)
}
}
function ComputePointerPosition() {
const end = startIndex + maxCount
endIndex = dataSource[end] ? end : dataSource.length
}
function GetRenderData() {
renderData = dataSource.slice(startIndex, endIndex)
}
function Render() {
ComputePointerPosition()
GetRenderData()
list.innerHTML = renderData.map(item => `<div class="item" style="height: ${itemHeight}px">${item}</div>`).join('')
}
let pointerIndex = 0
function ScrollHandle() {
startIndex = Math.floor(listScroll.scrollTop / itemHeight)
if (pointerIndex === startIndex) return
pointerIndex = startIndex
Render()
if (dataSource.length - startIndex >= maxCount) {
list.style.transform = `translateY(${startIndex * itemHeight}px)`
} else {
}
}
function init() {
GetData()
Render()
listScroll.addEventListener('scroll', ScrollHandle)
}
init()