1. 问题描述
首先我做了一个Activity,Activity的布局中放了ViewPager,用于管理Fragment
效果如下图:

然后我想放一个DrawerLayout,在第一个Fragment的时候可以向右滑拉出个人信息。
这个时候我发现出问题了,因为ViewPager的优先级高于DrawerLayout,所以判定是ViewPager在滑动,导致DrawerLayout出不来。
同时,如果你在ToolBar中设置一个按钮,用来展开DrawerLayout,你会发现:当你想要收起抽屉布局的时候,ViewPager滑动了。
2. 解决思路
- 首先应该明确一点,这个DrawerLayout应该写在Activity中,而不是写在第一个Fragment中
- 在第一个页面时,禁止从左向右滑动
- 当抽屉拉开的时候,我们也要禁止ViewPager滑动
3. 解决方案
3.1 布局

3.2 自定义MyViewPager
kotlin
class MyViewPager : ViewPager {
var xDistance: Float = 0f
var xLast: Float = 0f
private var noScroll: Boolean = false
constructor(context: Context?) : super(context!!)
constructor(context: Context?, attrs: AttributeSet?) : super(context!!, attrs)
/**
* 禁止第一个fragment右滑
*/
override fun onInterceptTouchEvent(ev: MotionEvent?): Boolean {
if (noScroll) return false
when(ev?.action){
MotionEvent.ACTION_DOWN -> {
xDistance = 0f
xLast = ev.x
}
MotionEvent.ACTION_MOVE -> {
val curX: Float = ev.x
// 第一个fragment禁止右滑
if (xLast-curX<0 && currentItem==0) return false
}
}
return super.onInterceptTouchEvent(ev)
}
/**
* 控制viewPager是否能滑动
*/
fun setNoScroll(_noScroll: Boolean){
noScroll = _noScroll
}
override fun onTouchEvent(ev: MotionEvent?): Boolean {
if (noScroll) return false
else return super.onTouchEvent(ev)
}
}
3.3 设置Activity中的DrawerLayout
kotlin
fun setDrawerLayout(){
binding.userInfoView.setDrawerListener(object : DrawerLayout.DrawerListener{
override fun onDrawerSlide(drawerView: View, slideOffset: Float) {}
override fun onDrawerOpened(drawerView: View) {
binding.viewPager.setNoScroll(true)
}
override fun onDrawerClosed(drawerView: View) {
binding.viewPager.setNoScroll(false)
}
override fun onDrawerStateChanged(newState: Int) {}
})
}