Coroutine Tips and Tricks
This section presents techniques to use coroutines efficiently and avoid common pitfalls.
Switching Between the Background Threads and EDT
Avoid the invokeLater
-style often found in Java:
The recommended approach:
Dispatching to the End of a Queue
In some cases, it is required to exit the current EDT event and continue after all events in the queue are processed. In a non-coroutine context, it could be implemented like in the following snippet:
In a coroutine context, use the following approach:
This approach works with any sequential dispatcher, e.g., created with Dispatchers.Default.limitedParallelism(1)
.
The same applies to runBlockingCancellable
:
Scheduling Tasks With a Fixed Delay
There is no scheduleWithFixedDelay()
in coroutines, because it can be easily implemented with the following snippet:
When the job is no longer needed, remember to cancel the launched coroutine:
or the whole scope:
Limiting Dispatcher Parallelism
Each call of limitedParallelism()
creates a new independent dispatcher instance, effectively not limiting the parallelism:
Instead, store the dispatcher instance into a static property and use it as a context:
Changing Modality State
Avoid changing modality state in the middle of a running coroutine:
Add the modality state to the context when launching a coroutine:
It is possible that the coroutine is launched as a response to a user event from EDT, where ModalityState.current()
is available.
If the coroutine is launched from a background thread, then it should not be invoked on top of an unrelated dialog anyway. The absence of the context modality state is effectively equivalent to specifying ModalityState.nonModal()
.