【问题标题】:How to Implement or Handle the CountDownTimer using Kotlin Coroutines如何使用 Kotlin 协程实现或处理 CountDownTimer
【发布时间】:2022-11-02 20:03:41
【问题描述】:

我构建了一个安卓应用倒计时器使用科特林。当我使用启动计时器时协程它会引发如下错误。

需要您的帮助:

  • 如何处理或实现倒数计时器的处理程序,该处理程序将在不同的设备上运行 线程而不是主线程...或者...如何使用 kotlin 协程实现计时器?

错误文本:

java.lang.RuntimeException: Can't create handler inside thread Thread[DefaultDispatcher-worker-1,5,main] that has not called Looper.prepare()

代码:

override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)

        btnStartPause.setOnClickListener {
            if (isRunning) {
                pauseTimer()
            } else {
                val time = edtTxtTimer.text.toString().trim()
                timeInMilliSeconds = time.toLong() * 60000L // 1m = 60,000ms
               
                CoroutineScope(Dispatchers.Default).launch {
                        startTimer(timeInMilliSeconds)
                }
            }
        }
    }
    
    ////////////////////////////////////////////////////
    ////////////////////////////////////////////////////

    private fun startTimer(time_in_milli_second: Long) {
        countdown_timer = object : CountDownTimer(time_in_milli_second, 1000) {
            override fun onTick(millisUntilFinished: Long) {
                timeInMilliSeconds = millisUntilFinished
                updateUI()
            }

            override fun onFinish() {
                btnStartPause.text = "Start"
                loadConfeti()
            }
        }
        countdown_timer.start()

        isRunning = true
        btnStartPause.text = "Pause"
        btnReset.visibility = View.GONE
    }

【问题讨论】:

    标签: android kotlin kotlin-coroutines countdowntimer android-handler


    【解决方案1】:

    CountdownTimer 只能从 Looper 线程启动。这通常只是主线程,除非您在特定的其他线程上创建了自己的 Looper。 Dispatchers.Main 是 Kotlin 提供的唯一具有 Looper 的调度程序。

    您不需要使用协程来启动 CountdownTimer。该类自动在后台运行而不会阻塞。这实际上是它需要 Looper 线程的原因......因此它可以在启动它的同一线程上触发其 onTickonFinish 而不会阻塞该线程。

    【讨论】:

      【解决方案2】:

      有两种实现方式倒计时器解决上述错误:

      第一种方式

      • 通过使用HandlerThread 创建您自己的Dispatcher 来实现计时器
      • 但这不是最好的方法

      第二种方式

      • 使用Kotlin Flows 实现定时器
      • 在任何设备上启动计时器调度员以外主线程
      • Main Thread 上的生产者收集数据

      【讨论】:

        猜你喜欢
        • 2019-06-02
        • 2020-01-10
        • 1970-01-01
        • 2019-07-16
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多