解决ViewPager和DrawerLayout滑动冲突

1. 问题描述

首先我做了一个Activity,Activity的布局中放了ViewPager,用于管理Fragment

效果如下图:

然后我想放一个DrawerLayout,在第一个Fragment的时候可以向右滑拉出个人信息。

这个时候我发现出问题了,因为ViewPager的优先级高于DrawerLayout,所以判定是ViewPager在滑动,导致DrawerLayout出不来。

同时,如果你在ToolBar中设置一个按钮,用来展开DrawerLayout,你会发现:当你想要收起抽屉布局的时候,ViewPager滑动了。

2. 解决思路

  1. 首先应该明确一点,这个DrawerLayout应该写在Activity中,而不是写在第一个Fragment中
  2. 在第一个页面时,禁止从左向右滑动
  3. 当抽屉拉开的时候,我们也要禁止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) {}
    })
}
相关推荐
消失的旧时光-194315 分钟前
Flutter 响应式 + Clean Architecture / MVU 模式 实战指南
android·flutter·架构
404未精通的狗36 分钟前
(数据结构)栈和队列
android·数据结构
恋猫de小郭1 小时前
今年各大厂都在跟进的智能眼镜是什么?为什么它突然就成为热点之一?它是否是机会?
android·前端·人工智能
游戏开发爱好者83 小时前
iOS 混淆工具链实战 多工具组合完成 IPA 混淆与加固 无源码混淆
android·ios·小程序·https·uni-app·iphone·webview
豆豆豆大王8 小时前
Android 数据持久化(SharedPreferences)
android
Paper_Love8 小时前
RK3588-android-reboot命令内核调用流程
android
介一安全8 小时前
【Frida Android】基础篇12:Native层hook基础——调用原生函数
android·网络安全·逆向·安全性测试·frida·1024程序员节
2501_916008899 小时前
用多工具组合把 iOS 混淆做成可复用的工程能力(iOS混淆|IPA加固|无源码混淆|Ipa Guard|Swift Shield)
android·开发语言·ios·小程序·uni-app·iphone·swift
Zach_yuan9 小时前
程序地址空间
android·linux·运维·服务器
带电的小王10 小时前
llama.cpp:Android端测试Qwen2.5-Omni
android·llama.cpp·qwen2.5-omni