Android 临时/动态禁用Viewpager中的单个页面

Android 临时/动态禁用Viewpager中的单个页面,android,android-fragments,android-viewpager,android-tabs,Android,Android Fragments,Android Viewpager,Android Tabs,我有一个扩展的FragmentPagerAdapter,它为一个ViewPager提供3个片段,给我3个页面,我可以在它们之间滑动,也可以使用添加到actionbar的选项卡手动选择页面 我想暂时禁用用户访问最终页面(禁用任何特定页面的更通用的解决方案也会很有趣,但不是必需的),无论是哪种导航类型。然后,我将使用来自其中一个片段的回调来重新启用它们的访问 我已经阅读了一些类似问题的答案,这些问题是关于通过覆盖onTouchEvent和onInterceptTouchEvent,然后在其中使用一些

我有一个扩展的FragmentPagerAdapter,它为一个ViewPager提供3个片段,给我3个页面,我可以在它们之间滑动,也可以使用添加到actionbar的选项卡手动选择页面

我想暂时禁用用户访问最终页面(禁用任何特定页面的更通用的解决方案也会很有趣,但不是必需的),无论是哪种导航类型。然后,我将使用来自其中一个片段的回调来重新启用它们的访问

我已经阅读了一些类似问题的答案,这些问题是关于通过覆盖onTouchEvent和onInterceptTouchEvent,然后在其中使用一些自定义手势检测,甚至使用beginFakeDrag()的半解决方案来不允许刷卡

我当前的解决方案只是在适配器中设置一个较小的项计数,确保使用notifyDataSetChanged(),并在必要时将其更改回原来的值。除了这些方法之外,还有什么优雅的替代方法吗?也许是一种不需要更改数据集的方法

我还看到ActionBar.Tab没有setEnable()方法,大多数人建议只删除该选项卡。有没有办法让选项卡保持可见但不可选择?我的方法是定义禁用哪个选项卡,并在用户选择禁用的选项卡时重新选择先前选择的选项卡


编辑:我的目标是禁用制表符和滑动到最后一页。

您肯定要创建自己的自定义ViewPager子类。我创建了一个名为
CustomSwipePager
的简单自定义
ViewPager
,它将在需要时处理阻止用户交互的问题

public class CustomSwipeViewPager extends ViewPager {

    private boolean mLastPageEnabled = false;
    private int mLastPageIndex = 0;

    public NoSwipeViewPager(Context context) {
        super(context);
    }

    public NoSwipeViewPager(Context context, AttributeSet attrs) {
        super(context, attrs);
    }

    public void setLastPageEnabled(boolean enabled) {
        mLastPageEnabled = enabled;
    }

    public void setLastPageIndex(int index) {
        mLastPageIndex = index;
    }

    @Override
    public boolean onInterceptTouchEvent(MotionEvent event){

        if(!mLastPageEnabled && getCurrentItem() >= (mLastPageIndex - 1)) {
            // Always return false to disable user swipes
            return false;
        }

        return true;
    }

    @Override
    public boolean onTouchEvent(MotionEvent event) {

        if (!mLastPageEnabled && getCurrentItem() >= (mLastPageIndex - 1)) {
            // Always return false to disable user swipes
            return false;
        }

        return true;
    }
}
在类
setLastPageEnabled()
setLastPageIndex()
中,有两个关键方法可以利用。您可以将最后一页索引设置为所需的任何值,如果您有三项,则可以将其设置为2。然后还可以使用
setLastPageEnabled(false)
禁用刷卡或使用
setLastPageEnabled(true)
重新启用

您可以将此自定义视图包括到布局中,如下所示:

<com.mypackage.CustomSwipeViewPager
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:id="@+id/custom_swipe_view_pager"
    android:layout_width="match_parent"
    android:layout_height="match_parent" />

为什么不将最后一个选项卡的布局切换到用户无法交互的位置
ViewPager
并不真正适合这些需求。是的,您可以通过更改数据集来动态使用它,但是阻止选项卡ui要比更改
ViewPager
的行为容易得多。好吧,我并不是在寻找更简单的方法。我同时使用标签和滑动进行导航。我对这两个问题都有可行的解决方案;我只是想寻求其他更好的打包建议。但是你是对的,无论如何,阻止与页面的交互是一个可行的解决方案。你还必须考虑到一个用户没有真正使用Android设备上的阻止标签页面。因此,除非你让他完全明白你的行为,否则他可能会觉得你的应用程序工作不正常,因为标签通常都是可以访问的。我个人总是有点困惑,当我看到禁用的按钮,当我点击它们或其他奇怪的东西时,它们什么也不做。我的第一个想法总是“它是正常工作还是一个bug?”。因此,也许使用另一个ui解决方案会更好。这是一个非常好的观点。最终,问题的一部分归结于用户反馈,我会考虑我最终解决方案的所有可能性。话虽如此,问题依然存在,是否会让用户感到困惑将在最终确定之前决定。作为旁注,我已经在考虑删除该选项卡,直到启用最后一页。这类似于我在问题中提到的解决方案,其中覆盖onTouchEvent和onTouchEvent。非常干净的实现。此解决方案缺少的部分是检测手势的方向,以便仍然允许从倒数第二页滑回上一页。如果我决定走这条路,我会把我的代码包括进去。正如@einschnaehkeee在他的评论中暗示的那样,这有点像是对ViewPager的黑客攻击,但我已经考虑了其他选项,并认为这个功能最适合我的用例。我想我希望我错过了一些明显的东西。我想唯一的选择是根据需要添加/删除最后一页。在这一点上,您可能需要考虑UI的更改。也许最后一页甚至不属于ViewPager,我不熟悉您的设计思想是的,我考虑过其他UI选项。为此目的使用移动软件已经相当独特,所以我不得不做很多决定,是坚持使用Android API组件还是重新设计。但我确实有理由认为当前我希望在ViewPager中显示该页面;我只是觉得它们与发布的问题无关,因为这是一个假设。谢谢你的建议。
private CustomSwipeViewPager mPager;

@Override
protected void onCreate(Bundle savedInstanceState){
    super.onCreate(savedInstanceState);

    mPager = (CustomSwipeViewPager) findViewById(R.id.custom_swipe_view_pager);
    mPager.setLastPageEnabled(false);
    mPager.setLastPageIndex(2);
}