Skip to content

IFMO-Android-2015/lesson2

Repository files navigation

Вторая лекция

  • Потоки в Android
  • Выполнение сетевых запросов
  • AsyncTask для асинхронного выполнения задач
  • Смена конфигурации

Код второй лекции демонистрирует использование AsyncTask для выполнения долгих операций в фоновом потоке и доставки результата в UI поток. В качестве примера долгой опреации выполняется скачивание большого файла при помощи HttpURLConnection. Обратите особое внимание на то, как сохраняется и восстанавливается объект DownloadFileTask при смене конфигурации в InitSplashActivity -- при повороте экрана ранее запущенный таск продолжает выполнение, а результат показывается в новой активности.

В разных ветках можно посмотреть разные варианты кода, которые ведут себя по-разному. Окончательный правильный вариант лежит в ветке master. Можно посмотреть код в разных ветках, позапускать его и посмотреть, как по-разному ведет себя приложение.

master

Ветка master содержит полный вариант кода, в котором Activity запускает AsyncTask только один раз, а при смене конфигурации использует non-configuration-state для передачи запущенного AsyncTask из старого объекта Activity (который убивается) в новый (который создается после смены конфигурации). Можно запустить приложение и покрутить экран (в эмуляторе Ctrl-F11 или Ctrl-F12) и увидеть что все работает как надо. В логах видно, что скачивание происходит один раз

example-2.1

В этой ветке скачивание файла происходит в UI потоке в методе SplashInitActivity.onCreate(). Это очень плохо! Даже потребовалось включить специальный режим StrictMode для того, чтобы система в принципе позволила выполнить сетевой запрос (см. комментарий в SplashInitActivity.onCreate()). Если запустить, то можно увидеть белый экран -- приложение висит. Если закомментировать StrictMode, то приложение упадет с NetworkOnMainThreadException

example-2.2

В этой ветке сделан класс DownloadFileTask, в котором происходит скачивание файла в фоновом потоке в методе doInBackground. Во время скачивания показывается индикатор типа Indeterminate (крутилка) при помощи ProgressBarView. Таск всегда просто запускается в методе onCreate, поэтому при каждом повороте экрана скачивание запускается снова (осторожно, трафик!)

example-2.3

Индикатор типа Indeterminate заменен на индикатор прогресса -- этот тот же ProgressBarView, но с другим стилем. Используются методы AsyncTask.publishProgress и AsyncTask.onProgressUpdate для отображения прогресса загрузки. По-прежнему запускается новый таск при каждой смене конфигурации (повороте экрана) -- в логах можно увидеть, как после поворота экрана продолжается выполнение старого таска загрузки, и только после завершения старой загрузки стартует новая загрузка. В интерфейсе это заметно по тому, как останавливаетя прогресс после поворота экрана (в это время выполняется старый таск, но он не связан с новым экраном и не обновляет прогресс), а спустя некоторое время он сбрасывается в начало (это начинает работать новый таск, связанный с текущим экраном)

example-2.3-stetho

Отличается от example-2.3 тем, что в приложение внедрена библиотека Stetho (http://facebook.github.io/stetho/), позволяющая наблюдать за работой приложения в окне браузера Chrome. Введите в строке браузера chrome://inspect/devices -- появится список подключенных устройств и эмуляторов с запущенными приложениями. Можно выбрать работающее приложение, нажать Inspect и во вкладке Network увидеть выполнение HTTP запросов. Видно, что если покрутить экран, то выстраивается очередь запросов, которые выполняются один за другим и скачивают один и тот же файл, что не есть хорошо.

example-2.4

Это финальный пример, его код совпадает с master. Устранены описанные выше недостатки.

Материалы лекции

Power Point: https://cloud.mail.ru/public/3zAP/H1JTYoEpx

PDF: https://cloud.mail.ru/public/Fjuf/HgAgNX8ZH

Домашнее задание

https://github.com/IFMO-Android-2015/homework2

About

No description, website, or topics provided.

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published

Languages