實(shí)現(xiàn)效果如圖:
效果圖
實(shí)現(xiàn)原理:
1. 將原右側(cè)導(dǎo)航欄樣式在全局css中改為常顯示以及寬度為零。
body {
background-color: #3c3c3c;
overflow-x: hidden;
overflow-y: scroll;
}
::-webkit-scrollbar {
width: 0;
}
2. 在后綴為.vue
的文件中或者在自定義的布局(nuxt中的layouts)中柠偶,加入這兩個(gè)id
<template>
<div>
<!-- 導(dǎo)航欄上層樣式 -->
<div id="progressbar"></div>
<!-- 導(dǎo)航欄底層背景 -->
<div id="scrollPath"></div>
</div>
</template>
3.在全局樣式common.css
中引入自定義導(dǎo)航欄的樣式
/* 導(dǎo)航欄背景 */
#scrollPath {
position: fixed;
top: 0;
right: 0;
width: 10px;
height: 100%;
background-color: rgba(255, 255, 255, 0.068);
}
/* 導(dǎo)航欄樣式 */
#progressbar {
position: fixed;
top: 0;
right: 0;
width: 10px;
/* height: 100%; */
background: linear-gradient(to top, red, blue);
animation: animate 5s linear infinite;
}
@keyframes animate {
0%, 100% {
filter: hue-rotate(0deg);
}
50% {
filter: hue-rotate(360deg);
}
}
#progressbar::before {
content: "";
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
background: linear-gradient(to top, red, blue);
filter: blur(10px);
}
#progressbar::after {
content: "";
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
background: linear-gradient(to top, red, blue);
filter: blur(30px);
}
4.核心:用戶獲取劃過(guò)的距離 除以
( 頁(yè)面內(nèi)容總高度 減去
文檔顯示區(qū)高度 ),進(jìn)行計(jì)算要顯示導(dǎo)航欄占整個(gè)頁(yè)面的百分比主慰,替換高度嚣州,從而進(jìn)行顯示。
9猜荨!情竹!坑:因?yàn)閂ue中存在Dom渲染完成之后渲染數(shù)據(jù)藐不,因此,在mounted()中執(zhí)行導(dǎo)航欄計(jì)算方法,只能得到請(qǐng)求的頁(yè)面數(shù)據(jù)未渲染之前的初始的高度雏蛮,數(shù)據(jù)渲染之后和這里的高度不對(duì)應(yīng)涎嚼!
!L舯法梯!解決方案:使用watch
監(jiān)聽(tīng)要渲染的數(shù)據(jù),使用this.$nextTick(() => {});
屬性將回調(diào)延遲到下次 DOM 更新循環(huán)之后執(zhí)行犀概。
因?yàn)槊總€(gè)頁(yè)面渲染的數(shù)據(jù)都不同立哑,所以在每個(gè)后綴為.vue
的頁(yè)面中都要watch監(jiān)聽(tīng)要渲染的數(shù)據(jù)。如果沒(méi)有請(qǐng)求的頁(yè)面數(shù)據(jù)姻灶,那直接將function中的內(nèi)容放入mounted()中即可铛绰。
watch: {
"data": function() {
this.$nextTick(() => {
let progress = document.getElementById("progressbar");
//innerheight 返回窗口的文檔顯示區(qū)的高度。
//document.documentElement.scrollHeight——瀏覽器所有內(nèi)容高度
//window.pageYOffset 劃過(guò)的距離
let totalHeight = document.body.scrollHeight - window.innerHeight;
window.onscroll = function() {
let progressHeight = (window.pageYOffset / totalHeight) * 100;
progress.style.height = progressHeight + "%";
};
});
}
},