отношения kotlin coroutine и основного обработчика

У меня есть следующий фрагмент

verticalLayout { gravity = Gravity.CENTER button("BUTTON").onClick { trace("click on process") runBlocking { trace("blocking start") // #1 delay(20000L) #2 trace("blocking end") // #3 } trace("click process end") } } 

trace – это функция, определенная как служебная функция для вывода сообщений с использованием Log.e с текущим именем потока

когда я нажимаю кнопку, весь код работает так, как ожидалось, и журналы показывают, что все функции трассировки вызывается в журнале основного потока для # 3, появляется после # 1 в течение 20000L мс и не отображается ANR Dialog

но странные вещи произошли во время 20000L мс, кнопка удерживает нажатое состояние, даже когда я отпускаю кнопку сразу после щелчка, тогда я понял, что нажатое состояние восстанавливается, когда заканчивается метод onClick,

у меня была своя концепция, что coroutine – это магия компилятора, использующая CPS, чтобы преобразовать код в функцию стиля обратного вызова, например, следовать

 delay(20000L,callback = { trace("blocking end ")}) 

поэтому у меня есть следующие вопросы

  1. в конце концов, кто и когда на самом деле вызывает обратный вызов (например, трассировка («блокирующий конец»)), если ответ является основным петлером или чем-то (для nodejs, возможно, eventloop), нужно ли адаптировать структуру для сопрограммы и позволить событие coroutine put в очередь?
  2. говоря, что coroutine на самом деле является манерой компилятора, можем ли мы написать тот же код, что и фрагмент выше, который не вызывает ANR, но сохраняет нажатое состояние для 20000L?

Вы используете runBlocking который назван таким образом, потому что он блокирует поток, на который он вызывается, на время выполнения сопрограммы. В вашем конкретном случае вы блокируете поток пользовательского интерфейса с помощью runBlocking .

Вы можете заменить runBlocking на launch(UI) чтобы запустить фоновый сопрограмму в потоке пользовательского интерфейса без блокировки потока пользовательского интерфейса. Вы можете узнать больше о различных способах работы с сопрограммами в Руководстве по kotlinx.coroutines и в Руководстве по программированию пользовательского интерфейса с сопрограммами .

Intereting Posts
Kotlin zipВсе альтернатива Переменные не инициализируются должным образом при инициализации в абстрактной абстрактной функции, вызванной из конструктора или блока init Как умножить nullsafe float в котлин? Операторы с нулевым значением, допустимые в общем классе? Запустить Java в Kotlin-конвертер из командной строки? null в listOf (), а не null в listOf (значение) в Kotlin в одном лайнере? Невозможно создать класс объектов Android Room. Невозможно повторно назначить локальные переменные Retrofit2 + SimpleXML в Kotlin: MethodException: аннотация должна отмечать набор или метод get Ошибка Kotlin при ссылке на активность из внутреннего класса Ошибка: выполнение выполнено для задачи ': app: kaptDemoTestingDebugKotlin' Kotlin: Как дочерний конструктор может использовать вторичный конструктор своего родителя? Kotlin добавляет пользовательский прослушиватель для доступа к виджетам на Android Android Local VPN Service: не может получить ответ Ошибка подключаемого модуля: Kotlin бросил непроверенное исключение IllegalStateException