summaryrefslogtreecommitdiff
path: root/emulator/src/com/android/tools/idea/emulator/EmulatorUtils.kt
diff options
context:
space:
mode:
Diffstat (limited to 'emulator/src/com/android/tools/idea/emulator/EmulatorUtils.kt')
-rw-r--r--emulator/src/com/android/tools/idea/emulator/EmulatorUtils.kt31
1 files changed, 31 insertions, 0 deletions
diff --git a/emulator/src/com/android/tools/idea/emulator/EmulatorUtils.kt b/emulator/src/com/android/tools/idea/emulator/EmulatorUtils.kt
index 05baff8c3c2..178cc075d73 100644
--- a/emulator/src/com/android/tools/idea/emulator/EmulatorUtils.kt
+++ b/emulator/src/com/android/tools/idea/emulator/EmulatorUtils.kt
@@ -19,15 +19,21 @@ import com.android.annotations.concurrency.UiThread
import com.android.emulator.control.KeyboardEvent
import com.android.emulator.control.KeyboardEvent.KeyEventType
import com.android.emulator.control.ThemingStyle
+import com.google.common.util.concurrent.ListenableFuture
import com.intellij.ide.ui.LafManager
import com.intellij.openapi.Disposable
import com.intellij.openapi.application.ApplicationManager
import com.intellij.openapi.application.ModalityState
import com.intellij.openapi.project.Project
import com.intellij.openapi.project.ex.ProjectEx
+import com.intellij.util.concurrency.SameThreadExecutor
+import kotlinx.coroutines.cancelFutureOnCancellation
+import kotlinx.coroutines.suspendCancellableCoroutine
import java.awt.Container
import java.awt.Dimension
import java.awt.Point
+import kotlin.coroutines.resume
+import kotlin.coroutines.resumeWithException
import kotlin.math.abs
import kotlin.math.ceil
import kotlin.math.min
@@ -53,6 +59,31 @@ internal fun invokeLaterInAnyModalityState(@UiThread action: () -> Unit) {
}
/**
+ * Coroutine-friendly version of [ListenableFuture.get].
+ */
+suspend fun <T> ListenableFuture<T>.suspendingGet(): T {
+ if (isDone) {
+ @Suppress("BlockingMethodInNonBlockingContext")
+ return get()
+ }
+
+ return suspendCancellableCoroutine { continuation ->
+ continuation.cancelFutureOnCancellation(this)
+ val listener = Runnable {
+ val value = try {
+ get()
+ }
+ catch (e: Throwable) {
+ continuation.resumeWithException(e)
+ return@Runnable
+ }
+ continuation.resume(value)
+ }
+ addListener(listener, SameThreadExecutor.INSTANCE)
+ }
+}
+
+/**
* Creates a [KeyboardEvent] for the given hardware key.
* Key names are defined in https://developer.mozilla.org/en-US/docs/Web/API/KeyboardEvent/key/Key_Values.
*/