#android #kotlin
Вопрос:
Изображение меняет видимость только один раз. Я не могу понять, в чем может быть проблема.
class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
println("Let's do it")
val btn: ImageView = findViewById(R.id.imageView)
while (true) {
Handler().postDelayed({
btn.isVisible = true
Handler().postDelayed({
btn.isVisible = false
}, 1000)
}, 1000)
}
}
}
Комментарии:
1. Мне кажется, что вы публикуете много отложенных исполняемых файлов, так как другие
postDelayed
вызовы будут повторяться без задержек между ними.2. код : создайте миллионы обработчиков и исполняемых файлов как можно быстрее … пользовательский интерфейс : кричит «дай мне передохнуть!»
3. @Майкл, как я могу все исправить? Я просто пытаюсь каждую секунду менять видимость.
4. @DanGal удалите цикл while
Ответ №1:
минимальный пример :
class MainActivity : AppCompatActivity() {
private lateinit var target : ImageView
private val handler : Handler = Handler(Looper.getMainLooper())
private val runnable : Runnable = object : Runnable {
override fun run() {
target.isVisible = !target.isVisible
handler.postDelayed(this, 1_000)
}
}
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
target = findViewById<ImageView>(R.id.imageView)
}
override fun onResume() {
super.onResume()
handler.postDelayed(runnable, 1_000)
}
override fun onPause() {
super.onPause()
handler.removeCallbacksAndMessages(null)
}
}
Комментарии:
1. Могу ли я сделать задержку меньше миллисекунды?
2. Нет, и это было бы бессмысленно, учитывая, что «кадр» рисуется каждые 16 миллисекунд (60 кадров в секунду). Исполняемые файлы и обработчики не идеальны для быстрого обновления пользовательского интерфейса. Обычно вы используете
Animator
фреймворк или пользовательские представления и полностью контролируете холст. Не совсем уверен в вашем случае использования, чтобы задать такой вопрос.
Ответ №2:
давайте упростим этот код
while (true) { // you will keep running this
Handler().postDelayed({
... // this code will won't be exec until 1000ms
}, 1000)
}
Таким образом , вы можете видеть, что за 1000 мс вы добавите так много сообщений в очередь сообщений .
Хорошо, давайте посмотрим на 1000-2000 мс за этот период:
В этот период обработчик сделает две вещи :
- продолжайте публиковать сообщение о задержке в обработчике
- выполните предыдущее сообщение 1000 мс
Шаг 2 также сделает две вещи :
- установить видимое = true
- опубликуйте сообщение «сделать видимым» = ложь
Итак, давайте посмотрим на 2000-3000 мс :
на этот раз мы сделаем 3 вещи :
- продолжайте публиковать сообщение о задержке в обработчике
- выполните предыдущее сообщение 1000 мс
- выполните сообщение шага 2
шаг 3 сделает одну вещь: сделает вид невидимым.
Итак :
0-1000 мс : вид ничего не делает .
1000-2000 мс : вид будет установлен видимым
2000- : вид будет установлен видимым и невидимым очень быстро, так что вы не сможете определить разницу .
Ответ №3:
Вы делаете одну вещь неправильно
btn.isVisible = true
btn.isVisible = false
Это должно быть
btn.visibility = GONE
btn.visibility = VISIBLE
Комментарии:
1. нет, если вы используете
View.kt
расширения. Это не та «единственная» вещь, которая неверна.