Android 拖转改变视图高度

复制代码
class DraggableBottomView(
    context: Context,
    attrs: AttributeSet? = null,
) :LinearLayout(context, attrs, 0) {

    private var gestureDetector: GestureDetectorCompat
    private var initialY = 0f
    private var initialX = 0f
    private var initialHeight = 0
    private val minHeight: Int
    private val maxHeight: Int
    private val touchSlop: Int //触摸滑动距离
    private var isDragging = false // 是否正在拖动
    private var isUpOrDown = "up" // up向上  down 向下

    init {
        minHeight = CommonUtil.dpToPx(context,200)
        maxHeight = CommonUtil.dpToPx(context,500)
        touchSlop = ViewConfiguration.get(context).scaledTouchSlop
        gestureDetector = GestureDetectorCompat(context, object : GestureDetector.SimpleOnGestureListener() {
            override fun onDown(e: MotionEvent): Boolean {
                initialY = e.rawY
                initialX = e.rawX
                initialHeight = height
                return true
            }
        })

    }

    override fun onTouchEvent(event: MotionEvent): Boolean {
        gestureDetector.onTouchEvent(event)
        when (event.action) {
            MotionEvent.ACTION_MOVE -> {
                val dy = event.rawY - initialY
                val dx = event.rawX - initialX
                if (Math.abs(dy) > touchSlop && Math.abs(dy)>Math.abs(dx)){
                    isUpOrDown = if (dy < 0f) "up" else "down"
                    isDragging = true
                }else{
                    isDragging = false
                }
                // 设置跟随手指滑动
                val newHeight = (initialHeight - dy).toInt()
                val clampedHeight = newHeight.coerceIn(minHeight, maxHeight)
                val params = layoutParams as ViewGroup.LayoutParams
                params.height = clampedHeight
                layoutParams = params
                requestLayout()

            }
            MotionEvent.ACTION_UP, MotionEvent.ACTION_CANCEL -> {
                if (isDragging) {
                    // 滑动松手后的逻辑
                    if (isUpOrDown == "up") {
                        animateHeightChange(maxHeight)
                    } else {
                        // 固定到初始位置位置
                        animateHeightChange(minHeight)
                    }
                    isDragging = false
                } else {

                }
            }
        }
        return true
    }

    private fun animateHeightChange(targetHeight: Int) {
        val valueAnimator = ValueAnimator.ofInt(height, targetHeight)
        valueAnimator.duration = 200 // 动画持续时间,可根据需要调整
        valueAnimator.addUpdateListener { animator ->
            val animatedValue = animator.animatedValue as Int
            val params = layoutParams as ViewGroup.LayoutParams
            params.height = animatedValue
            layoutParams = params
            requestLayout()
        }
        valueAnimator.start()
    }
}
相关推荐
李斯维1 小时前
循序渐进 Android Binder(二):传递自定义对象和 AIDL 回调
android·java·android studio
androidwork1 小时前
OkHttp 3.0源码解析:从设计理念到核心实现
android·java·okhttp·kotlin
像风一样自由2 小时前
【001】frida API分类 总览
android·frida
casual_clover2 小时前
Android 之 kotlin 语言学习笔记四(Android KTX)
android·学习·kotlin
移动开发者1号4 小时前
Android 大文件分块上传实战:突破表单数据限制的完整方案
android·java·kotlin
移动开发者1号4 小时前
单线程模型中消息机制解析
android·kotlin
每次的天空6 小时前
Android第十五次面试总结(第三方组件和adb命令)
android
追随远方6 小时前
Android音频开发:Speex固定帧与变长帧编解码深度解析
android·音视频
消失的旧时光-19436 小时前
Android和硬件通信
android
0wioiw06 小时前
安卓基础(编译.Class)
android