关于小程序和uniapp中如何解决弹出层scrollview滚动影响页面级滚动的方案
最近在开发的时候,碰到scrollview在弹出层滑动时,影响了页面的滚动,在网上找了很多种方法之后,在这里谈一谈我的理解:
解决方案一:弹出层没有需要滚动的容器时,可以直接给整个弹出层加@touchmove.stop.prevent事件阻止滑动穿透;
解决方案二:给页面最外层的view动态绑定,(没有搜索到可以给page直接动态绑定css属性的方法)
overflow:hidden; height:100vh;
相当于固定了页面的高度。使得页面没有滚动条,从而页面也就不会滚动了。但是这样的话,每一次动态给page绑定属性的时候,页面都会回弹到顶部,操作体验非常的不好。
解决方案三
给page添加属性:
overflow: visible;
height:100vh;
最外层元素加属性:
overflow::auto;
height:100%;
当拉起弹框时动态给最外层元素加属性
overflow:hidden;
这种解决方案我理解为直接让最外层滚动,并没有触发页面级的滚动,看效果也解决了页面回弹的问题,但是美中不足的是,失去了页面级的滚动,如果页面需要监听滚动条的位置,那这种方案就没有办法用了;
所以为了符合我的需求,我最终使用的方法如下:
首先在页面弹框弹出时,动态给最外层元素加如下属性
position: fixed;
top:0;
left:0;
overflow: hidden;
通过小程序的onPagescroll事件,实时记录下当前滚动条距离页面顶部的距离
onPageScroll(e) {
if(e.scrollTop>0){
this.nowscrolltop = e.scrollTop
}else{
}
this.topopacity = e.scrollTop / 300;
},
要判断是不是0,因为当设置最外层position:fixed的时候,滚动条会回弹到0,这时候不能赋值
最终再给最外层元素绑定属性:
:style="{'transform' : transformshow ? 'translateY('+(-nowscrolltop) +'px)' : 'none'}"
就是在回弹到顶部之后,通过transform再让最外层view向下平移一段距离,这里使用transform而不直接用top的原因是因为用了top之后,我的弹框使用的animate属性就会变得特别卡。所以在弹出层的最外层,要给一个相反的transform
:style="{'transform' : transformshow ? 'translateY('+(nowscrolltop) +'px)' : 'none'}"
关闭弹框的时要加入如下代码(如果你实验到这里,那肯定知道我这代码的意思,这就不过多解释了)自我感觉良好的解决方案诞生了~
this.transformshow=!this.transformshow
this.$nextTick(()=>{
uni.pageScrollTo({
scrollTop: this.nowscrolltop,
duration:0
});
})
注意:弹框的外层的高度要给100vh