View model due date as state flow

pull/1923/head
Alex Baker 2 years ago
parent 1f3b8fd228
commit 6513c40c97

@ -23,13 +23,9 @@ import com.todoroo.astrid.data.Task
import com.todoroo.astrid.service.TaskCreator
import com.todoroo.astrid.timers.TimerControlSet.TimerControlSetCallback
import dagger.hilt.android.AndroidEntryPoint
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.async
import kotlinx.coroutines.coroutineScope
import kotlinx.coroutines.*
import kotlinx.coroutines.flow.launchIn
import kotlinx.coroutines.flow.onEach
import kotlinx.coroutines.launch
import kotlinx.coroutines.withContext
import org.tasks.BuildConfig
import org.tasks.LocalBroadcastManager
import org.tasks.R
@ -54,19 +50,14 @@ import org.tasks.preferences.Preferences
import org.tasks.themes.ColorProvider
import org.tasks.themes.Theme
import org.tasks.themes.ThemeColor
import org.tasks.ui.DeadlineControlSet.DueDateChangeListener
import org.tasks.ui.*
import org.tasks.ui.EmptyTaskEditFragment.Companion.newEmptyTaskEditFragment
import org.tasks.ui.MainActivityEvent
import org.tasks.ui.MainActivityEventBus
import org.tasks.ui.NavigationDrawerFragment
import org.tasks.ui.NavigationDrawerFragment.Companion.newNavigationDrawer
import org.tasks.ui.TaskListEvent
import org.tasks.ui.TaskListEventBus
import timber.log.Timber
import javax.inject.Inject
@AndroidEntryPoint
class MainActivity : InjectingAppCompatActivity(), TaskListFragmentCallbackHandler, TimerControlSetCallback, DueDateChangeListener, CommentBarFragmentCallback, SortDialogCallback {
class MainActivity : InjectingAppCompatActivity(), TaskListFragmentCallbackHandler, TimerControlSetCallback, CommentBarFragmentCallback, SortDialogCallback {
@Inject lateinit var preferences: Preferences
@Inject lateinit var defaultFilterProvider: DefaultFilterProvider
@Inject lateinit var theme: Theme
@ -471,10 +462,6 @@ class MainActivity : InjectingAppCompatActivity(), TaskListFragmentCallbackHandl
actionMode = null
}
override fun dueDateChanged() {
taskEditFragment!!.onDueDateChanged()
}
override fun onStart() {
super.onStart()

@ -40,9 +40,7 @@ import com.todoroo.astrid.api.Filter
import com.todoroo.astrid.dao.TaskDao
import com.todoroo.astrid.data.Task
import com.todoroo.astrid.notes.CommentsController
import com.todoroo.astrid.repeats.RepeatControlSet
import com.todoroo.astrid.timers.TimerPlugin
import com.todoroo.astrid.ui.StartDateControlSet
import dagger.hilt.android.AndroidEntryPoint
import kotlinx.coroutines.NonCancellable
import kotlinx.coroutines.flow.launchIn
@ -63,7 +61,6 @@ import org.tasks.fragments.TaskEditControlSetFragmentManager
import org.tasks.markdown.MarkdownProvider
import org.tasks.notifications.NotificationManager
import org.tasks.preferences.Preferences
import org.tasks.ui.TaskEditControlFragment
import org.tasks.ui.TaskEditEvent
import org.tasks.ui.TaskEditEventBus
import org.tasks.ui.TaskEditViewModel
@ -325,21 +322,6 @@ class TaskEditFragment : Fragment(), Toolbar.OnMenuItemClickListener {
suspend fun save(remove: Boolean = true) = editViewModel.save(remove)
/*
* ======================================================================
* =============================================== model reading / saving
* ======================================================================
*/
private val repeatControlSet: RepeatControlSet?
get() = getFragment<RepeatControlSet>(RepeatControlSet.TAG)
private val startDateControlSet: StartDateControlSet?
get() = getFragment<StartDateControlSet>(StartDateControlSet.TAG)
private fun <T : TaskEditControlFragment?> getFragment(tag: Int): T? {
return childFragmentManager.findFragmentByTag(getString(tag)) as T?
}
/*
* ======================================================================
* ======================================================= event handlers
@ -378,10 +360,6 @@ class TaskEditFragment : Fragment(), Toolbar.OnMenuItemClickListener {
* ========================================== UI component helper classes
* ======================================================================
*/
fun onDueDateChanged() {
repeatControlSet?.onDueDateChanged()
startDateControlSet?.onDueDateChanged()
}
fun addComment(message: String?, picture: Uri?) {
val model = editViewModel.task!!

@ -15,6 +15,7 @@ import android.widget.AdapterView
import android.widget.LinearLayout
import android.widget.Spinner
import android.widget.TextView
import androidx.lifecycle.lifecycleScope
import dagger.hilt.android.AndroidEntryPoint
import net.fortuna.ical4j.model.Recur
import net.fortuna.ical4j.model.WeekDay
@ -31,7 +32,6 @@ import org.tasks.time.DateTimeUtils.currentTimeMillis
import org.tasks.ui.HiddenTopArrayAdapter
import org.tasks.ui.OnItemSelected
import org.tasks.ui.TaskEditControlFragment
import java.util.*
import javax.inject.Inject
/**
@ -68,7 +68,7 @@ class RepeatControlSet : TaskEditControlFragment() {
}
}
fun onDueDateChanged() {
private fun onDueDateChanged() {
viewModel.recur?.let { recur ->
if (recur.frequency == Recur.Frequency.MONTHLY && recur.dayList.isNotEmpty()) {
val weekdayNum = recur.dayList[0]
@ -111,6 +111,12 @@ class RepeatControlSet : TaskEditControlFragment() {
typeSpinner.adapter = typeAdapter
typeSpinner.setSelection(if (viewModel.repeatAfterCompletion!!) TYPE_COMPLETION_DATE else TYPE_DUE_DATE)
refreshDisplayView()
lifecycleScope.launchWhenResumed {
viewModel.dueDate.collect {
onDueDateChanged()
}
}
}
private fun onRepeatTypeChanged(position: Int) {
@ -120,7 +126,7 @@ class RepeatControlSet : TaskEditControlFragment() {
}
private val dueDate: Long
get() = viewModel.dueDate!!.let { if (it > 0) it else currentTimeMillis() }
get() = viewModel.dueDate.value.let { if (it > 0) it else currentTimeMillis() }
override fun onRowClick() {
BasicRecurrenceDialog.newBasicRecurrenceDialog(

@ -5,6 +5,7 @@ import android.content.Intent
import android.os.Bundle
import android.view.ViewGroup
import android.widget.TextView
import androidx.lifecycle.lifecycleScope
import com.todoroo.andlib.utility.DateUtilities
import com.todoroo.andlib.utility.DateUtilities.now
import com.todoroo.astrid.data.Task
@ -39,7 +40,7 @@ class StartDateControlSet : TaskEditControlFragment() {
private lateinit var startDate: TextView
private val dueDateTime
get() = viewModel.dueDate!!
get() = viewModel.dueDate.value
private var selectedDay = NO_DAY
private var selectedTime = NO_TIME
@ -92,7 +93,11 @@ class StartDateControlSet : TaskEditControlFragment() {
selectedDay = savedInstanceState.getLong(EXTRA_DAY)
selectedTime = savedInstanceState.getInt(EXTRA_TIME)
}
applySelectionToHideUntil()
lifecycleScope.launchWhenResumed {
viewModel.dueDate.collect {
applySelectionToHideUntil()
}
}
}
override fun bind(parent: ViewGroup?) =
@ -153,8 +158,6 @@ class StartDateControlSet : TaskEditControlFragment() {
)
}
fun onDueDateChanged() = applySelectionToHideUntil()
private fun applySelectionToHideUntil() {
val due = dueDateTime.takeIf { it > 0 }?.toDateTime()
val millisOfDay = selectedTime

@ -25,12 +25,6 @@ class DeadlineControlSet : TaskEditControlFragment() {
@Inject lateinit var preferences: Preferences
private lateinit var dueDate: TextView
private lateinit var callback: DueDateChangeListener
override fun onAttach(activity: Activity) {
super.onAttach(activity)
callback = activity as DueDateChangeListener
}
override fun createView(savedInstanceState: Bundle?) {
refreshDisplayView()
@ -42,7 +36,7 @@ class DeadlineControlSet : TaskEditControlFragment() {
newDateTimePicker(
this,
REQUEST_DATE,
viewModel.dueDate!!,
viewModel.dueDate.value,
preferences.getBoolean(R.string.p_auto_dismiss_datetime_edit_screen, false))
.show(fragmentManager, FRAG_TAG_DATE_PICKER)
}
@ -63,8 +57,7 @@ class DeadlineControlSet : TaskEditControlFragment() {
override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
if (requestCode == REQUEST_DATE) {
if (resultCode == Activity.RESULT_OK) {
viewModel.dueDate = data!!.getLongExtra(DateTimePicker.EXTRA_TIMESTAMP, 0L)
callback.dueDateChanged()
viewModel.setDueDate(data!!.getLongExtra(DateTimePicker.EXTRA_TIMESTAMP, 0L))
}
refreshDisplayView()
} else {
@ -73,7 +66,7 @@ class DeadlineControlSet : TaskEditControlFragment() {
}
private fun refreshDisplayView() {
val date = viewModel.dueDate!!
val date = viewModel.dueDate.value
if (date == 0L) {
dueDate.text = ""
setTextColor(false)
@ -99,10 +92,6 @@ class DeadlineControlSet : TaskEditControlFragment() {
activity.getColor(if (overdue) R.color.overdue else R.color.text_primary))
}
interface DueDateChangeListener {
fun dueDateChanged()
}
companion object {
const val TAG = R.string.TEA_ctrl_when_pref
private const val REQUEST_DATE = 504

@ -86,6 +86,7 @@ class TaskEditViewModel @Inject constructor(
alarms: List<Alarm>,
) {
this.task = task
dueDate.value = task.dueDate
isNew = task.isNew
originalList = list
selectedList.value = list
@ -138,16 +139,15 @@ class TaskEditViewModel @Inject constructor(
var completed: Boolean? = null
get() = field ?: task.isCompleted
var dueDate: Long? = null
get() = field ?: task.dueDate
set(value) {
field = when {
value == null -> null
value == 0L -> 0
hasDueTime(value) -> createDueDate(Task.URGENCY_SPECIFIC_DAY_TIME, value)
else -> createDueDate(Task.URGENCY_SPECIFIC_DAY, value)
}
val dueDate = MutableStateFlow(0L)
fun setDueDate(value: Long) {
dueDate.value = when {
value == 0L -> 0
hasDueTime(value) -> createDueDate(Task.URGENCY_SPECIFIC_DAY_TIME, value)
else -> createDueDate(Task.URGENCY_SPECIFIC_DAY, value)
}
}
var priority = MutableStateFlow(Task.Priority.NONE)
@ -287,7 +287,7 @@ class TaskEditViewModel @Inject constructor(
fun hasChanges(): Boolean =
(task.title != title || (isNew && title?.isNotBlank() == true)) ||
task.isCompleted != completed ||
task.dueDate != dueDate ||
task.dueDate != dueDate.value ||
task.priority != priority.value ||
if (task.notes.isNullOrBlank()) {
!description.isNullOrBlank()
@ -332,7 +332,7 @@ class TaskEditViewModel @Inject constructor(
}
clear(remove)
task.title = if (title.isNullOrBlank()) context.getString(R.string.no_title) else title
task.dueDate = dueDate!!
task.dueDate = dueDate.value
task.priority = priority.value
task.notes = description
task.hideUntil = hideUntil!!

Loading…
Cancel
Save