Home > Enterprise >  Observers not being triggered whe LiveData changes - Kotlin
Observers not being triggered whe LiveData changes - Kotlin

Time:05-02

I know this question has been asked a couple of times, but I have a funny situation here that I can't figure out.

I have a database with "TASKS" and, apart from the writing/updating methods, I'm calling the get method twice: one for getting the last created task, and another to select an specific task by ID

@Query("SELECT * FROM tasks_history_table ORDER BY taskId DESC LIMIT 1")
    suspend fun getCurrentTask(): Task2?

@Query("SELECT * from tasks_history_table WHERE  taskId = :key ")
    suspend fun get(key: Long): Task2?

Then in the viewModel I'm launching a coroutine for each time I call one of these methods.

This one for the last created Task:

private fun initializeCurrentTask(){
    viewModelScope.launch {
        _currentTask.value = getCurrentTaskFromDatabase()!!
    }
}
suspend fun getCurrentTaskFromDatabase(): Task2? {
    var currentTask = database.getCurrentTask()
    return currentTask
    }

And this one for the specific task

fun initializeSelectedTask(){
        viewModelScope.launch {
            _currentTask.value = getSelectedTaskFromDatabase(selectedTaskId.value!!)!!
        }
    }
    suspend fun getSelectedTaskFromDatabase(taskId: Long): Task2? {
        var currentTask = database.get(selectedTaskId.value!!)!!
        return currentTask
    }

So they are both pretty much the same, except for the parameter Id passed.

Then, I'm sending that data to the Fragment to update the UI, via LiveData

private val _currentTask = MutableLiveData<Task2>()
    val currentTask : LiveData<Task2>
        get() = _currentTask

And here the observer:

timerViewModel.currentTask.observe(viewLifecycleOwner) {
            updateUIText()
            updateCountdownUI()
            updateAnimation()
        }

Everytime I call the function to get the las saved task, the observers are called and everything works fine. But whenever I call the function to get a specific task by Id, the observers are not called.

I've set Logs all around and I've reached the conclusion that the LiveData is getting updated, but the observer is not triggered.

Here's the repo in case someone can have it a look. Thanks!! https://github.com/arieldipietro/PomodoroTechnique

CodePudding user response:

In FragmentTimer and FragmentHistory, you have created viewModel instances using their respective fragments as owners, which makes them to observe liveData which are triggered by their instances only. So, now when you trigger a task from FragmentHistory it isn't get observed in FragmentTimer.

You need to use SharedViewModel for passing data between fragments, you have to create object of TimerViewModel using activity as its owner, then you would be able to observe from FragmentTimer. Pass requireActivity() as the owner in ViewModelProvider's constructor.

timerViewModel = ViewModelProvider(requireActivity(), viewModelFactory)[TimerViewModel::class.java]

You can read more about it in this codelab tutorial.

  • Related