我们来详细讲解在原生 JavaScript 中如何实现仿浏览器滚动条效果。
1. 设计实现思路
在实现仿浏览器滚动条的效果时,需要考虑以下几个方面:
- 创建滚动条:根据需要创建一个滚动条,并设置它的高度和样式。
- 监听内容滚动:监听页面内容的滚动事件。
- 计算滑块位置:根据内容滚动的位置和内容高度,计算出滑块的位置。
- 移动滑块:根据计算得出的滑块位置,改变滑块的样式使其滑动。
2. 创建滚动条
创建滚动条时,需要创建两个 div
元素,一个作为滑道,另一个作为滑块,如下所示:
<div class="scrollbar">
<div class="slider"></div>
</div>
然后为这两个元素设置样式,使它们能够正确地显示在页面上。需要注意的是,滑道的高度应该等于内容区域的高度,而滑块的高度应该是一个比例,比例的大小为滑块能够滑移的区域长度和滑道长度之比。
.scrollbar {
position: relative;
height: 200px; /* 设置滑道高度 */
overflow-y: scroll; /* 开启垂直滚动条 */
}
.slider {
position: absolute;
top: 0;
right: 0;
width: 10px;
height: calc(200px * 200px / 10000); /* 计算滑块高度 */
background-color: #ccc;
cursor: pointer;
border-radius: 5px;
}
3. 监听内容滚动
使用原生 JavaScript,可以通过在内容区域上绑定 scroll
事件来监听内容的滚动。
const content = document.querySelector('.content');
const slider = document.querySelector('.slider');
content.addEventListener('scroll', e => {
// do something
});
4. 计算滑块位置
计算滑块位置的核心是确定内容区域的滚动位置和内容区域的高度,然后通过它们来计算滑块位置。具体实现如下:
function calculateSliderPosition() {
const content = document.querySelector('.content');
const slider = document.querySelector('.slider');
// 获取内容区域高度
const contentHeight = content.scrollHeight;
// 获取滑块能够滑动的最大距离
const maxSliderDistance = slider.parentElement.offsetHeight - slider.offsetHeight;
// 计算滑块位置
const sliderPosition = (content.scrollTop / contentHeight) * maxSliderDistance;
// 设置滑块位置
slider.style.top = `${sliderPosition}px`;
}
5. 移动滑块
当计算出滑块位置后,还需要更新滑块的样式,让它能够滑动。这可以通过改变滑块的 top
样式来实现,如下所示:
function moveSlider() {
const content = document.querySelector('.content');
const slider = document.querySelector('.slider');
// 获取内容区域高度
const contentHeight = content.scrollHeight;
// 获取滑块能够滑动的最大距离
const maxSliderDistance = slider.parentElement.offsetHeight - slider.offsetHeight;
// 计算滑块位置
const sliderPosition = (content.scrollTop / contentHeight) * maxSliderDistance;
// 移动滑块
slider.style.top = `${sliderPosition}px`;
}
示例
我们可以利用以上的步骤,实现一个简单的仿浏览器滚动条效果,代码如下:
<html>
<head>
<style>
.wrapper {
position: relative;
height: 200px;
width: 200px;
overflow: hidden;
}
.content {
position: absolute;
top: 0;
bottom: 0;
left: 0;
right: 0;
padding-right: 10px;
overflow-y: scroll;
}
.scrollbar {
position: absolute;
top: 0;
bottom: 0;
right: 0;
width: 10px;
}
.slider {
position: absolute;
top: 0;
right: 0;
width: 10px;
background-color: #ccc;
border-radius: 5px;
cursor: pointer;
}
</style>
</head>
<body>
<div class="wrapper">
<div class="content">
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nam varius ipsum sed faucibus consectetur. Cras fringilla sapien et felis vehicula consectetur. Nam eu ex lectus. Curabitur auctor fermentum lectus. Aliquam nec mollis odio, in tincidunt tellus. Sed bibendum justo a sapien euismod accumsan. Quisque tincidunt sapien ante, eget consectetur erat aliquet vehicula. Etiam convallis posuere justo, in pretium nulla maximus eu. Suspendisse eget justo faucibus, molestie tortor et, feugiat odio.</p>
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nam varius ipsum sed faucibus consectetur. Cras fringilla sapien et felis vehicula consectetur. Nam eu ex lectus. Curabitur auctor fermentum lectus. Aliquam nec mollis odio, in tincidunt tellus. Sed bibendum justo a sapien euismod accumsan. Quisque tincidunt sapien ante, eget consectetur erat aliquet vehicula. Etiam convallis posuere justo, in pretium nulla maximus eu. Suspendisse eget justo faucibus, molestie tortor et, feugiat odio.</p>
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nam varius ipsum sed faucibus consectetur. Cras fringilla sapien et felis vehicula consectetur. Nam eu ex lectus. Curabitur auctor fermentum lectus. Aliquam nec mollis odio, in tincidunt tellus. Sed bibendum justo a sapien euismod accumsan. Quisque tincidunt sapien ante, eget consectetur erat aliquet vehicula. Etiam convallis posuere justo, in pretium nulla maximus eu. Suspendisse eget justo faucibus, molestie tortor et, feugiat odio.</p>
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nam varius ipsum sed faucibus consectetur. Cras fringilla sapien et felis vehicula consectetur. Nam eu ex lectus. Curabitur auctor fermentum lectus. Aliquam nec mollis odio, in tincidunt tellus. Sed bibendum justo a sapien euismod accumsan. Quisque tincidunt sapien ante, eget consectetur erat aliquet vehicula. Etiam convallis posuere justo, in pretium nulla maximus eu. Suspendisse eget justo faucibus, molestie tortor et, feugiat odio.</p>
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nam varius ipsum sed faucibus consectetur. Cras fringilla sapien et felis vehicula consectetur. Nam eu ex lectus. Curabitur auctor fermentum lectus. Aliquam nec mollis odio, in tincidunt tellus. Sed bibendum justo a sapien euismod accumsan. Quisque tincidunt sapien ante, eget consectetur erat aliquet vehicula. Etiam convallis posuere justo, in pretium nulla maximus eu. Suspendisse eget justo faucibus, molestie tortor et, feugiat odio.</p>
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nam varius ipsum sed faucibus consectetur. Cras fringilla sapien et felis vehicula consectetur. Nam eu ex lectus. Curabitur auctor fermentum lectus. Aliquam nec mollis odio, in tincidunt tellus. Sed bibendum justo a sapien euismod accumsan. Quisque tincidunt sapien ante, eget consectetur erat aliquet vehicula. Etiam convallis posuere justo, in pretium nulla maximus eu. Suspendisse eget justo faucibus, molestie tortor et, feugiat odio.</p>
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nam varius ipsum sed faucibus consectetur. Cras fringilla sapien et felis vehicula consectetur. Nam eu ex lectus. Curabitur auctor fermentum lectus. Aliquam nec mollis odio, in tincidunt tellus. Sed bibendum justo a sapien euismod accumsan. Quisque tincidunt sapien ante, eget consectetur erat aliquet vehicula. Etiam convallis posuere justo, in pretium nulla maximus eu. Suspendisse eget justo faucibus, molestie tortor et, feugiat odio.</p>
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nam varius ipsum sed faucibus consectetur. Cras fringilla sapien et felis vehicula consectetur. Nam eu ex lectus. Curabitur auctor fermentum lectus. Aliquam nec mollis odio, in tincidunt tellus. Sed bibendum justo a sapien euismod accumsan. Quisque tincidunt sapien ante, eget consectetur erat aliquet vehicula. Etiam convallis posuere justo, in pretium nulla maximus eu. Suspendisse eget justo faucibus, molestie tortor et, feugiat odio.</p>
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nam varius ipsum sed faucibus consectetur. Cras fringilla sapien et felis vehicula consectetur. Nam eu ex lectus. Curabitur auctor fermentum lectus. Aliquam nec mollis odio, in tincidunt tellus. Sed bibendum justo a sapien euismod accumsan. Quisque tincidunt sapien ante, eget consectetur erat aliquet vehicula. Etiam convallis posuere justo, in pretium nulla maximus eu. Suspendisse eget justo faucibus, molestie tortor et, feugiat odio.</p>
</div>
<div class="scrollbar">
<div class="slider"></div>
</div>
</div>
<script>
function calculateSliderPosition() {
const content = document.querySelector('.content');
const slider = document.querySelector('.slider');
const contentHeight = content.scrollHeight;
const maxSliderDistance = slider.parentElement.offsetHeight - slider.offsetHeight;
const sliderPosition = (content.scrollTop / contentHeight) * maxSliderDistance;
slider.style.top = `${sliderPosition}px`;
}
const content = document.querySelector('.content');
const slider = document.querySelector('.slider');
content.addEventListener('scroll', () => {
calculateSliderPosition();
});
slider.addEventListener('mousedown', e => {
const startY = e.clientY;
const startTop = parseInt(slider.style.top);
const onMouseMove = e => {
const distance = e.clientY - startY;
const sliderPosition = Math.min(Math.max(0, startTop + distance), slider.parentElement.offsetHeight - slider.offsetHeight);
const content = document.querySelector('.content');
const contentHeight = content.scrollHeight;
const maxSliderDistance = slider.parentElement.offsetHeight - slider.offsetHeight;
const scrollTop = (sliderPosition / maxSliderDistance) * contentHeight;
content.scrollTop = scrollTop;
slider.style.top = `${sliderPosition}px`;
};
const onMouseUp = () => {
document.removeEventListener('mousemove', onMouseMove);
document.removeEventListener('mouseup', onMouseUp);
};
document.addEventListener('mousemove', onMouseMove);
document.addEventListener('mouseup', onMouseUp);
});
</script>
</body>
</html>
此代码模拟出一个包含滚动条的内容区域,在滑动滑块时会自动滚动内容区域,并且滑块位置也会随着内容区域的滚动而变化。同时,在鼠标按下滑块、拖动滑块和松开鼠标等过程中,滑块也能够正确地响应。
本站文章如无特殊说明,均为本站原创,如若转载,请注明出处:原生js仿浏览器滚动条效果 - Python技术站