ScrollView Inside ScrollView

AjO*_*ire 30 android scrollview

我知道谷歌的人已经要求我们不要将Scrollable视图放在另一个Scrollable视图中,但他们是否有任何官方声明指示我们不要这样做?

Atu*_*waj 62

试试这个吧

注意:这里的parentScrollView意思是外部ScrollView并且childScrollView意味着Innner ScrollView

parentScrollView.setOnTouchListener(new View.OnTouchListener() {

        @Override
        public boolean onTouch(View v, MotionEvent event) {
        Log.v(TAG, "PARENT TOUCH");

        findViewById(R.id.child_scroll).getParent()
                .requestDisallowInterceptTouchEvent(false);
        return false;
    }
});

childScrollView.setOnTouchListener(new View.OnTouchListener() {

        @Override
        public boolean onTouch(View v, MotionEvent event) {
        Log.v(TAG, "CHILD TOUCH");

        // Disallow the touch request for parent scroll on touch of  child view
        v.getParent().requestDisallowInterceptTouchEvent(true);
        return false;
    }
});
Run Code Online (Sandbox Code Playgroud)


Ped*_*iro 16

这够近了吗?

你永远不应该使用带有ListView的Horizo​​ntalScrollView,因为ListView负责自己的滚动.最重要的是,这样做会使ListView中的所有重要优化都无法处理大型列表,因为它有效地强制ListView显示其整个项目列表以填充Horizo​​ntalScrollView提供的无限容器.

http://developer.android.com/reference/android/widget/Horizo​​ntalScrollView.html

更新:

由于您可能被迫使用二维滚动视图,您可以考虑使用此: blog.gorges.us/2010/06/android-two-dimensional-scrollview/的Internet存档

我没有用过这个,但这可能是一个合理的方法.


zeh*_*zeh 16

Atul Bhardwaj上面的回答是正确的方法.但是如果有人需要将它应用到你对父母的控制较少的ScrollView,我认为这足够灵活,只是它应该工作的方式:

private void makeMyScrollSmart() {
    myScroll.setOnTouchListener(new View.OnTouchListener() {
        @Override
        public boolean onTouch(View __v, MotionEvent __event) {
            if (__event.getAction() == MotionEvent.ACTION_DOWN) {
                //  Disallow the touch request for parent scroll on touch of child view
                requestDisallowParentInterceptTouchEvent(__v, true);
            } else if (__event.getAction() == MotionEvent.ACTION_UP || __event.getAction() == MotionEvent.ACTION_CANCEL) {
                // Re-allows parent events
                requestDisallowParentInterceptTouchEvent(__v, false);
            }
            return false;
        }
    });
}

private void requestDisallowParentInterceptTouchEvent(View __v, Boolean __disallowIntercept) {
    while (__v.getParent() != null && __v.getParent() instanceof View) {
        if (__v.getParent() instanceof ScrollView) {
            __v.getParent().requestDisallowInterceptTouchEvent(__disallowIntercept);
        }
        __v = (View) __v.getParent();
    }
}
Run Code Online (Sandbox Code Playgroud)

该功能的作用是添加一个触摸监听myScroll器,当孩子触摸开始时禁用父母的触摸拦截,然后在触摸实际结束时启用它.您不需要对父级的引用ScrollView,也不必是直接父级...它将在显示列表中移动直到找到它.

在我看来,两全其美.


M. *_*han 7

childScrollView.setOnTouchListener(new View.OnTouchListener() {

      @Override
    public boolean onTouch(View v, MotionEvent event) {

        int action = event.getAction();
        switch (action) {
        case MotionEvent.ACTION_DOWN:
           // Disallow ScrollView to intercept touch events.
          v.getParent().requestDisallowInterceptTouchEvent(true);
           break;

        case MotionEvent.ACTION_UP:
            // Allow ScrollView to intercept touch events.
            v.getParent().requestDisallowInterceptTouchEvent(false);
            break;
        }

        return false;
    }
});
Run Code Online (Sandbox Code Playgroud)

v.getParent()=父scrollView.