问题
I want to disable right to left swipe in ViewPager2.
I basically have a viewpager2 element with 2 pages in my navigation drawer. I want my second page to show up only when I click some element in my first page (right to left swipe from the first page should not open the second page), while when I'm in the second page, the viewpager2 swipe (left to right swipe) should swipe as it should do in viewpager.
I've tried extending the ViewPager2 class and override the touch events, but unfortunately it ViewPager2 is a final class, so I cannot extend it.
Secondly, I tried to use setUserInputEnabled method to false, but this disabled all swipes altogether (I just want to disable right to left swipe). If I could find some listener which checks for the current page before swiping and disable swipe otherwise, it would probably work.
implementation 'androidx.viewpager2:viewpager2:1.0.0-alpha05'
Code for setting up of ViewPager2
ViewPager2 pager = view.findViewById(R.id.pager);
ArrayList<Fragment> abc = new ArrayList<>();
abc.add(first);
abc.add(second);
navigationDrawerPager.setAdapter(new DrawerPagerAdapter(
this, drawerFragmentList));
pager.setAdapter(new FragmentStateAdapter(this), abc);
回答1:
I found a listener which can listen when the user tries to swipe, it'll then check the current page, if it's the first page, disable the user input else enable it as it was by default.
Here's the code snippet for that:-
pager.registerOnPageChangeCallback(new ViewPager2.OnPageChangeCallback() {
@Override
public void onPageScrollStateChanged(int state) {
super.onPageScrollStateChanged(state);
if (state == SCROLL_STATE_DRAGGING && pager.getCurrentItem() == 0) {
pager.setUserInputEnabled(false);
} else {
pager.setUserInputEnabled(true);
}
}
});
Since my scenario was of 2 pages only, checking the page number would be good for me, but in case we have more than 2 pages and we need to disable the swipe in one particular direction, we may use onPageScrolled(int position, float positionOffset, int positionOffsetPixels) listener of viewpager2 and handle the desired scenario according to the positive or negative values of position and positionOffset.
回答2:
Extend the viewpager class and override the functions onInterceptTouchEvent and onTouchEvent. Then identify the direction of the swipe and return false if you don't want to swipe.
You can use this helper method for swipe detection:
float downX; // define class level variable in viewpager
private boolean wasSwipeToLeftEvent(MotionEvent event){
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
downX = event.getX();
return false;
case MotionEvent.ACTION_MOVE:
case MotionEvent.ACTION_UP:
return event.getX() - downX > 0;
default:
return false;
}
}
Then in your method for touch events:
@Override
public boolean onInterceptTouchEvent(MotionEvent event) {
return !this.wasSwipeToLeftEvent(event);
}
@Override
public boolean onTouchEvent(MotionEvent event) {
return return !this.wasSwipeToLeftEvent(event);
}
I modified the code from this answer, if you need more explanation please see this: https://stackoverflow.com/a/34111034/4428159
来源:https://stackoverflow.com/questions/56647971/how-to-disable-swiping-in-specific-direction-in-viewpager2