Feature: Add drag-and-drop reordering for checklist items
Users can now reorder checklist items by dragging them up or down using the drag handle icon (6-dot pattern) on each item. Changes: - Added ic_drag_handle.xml drawable with 6-dot pattern icon - Updated item_checklist_row.xml to include drag handle ImageButton - Modified ChecklistAdapter to support moveItem() operation - Added ItemTouchHelper in NoteEditorFragment for drag-and-drop functionality - Items reorder smoothly and changes are auto-saved
This commit is contained in:
parent
30bfe441f8
commit
342262e892
|
|
@ -23,6 +23,7 @@ public class ChecklistAdapter extends RecyclerView.Adapter<ChecklistAdapter.Chec
|
|||
void onTextChange(ChecklistItem item, String text);
|
||||
void onCheckedChange(ChecklistItem item, boolean checked);
|
||||
void onDeleteClick(int position, ChecklistItem item);
|
||||
void onMoveItems(int fromPosition, int toPosition);
|
||||
}
|
||||
|
||||
public ChecklistAdapter(OnItemChangeListener listener) {
|
||||
|
|
@ -88,13 +89,34 @@ public class ChecklistAdapter extends RecyclerView.Adapter<ChecklistAdapter.Chec
|
|||
return items;
|
||||
}
|
||||
|
||||
// Move item from one position to another
|
||||
public void moveItem(int fromPosition, int toPosition) {
|
||||
if (fromPosition < toPosition) {
|
||||
for (int i = fromPosition; i < toPosition; i++) {
|
||||
ChecklistItem temp = items.get(i);
|
||||
items.set(i, items.get(i + 1));
|
||||
items.set(i + 1, temp);
|
||||
}
|
||||
} else {
|
||||
for (int i = fromPosition; i > toPosition; i--) {
|
||||
ChecklistItem temp = items.get(i);
|
||||
items.set(i, items.get(i - 1));
|
||||
items.set(i - 1, temp);
|
||||
}
|
||||
}
|
||||
|
||||
notifyItemMoved(fromPosition, toPosition);
|
||||
}
|
||||
|
||||
static class ChecklistViewHolder extends RecyclerView.ViewHolder {
|
||||
ImageButton dragHandle;
|
||||
CheckBox checkBox;
|
||||
EditText editText;
|
||||
ImageButton deleteButton;
|
||||
|
||||
public ChecklistViewHolder(@NonNull View itemView) {
|
||||
super(itemView);
|
||||
dragHandle = itemView.findViewById(R.id.drag_handle);
|
||||
checkBox = itemView.findViewById(R.id.check_box);
|
||||
editText = itemView.findViewById(R.id.item_text);
|
||||
deleteButton = itemView.findViewById(R.id.delete_button);
|
||||
|
|
|
|||
|
|
@ -14,6 +14,7 @@ import android.widget.Toast;
|
|||
import androidx.annotation.NonNull;
|
||||
import androidx.annotation.Nullable;
|
||||
import androidx.fragment.app.Fragment;
|
||||
import androidx.recyclerview.widget.ItemTouchHelper;
|
||||
import androidx.recyclerview.widget.LinearLayoutManager;
|
||||
import androidx.recyclerview.widget.RecyclerView;
|
||||
|
||||
|
|
@ -175,12 +176,39 @@ public class NoteEditorFragment extends Fragment {
|
|||
updateProgress();
|
||||
saveNoteImmediately();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onMoveItems(int fromPosition, int toPosition) {
|
||||
scheduleSave();
|
||||
}
|
||||
});
|
||||
|
||||
checklistAdapter.setItems(note.getItems());
|
||||
checklistRecyclerView.setLayoutManager(new LinearLayoutManager(requireContext()));
|
||||
checklistRecyclerView.setAdapter(checklistAdapter);
|
||||
|
||||
// Add drag-and-drop support
|
||||
ItemTouchHelper itemTouchHelper = new ItemTouchHelper(
|
||||
new ItemTouchHelper.SimpleCallback(ItemTouchHelper.UP | ItemTouchHelper.DOWN, 0) {
|
||||
@Override
|
||||
public boolean onMove(@NonNull RecyclerView recyclerView,
|
||||
@NonNull RecyclerView.ViewHolder viewHolder,
|
||||
@NonNull RecyclerView.ViewHolder target) {
|
||||
int fromPosition = viewHolder.getAdapterPosition();
|
||||
int toPosition = target.getAdapterPosition();
|
||||
|
||||
checklistAdapter.moveItem(fromPosition, toPosition);
|
||||
scheduleSave();
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onSwiped(@NonNull RecyclerView.ViewHolder viewHolder, int direction) {}
|
||||
});
|
||||
|
||||
itemTouchHelper.attachToRecyclerView(checklistRecyclerView);
|
||||
|
||||
addImageButton.setOnClickListener(v -> {
|
||||
ChecklistItem newItem = new ChecklistItem("");
|
||||
note.getItems().add(newItem);
|
||||
|
|
|
|||
|
|
@ -0,0 +1,32 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:width="24dp"
|
||||
android:height="24dp"
|
||||
android:viewportWidth="24"
|
||||
android:viewportHeight="24">
|
||||
|
||||
<!-- Top row of dots -->
|
||||
<path
|
||||
android:pathData="M9,3C10.105,3 11,3.895 11,5C11,6.105 10.105,7 9,7C7.895,7 7,6.105 7,5C7,3.895 7.895,3 9,3Z"
|
||||
android:fillColor="@android:color/darker_gray"/>
|
||||
<path
|
||||
android:pathData="M15,3C16.105,3 17,3.895 17,5C17,6.105 16.105,7 15,7C13.895,7 13,6.105 13,5C13,3.895 13.895,3 15,3Z"
|
||||
android:fillColor="@android:color/darker_gray"/>
|
||||
|
||||
<!-- Middle row of dots -->
|
||||
<path
|
||||
android:pathData="M9,12C10.105,12 11,12.895 11,14C11,15.105 10.105,16 9,16C7.895,16 7,15.105 7,14C7,12.895 7.895,12 9,12Z"
|
||||
android:fillColor="@android:color/darker_gray"/>
|
||||
<path
|
||||
android:pathData="M15,12C16.105,12 17,12.895 17,14C17,15.105 16.105,16 15,16C13.895,16 13,15.105 13,14C13,12.895 13.895,12 15,12Z"
|
||||
android:fillColor="@android:color/darker_gray"/>
|
||||
|
||||
<!-- Bottom row of dots -->
|
||||
<path
|
||||
android:pathData="M9,21C10.105,21 11,21.895 11,23C11,24.105 10.105,25 9,25C7.895,25 7,24.105 7,23C7,21.895 7.895,21 9,21Z"
|
||||
android:fillColor="@android:color/darker_gray"/>
|
||||
<path
|
||||
android:pathData="M15,21C16.105,21 17,21.895 17,23C17,24.105 16.105,25 15,25C13.895,25 13,24.105 13,23C13,21.895 13.895,21 15,21Z"
|
||||
android:fillColor="@android:color/darker_gray"/>
|
||||
|
||||
</vector>
|
||||
|
|
@ -1,16 +1,27 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:app="http://schemas.android.com/apk/res-auto"
|
||||
android:id="@+id/item_container"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="horizontal"
|
||||
android:paddingVertical="4dp">
|
||||
|
||||
<ImageButton
|
||||
android:id="@+id/drag_handle"
|
||||
android:layout_width="32dp"
|
||||
android:layout_height="32dp"
|
||||
android:layout_gravity="center_vertical"
|
||||
android:background="?attr/selectableItemBackgroundBorderless"
|
||||
android:src="@drawable/ic_drag_handle"
|
||||
app:tint="@color/text_secondary" />
|
||||
|
||||
<CheckBox
|
||||
android:id="@+id/check_box"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="center_vertical" />
|
||||
android:layout_gravity="center_vertical"
|
||||
android:layout_marginStart="4dp" />
|
||||
|
||||
<EditText
|
||||
android:id="@+id/item_text"
|
||||
|
|
|
|||
Loading…
Reference in New Issue