uni-Identify-quality/components/mask-guide-uni/mask-guide-uni.vue

189 lines
4.4 KiB
Vue
Raw Normal View History

2023-09-19 01:40:04 +00:00
<template>
<view>
<view v-if="showGuide" class="outer" @click="nextGuide" @touchmove.stop.prevent="moveHandle">
<view class="inner" :style="[innerStyle]"></view>
<view class="innerText" :style="[innerTextStyle]">
<view v-if="nextBtnPosition === 'top' && showNextButton" class="next-btn-wrap">
<slot name='nextButton'>
<view class="next-btn">我知道啦~</view>
</slot>
</view>
<text :style="[textStyle]">{{innerText}}</text>
<view v-if="nextBtnPosition === 'bottom' && showNextButton" class="next-btn-wrap">
<slot name='nextButton'>
<view class="next-btn">我知道啦~</view>
</slot>
</view>
</view>
</view>
</view>
</template>
<script>
export default {
name: "mask-guide-uni",
data() {
return {
innerStyle: {},
innerTextStyle: {},
guide: 0,
showGuide: false,
innerText: '',
deviceInfo: {},
textStyle: {},
showNextButton: true,
nextBtnPosition: 'top'
};
},
methods: {
start(props) {
for (let k in props) {
this[k] = props[k];
};
this.deviceInfo = uni.getSystemInfoSync();
this.showGuide = true;
this.nextGuide();
},
moveHandle(){
},
nextGuide() {
const index = this.guide;
uni.createSelectorQuery().select(`#guide-container #guide_${index}`).fields({
id: true,
dataset: true,
rect: true,
size: true,
scrollOffset: true,
context: true,
properties: ['scrollX', 'scrollY'],
computedStyle: ['borderRadius'],
}, data => {
if (data) {
let {
left,
right,
top,
width,
height,
borderRadius,
dataset
} = data;
//判断是否需要滚动
const { windowHeight } = this.deviceInfo;
this.innerStyle = {
'left': `${left}px`,
'top': `${top}px`,
'width': `${width}px`,
'height': `${height}px`,
'borderRadius': borderRadius
};
//根据位置设置显示的位置
const leftRpx = this.pxToRpx(left);
let innerTextStyle = {
'top': `${top + height + 5}px`,
}
if(leftRpx > 400){
innerTextStyle.textAlign = 'right';
innerTextStyle.right = `${750 - this.pxToRpx(right)}rpx`;
innerTextStyle.marginLeft = `10px`;
}else{
innerTextStyle.textAlign = 'left';
innerTextStyle.left = `${left}px`;
innerTextStyle.marginRight = `10px`;
}
//如果长度够长 居中显示
if(width > 300){
innerTextStyle.width = `${width}px`;
innerTextStyle.textAlign = 'center';
}
//内容在可视区域以下
if(windowHeight < top){
uni.pageScrollTo({
scrollTop: top - windowHeight + height + 10,
duration: 0
});
this.innerStyle.top = `${windowHeight - height - 10}px`;
}
//内容在可视区域以上
if(top < 0){
uni.pageScrollTo({
scrollTop: top,
duration: 0
});
this.nextGuide();
return;
}
//如果在可视区域下方,提示文字显示在上方
if(parseFloat(this.innerStyle.top) > windowHeight / 2){
innerTextStyle.bottom = `${windowHeight - parseFloat(this.innerStyle.top) + 10}px`;
delete innerTextStyle.top;
this.nextBtnPosition = 'top';
}else{
this.nextBtnPosition = 'bottom';
}
this.innerTextStyle = innerTextStyle;
this.innerText = dataset.guideText ?? '';
this.guide++;
} else {
this.showGuide = false;
this.$emit('update:showGuide', this.showGuide);
uni.pageScrollTo({
scrollTop: 0,
duration: 0
});
this.guide = 0;
}
}).exec()
},
pxToRpx(val){
return val/(uni.upx2px(100)/100);
}
}
}
</script>
<style>
.outer {
position: fixed;
left: 0;
right: 0;
top: 0;
bottom: 0;
background: transparent;
overflow: hidden;
z-index: 99999;
}
.inner {
position: absolute;
box-shadow: rgba(0, 0, 0, .8) 0 0 0 2021px;
z-index: 99999;
}
.innerText {
color: #fff;
position: absolute;
z-index: 99999;
font-size: 28rpx;
letter-spacing: 2rpx;
text-align: center;
}
.next-btn-wrap{
display: flex;
justify-content: center;
align-items: center;
}
.next-btn{
display: flex;
justify-content: center;
align-items: center;
height: 60rpx;
padding: 0 30rpx;
border: 2rpx solid #ddd;
border-radius: 10rpx;
margin: 10rpx;
font-size: 26rpx;
}
</style>