|
@@ -0,0 +1,425 @@
|
|
|
|
|
+<table style="width: 100%;"><tr><td style="width: 40%;">
|
|
|
|
|
+<a href="../articles/android_studio.md">Первый проект в Android Studio
|
|
|
|
|
+</a></td><td style="width: 20%;">
|
|
|
|
|
+<a href="../readme.md">Содержание
|
|
|
|
|
+</a></td><td style="width: 40%;">
|
|
|
|
|
+<a href="../articles/themes.md">Темы. Фигуры. Обработчики событий.
|
|
|
|
|
+</a></td><tr></table>
|
|
|
|
|
+
|
|
|
|
|
+`<` `>`
|
|
|
|
|
+
|
|
|
|
|
+# Стили и темы
|
|
|
|
|
+
|
|
|
|
|
+## Стили
|
|
|
|
|
+
|
|
|
|
|
+Мы можем настроить элемент с помощью различных атрибутов, которые задают высоту, ширину, цвет фона, текста и так далее. Но если у нас несколько элементов используют одни и те же настройки, то мы можем объединить эти настройки в стили.
|
|
|
|
|
+
|
|
|
|
|
+Например, пусть у нас есть несколько элементов TextView:
|
|
|
|
|
+
|
|
|
|
|
+```xml
|
|
|
|
|
+<?xml version="1.0" encoding="utf-8"?>
|
|
|
|
|
+<androidx.constraintlayout.widget.ConstraintLayout
|
|
|
|
|
+ xmlns:android="http://schemas.android.com/apk/res/android"
|
|
|
|
|
+ xmlns:app="http://schemas.android.com/apk/res-auto"
|
|
|
|
|
+ android:layout_width="match_parent"
|
|
|
|
|
+ android:layout_height="match_parent">
|
|
|
|
|
+
|
|
|
|
|
+ <TextView
|
|
|
|
|
+ android:id="@+id/textView1"
|
|
|
|
|
+ android:layout_width="0dp"
|
|
|
|
|
+ android:layout_height="wrap_content"
|
|
|
|
|
+ android:gravity="center"
|
|
|
|
|
+ android:textSize="28sp"
|
|
|
|
|
+ android:textColor="#3f51b5"
|
|
|
|
|
+ android:text="Android Lollipop"
|
|
|
|
|
+
|
|
|
|
|
+ app:layout_constraintLeft_toLeftOf="parent"
|
|
|
|
|
+ app:layout_constraintRight_toRightOf="parent"
|
|
|
|
|
+ app:layout_constraintTop_toTopOf="parent"
|
|
|
|
|
+ app:layout_constraintBottom_toTopOf="@+id/textView2"
|
|
|
|
|
+ />
|
|
|
|
|
+ <TextView
|
|
|
|
|
+ android:id="@+id/textView2"
|
|
|
|
|
+ android:layout_width="0dp"
|
|
|
|
|
+ android:layout_height="wrap_content"
|
|
|
|
|
+ android:gravity="center"
|
|
|
|
|
+ android:textSize="28sp"
|
|
|
|
|
+ android:textColor="#3f51b5"
|
|
|
|
|
+ android:text="Android Marshmallow"
|
|
|
|
|
+
|
|
|
|
|
+ app:layout_constraintLeft_toLeftOf="parent"
|
|
|
|
|
+ app:layout_constraintRight_toRightOf="parent"
|
|
|
|
|
+ app:layout_constraintBottom_toTopOf="@+id/textView3"
|
|
|
|
|
+ app:layout_constraintTop_toBottomOf="@+id/textView1"
|
|
|
|
|
+ />
|
|
|
|
|
+ <TextView
|
|
|
|
|
+ android:id="@+id/textView3"
|
|
|
|
|
+ android:layout_width="0dp"
|
|
|
|
|
+ android:layout_height="wrap_content"
|
|
|
|
|
+ android:gravity="center"
|
|
|
|
|
+ android:textSize="28sp"
|
|
|
|
|
+ android:textColor="#3f51b5"
|
|
|
|
|
+ android:text="Android Nougat"
|
|
|
|
|
+
|
|
|
|
|
+ app:layout_constraintLeft_toLeftOf="parent"
|
|
|
|
|
+ app:layout_constraintRight_toRightOf="parent"
|
|
|
|
|
+ app:layout_constraintBottom_toBottomOf="parent"
|
|
|
|
|
+ app:layout_constraintTop_toBottomOf="@+id/textView2"
|
|
|
|
|
+ />
|
|
|
|
|
+
|
|
|
|
|
+</androidx.constraintlayout.widget.ConstraintLayout>
|
|
|
|
|
+```
|
|
|
|
|
+
|
|
|
|
|
+
|
|
|
|
|
+
|
|
|
|
|
+Все эти **TextView** имеют одинаковый набор свойств, и, к примеру, если нам захочется изменить цвет текста, то придется менять его у всех трех TextView. Данный подход не оптимален, а более оптимальный подход представляет использование стилей, которые определяются в проекте в папке `res/values`.
|
|
|
|
|
+
|
|
|
|
|
+Итак, добавим в проект в папку `res/values` новый элемент Value Resourse File, который назовем `styles.xml`:
|
|
|
|
|
+
|
|
|
|
|
+
|
|
|
|
|
+
|
|
|
|
|
+
|
|
|
|
|
+Определим в файле styles.xml следующее содержимое:
|
|
|
|
|
+
|
|
|
|
|
+```xml
|
|
|
|
|
+<?xml version="1.0" encoding="utf-8"?>
|
|
|
|
|
+<resources>
|
|
|
|
|
+ <style name="TextViewStyle">
|
|
|
|
|
+ <item name="android:layout_width">0dp</item>
|
|
|
|
|
+ <item name="android:layout_height">wrap_content</item>
|
|
|
|
|
+ <item name="android:textColor">#3f51b5</item>
|
|
|
|
|
+ <item name="android:textSize">28sp</item>
|
|
|
|
|
+ <item name="android:gravity">center</item>
|
|
|
|
|
+ </style>
|
|
|
|
|
+</resources>
|
|
|
|
|
+```
|
|
|
|
|
+
|
|
|
|
|
+Здесь определен новый стиль **TextViewStyle**, который с помощью элементов **item** задает значения для атрибутов **TextView**.
|
|
|
|
|
+
|
|
|
|
|
+Стиль задается с помощью элемента `<style>`. Атрибут **name** указывает на название стиля, через которое потом можно ссылаться на него. Необязательный атрибут **parent** устанавливает для данного стиля родительский стиль, от которого дочерний стиль будет наследовать все свои характеристики.
|
|
|
|
|
+
|
|
|
|
|
+С помощью элементов **item** устанавливаются конкретные свойства виджета, который принимает в качестве значения атрибута **name** имя устанавливаемого свойства.
|
|
|
|
|
+
|
|
|
|
|
+Теперь применим стиль элементов TextView в файле `activity_main.xml`:
|
|
|
|
|
+
|
|
|
|
|
+```xml
|
|
|
|
|
+<TextView
|
|
|
|
|
+ android:id="@+id/textView1"
|
|
|
|
|
+
|
|
|
|
|
+ style="@style/TextViewStyle"
|
|
|
|
|
+ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
|
|
|
+
|
|
|
|
|
+ android:text="Android Lollipop"
|
|
|
|
|
+ app:layout_constraintLeft_toLeftOf="parent"
|
|
|
|
|
+ app:layout_constraintRight_toRightOf="parent"
|
|
|
|
|
+ app:layout_constraintTop_toTopOf="parent"
|
|
|
|
|
+ app:layout_constraintBottom_toTopOf="@+id/textView2"
|
|
|
|
|
+ />
|
|
|
|
|
+```
|
|
|
|
|
+
|
|
|
|
|
+Используя определение `style="@style/TextViewStyle"` текстовое поле связывается с определением стиля. Итоговый результат буде тот же, что и раньше, только кода становится меньше. А если мы захотим поменять какие-то характеристики, то достаточно изменить нужный элемент item в определении стиля.
|
|
|
|
|
+
|
|
|
|
|
+## Темы
|
|
|
|
|
+
|
|
|
|
|
+Кроме применение отдельных стилей к отдельным элементам, мы можем задавать стили для всего приложения или activity в виде тем. Тема предтавляет коллекцию атрибутов, которые применяются в целом ко всему приложению, классу activity или иерархии виджетов.
|
|
|
|
|
+
|
|
|
|
|
+Мы можем сами создать тему. Однако Android уже предоставляет несколько предустановленных тем для стилизации приложения, например, Theme.AppCompat.Light.DarkActionBar и ряд других.
|
|
|
|
|
+
|
|
|
|
|
+По умолчанию приложение уже применяет темы. Так, откроем файл AndroidManifest.xml. В нем мы можем увидеть следующее определение элемента application, представляющего приложение:
|
|
|
|
|
+
|
|
|
|
|
+```xml
|
|
|
|
|
+<application
|
|
|
|
|
+ android:allowBackup="true"
|
|
|
|
|
+ android:icon="@mipmap/ic_launcher"
|
|
|
|
|
+ android:label="@string/app_name"
|
|
|
|
|
+ android:roundIcon="@mipmap/ic_launcher_round"
|
|
|
|
|
+ android:supportsRtl="true"
|
|
|
|
|
+ android:theme="@style/Theme.ViewApp">
|
|
|
|
|
+```
|
|
|
|
|
+
|
|
|
|
|
+Задание темы происходит с помощью атрибута *android:theme*. В данном случае используется ресурс, который называется в моем случае *Theme.ViewApp*. По умолчанию файлы тем определены в папке `res/values`. В частности, здесь можно найти условный каталог themes, в котором по умолчанию есть два элемента: `themes.xml`:
|
|
|
|
|
+
|
|
|
|
|
+Дальше про темы читайте в [оригинальной лекции](https://metanit.com/java/android/6.2.php)
|
|
|
|
|
+
|
|
|
|
|
+# Работа с ресурсами
|
|
|
|
|
+
|
|
|
|
|
+Ресурс в приложении Android представляет собой файл, например, файл разметки интерфейса или некоторое значение, например, простую строку. То есть ресурсы представляют собой и файлы разметки, и отдельные строки, и звуковые файлы, файлы изображений и т.д. Все ресурсы находятся в проекте в каталоге `res`. Для различных типов ресурсов, определенных в проекте, в каталоге res создаются подкаталоги. Поддерживаемые подкаталоги:
|
|
|
|
|
+
|
|
|
|
|
+* **animator**: xml-файлы, определяющие анимацию свойств
|
|
|
|
|
+* **anim**: xml-файлы, определяющие tween-анимацию
|
|
|
|
|
+* **color**: xml-файлы, определяющие список цветов
|
|
|
|
|
+* **drawable**: Графические файлы (.png, .jpg, .gif) или описание фигур в .xml формате
|
|
|
|
|
+* **mipmap**: Графические файлы, используемые для иконок приложения под различные разрешения экранов
|
|
|
|
|
+* **layout**: xml-файлы, определяющие пользовательский интерфейс приложения
|
|
|
|
|
+* **menu**: xml-файлы, определяющие меню приложения
|
|
|
|
|
+* **raw**: различные файлы, которые сохраняются в исходном виде
|
|
|
|
|
+* **values**: xml-файлы, которые содержат различные используемые в приложении значения, например, ресурсы строк
|
|
|
|
|
+* **xml**: Произвольные xml-файлы
|
|
|
|
|
+* **font**: файлы с определениями шрифтом и расширениями .ttf, .otf или .ttc, либо файлы XML, который содержат элемент `<font-family>`
|
|
|
|
|
+
|
|
|
|
|
+## Применение ресурсов
|
|
|
|
|
+
|
|
|
|
|
+Существует два способа доступа к ресурсам: в файле исходного кода и в файле xml.
|
|
|
|
|
+
|
|
|
|
|
+### Ссылка на ресурсы в коде
|
|
|
|
|
+
|
|
|
|
|
+Тип ресурса в данной записи ссылается на одно из пространств (вложенных классов), определенных в файле `R.java`, которые имеют соответствующие им типы в xml:
|
|
|
|
|
+
|
|
|
|
|
+* **R.drawable** (ему соответствует тип в xml drawable)
|
|
|
|
|
+* **R.id** (id)
|
|
|
|
|
+* **R.layout** (layout)
|
|
|
|
|
+* **R.string** (string)
|
|
|
|
|
+* **R.attr** (attr)
|
|
|
|
|
+* **R.plural** (plurals)
|
|
|
|
|
+* **R.array** (string-array)
|
|
|
|
|
+
|
|
|
|
|
+Например, для установки ресурса `activity_main.xml` в качестве графического интерфейса в коде **MainActivity** в методе *onCreate()* есть такая строка:
|
|
|
|
|
+
|
|
|
|
|
+```kt
|
|
|
|
|
+setContentView(R.layout.activity_main)
|
|
|
|
|
+```
|
|
|
|
|
+
|
|
|
|
|
+Через выражение **R.layout.activity_main** мы и ссылаемся на ресурс `activity_main.xml`, где **layout** - тип ресурса, а **activity_main** - имя ресурса.
|
|
|
|
|
+
|
|
|
|
|
+Подобным образом мы можем получать другие ресурсы. Например, в файле `res/values/strings.xml` определен ресурс **app_name**:
|
|
|
|
|
+
|
|
|
|
|
+```xml
|
|
|
|
|
+<resources>
|
|
|
|
|
+ <string name="app_name">ViewApp</string>
|
|
|
|
|
+</resources>
|
|
|
|
|
+```
|
|
|
|
|
+
|
|
|
|
|
+Этот ресурс ссылается на строку. Чтобы получить ссылку на данный ресурс в коде, мы можем использовать выражение **R.string.app_name**.
|
|
|
|
|
+
|
|
|
|
|
+### Доступ в файле xml
|
|
|
|
|
+
|
|
|
|
|
+Нередко возникает необходимость ссылаться на ресурс в файле xml, например, в файле, который определяет визуальный интерфейс, к примеру, в `activity_main.xml`. Ссылки на ресурсы в файлах xml имеют следующую формализованную форму: `@[имя_пакета:]тип_ресурса/имя_ресурса`
|
|
|
|
|
+
|
|
|
|
|
+* имя_пакета представляет имя пакета, в котором ресурс находится (указывать необязательно, если ресурс находится в том же пакете)
|
|
|
|
|
+
|
|
|
|
|
+* тип_ресурса представляет подкласс, определенный в классе R для типа ресурса
|
|
|
|
|
+
|
|
|
|
|
+* имя_ресурса имя файла ресурса без расширения или значение атрибута android:name в XML-элементе (для простых значений).
|
|
|
|
|
+
|
|
|
|
|
+Например, мы хотим вывести в элемент **TextView** строку, которая определена в виде ресурса в файле `strings.xml`:
|
|
|
|
|
+
|
|
|
|
|
+```xml
|
|
|
|
|
+<TextView
|
|
|
|
|
+ android:id="@+id/textView"
|
|
|
|
|
+ android:layout_width="wrap_content"
|
|
|
|
|
+ android:layout_height="wrap_content"
|
|
|
|
|
+ android:text="@string/app_name" />
|
|
|
|
|
+```
|
|
|
|
|
+
|
|
|
|
|
+В данном случае свойство *text* в качестве значения будет получать значение строкового ресурса **app_name**.
|
|
|
|
|
+
|
|
|
|
|
+Подробнее про ресурсы можно посмотреть в [отдельной лекции](https://metanit.com/java/android/2.5.php)
|
|
|
|
|
+
|
|
|
|
|
+# Фигуры в качестве фона для визуальных элементов
|
|
|
|
|
+
|
|
|
|
|
+Часто применяется для круглых кнопок.
|
|
|
|
|
+
|
|
|
|
|
+Вообще для задания цвета фона используется атрибут *android:background*, но в андроиде невозможно задать скругленные углы, чтобы получить круглые кнопки (или прямоугольные со скруглёнными углами).
|
|
|
|
|
+
|
|
|
|
|
+Для реализации такой фичи можно в качестве фона задать *drawable* ресурс: `@drawable/название_файла_ресурса`
|
|
|
|
|
+
|
|
|
|
|
+А в качестве *drawable* ресурса может быть, как мы уже знаем, картинка или фигура.
|
|
|
|
|
+
|
|
|
|
|
+Про фигуры расскажу подробнее:
|
|
|
|
|
+
|
|
|
|
|
+В каталоге `res/drawable` создайте "Drawable Resource File" c корневым элементом **shape** ([фигура](https://developer.android.com/guide/topics/resources/drawable-resource#Shape))
|
|
|
|
|
+
|
|
|
|
|
+В качестве фигуры можно использовать 4 примитива.
|
|
|
|
|
+
|
|
|
|
|
+* **rectangle** - прямоугольник
|
|
|
|
|
+* **oval** - овал
|
|
|
|
|
+* **line** - горизонтальная линия
|
|
|
|
|
+* **ring** - кольцо
|
|
|
|
|
+
|
|
|
|
|
+Для фигуры **ring** в теге **shape** могут быть определены дополнительные атрибуты:
|
|
|
|
|
+
|
|
|
|
|
+* **android:innerRadius** - внутренний радиус
|
|
|
|
|
+*
|
|
|
|
|
+
|
|
|
|
|
+Также в теге **shape** могут быт вложенные теги для настройки фигур:
|
|
|
|
|
+
|
|
|
|
|
+* **stroke** - можно задать толщину и цвет границы фигуры, например овал с тонкой черной границей:
|
|
|
|
|
+
|
|
|
|
|
+ ```xml
|
|
|
|
|
+ <?xml version="1.0" encoding="utf-8"?>
|
|
|
|
|
+ <shape
|
|
|
|
|
+ xmlns:android="http://schemas.android.com/apk/res/android"
|
|
|
|
|
+ android:shape="oval">
|
|
|
|
|
+ <stroke
|
|
|
|
|
+ android:width="1dp"
|
|
|
|
|
+ android:color="#000000">
|
|
|
|
|
+ </stroke>
|
|
|
|
|
+ </shape>
|
|
|
|
|
+ ```
|
|
|
|
|
+
|
|
|
|
|
+ 
|
|
|
|
|
+
|
|
|
|
|
+ ещё у тега **stroke** есть атрибуты *android:dashWidth* - ширина пунктирной линии и *android:dashGap* - промежуток между линиями
|
|
|
|
|
+
|
|
|
|
|
+* **solid** - задаёт цвет заливки фигуры
|
|
|
|
|
+
|
|
|
|
|
+ ```xml
|
|
|
|
|
+ <?xml version="1.0" encoding="utf-8"?>
|
|
|
|
|
+ <shape
|
|
|
|
|
+ xmlns:android="http://schemas.android.com/apk/res/android"
|
|
|
|
|
+ android:shape="rectangle">
|
|
|
|
|
+ <stroke
|
|
|
|
|
+ android:width="2dp"
|
|
|
|
|
+ android:color="#0000FF">
|
|
|
|
|
+ </stroke>
|
|
|
|
|
+ <solid
|
|
|
|
|
+ android:color="#00FF00">
|
|
|
|
|
+ </solid>
|
|
|
|
|
+ </shape>
|
|
|
|
|
+ ```
|
|
|
|
|
+
|
|
|
|
|
+ 
|
|
|
|
|
+
|
|
|
|
|
+* **size** - по умолчанию фигура занимает все доступное ей пространство, но мы можем явно указать её размер с помощью тега size.
|
|
|
|
|
+
|
|
|
|
|
+ ```xml
|
|
|
|
|
+ <?xml version="1.0" encoding="utf-8"?>
|
|
|
|
|
+ <shape
|
|
|
|
|
+ xmlns:android="http://schemas.android.com/apk/res/android"
|
|
|
|
|
+ android:shape="rectangle">
|
|
|
|
|
+ <stroke
|
|
|
|
|
+ android:width="2dp"
|
|
|
|
|
+ android:color="#0000FF">
|
|
|
|
|
+ </stroke>
|
|
|
|
|
+ <size
|
|
|
|
|
+ android:width="100dp"
|
|
|
|
|
+ android:height="100dp">
|
|
|
|
|
+ </size>
|
|
|
|
|
+ </shape>
|
|
|
|
|
+ ```
|
|
|
|
|
+
|
|
|
|
|
+ 
|
|
|
|
|
+
|
|
|
|
|
+* **padding** - позволяет нам задать величину отступа внутри фигуры. Это актуально, например, для **TextView**. Отступ будет учтен при размещении текста.
|
|
|
|
|
+
|
|
|
|
|
+ ```xml
|
|
|
|
|
+ <?xml version="1.0" encoding="utf-8"?>
|
|
|
|
|
+ <shape
|
|
|
|
|
+ xmlns:android="http://schemas.android.com/apk/res/android"
|
|
|
|
|
+ android:shape="rectangle">
|
|
|
|
|
+ <stroke
|
|
|
|
|
+ android:width="2dp"
|
|
|
|
|
+ android:color="#0000FF">
|
|
|
|
|
+ </stroke>
|
|
|
|
|
+ <padding
|
|
|
|
|
+ android:bottom="5dp"
|
|
|
|
|
+ android:top="20dp"
|
|
|
|
|
+ android:left="50dp"
|
|
|
|
|
+ android:right="30dp">
|
|
|
|
|
+ </padding>
|
|
|
|
|
+ </shape>
|
|
|
|
|
+ ```
|
|
|
|
|
+
|
|
|
|
|
+ 
|
|
|
|
|
+
|
|
|
|
|
+* **gradient** - заливка с переходом из одного цвета в другой (можно с переходом через третий цвет). Градиенту можно указать угол и тип (линейный, радиальный).
|
|
|
|
|
+
|
|
|
|
|
+* **corners** - с помощью этого тега мы можем задать скруглённые углы для прямоугольника
|
|
|
|
|
+
|
|
|
|
|
+ ```xml
|
|
|
|
|
+ <?xml version="1.0" encoding="utf-8"?>
|
|
|
|
|
+ <shape
|
|
|
|
|
+ xmlns:android="http://schemas.android.com/apk/res/android"
|
|
|
|
|
+ android:shape="rectangle">
|
|
|
|
|
+ <stroke
|
|
|
|
|
+ android:width="1dp"
|
|
|
|
|
+ android:color="#000000">
|
|
|
|
|
+ </stroke>
|
|
|
|
|
+ <corners
|
|
|
|
|
+ android:radius="40dp">
|
|
|
|
|
+ </corners>
|
|
|
|
|
+ </shape>
|
|
|
|
|
+ ```
|
|
|
|
|
+
|
|
|
|
|
+ 
|
|
|
|
|
+
|
|
|
|
|
+ Причем можно задать свой радиус для каждого угла
|
|
|
|
|
+
|
|
|
|
|
+ ```xml
|
|
|
|
|
+ <?xml version="1.0" encoding="utf-8"?>
|
|
|
|
|
+ <shape
|
|
|
|
|
+ xmlns:android="http://schemas.android.com/apk/res/android"
|
|
|
|
|
+ android:shape="rectangle">
|
|
|
|
|
+ <stroke
|
|
|
|
|
+ android:width="1dp"
|
|
|
|
|
+ android:color="#000000">
|
|
|
|
|
+ </stroke>
|
|
|
|
|
+ <corners
|
|
|
|
|
+ android:topLeftRadius="15dp"
|
|
|
|
|
+ android:topRightRadius="30dp"
|
|
|
|
|
+ android:bottomRightRadius="45dp"
|
|
|
|
|
+ android:bottomLeftRadius="60dp">
|
|
|
|
|
+ </corners>
|
|
|
|
|
+ </shape>
|
|
|
|
|
+ ```
|
|
|
|
|
+
|
|
|
|
|
+ 
|
|
|
|
|
+
|
|
|
|
|
+* **ring** - кольцо. Для кольца мы можем настроить два параметра: размер внутреннего радиуса и толщина кольца. Причем, эти два параметра мы можем указывать в абсолютном и относительном выражении.
|
|
|
|
|
+
|
|
|
|
|
+ ```xml
|
|
|
|
|
+ <?xml version="1.0" encoding="utf-8"?>
|
|
|
|
|
+ <shape
|
|
|
|
|
+ xmlns:android="http://schemas.android.com/apk/res/android"
|
|
|
|
|
+ android:innerRadius="50dp"
|
|
|
|
|
+ android:shape="ring"
|
|
|
|
|
+ android:thickness="40dp"
|
|
|
|
|
+ android:useLevel="false">
|
|
|
|
|
+ <solid
|
|
|
|
|
+ android:color="#FF0000">
|
|
|
|
|
+ </solid>
|
|
|
|
|
+ <size
|
|
|
|
|
+ android:height="200dp"
|
|
|
|
|
+ android:width="200dp">
|
|
|
|
|
+ </size>
|
|
|
|
|
+ </shape>
|
|
|
|
|
+ ```
|
|
|
|
|
+
|
|
|
|
|
+ 
|
|
|
|
|
+
|
|
|
|
|
+ Подробнее про режимы отображения кольца (и других фигур) можно посмотреть [здесь](https://startandroid.ru/ru/uroki/vse-uroki-spiskom/377-urok-162-grafika-drawable-shape-gradient.html)
|
|
|
|
|
+
|
|
|
|
|
+# Обработка событий (клик по кнопке)
|
|
|
|
|
+
|
|
|
|
|
+Для кнопок (тег **Button**) можно задать обработчик клика, для этого в разметке добавьте атрибут *android:onClick* и задайте имя функции обработчика:
|
|
|
|
|
+
|
|
|
|
|
+```xml
|
|
|
|
|
+<Button
|
|
|
|
|
+ ...
|
|
|
|
|
+ android:onClick="onOperationClick"/>
|
|
|
|
|
+```
|
|
|
|
|
+
|
|
|
|
|
+Чтобы не писать вручную эту функцию можно нажать на её названии клавиши `Alt+Enter` и выбрать действие "Create onOperationClick(view) in MainActivity"
|
|
|
|
|
+
|
|
|
|
|
+Один и тот же обработчик можно назначить нескольким кнопкам (в калькуляторе можно сделать всего два обработчика: один для числовых кнопок, а второй для функциональных)
|
|
|
|
|
+
|
|
|
|
|
+В коде обработчика мы должны либо привести параметр *view* к типу **Button**:
|
|
|
|
|
+
|
|
|
|
|
+```kt
|
|
|
|
|
+fun onOperatorClick(view: View) {
|
|
|
|
|
+ when((view as Button).text){
|
|
|
|
|
+ "*" -> {
|
|
|
|
|
+ // реализовать операцию умножения
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+}
|
|
|
|
|
+```
|
|
|
|
|
+
|
|
|
|
|
+Либо в разметке добавить кнопкам атрибут *android:tag* и в коде анализировать его содержимое (ему приведение типов не нужно, т.к. он объявлен в классе **View**)
|
|
|
|
|
+
|
|
|
|
|
+# Задание
|
|
|
|
|
+
|
|
|
|
|
+* используя стили раскрасить функциональные и цифровые кнопки калькулятора
|
|
|
|
|
+* сделать кнопки со скругленными углами используя фигуры
|
|
|
|
|
+* создайте обработчики нажатия кнопок и реализуйте работу калькулятора
|
|
|
|
|
+
|