ansman
08/26/2019, 12:37 AMDispatchers.Main.immediate? yield() will not do anything. delay(1) works but is kind of uglyoctylFractal
08/26/2019, 12:42 AMDispatchers.Main?ansman
08/26/2019, 12:42 AMansman
08/26/2019, 12:43 AMstreetsofboston
08/26/2019, 12:43 AMpost of a Runnable, but putting in front of the queue?octylFractal
08/26/2019, 12:43 AMwithContext(Dispatchers.Main) then?ansman
08/26/2019, 12:44 AMsuspend fun defer() {
val dispatcher = coroutineContext[ContinuationInterceptor] as? CoroutineDispatcher
if (dispatcher == null) {
Timber.w("No coroutine dispatcher found, using delay instead")
delay(1)
} else {
suspendCancellableCoroutine { cont ->
dispatcher.dispatch(EmptyCoroutineContext, Runnable { cont.resume(Unit) })
}
}
}streetsofboston
08/26/2019, 12:50 AMansman
08/26/2019, 12:51 AMstreetsofboston
08/26/2019, 12:55 AMdefer is called on the main thread)?
I'd write something myself to make the synchronization you need more explicit instead of relying on delay or dispatcher.dispatch.ansman
08/26/2019, 12:55 AMdispatcher.dispatch will always post it to the queue, even on the immediate dispatcheransman
08/26/2019, 12:56 AMstreetsofboston
08/26/2019, 12:57 AMansman
08/26/2019, 12:58 AMviewCreatedScope.launch {
view.awaitPredraw()
// Setup animation
defer()
TransitionManager.beginDelayedTransition(...)
// Set to final state
}octylFractal
08/26/2019, 1:00 AMimmediate -- any suspend point that actually suspends will still re-dispatch, since coroutine suspension removes the code from the thread, and any point that doesn't suspend will continue in the same thread regardless of immediatestreetsofboston
08/26/2019, 1:00 AMoctylFractal
08/26/2019, 1:00 AMimmediate only affects the initial coroutine launchansman
08/26/2019, 1:01 AMimmediate since it would actually draw the frame where i want to set up the animationansman
08/26/2019, 1:02 AMansman
08/26/2019, 1:03 AMresumeWith for a coroutine dispatcher:
override fun resumeWith(result: Result<T>) {
val context = continuation.context
val state = result.toState()
if (dispatcher.isDispatchNeeded(context)) {
_state = state
resumeMode = MODE_ATOMIC_DEFAULT
dispatcher.dispatch(context, this)
} else {
executeUnconfined(state, MODE_ATOMIC_DEFAULT) {
withCoroutineContext(this.context, countOrElement) {
continuation.resumeWith(result)
}
}
}
}streetsofboston
08/26/2019, 1:03 AMpost methods for sync, not relying on the Coroutine Dispatchers. You can the wrap that in a suspend function called defer()ansman
08/26/2019, 1:03 AMisDispatchNeeded would return false if called on the main thread when using the immediate dispatcheransman
08/26/2019, 1:04 AMdefer could pretty much only be called on the main threadansman
08/26/2019, 1:04 AMstreetsofboston
08/26/2019, 1:05 AMpost from any thread.ansman
08/26/2019, 1:05 AMdeferstreetsofboston
08/26/2019, 1:06 AMlouiscad
08/26/2019, 6:55 AMyield() should support the immediate dispatcher. You should open an issue on GitHub.David Glasser
08/26/2019, 7:04 PM