1 00:00:04,220 --> 00:00:06,340 G'day everyone, welcome back. 2 00:00:06,340 --> 00:00:13,800 In the last video, we saw our AppDialog class displaying a dialog, when we try to delete a Task record. 3 00:00:13,800 --> 00:00:20,000 The next step is to get MainActivityFragment to handle the situation correctly. 4 00:00:20,000 --> 00:00:28,380 Correctly here means, not performing the deletion until the user has confirmed that they really do want to delete the task. 5 00:00:28,380 --> 00:00:35,900 We achieve that by moving the deleteTask call into the onPositiveDialogResult function. 6 00:00:35,900 --> 00:00:39,500 So we'll cut these two lines from here, 7 00:00:39,500 --> 00:00:43,480 and paste them down here. 8 00:00:43,480 --> 00:00:47,840 We've got an error because the task id isn't available. 9 00:00:47,840 --> 00:01:03,860 We can fix that by retrieving the id from the args bundle. 10 00:01:03,860 --> 00:01:08,140 We should also make sure that we're responding to the correct dialog. 11 00:01:08,140 --> 00:01:14,200 We're only showing one dialog at the moment, but we don't want to go deleting tasks by mistake. 12 00:01:14,200 --> 00:01:25,020 So let's wrap this in an if block. 13 00:01:25,020 --> 00:01:29,820 I haven't included a check that the task id key exists in the bundle. 14 00:01:29,820 --> 00:01:33,820 You could do, and throw an exception if it doesn't exist. 15 00:01:33,820 --> 00:01:44,840 Let's check the documentation for the getLong function, using ctrl Q, or ctrl J on a Mac. 16 00:01:44,840 --> 00:01:49,560 getLong returns 0 if the key isn't present in the bundle. 17 00:01:49,560 --> 00:01:52,720 If that happens, it's a programming error. 18 00:01:52,720 --> 00:02:00,880 It can't happen once the app's released, because Sqlite doesn't create integer primary key values of 0. 19 00:02:00,880 --> 00:02:06,520 We should always have a non zero ID, unless the programmer has done something wrong. 20 00:02:06,520 --> 00:02:20,320 Rather than throwing an exceptionm we can use an assertion. 21 00:02:20,320 --> 00:02:25,840 This is different to just testing the task id and throwing an exception. 22 00:02:25,840 --> 00:02:31,860 BuildConfig.DEBUG is a system-wide constant that the compiler can use. 23 00:02:31,860 --> 00:02:37,460 When you produce the release version of the app, BuildConfi.debug will be false, 24 00:02:37,460 --> 00:02:41,100 and this code won't be compiled into the final app. 25 00:02:41,100 --> 00:02:46,640 It will only be present while we're developing, and won't appear in the released app. 26 00:02:46,640 --> 00:02:51,700 This is one time where it's acceptable to put all the code on one line, by the way. 27 00:02:51,700 --> 00:03:04,040 To see it working, I'll comment out the line that adds a task id to the bundle in the onDelete click function, 28 00:03:04,040 --> 00:03:09,780 then run the app again. 29 00:03:09,780 --> 00:03:14,260 I'll tap the delete button. 30 00:03:14,260 --> 00:03:18,280 When I tap the dialog's delete button to confirm the deletion, 31 00:03:18,280 --> 00:03:31,660 we get an exception in the logcat: 32 00:03:31,660 --> 00:03:33,880 task id is zero. 33 00:03:33,880 --> 00:03:40,720 There's a subtle difference between this MainActivityFragment class, and the AppDialog class. 34 00:03:40,720 --> 00:03:47,040 MainActivityFragment is part of this TaskTimer app and won't be used anywhere else. 35 00:03:47,040 --> 00:03:52,720 AppDialog, on the other hand, has been designed to be a general-purpose dialog class, 36 00:03:52,720 --> 00:03:54,800 that we can use in other apps. 37 00:03:54,800 --> 00:03:58,220 We could still be using other apps in ten years time. 38 00:03:58,220 --> 00:04:01,880 Other members of our team could be including it in their apps, 39 00:04:01,880 --> 00:04:07,540 so that's why we've taken a different approach to invalid arguments in the two classes. 40 00:04:07,540 --> 00:04:15,720 Our assert error in MainActivityFragment is there to warn us that we've forgotten to store the task in the bundle. 41 00:04:15,720 --> 00:04:21,459 The assert error code will be removed when the release version of the app's compiled. 42 00:04:21,459 --> 00:04:27,180 The exceptions in AppDialog are intended to warn other programmers who use the class. 43 00:04:27,180 --> 00:04:29,820 That may be us, but it may not be. 44 00:04:29,820 --> 00:04:35,420 The AppDialog exceptions aren't removed when the code is compiled as a release version. 45 00:04:35,420 --> 00:04:42,320 We might want to compile it, and include it in a library that's imported into other projects, for example. 46 00:04:42,320 --> 00:04:46,400 So we want the checks to remain in the compiled release version. 47 00:04:46,400 --> 00:04:53,740 Okay, I'll put back the code to store the id in the bundle, 48 00:04:53,740 --> 00:05:00,520 and let's see if it works. 49 00:05:00,520 --> 00:05:05,920 Run the app again, and I'm going to do the non-destructive tests first. 50 00:05:05,920 --> 00:05:12,620 You don't want to spend time watching me type in the task records, so I'll try to keep deletions to a minimum. 51 00:05:12,620 --> 00:05:16,180 I suggest you don't take that approach in your testing. 52 00:05:16,180 --> 00:05:18,660 It makes sense when doing a quick check, 53 00:05:18,660 --> 00:05:24,480 but always performing operations in the same sequence, can result in you missing bugs. 54 00:05:24,480 --> 00:05:31,460 To make up an example, if your edit code creates a global object that's also used when you delete, 55 00:05:31,460 --> 00:05:39,160 and you always edit before deleting. you might fail to spot that the delete code fails to create the object. 56 00:05:39,160 --> 00:05:40,200 Okay. 57 00:05:40,200 --> 00:05:46,300 I'll tap on the delete button to get the confirmation dialogue. 58 00:05:46,300 --> 00:05:51,880 First, I'll use the cancel button. 59 00:05:51,880 --> 00:05:55,540 Remember, that's not the same as cancelling the dialogue. 60 00:05:55,540 --> 00:06:01,460 We give the button the caption cancel, but it's really the negative dialog button. 61 00:06:01,460 --> 00:06:04,380 That's good. The record isn't deleted. 62 00:06:04,380 --> 00:06:09,740 There are two ways to cancel dialogue, and both do exactly the same thing. 63 00:06:09,740 --> 00:06:17,820 To test that, I'll delete again, and tap the screen outside the dialogue. 64 00:06:17,820 --> 00:06:22,380 The dialogue closes, and the task hasn't been deleted. 65 00:06:22,380 --> 00:06:25,400 The same thing should happen with the back button. 66 00:06:25,400 --> 00:06:33,720 So get the dialogue back, and press the back button. 67 00:06:33,720 --> 00:06:36,320 That's working fine as well. 68 00:06:36,320 --> 00:06:38,560 Now to test deletion. 69 00:06:38,560 --> 00:06:51,980 I'll clear the logcat, then delete a task and confirm the deletion. 70 00:06:51,980 --> 00:06:57,740 A bit more happens here, because we're causing the database notification system to kick in. 71 00:06:57,740 --> 00:07:04,340 But we can see the onPositiveDialogResult function, then the record being deleted, 72 00:07:04,340 --> 00:07:13,620 and we can see it's gone from the emulator screen. 73 00:07:13,620 --> 00:07:29,100 Mixed in with all the database logging, we can see the dialog's onDismiss and onDetach functions in the log. 74 00:07:29,100 --> 00:07:35,460 Notice that the deletion and subsequent re-query, are happening on a different thread. 75 00:07:35,460 --> 00:07:39,240 Alright, our AppDialog class is looking good. 76 00:07:39,240 --> 00:07:41,420 There's a few things we haven't tested. 77 00:07:41,420 --> 00:07:45,860 Does it work when we provide a different caption for the negative button? 78 00:07:45,860 --> 00:07:51,620 Does it work when we don't provide any button captions, and rely on the defaults for both? 79 00:07:51,620 --> 00:07:54,500 Does everything work okay in landscape. 80 00:07:54,500 --> 00:07:57,840 I'm not going to go through those tests on the video, 81 00:07:57,840 --> 00:08:03,180 but you should certainly test all combinations of input, to any classes you create. 82 00:08:03,180 --> 00:08:07,720 I'll leave you to perform those tests, and stop this video here. 83 00:08:07,720 --> 00:08:12,420 In the next video, we'll have a quick look at some strange behavior. 84 00:08:12,420 --> 00:08:15,160 See you in the next one.