使用RecyclerView自定义onItemTouchListener进行Android数据绑定

时间:2017-04-08 16:57:12

标签: android android-recyclerview ontouchlistener android-databinding

我已经掌握了很好的Android数据绑定,但我仍然坚持我的应用程序中的最后一件事,我还没有能够绑定数据绑定。我有一个RecyclerView,我已经实现了一个自定义触摸侦听器来处理短按和长按。我只是不确定我应该绑定什么。甚至可以为onItemTouchListener使用数据绑定吗?我将粘贴我的代码,并希望有人可以通过告诉我应该尝试绑定的内容,或者是否有一点来指出我正确的方向。

触控听众:

public class RecyclerViewTouchListener implements RecyclerView.OnItemTouchListener
{
    private RecyclerViewClickListener clickListener;
    private GestureDetector gestureDetector;

    public RecyclerViewTouchListener(Context context, final RecyclerView recycleView, final RecyclerViewClickListener cl)
    {
        this.clickListener = cl;
        gestureDetector = new GestureDetector(context, new GestureDetector.SimpleOnGestureListener()
        {
            @Override
            public boolean onSingleTapUp(MotionEvent e)
            {
                return true;
            }

            @Override
            public void onLongPress(MotionEvent e)
            {
                View child = recycleView.findChildViewUnder(e.getX(), e.getY());
                if (child != null && cl != null)
                {
                    cl.onLongClick(child, recycleView.getChildAdapterPosition(child));
                }
            }
        });
    }

    @Override
    public boolean onInterceptTouchEvent(RecyclerView rv, MotionEvent e)
    {
        View child = rv.findChildViewUnder(e.getX(), e.getY());
        if (child != null && clickListener != null && gestureDetector.onTouchEvent(e))
        {
            clickListener.onClick(child, rv.getChildAdapterPosition(child));
        }

        return false;
    }

    @Override
    public void onTouchEvent(RecyclerView rv, MotionEvent e)
    {
    }

    @Override
    public void onRequestDisallowInterceptTouchEvent(boolean disallowIntercept)
    {
    }
}

点击监听器:

public interface RecyclerViewClickListener
{
    void onClick(View view, int position);
    void onLongClick(View view, int position);
}

当前的xml:

<?xml version="1.0" encoding="utf-8"?>
<layout xmlns:android="http://schemas.android.com/apk/res/android">

    <data>
        <variable
            name="activity"
            type="com.redacted.ListActivity"/>
    </data>

    <android.support.design.widget.CoordinatorLayout
        xmlns:app="http://schemas.android.com/apk/res-auto"
        xmlns:tools="http://schemas.android.com/tools"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:fitsSystemWindows="true"
        tools:context="com.redacted.ListActivity">

        <android.support.design.widget.AppBarLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:theme="@style/AppTheme.AppBarOverlay">

            <android.support.v7.widget.Toolbar
                android:id="@+id/toolbar"
                android:layout_width="match_parent"
                android:layout_height="?attr/actionBarSize"
                android:background="?attr/colorPrimary"
                app:popupTheme="@style/AppTheme.PopupOverlay"/>

        </android.support.design.widget.AppBarLayout>

        <android.support.constraint.ConstraintLayout
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            app:layout_behavior="@string/appbar_scrolling_view_behavior">

            <android.support.v7.widget.RecyclerView
                android:id="@+id/listRv"
                android:layout_width="0dp"
                android:layout_height="0dp"
                android:layout_marginBottom="8dp"
                android:layout_marginTop="8dp"
                app:layout_constraintBottom_toBottomOf="parent"
                app:layout_constraintLeft_toLeftOf="parent"
                app:layout_constraintRight_toRightOf="parent"
                app:layout_constraintTop_toTopOf="parent"/>
        </android.support.constraint.ConstraintLayout>


        <com.github.clans.fab.FloatingActionButton
            xmlns:fab="http://schemas.android.com/apk/res-auto"
            android:id="@+id/addItemFab"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:onClick="@{activity::fabClicked}"
            android:layout_gravity="bottom|end"
            android:layout_margin="@dimen/fab_margin"
            android:src="@drawable/ic_add"
            fab:fab_colorNormal="@color/colorAccent"
            fab:fab_colorPressed="@color/colorAccentLight"
            fab:fab_size="normal"/>

    </android.support.design.widget.CoordinatorLayout>
</layout>

我的活动:

public class ListActivity extends AppCompatActivity
{
    private OrderedRealmCollection<MyObject> allItems;
    private Realm realm;
    private ActivityListBinding b;

    @Override
    protected void onCreate(Bundle savedInstanceState)
    {
        super.onCreate(savedInstanceState);
        b = DataBindingUtil.setContentView(this, R.layout.activity_list);
        b.setActivity(this);

        setSupportActionBar(b.toolbar);

        realm = Realm.getDefaultInstance();

        CreateViewModel();

        b.listRv.setHasFixedSize(true);
        b.listRv.setAdapter(new ListAdapter(allItems, true));
        b.listRv.setLayoutManager(new LinearLayoutManager(this));

        b.listRv.addOnItemTouchListener(new RecyclerViewTouchListener(this,
                b.listRv, new RecyclerViewClickListener()
        {
            @Override
            public void onClick(View view, final int position)
            {
                //unimportant code
            }

            @Override
            public void onLongClick(View view, int position)
            {
                //unimportant code
            }
        }));
    }

    private void CreateViewModel()
    {
        ListViewModel vm = new ListViewModel(realm);
        allItems = vm.getAllItems();
    }

    @Override
    protected void onDestroy()
    {
        super.onDestroy();
        b.listRv.setAdapter(null);
        realm.close();
    }

    public void fabClicked(View view)
    {
        //unimportant code
    }
}

我的目标是以某种方式将OnClickOnLongClick绑定在XML中。如果有更好的方法来处理RecyclerView项目的短期和长期压力,你可以告诉我我的做法也是错误的。

1 个答案:

答案 0 :(得分:0)

  

我的目标是以某种方式在XML中绑定OnClick和OnLongClick

如果我在你身边,我会选择两种不同的界面。但那只是品味问题。要绑定它,您需要一个绑定适配器:

B

当然,您的.h应该为virtual声明一个setter。在你的布局中,你应该有像

这样的东西
@SuppressWarnings("unchecked")
@BindingAdapter("onItemClickListener")
public static <T> void setOnItemClickListener(RecyclerView recyclerView, RecyclerViewClickListener clickListener) {
   if (recyclerView instanceof RecyclerViewTouchListener) {
        ((RecyclerViewTouchListener) recyclerView).setItemClickListener(clickListener);
   }
}