我正在尝试将一些iOS功能移植到Android.
我打算创建一个表格,向左滑动显示2按钮:编辑和删除.
我一直在玩它,我知道我非常接近.秘密真正在于OnChildDraw方法.
我想绘制一个适合文本删除的Rect,然后用它们各自的背景颜色绘制除此之外的Edit文本.单击时剩余的空白区域应将行恢复到其初始位置.
我设法在用户向侧面滑动时绘制背景,但我不知道如何添加侦听器,一旦将其滑到一边,拖动功能就开始行为不端.
我正在研究Xamarin,但纯java解决方案也被接受,因为我可以轻松地将它们移植到c#.
public class SavedPlacesItemTouchHelper : ItemTouchHelper.SimpleCallback
{
private SavedPlacesRecyclerviewAdapter adapter;
private Paint paint = new Paint();
private Context context;
public SavedPlacesItemTouchHelper(Context context, SavedPlacesRecyclerviewAdapter adapter) : base(ItemTouchHelper.ActionStateIdle, ItemTouchHelper.Left)
{
this.context = context;
this.adapter = adapter;
}
public override bool OnMove(RecyclerView recyclerView, RecyclerView.ViewHolder viewHolder, RecyclerView.ViewHolder target)
{
return false;
}
public override void OnSwiped(RecyclerView.ViewHolder viewHolder, int direction)
{
}
public override void OnChildDraw(Canvas c, RecyclerView recyclerView, RecyclerView.ViewHolder viewHolder, float dX, float dY, int actionState, bool isCurrentlyActive)
{ …Run Code Online (Sandbox Code Playgroud) 我已经实现了如下所述的ItemTouchHelper:https://medium.com/@ipaulpro/drag-and-swipe-with-recyclerview-b9456d2b1aaf#.k7xm7amxi
如果RecyclerView是CoordinatorLayout的子项,则一切正常.
但是如果RecyclerView是CoordinatorLayout中NestedScrollView的子代,则拖动滚动不再起作用.拖动项目并将其移动到屏幕的顶部或底部,RecyclerView不会像它不是NestedScrollView的子项那样滚动.
有任何想法吗?
android android-recyclerview android-nestedscrollview itemtouchhelper
我在android中有一个Recycler View.我已经附上了ItemTouchHelper它.我只启用了从左到右的滑动.
因此,当我滑动Recycler视图的任何项目时,项目开始向右移动,在左侧我绘制文本.这可以 .我的要求是,我希望允许用户仅滑动到一定距离,当达到该距离并且用户松开触摸时,正在滑动的项目应该返回到其向左的位置.
问题是,当我从左向右滑动时,视图会完全滑出屏幕.如何限制它只能滑到一定距离?我该怎么做 ?
这是我的项目触摸回调的代码:
private void initSwipe(){
ItemTouchHelper.SimpleCallback simpleItemTouchCallback = new ItemTouchHelper.SimpleCallback(0, ItemTouchHelper.RIGHT) {
@Override
public boolean onMove(RecyclerView recyclerView, RecyclerView.ViewHolder viewHolder, RecyclerView.ViewHolder target) {
return false;
}
@Override
public void onSwiped(RecyclerView.ViewHolder viewHolder, int direction) {
int position = viewHolder.getAdapterPosition();
}
@Override
public void onChildDraw(Canvas c, RecyclerView recyclerView, RecyclerView.ViewHolder viewHolder, float dX, float dY, int actionState, boolean isCurrentlyActive) {
ViewHolder viewHolder1 = (ViewHolder)viewHolder;
int position = viewHolder1.getAdapterPosition();
MyItem item = dataList.get(position);
if (item==null )return;
if(actionState == …Run Code Online (Sandbox Code Playgroud) 首先,我整天都在努力,但无法完成任何事情.我有一个RecyclerView使用RecyclerView's 的适配器SortedList.我尝试TouchHelper使用回调类实现:
public class TimerListTouchHelperCallback extends ItemTouchHelper.SimpleCallback {
private OnItemChangeListener onItemChangeListener;
public TimerListTouchHelperCallback(OnItemChangeListener listener, int dragDirs, int swipeDirs) {
super(dragDirs, swipeDirs);
this.onItemChangeListener = listener;
}
@Override
public int getSwipeDirs(RecyclerView recyclerView, RecyclerView.ViewHolder viewHolder) {
TimerHolder holder = (TimerHolder) viewHolder;
int holderState = holder.getState();
if (holderState == TimerHolder.TIMER_PENDING_DELETE) return 0;
else return super.getSwipeDirs(recyclerView, viewHolder);
}
@Override
public boolean onMove(RecyclerView recyclerView, RecyclerView.ViewHolder viewHolder, RecyclerView.ViewHolder target) {
return false;
}
@Override
public void onSwiped(RecyclerView.ViewHolder viewHolder, int …Run Code Online (Sandbox Code Playgroud) 当项目部分在屏幕外时,ItemTouchHelper.Callback默认调用interpolateOutOfBoundsScroll.但是,当项目逐渐拖动到屏幕底部时,如何滚动回收器视图.
public class SimpleItemTouchHelperCallback extends ItemTouchHelper.Callback {
public static final float ALPHA_FULL = 1.0f;
private final ItemTouchHelperAdapter mAdapter;
private boolean isElevated;
public SimpleItemTouchHelperCallback(ItemTouchHelperAdapter adapter) {
mAdapter = adapter;
}
@Override
public boolean isLongPressDragEnabled() {
return true;
}
@Override
public boolean isItemViewSwipeEnabled() {
return true;
}
@Override
public int getMovementFlags(RecyclerView recyclerView, RecyclerView.ViewHolder viewHolder) {
// Set movement flags based on the layout manager
if (recyclerView.getLayoutManager() instanceof GridLayoutManager) {
final int dragFlags = ItemTouchHelper.UP | ItemTouchHelper.DOWN | ItemTouchHelper.LEFT | ItemTouchHelper.RIGHT;
final int …Run Code Online (Sandbox Code Playgroud) 我正在尝试使用带有垂直 LinearLayoutManager 的 RecyclerView 来显示列表项。该列表可以包含多种不同的项目类型(不同的布局),并且可以由用户使用拖放进行重新排序。
对于项目类型,如 Android 文档中所述,我已经覆盖了getItemType方法,以便在回收器中处理不同类型的视图,并在 onCreateViewHolder 和 onBindViewHolder 中处理它。这就像一个魅力。
对于拖放重新排序,我使用了ItemTouchHelper.Callback(受此示例项目启发)。这也很有效。
当我尝试使用不同的项目类型和拖放行为时会出现问题。只要拖动发生在相同类型的项目之间,这就会很好地工作,但是当我将类型 A 的视图拖动到类型 B 的视图上时,拖动停止并且视图返回到其原始位置。
这是我的代码:
我的片段
public class MyFragment extends Fragment implements MyAdapter.Listener {
private MyViewModel mViewModel;
private RecyclerView mRecyclerView;
private MyAdapter mAdapter;
private ItemTouchHelper mItemTouchHelper;
@Nullable
@Override
public View onCreateView(@NonNull LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
View root = inflater.inflate(R.layout.fragment, container, false);
mRecyclerView = root.findViewById(R.id.recyclerView);
mAdapter = new MyAdapter(this);
mRecyclerView.setAdapter(mAdapter);
mItemTouchHelper = new ItemTouchHelper(new MyDragHelperCallback(mAdapter));
mItemTouchHelper.attachToRecyclerView(mRecyclerView); …Run Code Online (Sandbox Code Playgroud) java android drag-and-drop android-recyclerview itemtouchhelper
我正在使用 ItemTouchHelper 类来支持 RecyclerView 中的拖放。我有一个按预期工作的实现,但它似乎效率很低。在我的 onMoved 方法中,我获取列表的当前版本,交换拖动的项目,然后使用新版本的列表调用 SubmitList。问题是,每次发生交换时都会调用 onMoved,并且交换在列表中拖动时会一一执行。因此,如果位置 1 处的项目被拖动到位置 11,则每次交换时都会调用 onMoved (1 -> 2) 、 (2 -> 3) 等。这意味着我获得了列表的新版本,并在拖动完成时调用了 SubmitList 10 次。
我尝试过的:
我尝试在拖动完成后使用更新的列表调用submitList,但它没有改变。我在调用submitList之前记录了适配器的getCurrentList(),它显示了原始的未更改列表(这是预期的)。我已经记录了 MainActivity 的 currentList 变量,它显示了更新的交换列表。我将 currentList 变量传递给submitList,然后记录适配器的 getCurrentList(),它仍然显示原始未更改的列表。我已阅读这篇文章,但建议的解决方案均无效。任何帮助,将不胜感激!
编辑:我还在适配器中使用 DiffUtil。
MainActivity.java
...
private void createItemTouchHelper() {
new ItemTouchHelper(new ItemTouchHelper.SimpleCallback(
ItemTouchHelper.UP | ItemTouchHelper.DOWN,
ItemTouchHelper.START | ItemTouchHelper.END) {
// To track changes when user drags
List<ListItem> currentList;
// This method is called when user starts dragging an item
public void onSelectedChanged(@Nullable RecyclerView.ViewHolder viewHolder, int actionState) …Run Code Online (Sandbox Code Playgroud) java android android-recyclerview itemtouchhelper android-listadapter
我想实现拖动卡片的方式,当我拖动的卡片没有完全重叠元素时,卡片的重新排列开始,但只有 50%。
看看一个例子:

现在,为了让右边的卡片向左移动,我需要将它与我正在拖动的卡片完全重叠。
我尝试从 ItemTouchHelper.Callback 覆盖此方法:
public float getMoveThreshold(@NonNull ViewHolder viewHolder) {
return .5f;
}
Run Code Online (Sandbox Code Playgroud)
但它没有帮助。
那么我怎样才能让交换发生在 50% 而不是 100% 重叠?
java android drag-and-drop android-recyclerview itemtouchhelper
这张图片是从我目前的项目中拍摄的,但它是用它创建的,SwipeRevealLayout我很难自定义它。前几天,我看到了这个问题,并明白我可以ItemTouchHelper用来解决我的问题。我找到了这段代码并尝试在我的项目中使用它:
val simpleCallback = object : ItemTouchHelper.SimpleCallback(0, ItemTouchHelper.LEFT or ItemTouchHelper.RIGHT) {
override fun onMove(p0: RecyclerView, p1: RecyclerView.ViewHolder, p2: RecyclerView.ViewHolder): Boolean {
return false
}
override fun getSwipeDirs(recyclerView: RecyclerView, viewHolder: RecyclerView.ViewHolder): Int {
val position = viewHolder.adapterPosition
if (position != editPosition) {
if (editPosition != -1 && flagSwiped) {
adapter.notifyItemChanged(position)
flagSwiped = false
editPosition = position
}
}
return super.getSwipeDirs(recyclerView, viewHolder)
}
override fun onSwiped(holder: RecyclerView.ViewHolder, direction: Int) {
} …Run Code Online (Sandbox Code Playgroud) 我正在尝试拥有一个具有不同视图类型的 RecyclerView,但具有拖放功能以及单击和长按操作的能力。
它类似于您在电话应用程序上的功能,您可以在其中更改收藏夹项目的顺序。在电话应用程序中,当您长按某个项目时,会立即出现一个上下文菜单,如果您继续拖动,上下文菜单就会消失。
但是,在这种情况下,我需要做相反的事情。长按时,如果用户在很短的时间内没有拖动,或者用户在没有拖动的情况下停止长按,我们会在屏幕上显示一个对话框,我需要停止拖动过程。
虽然我已经成功地处理了长触摸机制,并且我在这些特殊情况下显示了一个对话框,但我未能使拖动停止。
这意味着,如果用户在对话框出现后继续触摸屏幕,仍然可以继续拖动:
整个代码在这里可用(没有长触摸行为的代码在这里可用),但这里是主要代码:
class MainActivity : AppCompatActivity() {
sealed class Item(val id: Long, val itemType: Int) {
class HeaderItem(id: Long) : Item(id, ITEM_TYPE_HEADER)
class NormalItem(id: Long, val data: Long) : Item(id, 1)
}
enum class ItemActionState {
IDLE, LONG_TOUCH_OR_SOMETHING_ELSE, DRAG, SWIPE, HANDLED_LONG_TOUCH
}
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
setSupportActionBar(toolbar)
val items = ArrayList<Item>(100)
var itemDataCounter = 0L
items.add(Item.HeaderItem(0L))
for (i in 0 until 100) {
items.add(Item.NormalItem(itemDataCounter, itemDataCounter))
++itemDataCounter …Run Code Online (Sandbox Code Playgroud)