1
00:00:05,150 --> 00:00:06,150
Welcome back.

2
00:00:06,950 --> 00:00:09,950
Having those buttons in the RecyclerView looks untidy,

3
00:00:10,250 --> 00:00:12,850
and it doesn't fit with modern user interfaces.

4
00:00:13,550 --> 00:00:16,850
Users are used to removing items by swiping them left.

5
00:00:17,650 --> 00:00:19,350
That's not very hard to implement,

6
00:00:19,710 --> 00:00:22,510
and we'll see how to do that in the next few videos.

7
00:00:24,110 --> 00:00:26,410
We could use a gesture detector,

8
00:00:26,410 --> 00:00:29,610
and we've seen how those work in the FlickrBrowserApp.

9
00:00:30,110 --> 00:00:33,310
But for this app, I'm going to use an ItemTouch helper.

10
00:00:33,810 --> 00:00:36,510
We'll check for swipes in MainActivityFragment.

11
00:00:37,210 --> 00:00:39,210
You set up an ItemTouchHelper

12
00:00:39,460 --> 00:00:41,460
then attach it to your RecyclerView.

13
00:00:42,160 --> 00:00:44,360
I'll do that in OnViewCreated.

14
00:01:03,860 --> 00:01:06,060
That's where we configure the RecycleView.

15
00:01:06,460 --> 00:01:10,460
So it makes sense to attach the ItemTouchHelper in there too.

16
00:01:10,960 --> 00:01:12,860
Accept the import from

17
00:01:12,860 --> 00:01:16,740
androidx.RecyclerView.widget.itemtouchhelper

18
00:01:17,040 --> 00:01:18,840
if it's not imported automatically.

19
00:01:19,500 --> 00:01:22,860
The ItemTouchHelper will replace the delete buttons

20
00:01:22,860 --> 00:01:24,160
OnClickListener,

21
00:01:24,820 --> 00:01:27,420
that's in our adapter and we'll have a look at that in a moment.

22
00:01:27,920 --> 00:01:29,280
But first we've got an error.

23
00:01:29,940 --> 00:01:33,930
When we call OnDelete click, on line 77,

24
00:01:34,180 --> 00:01:37,480
we need to give it a task, but we don't know the task.

25
00:01:38,080 --> 00:01:40,980
The adapter does or more precisely

26
00:01:40,980 --> 00:01:43,580
the adapter's ViewHolder class does.

27
00:01:44,910 --> 00:01:48,510
That's where we're getting the task from on line 76.

28
00:01:49,170 --> 00:01:53,170
To fix the error, we need to make the ViewHoldersTask available.

29
00:01:53,870 --> 00:01:56,870
That's one of the few changes we have to make in the adapter.

30
00:01:57,370 --> 00:02:00,570
So let's have a look at our CursorRecyclerViewAdapter class.

31
00:02:07,230 --> 00:02:10,229
We defined our ViewHolder at the start of the file

32
00:02:10,229 --> 00:02:11,730
up on line 17.

33
00:02:12,130 --> 00:02:15,130
It gets passed a task in its bind function,

34
00:02:15,630 --> 00:02:18,630
and we need to make that available as a class attribute.

35
00:02:34,430 --> 00:02:37,530
The ViewHolder won't be displayed in the RecyclerView until

36
00:02:37,530 --> 00:02:39,890
after its bind function has been called,

37
00:02:40,390 --> 00:02:42,790
that means we can use late init there

38
00:02:42,790 --> 00:02:44,790
rather than using a nullable type.

39
00:02:45,490 --> 00:02:49,490
Our task attribute will get its value when the bind function is called.

40
00:03:00,490 --> 00:03:02,490
We're going to remove the delete button.

41
00:03:02,490 --> 00:03:05,740
There's no point leaving it in the layout when we're going to be swiping.

42
00:03:06,400 --> 00:03:09,760
That means we'll no longer be able to refer to it in our ViewHolder.

43
00:03:10,120 --> 00:03:11,620
So I'll delete it.

44
00:03:15,870 --> 00:03:20,270
There's also no need to set its OnClickListener and we can delete those lines.

45
00:03:28,520 --> 00:03:31,020
If we're no longer setting the DeleteListener,

46
00:03:31,020 --> 00:03:35,320
there's no need to have it in our interface. So I'll remove that as well.

47
00:03:42,320 --> 00:03:46,320
The final change is in the OnBindViewHolder function

48
00:03:46,820 --> 00:03:48,320
where we hide the delete button.

49
00:03:48,820 --> 00:03:50,420
We don't need that line either.

50
00:03:56,220 --> 00:03:58,420
That's all the changes to our adapter.

51
00:03:58,420 --> 00:04:01,020
Close it, and return to MainActivityFragment.

52
00:04:04,020 --> 00:04:06,520
We fixed the error, and now we've got a task

53
00:04:06,520 --> 00:04:09,120
to pass to the OnDeleteClick function.

54
00:04:09,780 --> 00:04:12,380
We've got another error but I'll come to that soon.
So what's going on here?

55
00:04:14,940 --> 00:04:16,540
This is boilerplate code.

56
00:04:17,040 --> 00:04:20,640
When you want to attach an ItemTouchHelper to a RecyclerView,

57
00:04:21,140 --> 00:04:22,740
this is the standard code to do it.

58
00:04:23,620 --> 00:04:27,520
Our ItemTouchHelper contains an object of type

59
00:04:27,520 --> 00:04:30,820
ItemTouchHelper.SimpleCallback.

60
00:04:31,480 --> 00:04:35,680
SimpleCallback creates a callback for drag and swipe operations.

61
00:04:36,180 --> 00:04:40,480
Callback is an abstract class and we have to provide implementations

62
00:04:40,480 --> 00:04:41,780
for two functions,

63
00:04:42,080 --> 00:04:44,080
OnMove and OnSwiped.

64
00:04:44,880 --> 00:04:49,380
OnMove is used if you want to allow the recycler items to be dragged up and down.

65
00:04:50,180 --> 00:04:52,840
OnSwiped is where you define the behavior you want

66
00:04:52,840 --> 00:04:54,340
when the item's swiped,

67
00:04:54,640 --> 00:04:56,040
and that's what we're doing here.

68
00:04:56,440 --> 00:05:00,040
Our code is simple if the item swiped left,

69
00:05:00,840 --> 00:05:02,840
which we check on line 75,

70
00:05:03,340 --> 00:05:07,140
then we'll pass the ViewHolders task to OnDeleteClick.

71
00:05:07,940 --> 00:05:11,940
That's our ItemTouchHelper written. But there's one more step we need to do,

72
00:05:12,740 --> 00:05:14,940
we need to attach it to the RecyclerView.

73
00:05:15,440 --> 00:05:18,000
Otherwise, it won't be used when the items are swiped.

74
00:05:33,450 --> 00:05:37,950
Line 82 attaches our ItemTouchListener to the RecyclerView.

75
00:05:38,610 --> 00:05:41,810
Before we can test it, we need to fix the error

76
00:05:41,810 --> 00:05:43,310
in OnDeleteClicked

77
00:05:43,970 --> 00:05:45,670
on line 89.

78
00:05:46,330 --> 00:05:49,690
We've got an error because we removed this function from the interface.

79
00:05:50,350 --> 00:05:54,550
It's no longer overriding anything, so we have to remove the override.

80
00:05:58,150 --> 00:06:00,400
All right. The moment of truth.

81
00:06:00,800 --> 00:06:04,160
Let's see if we can delete tasks by swiping them left.

82
00:06:05,060 --> 00:06:07,260
Run the app, and swipe some tasks.

83
00:06:13,060 --> 00:06:17,270
To swipe in the emulators, you need to click the object to swipe

84
00:06:17,270 --> 00:06:18,770
then flick the mouse left.

85
00:06:19,570 --> 00:06:21,570
Make sure you swipe all the way.

86
00:06:22,070 --> 00:06:26,570
If you only sort of swipe halfway, the animation puts the item back in the list.

87
00:06:27,230 --> 00:06:30,480
It's much easier to do on a physical device with your finger

88
00:06:30,480 --> 00:06:32,480
rather than using a mouse in an emulator.

89
00:06:33,780 --> 00:06:37,140
That's looking good. We've got our confirmation dialog.

90
00:06:37,740 --> 00:06:40,540
I'll tap delete and the task's deleted.

91
00:06:42,200 --> 00:06:44,800
That wasn't a lot of work to implement swiping.

92
00:06:45,100 --> 00:06:47,200
We added a simple TouchHelper

93
00:06:47,200 --> 00:06:49,200
and attached it to the RecyclerView.

94
00:06:50,000 --> 00:06:51,500
And it almost works.

95
00:06:52,300 --> 00:06:53,300
There's a problem.

96
00:06:53,600 --> 00:06:56,800
To demonstrate it, I'll choose task 6.

97
00:06:57,790 --> 00:07:01,690
Make a mental note of the task number and then swipe it.

98
00:07:03,590 --> 00:07:06,590
When the dialog appears, tap cancel.

99
00:07:08,290 --> 00:07:11,550
That looks worrying, but it's normal behavior.

100
00:07:11,550 --> 00:07:14,150
The task hasn't been deleted from the database.

101
00:07:14,150 --> 00:07:17,350
We can confirm that by refreshing the activity.

102
00:07:17,900 --> 00:07:20,500
Rotating the device is an easy way to do that.

103
00:07:30,500 --> 00:07:33,500
When the recycler redraws we get our task back.

104
00:07:34,300 --> 00:07:36,900
As I said that's normal behavior.

105
00:07:37,400 --> 00:07:40,300
When you swipe something an animation runs

106
00:07:40,300 --> 00:07:42,300
and it gets removed from the RecycleView.

107
00:07:43,200 --> 00:07:46,200
In the next video, we'll see how to reverse that

108
00:07:46,500 --> 00:07:49,900
to get our task back if the user cancels the delete.

109
00:07:50,560 --> 00:07:51,460
I'll see you there.

