Про App Widgets в Android
На сегодняшний день уже опубликовано большое количество учебного материала, в котором подробно, по шагам описывается процесс создания простого App Widget в стиле «HelloWorld». Под App Widget-ами подразумеваются приложения, которые можно поместить на основной экран в ОС Android. Как правило это различные индикаторы (состояние батареи, яркость экрана, погода, твитты, пробки и т. д.). На мой взгляд лучшим руководством является статья, размещенная непосредственно на сайте гугл .
Здесь мне хотелось больше уделить внимание общей схеме работы с AppWidget-ами и некоторым особым моментам работы с ними. Публикация сделана на основе моего собственного опыта и актуальна на момент написания публикации, но поскольку платформа Android очень быстро развивается, при изучении этой статьи в будущем прошу сверяться с текущей официальной документацией.
Почему виджеты.
Идея попробовать написать свои виджеты возникла у меня давно, но до реальных опытов руки все-таки не доходили. По большому счету, для меня основным мотивов их создания было и остается любопытство и желание сделать что-то забавное.
В итоге в декабре, перед новым годом все-таки удалось выкроить пару недель для плотной работы с ними.
Для пробы были сделаны и выложены на Маркете пара виджетов (бесплатных):
1. Рождественская ёлка, на игрушках которой загораются различные индикаторы (громкость, включен ли WiFi, заряд батареи и т. д.)
Сhristmas Tree Widget
2. Робот. Тоже пять-в-одном виджет — показывает уровень громкости, заряд батареи, включен ли Wi-Fi, 3G, вибро-режим.
Face Widget
Приложения сейчас не только бесплатные. но и без рекламы. Я просто еще не начинал разбираться с работой AdMob SDK. Возможно, если все-таки разберусь, напишу об этом позже.
Итак.
Принципиальные отличия в работе с виджетами и диаграмма классов.
При работе с виджетами самое главное — нужно понимать, что виджеты обновляются в специальном отдельном процессе. Например, если вы работаете внутри обычного активити, то поменять содержимое текстового поля можно просто вызвав метод setText в UI нитке.
Если говорить про AppWidget-ы, то для того, чтобы изменить состояние графического элемента (TextView, ImageView и т. д.), из которого он состоит, нужно использовать специальные классы и методы.
Упрощенно изменения осуществляются в два шага:
1. Вначале нужно воспользоваться объектом RemoteViews, чтобы указать, что именно вы планируете поменять (например, метод setTextViewText ).
2. Затем с помощью AppWidgetManager применить изменения, передав созданный объект RemoteViews в метод update .
Если вы хотите обрабатывать событие нажатия на виджет, то это также можно сделать через объект класса RemoteViews с помощью метода setOnClickPendingIntent
Объект класса AppWidgetManager можно получить либо с помощью статического фабричного метода AppWidgetManager. getInstance(context). Также ссылка на менеджер виджетов передается в виде аргумента в методе onUpdate класса AppWidgetProvider .
Класс AppWidgetProvider наследуется от BroadcastReceiver. Поэтому желательно не забыть добавить его в файл AndroidManifest. xml и указать, где расположено xml-описание виджета:
<appwidget-provider xmlns:android=»http://schemas. android. com/apk/res/android» android:minWidth=»294dp» android:minHeight=»72dp» android:updatePeriodMillis=»86400000″ и т. д. > </appwidget-provider>
Этому XML-файлу соответствует класс AppWidgetProviderInfo (еще раз повторюсь, подробные примеры и пошаговое описание создание виджета нужно смотреть на сайте гугла).
В целом, диаграмма класса может быть описана грубо следующем образом:
Анимация.
AnimationDrawable может работать, а может не работать. Зависит от конкретной модели телефона/планшета. Поэтому анимация – это больная тема для многих программистов, которые пытаются сделать анимированный виджет.
Стабильного универсального способа, который бы обеспечивал полноценную работу анимации на всех телефонах пока нет.
Есть два подхода:
1. Делать анимацию самому. Например, с определенной частотой меняя картинку у ImageView .
Здесь есть один нюанс, поскольку виджет работает в отдельном процессе, то при определенной частоте обновлений bitmap-ы перестанут «пролезать» через межпроцессорную связывалку. Как вариант можно передавать не сами картинки, а идентификаторы их ресурсов, но тогда ограничиваемся только существующим набором изображений.
2. Использовать неопределенный прогресс бар. установив для него свой ресурс для отрисовки indeterminateDrawable .
История изменений
API по работе с App Widget-ами наращивалось следующими образом:
- Появление виджетов. Level 3 (Android 1.5)
- Изменения размера пользователем. Коллекции. Level 11 (Android 3)
- Возможность добавления на экран блокировки. Level 17 (Android 4.2)
Итоги
С виджетами работать интересно, хотя и неудобно. У меня получилось, что времени на работу с ними ушло немного больше, чем планировал.
Благодарности.
В первую очередь огромное спасибо супер-программистке Татьяне за совместную работу и разработку активити.
За бета-тестирование и замечания — Вове (Московскому), Нику (Лондонскому), Даниэлю (Балийскому), Беке, Гарику, Артуру и Валерии (Ива Виннер). Если кого забыл, прошу прощения, не специально.