【发布时间】:2019-11-23 02:10:31
【问题描述】:
假设我有一个动作要在一段时间后执行,而用户没有触摸屏幕。如何实现一个定时器,它在超时时执行一个动作,但每次用户触摸屏幕时都会重新开始?
【问题讨论】:
-
Getting Touches 并将其与Tenfour04s 答案结合起来
假设我有一个动作要在一段时间后执行,而用户没有触摸屏幕。如何实现一个定时器,它在超时时执行一个动作,但每次用户触摸屏幕时都会重新开始?
【问题讨论】:
这是一个未经测试的协同程序想法:
private const val INACTIVITY_SECONDS: Int = 5
abstract class InactivityActivity : AppCompatActivity() {
private val counterScope = CoroutineScope(Dispatchers.Main)
private fun restartCountDown() {
counterScope.cancel()
counterScope.launch {
delay(INACTIVITY_SECONDS * 1000L)
onInactivity()
}
}
protected abstract fun onInactivity()
override fun onPause() {
super.onPause()
counterScope.cancel()
}
override fun onResume() {
super.onResume()
restartCountDown()
}
override fun onUserInteraction() {
super.onUserInteraction()
restartCountDown()
}
}
【讨论】:
我搜索了几个答案,但找不到像我想要解决这个问题的解决方案一样简单的东西。这对我有用:
我使用了onUserInteraction() 函数,每次用户触摸屏幕时都会调用该函数。我声明了一个在 onCreate() 中开始并在 onDestroy() 中取消的 CountDownTimer。每次调用 onUserInteraction() 时,CountDownTimer 都会被取消、重置,然后再次启动。当 CountDownTimer 完成时,将执行该操作。
package com.example.inactivityapp
import androidx.appcompat.app.AppCompatActivity
import android.os.Bundle
import android.os.CountDownTimer
import android.util.Log
import android.widget.Toast
private val TAG = InactivityActivity::class.java.simpleName
private const val INACTIVITY_SECONDS: Int = 5
class InactivityActivity : AppCompatActivity() {
var inactivitySeconds = INACTIVITY_SECONDS
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_inactivity)
inactivityCountDownTimer.start()
}
override fun onDestroy() {
super.onDestroy()
inactivityCountDownTimer.cancel()
}
override fun onUserInteraction() {
super.onUserInteraction()
Log.i(TAG, "user interaction")
inactivityCountDownTimer.cancel()
inactivitySeconds = INACTIVITY_SECONDS
inactivityCountDownTimer.start()
}
var inactivityCountDownTimer =
object : CountDownTimer(inactivitySeconds * 1000.toLong(), 1000) {
override fun onTick(millisUntilFinished: Long) {
Log.i(TAG, inactivitySeconds.toString())
inactivitySeconds--
}
override fun onFinish() {
Toast.makeText(
this@InactivityActivity,
"Activity Timeout: Perform timeout task",
Toast.LENGTH_LONG
).show()
Log.i(TAG, "activity timeout")
}
}
}
【讨论】: