web操作指引 、图片锁定
收获
- 图片锁定
- 鼠标悬浮
- 按钮倒计时
CSS
.operation-guide {
/* display: none; 不能设置,会影响 js 设置为 '' 的效果。请使用元素级样式 */
position: fixed;
top: 0;
left: 0;
bottom: 0;
right: 0;
background-color: rgba(0, 0, 0, .6);
width: 100%;
height: 100%;
overflow: hidden;
color: white;
z-index: 9999;
}
.operation-guide .btn {
display: inline-block;
border: 1px solid #5daf34;
padding: 10px;
border-radius: 10px;
cursor: pointer;
position: absolute;
width: 70px;
box-sizing: border-box;
background-color: rgba(0, 0, 0, .6);
text-align: center;
user-select: none;
}
.operation-guide .btn:hover {
background-color: #5daf34;
}
.operation-guide img {
width: 100%;
height: 100%;
}
.operation-guide .btn-prev {
left: 30px;
bottom: 50px;
}
.operation-guide .btn-finish,
.operation-guide .btn-next {
right: 30px;
bottom: 50px;
}
JavaScript
const operationGuide = {
key: null,
el: null,
elBtnNext: null,
nextName: null,
elBtnPrev: null,
prevName: null,
elBtnFinish: null,
finishName: null,
imageList: [],
imageListLength: 0,
currentNo: 0,
lockSeconds: null,
init({key, urlList, lockSeconds, nextName, prevName, finishName} = options) {
this.key = key || 'operation-guide';
// 判断是否需要操作指引
let guide = this.storage(this.key);
if (guide) {
// 已查看过操作指引
return;
}
this.lockSeconds = lockSeconds || 5;
this.nextName = nextName || '下一步';
this.prevName = prevName || '上一步';
this.finishName = finishName || '完成';
// 根 <div id="operation_guide" style="display:none" class="operation-guide"></div>
this.el = document.createElement("div");
this.el.classList.add("operation-guide");
this.el.style.display = 'none';
/* 按钮
<span id="operation_guide_prev" class="btn btn-prev" v-text="'上一项'" ></span>
<span id="operation_guide_next" class="btn btn-next" v-text="'下一项'" ></span>
<span id="operation_guide_finish" class="btn btn-finish" v-text="'完成'" ></span>
*/
this.elBtnNext = document.createElement("span");
this.elBtnNext.classList.add("btn", "btn-next");
this.elBtnNext.innerText = this.nextName;
this.elBtnNext._name = this.nextName;
this.el.appendChild(this.elBtnNext);
this.elBtnPrev = document.createElement("span");
this.elBtnPrev.classList.add("btn", "btn-prev");
this.elBtnPrev.innerText = this.prevName;
this.elBtnPrev._name = this.prevName;
this.el.appendChild(this.elBtnPrev);
this.elBtnFinish = document.createElement("span");
this.elBtnFinish.classList.add("btn", "btn-finish");
this.elBtnFinish.innerText = this.finishName;
this.elBtnFinish._name = this.finishName;
this.el.appendChild(this.elBtnFinish);
// 图片
this.imageListLength = urlList.length;
for (let i = 0; i < this.imageListLength; i++) {
let img = document.createElement("img");
img.src = urlList[i];
img.style.display = 'none';
this.imageList.push(img);
}
this.imageList.forEach(item => this.el.appendChild(item));
this.imageListLength = this.imageList.length;
// 添加监听
this.elBtnNext.addEventListener("click", (e) => {
this.next(e);
}, false);
this.elBtnPrev.addEventListener("click", (e) => {
this.prev(e);
}, false);
this.elBtnFinish.addEventListener("click", (e) => {
this.finish(e);
}, false);
// 添加到body
document.body.appendChild(this.el);
this.start();
},
// 开始
start() {
this.currentNo = 0;
this.el.style.display = '';
this.next();
},
// 下一页
next(e) {
if (this.currentNo >= this.imageListLength) {
return;
}
this.currentNo++;
this.mainLogic();
},
// 上一页
prev(e) {
this.currentNo > 1 && this.currentNo--;
this.mainLogic();
},
// 完成
finish(e) {
this.el.style.display = 'none';
this.storage(this.key, "finish");
// 移除(如果要重复查看,请注悉下一行代码)
// this.el.remove();
},
// 缓存
storage(key, value) {
if (value) {
// 设置缓存并返回值
// ...
return value;
}
// 获取缓存
return '' ; // ...
},
// 主逻辑
mainLogic() {
// 图片轮询
// 当前号对应集合下标
let currentIndex = this.currentNo - 1;
this.imageList.forEach((item, index) => {
if (currentIndex === index) {
// 锁定图片
this.lockReadImage(item);
// 显示图片
item.style.display = '';
} else {
// 隐藏图片
item.style.display = 'none';
}
});
// 控制按钮是否显示
this.elBtnPrev.style.display = this.currentNo > 1 ? '' : 'none';
this.elBtnNext.style.display = this.currentNo < this.imageListLength ? '' : 'none';
this.elBtnFinish.style.display = this.currentNo === this.imageListLength ? '' : 'none';
},
// 每页锁定只是观看时间
lockReadImage(image) {
// 获取锁定时间
let lockSeconds = this.lockSeconds;
if (!lockSeconds || lockSeconds <= 0) {
// 不锁定
return;
}
// 判断锁定对象
if (image.isRead) {
// 已读过,不再锁定
return;
}
// 设置为已读严(格来说应该放在倒计时里面设置)
image.isRead = true;
// 获取按钮集
let btnList = [this.elBtnNext, this.elBtnPrev, this.elBtnFinish];
// 按钮倒计时
btnList.forEach(item => item.innerText = lockSeconds);
// span 禁用
btnList.forEach(item => item.style.pointerEvents = 'none');
// 每秒定时器
let nextInterval = window.setInterval(() => {
lockSeconds--;
// 按钮倒计时
btnList.forEach(item => item.innerText = lockSeconds);
if (lockSeconds <= 0) {
// 清除定时器
window.clearInterval(nextInterval);
// 恢复按钮名称
btnList.forEach(item => item.innerText = item._name);
// span 启用
btnList.forEach(item => item.style.pointerEvents = 'auto');
}
}, 1000);
}
};
operationGuide.init({
lockSeconds: 5,
key: "supplier-client-operation-guide", urlList: [
'https://gimg2.baidu.com/image_search/src=http%3A%2F%2Finews.gtimg.com%2Fnewsapp_bt%2F0%2F14711796970%2F641&refer=http%3A%2F%2Finews.gtimg.com&app=2002&size=f9999,10000&q=a80&n=0&g=0n&fmt=auto?sec=1652002089&t=e969199c7f4d1c3a111e0c35f3e3e2f7', 'https://gimg2.baidu.com/image_search/src=http%3A%2F%2Fnimg.ws.126.net%2F%3Furl%3Dhttp%253A%252F%252Fdingyue.ws.126.net%252F2022%252F0407%252F4180cabdj00r9z21e0042d200u000gwg00it00al.jpg%26thumbnail%3D660x2147483647%26quality%3D80%26type%3Djpg&refer=http%3A%2F%2Fnimg.ws.126.net&app=2002&size=f9999,10000&q=a80&n=0&g=0n&fmt=auto?sec=1652002089&t=f43e3d0f4d8df9553a9ebfb53653eef4',
'https://gimg2.baidu.com/image_search/src=http%3A%2F%2Finews.gtimg.com%2Fnewsapp_bt%2F0%2F14711797418%2F641&refer=http%3A%2F%2Finews.gtimg.com&app=2002&size=f9999,10000&q=a80&n=0&g=0n&fmt=auto?sec=1652002089&t=9369ee37535fc965dd85bf491762c6d3',
'https://gimg2.baidu.com/image_search/src=http%3A%2F%2Finews.gtimg.com%2Fnewsapp_bt%2F0%2F14711797309%2F641&refer=http%3A%2F%2Finews.gtimg.com&app=2002&size=f9999,10000&q=a80&n=0&g=0n&fmt=auto?sec=1652002089&t=b5321bbd2dd69eab3892a9df4d946064',
]
});