使用协程进行连续的数据轮询和转储到UI



我现有的Android代码使用AsyncTask虚拟COM连续轮询数据端口,并通过覆盖onProgressUpdate()函数将数据转储到UI线程。如下所示:

open class ComActivity(deviceID:Int, listener: OnComRxUpdateUI) : AsyncTask<..., ..., ...>(){
...   
override fun doInBackground(...) { 
...   //keep listening on serial port and transfer byte to buffer when available
}
override fun onProgressUpdate(...){
...  //dump to ui 
}  
}

上面的代码工作得很好(除了一些内存泄漏警告)。

时不时地,我看到Coroutine被提升为执行并发和异步操作,我发现有必要尝试用协程代替AsyncTask。OTOH,我没有完全掌握Coroutines代替AsyncTask的工作原理。所以我的问题是Coroutine是否是一个可行的替换我的用例(连续的数据轮询和在UI上转储)。任何好的高级(或伪)示例在那里演示这个用例是受欢迎的。

很难假设您如何在AsyncTask中的串行端口上侦听,无论您使用某种侦听器还是无限循环,但我猜使用FlowMVVM方法可以实现相同的结果。它看起来像下面这样:

在Repository类中:

fun listenPort(): Flow<String> = flow {
// keep listening on serial port, use emit() function to emit data
while (true) {
val data = listen()
emit(data)
}
}
suspend fun listen() = withContext(Dispatchers.IO) {
// listening on serial port
}

InViewModel:

private val _state = MutableStateFlow<State>(Loading)
val state = _state
init {
repository.listenPort()
.onEach { data ->
_state.value = Dump(data)
}.launchIn(viewModelScope)
}

:

sealed interface State
object Loading : State
data class Dump(val data: ...) : State

In Ui(ActivityorFragment):

vm.state
.flowWithLifecycle(lifecycle)
.onEach { state ->
// handle all states
if (state is Dump) {
val data = state.data
// use data
}
}.launchIn(lifecycleScope)

如果你不喜欢使用MVVM架构的方法,你可以在UI类(ActivityFragment)中完成所有这些,我不建议:

listenPort().flowWithLifecycle(lifecycle)
.onEach { data ->
// use data
}.launchIn(lifecycleScope)

相关内容

  • 没有找到相关文章

最新更新