Android: problem with clicking / dragging a nested bottom sheet

I have a bottom sheet nested in another bottom sheet ( FrameLayoutsusing layout behavior BottomSheet)

I also have a couple of “drop-in views” ( FrameLayouts) that have clicks attached to expand the bottom sheet (s), respectively, when clicked.

So, the application basically has 3 main screens. The "main container", then the first "bottom sheet", which can be expanded in full screen mode, and then at the bottom of the bottom sheet, is the second bottom sheet, which can also be expanded to full screen.

Problem:

When I add a RecyclerViewnested bottom sheet to the container view, the drag and drop stops working for the second view (view sheet 2). If I delete peek view ClickListeneror RecyclerView, everything will work fine.

Desired Result:

Both bottom sheets should remain draggable, and view views should be available to expand their parent bottom sheet. The bottom sheet should respond to nested scrolls, as usual.

I tried to remove ClickListenerand use touch gestures instead, but nothing I tried seems to help.

I use v25.3.1design support libraries, and I can reproduce this problem based on Galaxy S4 with version 4.4.4 and Nexus 6P with a margin of 7.1.2. (I have no other devices available).

github , : https://github.com/timusus/bottomsheet-test

, :

123

( ):

<CoordinatorLayout>

    <FrameLayout
        android:id="@+id/mainContainer" 
        android:layout_height="match_parent"/>

    <FrameLayout
        android:id="@+id/sheet1" 
        android:layout_height="match_parent"
        app:layout_behavior="CustomBottomSheetBehavior"
        app:behavior_peekHeight="64dp">

        <FrameLayout
            android:id="@+id/sheet1Container"
            android:layout_height="match_parent"/>

        <CoordinatorLayout>

        <FrameLayout
            android:id="@+id/sheet2
            android:layout_height="match_parent"
            app:layout_behavior="CustomBottomSheetBehavior"
            app:behavior_peekHeight="64dp">

            <FrameLayout
                android:id="@+id/sheet2Container"
                android:layout_height="match_parent">

                <!-- Problematic RecyclerView -->
                <RecyclerView 
                android:layout_height="match_parent"/>

            </FrameLayout>

            <!-- Problematic Click Listener on this view -->
            <FrameLayout 
                android:id="@+id/sheet2PeekView"
                android:layout_height=64dp"/>

        </FrameLayout>

        </CoordinatorLayout>

        <FrameLayout
            android:id="@+id/sheet1PeekView"
            android:layout_height=64dp"/>

    </FrameLayout>
</CoordinatorLayout/>

CustomBottomSheetBehavior - BottomSheetBehavior, , . "" "", .

public class CustomBottomSheetBehavior<V extends View> extends BottomSheetBehavior<V> {

    private boolean allowDragging = true;

    public void setAllowDragging(boolean allowDragging) {
        this.allowDragging = allowDragging;
    }

    @Override
    public boolean onInterceptTouchEvent(CoordinatorLayout parent, V child, MotionEvent event) {
        if (!allowDragging) {
            return false;
        }

        return super.onInterceptTouchEvent(parent, child, event);
    }
}

, BottomSheetBehavior , , , :

FrameLayout sheet1 = (FrameLayout) findViewById(R.id.sheet1);
bottomSheetBehavior1 = (CustomBottomSheetBehavior) BottomSheetBehavior.from(sheet1);

FrameLayout sheet2 = (FrameLayout) findViewById(R.id.sheet2);
       bottomSheetBehavior2 = (CustomBottomSheetBehavior) BottomSheetBehavior.from(sheet2);
       bottomSheetBehavior2.setBottomSheetCallback(new BottomSheetBehavior.BottomSheetCallback() {
           @Override
           public void onStateChanged(@NonNull View bottomSheet, int newState) {
                //If the second sheet is expanded or dragging, don't allow the first sheet to respond to touch events.
               if (newState == BottomSheetBehavior.STATE_EXPANDED || newState == BottomSheetBehavior.STATE_DRAGGING) {
                   bottomSheetBehavior1.setAllowDragging(false);
               } else {
                   bottomSheetBehavior1.setAllowDragging(true);
               }
           }

, onInterceptTouchEvent BottomSheet, RecyclerView, View.ClickListener , , - .

.

+6
1

Fixed

, onInterceptTouchEvent BottomSheet, RecyclerView, View.ClickListener, , - .

CustomBottomSheetBehavior View.ClickListener

bottomSheetBehavior1 getSheet2PeekView, getSheet2PeekView bottomSheetBehavior1. > false bottomSheetBehavior2 true


, .

findViewById(getSheet2PeekViewResId()).setOnTouchListener(new OnTouchListener() {
        @Override
        public boolean onTouch(View v, MotionEvent event) {
            Log.e(TAG, "onTouch: ");
            bottomSheetBehavior1.setAllowDragging(false);
            bottomSheetBehavior2.setAllowDragging(true);
            return false;
        }
    });

Pull Request .

+8

Source: https://habr.com/ru/post/1016942/


All Articles