[英]How do you call a suspend function inside a SAM?
我正在尝试创建一个需要从回调发出值的Flow
,但我不能调用emit
function 因为 SAM 是普通的 function
这是 class 和库中的 SAM,我无法按照我需要的方式对其进行修改。
class ValueClass {
fun registerListener(listener: Listener) {
...
}
interface Listener {
fun onNewValue(): String
}
}
这是我对创建Flow
object 的看法
class MyClass(private val valueClass: ValueClass) {
fun listenToValue = flow<String> {
valueClass.registerListener { value ->
emit(value) // Suspension functions can only be called on coroutine body
}
}
}
我想如果我可以更改ValueClass
会很简单,但在这种情况下,我不能。 我一直在思考这个问题并试图寻找实现。
至少据我所知,一种解决方案是像这样使用GlobalScope
class MyClass(private val valueClass: ValueClass) {
fun listenToValue = flow<String> {
valueClass.registerListener { value ->
GlobalScope.launch {
emit(value)
}
}
}
}
现在,这可行,但我不想使用GlobalScope
,因为我将使用viewModelScope
将它与我的应用程序的生命周期联系起来。
有没有办法解决这个问题?
提前致谢。 任何帮助将不胜感激!
您可以使用callbackFlow
从回调中创建一个Flow
。 它看起来像:
fun listenToValue(): Flow<String> = callbackFlow {
valueClass.registerListener { value ->
trySend(value)
channel.close() // close channel if no more values are expected
}
awaitClose { /*unregister listener*/ }
}
或者,如果回调中只需要一个值,您可以使用suspendCoroutine
或suspendCancellableCoroutine
。 在这种情况下, listenToValue()
function 必须suspend
,然后从协程(例如someScope.launch
)中调用:
suspend fun listenToValue(): String = suspendCoroutine { continuation ->
valueClass.registerListener { value ->
continuation.resumeWith(value)
}
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.