android scrollview嵌套scrollview,gridview,listview的方法和深层次原因

scrollview如何嵌套scrollview,gridview,listview的方法,我想大家在网上一搜一大把,总体来说又两个:

1.不要这么做,google告诉我们的,确实,这么做有点不好,但有时候确实要这么做,因为懒和方便

2.

        @Override
	protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
		int extendHeight = MeasureSpec.makeMeasureSpec(Integer.MAX_VALUE >> 2, MeasureSpec.AT_MOST);
		super.onMeasure(widthMeasureSpec, extendHeight);
	}
重载onmeasure函数,在里面将这个需要嵌套空间的的高度设置成wrapcontent,并且maxheight变成最大,为什么要右移两位,因为前面两位是用来表示match_parent和wrap_content的,不是具体的高度。这种解决方法其实很简单,就是子view的高度我给你弄到你所需要的最大,你需要多大我就在父控件中给你分配多高的高度,让你不需要自己滑动。


原因:scrollview源码https://android.googlesource.com/platform/frameworks/base/+/refs/heads/master/core/java/android/widget/ScrollView.java

         switch (action & MotionEvent.ACTION_MASK) {
            case MotionEvent.ACTION_MOVE: {
                /*
                 * mIsBeingDragged == false, otherwise the shortcut would have caught it. Check
                 * whether the user has moved far enough from his original down touch.
                 */
                /*
                * Locally do absolute value. mLastMotionY is set to the y value
                * of the down event.
                */
                final int activePointerId = mActivePointerId;
                if (activePointerId == INVALID_POINTER) {
                    // If we don't have a valid id, the touch down wasn't on content.
                    break;
                }
                final int pointerIndex = ev.findPointerIndex(activePointerId);
                if (pointerIndex == -1) {
                    Log.e(TAG, "Invalid pointerId=" + activePointerId
                            + " in onInterceptTouchEvent");
                    break;
                }
                final int y = (int) ev.getY(pointerIndex);
                final int yDiff = Math.abs(y - mLastMotionY);
                if (yDiff > mTouchSlop && (getNestedScrollAxes() & SCROLL_AXIS_VERTICAL) == 0) {
                    mIsBeingDragged = true;
                    mLastMotionY = y;
                    initVelocityTrackerIfNotExists();
                    mVelocityTracker.addMovement(ev);
                    mNestedYOffset = 0;
                    if (mScrollStrictSpan == null) {
                        mScrollStrictSpan = StrictMode.enterCriticalSpan("ScrollView-scroll");
                    }
                    final ViewParent parent = getParent();
                    if (parent != null) {
                        parent.requestDisallowInterceptTouchEvent(true);
                    }
                }
                break;
            }

这个函数中有比较重要的两句

if (yDiff > mTouchSlop && (getNestedScrollAxes() & SCROLL_AXIS_VERTICAL) == 0) {
                    mIsBeingDragged = true;

getNestedScrollAxes()这个函数为5.0添加的,应该是判断scrollview的滑动轴是否是竖直的,所以可以见到,只要move事件的移动距离大于一定的距离则,父控件scrollview就会截取所有的touchevent,这样子控件无论如何也接受不到touchevent了,当然也就不能滑动了。


PS:我无意中发现一种如何滑动的方法,就是用一个手指按住父控件不动,用另一个手指去滑动gridview类的子控件就能滑动了,具体为啥应该就是两个手指的手势处理了



评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值