android - ViewPager 的 fakeDragBy() 或 setCurrentItem() 不会吸附到当前项目

标签 android gallery android-viewpager

已解决。请参阅标记为正确的答案以及我的评论。如有必要,可以发布示例代码


我正在使用 VelocityViewPager实现“ throw ”行为。有一个已知的行为,如果您将页面拖动一定量,页面不会对齐。我试图绕过它但收效甚微......

尝试 1

我可以使用 setCurrentItem 使捕捉 Action 正常工作。需要注意的是,只有当我在当前页面之前或之后调用项目上的函数时,它才会捕捉,例如 setCurrentItem(getCurrentItem()+1)

所以这个解决方案有效,但如果我必须将当前项目设置得比他们预期的更远,它会给用户带来糟糕的用户体验。

有没有人对我如何调用 setCurrentItem(getCurrentItem()) 并让它实际动画/滚动/捕捉有任何建议?消息来源暗示它应该。 r7 code似乎总是调用滚动功能。

尝试 2

作为另一个测试,我进行了多次 fakeDragBy(1) 调用来拖动 ViewPager,认为它会在达到某个阈值后捕捉,但事实并非如此案子。 是什么阻止了 ViewPager 对齐?

如果您有兴趣,下面是重现此代码的代码。我用了同样的VelocityViewPager具有以下更改的代码

VelocityViewPager.java

public class VelocityViewPager extends ViewPager implements GestureDetector.OnGestureListener {
...
    @Override
    public boolean onTouchEvent(MotionEvent event) {
        // give all the events to the gesture detector. I'm returning true here so the viewpager doesn't
        // get any events at all, I'm sure you could adjust this to make that not true.
        mGestureDetector.onTouchEvent(event);
        if (event.getAction() == MotionEvent.ACTION_UP) {
            setCurrentItem(getCurrentItem(), true);
            Log.d("VelocityViewPager", "Setting to item " + getCurrentItem());
        }
        return true;
    }
....
}

MainActivity.java

package com.example.velocityviewpager;

import android.graphics.Color;
import android.os.Bundle;
import android.app.Activity;
import android.support.v4.view.PagerAdapter;
import android.view.Gravity;
import android.view.Menu;
import android.view.View;
import android.view.ViewGroup;
import android.widget.TextView;

public class MainActivity extends Activity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        VelocityViewPager pager = (VelocityViewPager)findViewById(R.id.view);
        PagerAdapter adapter = new PagerAdapter() {
            @Override
            public int getCount() {
                return 20;
            }

            @Override
            public Object instantiateItem(ViewGroup container, int position) {
                TextView view = new TextView(MainActivity.this);
                view.setText("Item "+position);
                view.setGravity(Gravity.CENTER);
                view.setBackgroundColor(Color.argb(255, position * 10, position * 10, position * 10));
                view.setTextColor(Color.argb(255, 200, 200, 200));

                container.addView(view);
                return view;
            }

            @Override
            public void destroyItem(ViewGroup container, int position, Object object) {
                container.removeView((View)object);
            }

            @Override
            public boolean isViewFromObject(View view, Object o) {
                return (view == o);
            }
        };
        pager.setAdapter(adapter);
        adapter.notifyDataSetChanged();

        pager.setOffscreenPageLimit(3);
        pager.setCurrentItem(0, true);
    }


    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        // Inflate the menu; this adds items to the action bar if it is present.
        getMenuInflater().inflate(R.menu.main, menu);
        return true;
    }

}

activity_main.xml

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:paddingLeft="@dimen/activity_horizontal_margin"
    android:paddingRight="@dimen/activity_horizontal_margin"
    android:paddingTop="@dimen/activity_vertical_margin"
    android:paddingBottom="@dimen/activity_vertical_margin"
    tools:context=".MainActivity">

    <view
            android:layout_width="300dip"
            android:layout_height="300dip"
            class="com.example.velocityviewpager.VelocityViewPager"
            android:id="@+id/view"
            android:layout_alignParentTop="true"
            android:layout_alignParentLeft="true"
            android:layout_alignParentRight="true"/>

</RelativeLayout>

最佳答案

我找到了解决方法。我跟踪之前完成的 Action ,当 MotionEvent.ACTION_UP 发生时,我触发了新的 Action 。我不确定这种方式在逻辑上是否正确(这是好的方向吗?这对新的尝试来说是否是一个好的速度?),但我测试了它,它有效:

private boolean isLeftDirection = false;

@Override
public boolean onTouchEvent(MotionEvent event) {
    // give all the events to the gesture detector. I'm returning true here
    // so the viewpager doesn't
    // get any events at all, I'm sure you could adjust this to make that
    // not true.

    if (event.getAction() == MotionEvent.ACTION_UP) {
        int id = getCurrentItem();
        setCurrentItem(id, true);
        if (isLeftDirection){
            mFlingRunnable.startUsingVelocity((int) 1);
        } else {
            mFlingRunnable.startUsingVelocity((int) -1);
        }
    }
    mGestureDetector.onTouchEvent(event);
    return true;
}

@Override
public boolean onScroll(MotionEvent e1, MotionEvent e2, float distX,
        float distY) {
    trackMotion(-distX);
    if (distX > 0){ 
        isLeftDirection = true;}
    else{
        isLeftDirection = false;
    }
    return false;
}

关于android - ViewPager 的 fakeDragBy() 或 setCurrentItem() 不会吸附到当前项目,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/16994595/

相关文章:

java - 如何通过单击一个创建的按钮来退出整个应用程序?

android - 为什么 Android Studio 中的模拟器拒绝连接到互联网?

ios - Swift - 强制从库和相机中获取方形照片

android - 嵌套 fragment 未显示在 ViewPager 中

安卓 : ViewPager with a dynamic height within a ScrollView

android - ViewPager 内的 LinearLayout 禁用滑动

java - 将 PHP Rijndael 算法重写为 Java (Android)

android - 将不同的 ViewModel 传递给包含布局

python - 如何创建 Django 图片库

PHP画廊中的CSS布局