需求:
- 禁止h5内部、区域滑动触发整个页面弹性下拉,
- 内部滑动与窗口下拉事件冲突(内部虚拟滑动时,总是触发系统页面下拉),无法正常交互
问题剖析:
微信下拉弹性效果其实是浏览器本身的一种特性,当不做任何处理时,达到某个时机,浏览器会认为可以触发整个页面弹性下拉。如果想禁止整个页面的下拉回弹,可以通过下面几种方式实现。
方式1
touch-action: none;
阻止了所有事件
方式2
类似这种暴力方式 会解决某一区域滑动阻止触发 整个页面弹性下拉
document.body.addEventListener('touchmove',
function (e) {
e.preventDefault()
},
{ passive: false })
特点: 简单粗暴直接
弊端:
1. 如果全局给body处理,过于直接,如果其他区域存在内部滑动,导致相应区域失效
2. React事件绑定无法通过onTouchMove event.preventDefault() 解决,没有提供类似VUE v-on:touchmove.prevent 。。。需要手动addEventListener + { passive: false } 绑定处理
方式3 区域滚动或者区域虚拟滚动
滚动区域 A , A区域的包裹层 AWrapper AWrapper绑定touchmove, touchstart, touchend 事件,处理触摸滚动操作A的展示区域。
当A 滚动到顶部(AWrapper.scrollTop === 0) 继续向下touchmove,浏览器会触发祖先元素滚动,直至会出现页面弹性下拉。
可以在A 与 AWapper中间增加一层 AParent 区域,此区域比AWrapper 高度偏高1~2px即可
原始处理绑定方式不变,只需要在touch事件中设置保持AWrapper.scrollTop = 1px 即可!
不管内部滚动到顶部或是什么位置[AParent:overflow:auto方式](或者监听touch偏移后 translateY 的 虚拟滚动 [AParent:overflow:hidden方式]),都不会触发页面滚动, 且AParent 1px偏移基本不会对视觉产生影响!!