How to prevent closing Navigation drawer by touch outside the drawer

后端 未结 3 1695
深忆病人
深忆病人 2020-12-20 19:58

I have an Activity with Navigation Drawer. if user device is table and orientation is landscape - I not need to close drawer by click on item in drawer:

if (         


        
相关标签:
3条回答
  • 2020-12-20 20:34

    Based on the other answer which I wrote here. I have modified the code to suit your question. Please check.

    Check more about touch hierarchy here

    dispatchTouchEvent() method should be overridden in Activity class

    @Override    
    public boolean dispatchTouchEvent(MotionEvent event) {
        if (event.getAction() == MotionEvent.ACTION_UP) {
            if (isDrawerOpen()) { //Your code here to check whether drawer is open or not. 
    
                View content = findViewById(R.id.drawer); //drawer view id
                int[] contentLocation = new int[2];
                content.getLocationOnScreen(contentLocation);
                Rect rect = new Rect(contentLocation[0],
                    contentLocation[1],
                    contentLocation[0] + content.getWidth(),
                    contentLocation[1] + content.getHeight());
    
                if (!(rect.contains((int) event.getX(), (int) event.getY()))) {
                    isOutSideClicked = true;
                } else {
                    isOutSideClicked = false;
                }
    
            } else {
                return super.dispatchTouchEvent(event);
            }
        } else if (event.getAction() == MotionEvent.ACTION_DOWN && isOutSideClicked) {
            isOutSideClicked = false;
            return super.dispatchTouchEvent(event);
        } else if (event.getAction() == MotionEvent.ACTION_MOVE && isOutSideClicked) {
            return super.dispatchTouchEvent(event);
        }
    
        if (isOutSideClicked) {
            return true; //restrict the touch event here
        }else{
            return super.dispatchTouchEvent(event);
        }
    }
    

    Note: As mentioned in the question comments, this is against of Android guidelines. So try to avoid it until unless it is mandatory.

    0 讨论(0)
  • 2020-12-20 20:47

    Simplified version of Noundla's answer which works for me. I wrote my custom Drawer which extends DrawerLayout and implement dispatchTouchEvent() method.

    @Override
    public boolean dispatchTouchEvent(MotionEvent event) {
        if (!this.isDrawerOpen(Gravity.LEFT)) {
            return super.dispatchTouchEvent(event);
        }
        boolean isOutSideClicked = false;
        if (event.getAction() == MotionEvent.ACTION_UP) {
            View content = findViewById(R.id.drawer_view); 
            int[] contentLocation = new int[2];
            content.getLocationOnScreen(contentLocation);
            Rect rect = new Rect(contentLocation[0],
                    contentLocation[1],
                    contentLocation[0] + content.getWidth(),
                    contentLocation[1] + content.getHeight());
            isOutSideClicked = !(rect.contains((int) event.getX(), (int) event.getY()));
        }
        this.setDrawerLockMode(isOutSideClicked ? DrawerLayout.LOCK_MODE_LOCKED_OPEN : DrawerLayout.LOCK_MODE_UNLOCKED);
        return super.dispatchTouchEvent(event);
    }
    

    Also if you want to keep interact with main content fragment while drawer is open you should add this line at the beginning of the method.

    getChildAt(0).dispatchTouchEvent(event);
    
    0 讨论(0)
  • 2020-12-20 20:50

    it very simple use your drawer instance to prevent

    1. implement DrawerLayout.DrawerListener

    2. add this single statement inside this method us

     @Override
    public void onDrawerOpened(View drawerView) {
        drawer.setDrawerLockMode(DrawerLayout.LOCK_MODE_LOCKED_OPEN);//DrawerLayout instance
    }
    
    0 讨论(0)
提交回复
热议问题