Use coroutines in task edit fragment

pull/1047/head
Alex Baker 4 years ago
parent 29de2d0d53
commit 1846559fd7

@ -21,29 +21,28 @@ import android.view.inputmethod.InputMethodManager
import androidx.appcompat.widget.Toolbar import androidx.appcompat.widget.Toolbar
import androidx.coordinatorlayout.widget.CoordinatorLayout import androidx.coordinatorlayout.widget.CoordinatorLayout
import androidx.fragment.app.Fragment import androidx.fragment.app.Fragment
import androidx.lifecycle.lifecycleScope
import com.google.android.material.appbar.AppBarLayout import com.google.android.material.appbar.AppBarLayout
import com.google.android.material.appbar.AppBarLayout.Behavior.DragCallback import com.google.android.material.appbar.AppBarLayout.Behavior.DragCallback
import com.google.android.material.appbar.AppBarLayout.OnOffsetChangedListener import com.google.android.material.appbar.AppBarLayout.OnOffsetChangedListener
import com.google.common.base.Predicates
import com.google.common.collect.Iterables
import com.todoroo.andlib.utility.AndroidUtilities import com.todoroo.andlib.utility.AndroidUtilities
import com.todoroo.andlib.utility.DateUtilities import com.todoroo.andlib.utility.DateUtilities
import com.todoroo.astrid.api.Filter import com.todoroo.astrid.api.Filter
import com.todoroo.astrid.dao.TaskDaoBlocking import com.todoroo.astrid.dao.TaskDao
import com.todoroo.astrid.data.Task import com.todoroo.astrid.data.Task
import com.todoroo.astrid.notes.CommentsController import com.todoroo.astrid.notes.CommentsController
import com.todoroo.astrid.repeats.RepeatControlSet import com.todoroo.astrid.repeats.RepeatControlSet
import com.todoroo.astrid.service.TaskDeleter import com.todoroo.astrid.service.TaskDeleter
import com.todoroo.astrid.timers.TimerPlugin import com.todoroo.astrid.timers.TimerPlugin
import dagger.hilt.android.AndroidEntryPoint import dagger.hilt.android.AndroidEntryPoint
import io.reactivex.Completable import kotlinx.coroutines.NonCancellable
import io.reactivex.android.schedulers.AndroidSchedulers import kotlinx.coroutines.launch
import io.reactivex.schedulers.Schedulers import kotlinx.coroutines.withContext
import org.tasks.R import org.tasks.R
import org.tasks.Strings.isNullOrEmpty import org.tasks.Strings.isNullOrEmpty
import org.tasks.analytics.Firebase import org.tasks.analytics.Firebase
import org.tasks.data.UserActivity import org.tasks.data.UserActivity
import org.tasks.data.UserActivityDaoBlocking import org.tasks.data.UserActivityDao
import org.tasks.databinding.FragmentTaskEditBinding import org.tasks.databinding.FragmentTaskEditBinding
import org.tasks.date.DateTimeUtils.newDateTime import org.tasks.date.DateTimeUtils.newDateTime
import org.tasks.dialogs.DialogBuilder import org.tasks.dialogs.DialogBuilder
@ -60,8 +59,8 @@ import kotlin.math.abs
@AndroidEntryPoint @AndroidEntryPoint
class TaskEditFragment : Fragment(), Toolbar.OnMenuItemClickListener { class TaskEditFragment : Fragment(), Toolbar.OnMenuItemClickListener {
@Inject lateinit var taskDao: TaskDaoBlocking @Inject lateinit var taskDao: TaskDao
@Inject lateinit var userActivityDao: UserActivityDaoBlocking @Inject lateinit var userActivityDao: UserActivityDao
@Inject lateinit var taskDeleter: TaskDeleter @Inject lateinit var taskDeleter: TaskDeleter
@Inject lateinit var notificationManager: NotificationManager @Inject lateinit var notificationManager: NotificationManager
@Inject lateinit var dialogBuilder: DialogBuilder @Inject lateinit var dialogBuilder: DialogBuilder
@ -239,31 +238,27 @@ class TaskEditFragment : Fragment(), Toolbar.OnMenuItemClickListener {
/** Save task model from values in UI components */ /** Save task model from values in UI components */
fun save() { fun save() {
val fragments = taskEditControlSetFragmentManager.getFragmentsInPersistOrder(childFragmentManager) val fragments = taskEditControlSetFragmentManager.getFragmentsInPersistOrder(childFragmentManager)
if (hasChanges(fragments)) { lifecycleScope.launch(NonCancellable) {
val isNewTask = model.isNew if (hasChanges(fragments)) {
val taskListFragment = (activity as MainActivity?)!!.taskListFragment val isNewTask = model.isNew
val title = title val taskListFragment = (activity as MainActivity?)!!.taskListFragment
model.title = if (isNullOrEmpty(title)) getString(R.string.no_title) else title val title = title
if (completed != model.isCompleted) { model.title = if (isNullOrEmpty(title)) getString(R.string.no_title) else title
model.completionDate = if (completed) DateUtilities.now() else 0 if (completed != model.isCompleted) {
} model.completionDate = if (completed) DateUtilities.now() else 0
for (fragment in Iterables.filter(fragments, Predicates.not { obj: TaskEditControlFragment? -> obj!!.requiresId() })) { }
fragment.applyBlocking(model) val partition = fragments.partition { it.requiresId() }
} partition.second.forEach { it.apply(model) }
Completable.fromAction {
AndroidUtilities.assertNotMainThread()
if (isNewTask) { if (isNewTask) {
taskDao.createNew(model) taskDao.createNew(model)
} }
for (fragment in Iterables.filter(fragments) { obj: TaskEditControlFragment? -> obj!!.requiresId() }) { partition.first.forEach { it.apply(model) }
fragment.applyBlocking(model)
}
taskDao.save(model, null) taskDao.save(model, null)
if (isNewTask) { if (isNewTask) {
taskListFragment!!.onTaskCreated(model.uuid) taskListFragment!!.onTaskCreated(model.uuid)
if (!isNullOrEmpty(model.calendarURI)) { if (!isNullOrEmpty(model.calendarURI)) {
taskListFragment.makeSnackbar(R.string.calendar_event_created, model.title) taskListFragment.makeSnackbar(R.string.calendar_event_created, model.title)
.setAction(R.string.action_open) { v: View? -> .setAction(R.string.action_open) {
val uri = model.calendarURI val uri = model.calendarURI
val intent = Intent(Intent.ACTION_VIEW, Uri.parse(uri)) val intent = Intent(Intent.ACTION_VIEW, Uri.parse(uri))
taskListFragment.startActivity(intent) taskListFragment.startActivity(intent)
@ -271,13 +266,10 @@ class TaskEditFragment : Fragment(), Toolbar.OnMenuItemClickListener {
.show() .show()
} }
} }
callback!!.removeTaskEditFragment()
} else {
discard()
} }
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe()
callback!!.removeTaskEditFragment()
} else {
discard()
} }
} }
@ -299,7 +291,7 @@ class TaskEditFragment : Fragment(), Toolbar.OnMenuItemClickListener {
private val title: String private val title: String
get() = binding.title.text.toString().trim { it <= ' ' } get() = binding.title.text.toString().trim { it <= ' ' }
private fun hasChanges(fragments: List<TaskEditControlFragment>): Boolean { private suspend fun hasChanges(fragments: List<TaskEditControlFragment>): Boolean {
val newTitle = title val newTitle = title
if (newTitle != model.title if (newTitle != model.title
|| !model.isNew && completed != model.isCompleted || !model.isNew && completed != model.isCompleted
@ -307,11 +299,7 @@ class TaskEditFragment : Fragment(), Toolbar.OnMenuItemClickListener {
return true return true
} }
try { try {
for (fragment in fragments) { return fragments.any { it.hasChanges(model) }
if (fragment.hasChangesBlocking(model)) {
return true
}
}
} catch (e: Exception) { } catch (e: Exception) {
firebase.reportException(e) firebase.reportException(e)
} }
@ -324,15 +312,17 @@ class TaskEditFragment : Fragment(), Toolbar.OnMenuItemClickListener {
* ====================================================================== * ======================================================================
*/ */
fun discardButtonClick() { fun discardButtonClick() {
if (hasChanges( val fragments = taskEditControlSetFragmentManager.getFragmentsInPersistOrder(childFragmentManager)
taskEditControlSetFragmentManager.getFragmentsInPersistOrder(childFragmentManager))) { lifecycleScope.launch {
dialogBuilder if (hasChanges(fragments)) {
.newDialog(R.string.discard_confirmation) dialogBuilder
.setPositiveButton(R.string.keep_editing, null) .newDialog(R.string.discard_confirmation)
.setNegativeButton(R.string.discard) { _, _ -> discard() } .setPositiveButton(R.string.keep_editing, null)
.show() .setNegativeButton(R.string.discard) { _, _ -> discard() }
} else { .show()
discard() } else {
discard()
}
} }
} }
@ -378,8 +368,12 @@ class TaskEditFragment : Fragment(), Toolbar.OnMenuItemClickListener {
userActivity.message = message userActivity.message = message
userActivity.targetId = model.uuid userActivity.targetId = model.uuid
userActivity.created = DateUtilities.now() userActivity.created = DateUtilities.now()
userActivityDao.createNew(userActivity) lifecycleScope.launch {
commentsController.reloadView() withContext(NonCancellable) {
userActivityDao.createNew(userActivity)
}
commentsController.reloadView()
}
} }
interface TaskEditFragmentCallbackHandler { interface TaskEditFragmentCallbackHandler {

@ -60,18 +60,8 @@ abstract class TaskEditControlFragment : Fragment() {
return false return false
} }
@Deprecated("use coroutines")
fun applyBlocking(task: Task) = runBlocking {
apply(task)
}
abstract suspend fun apply(task: Task) abstract suspend fun apply(task: Task)
@Deprecated("use coroutines")
fun hasChangesBlocking(original: Task) = runBlocking {
hasChanges(original)
}
open suspend fun hasChanges(original: Task): Boolean { open suspend fun hasChanges(original: Task): Boolean {
return false return false
} }

Loading…
Cancel
Save