如何使用SnapHelper将捕捉位置从RecycleView的中心向左移动?

时间:2019-12-10 14:26:40

标签: android-recyclerview xamarin.android pagersnaphelper

我有一个包含ImageViews的RecycleView,我的问题是如何将捕捉移动到RecycleView的左侧而不是中心?

当我移动ImageView时,它们会捕捉到中心,并且可以通过覆盖CalculateDistanceToFinalSnap方法将它们移到该“快照窗口”内的左侧或右侧。我想我现在需要将“快照窗口”移到RecycleView的左侧,但是我不知道如何操作,或者还有另一种方法,请帮忙。

这是我的问题的图片,也许它将帮助您更清楚地了解: image

1 个答案:

答案 0 :(得分:0)

我已经实现了此功能,我们需要创建一个类和扩展类LinearSnapHelper并覆盖方法CalculateDistanceToFinalSnapFindSnapView。您可以查看完整的演示here

主要代码如下:

 public class StartSnapHelper: LinearSnapHelper
 {
    private OrientationHelper mVerticalHelper, mHorizontalHelper;

    public StartSnapHelper()
    {
    }

    public override void AttachToRecyclerView(RecyclerView recyclerView)
    {
        base.AttachToRecyclerView(recyclerView);
    }

    public override int[] CalculateDistanceToFinalSnap(RecyclerView.LayoutManager layoutManager, View targetView)
    {
        //return base.CalculateDistanceToFinalSnap(layoutManager, targetView);
        int[] outer = new int[2];

        if (layoutManager.CanScrollHorizontally())
        {
            outer[0] = distanceToStart(targetView, getHorizontalHelper(layoutManager));
        } else {
            outer[0] = 0;
        }

    if (layoutManager.CanScrollVertically()) {
            outer[1] = distanceToStart(targetView, getVerticalHelper(layoutManager));
    } else {
            outer[1] = 0;
    }
    return outer;
    }

    private int distanceToStart(View targetView, OrientationHelper helper)
    {
        return helper.GetDecoratedStart(targetView) - helper.StartAfterPadding;
    }

    public override View FindSnapView(RecyclerView.LayoutManager layoutManager)
    {
        if (layoutManager is LinearLayoutManager) {

            if (layoutManager.CanScrollHorizontally())
            {
                return getStartView(layoutManager, getHorizontalHelper(layoutManager));
            }
            else
            {
                return getStartView(layoutManager, getVerticalHelper(layoutManager));
            }
        }

        return base.FindSnapView(layoutManager);
    }

    private View getStartView(RecyclerView.LayoutManager layoutManager,
                          OrientationHelper helper)
    {

        if (layoutManager is LinearLayoutManager) {
            int firstChild = ((LinearLayoutManager)layoutManager).FindFirstVisibleItemPosition();

            bool isLastItem = ((LinearLayoutManager)layoutManager)
                    .FindLastCompletelyVisibleItemPosition()
                    == layoutManager.ItemCount - 1;

            if (firstChild == RecyclerView.NoPosition || isLastItem)
            {
                return null;
            }

            View child = layoutManager.FindViewByPosition(firstChild);

            if (helper.GetDecoratedEnd(child) >= helper.GetDecoratedMeasurement(child) / 2
                    && helper.GetDecoratedEnd(child) > 0)
            {
                return child;
            }
            else
            {
                if (((LinearLayoutManager)layoutManager).FindLastCompletelyVisibleItemPosition()
                        == layoutManager.ItemCount - 1)
                {
                    return null;
                }
                else
                {
                    return layoutManager.FindViewByPosition(firstChild + 1);
                }
            }
        }
        return base.FindSnapView(layoutManager);
    }


    private OrientationHelper getVerticalHelper(RecyclerView.LayoutManager layoutManager)
    {
        if (mVerticalHelper == null)
        {
            mVerticalHelper = OrientationHelper.CreateVerticalHelper(layoutManager);
        }
        return mVerticalHelper;
    }

    private OrientationHelper getHorizontalHelper(RecyclerView.LayoutManager layoutManager)
    {
        if (mHorizontalHelper == null)
        {
            mHorizontalHelper = OrientationHelper.CreateHorizontalHelper(layoutManager);
        }
        return mHorizontalHelper;
    }
}

并像这样使用:

  SnapHelper snapHelperStart = new StartSnapHelper();
  snapHelperStart.AttachToRecyclerView(recyclerView);