[Из песочницы] Краткий обзор нового Unity UI с примерами организации интерфейса

3e21e64d9f6947329fe76c0b5683a7cc.pngПожалуй, для многих новость о выходе новой системы Unity UI (далее просто UI) не показалась чем-то значимым. Как минимум — по причине её сырости, как максимум — из-за существования NGUI. Я поначалу не стал исключением, но открытие исходного кода UI системы (1) под либеральной лицензией MIT/X11, а так же энтузиазм разработчиков Unity Technologies заставили меня изменить мнение.

На мой взгляд, новый UI принесет нам довольно много плюсов:

Вполне достойный инструмент из коробки; Возможность более глубоко понимать работу UI благодаря наличию исходников; Общепринятый механизм внесения изменений в исходный код UI — fork/pull request; Здоровая конкуренция между разными системами UI в конечном итоге принесет свои плоды в виде более качественных и удобных инструментов для Unity, а возможно и демпинг цен; Тесное взаимодействие команды разработки UI и ядра Unity уже сейчас приносят плоды в виде оптимизаций производительности, да и в будущем надеюсь они будут идти нога в ногу. Руководствуясь этими мыслями было решено разрабатывать интерфейс игры, используя новый UI. Как показало время, решение было оправдано, игра увидела свет и благополучно функционирует на Android девайсах. К слову сказать, финальное решение было после анонса патча Unity 4.6.1 (2), который включал тонну фиксов и импрувов UI.Давайте перейдем к конкретике. Начну с общего представления, сформировавшегося после раскуривания скудной документации, просмотра видео-уроков и раскопки исходного кода.

Концепция UIПодход к организации интерфейса переработан впринципе. То есть если вы ранее работали с GUI, в новом UI вы почти не найдете ничего похожего. И наоборот — если вы работали с NGUI, то найдете очень много общего. В целом ее можно назвать типичной для сред с инструментами визуальной разработки.В основе понимания новой концепции лежат три компонента: Canvas, Rect Transform и Event Trigger.

Canvas — является контейнером для всех элементов UI и определяет режим рендера. Таких контейнеров на сцене может быть более одного (3).

Rect Transform — этот компонент позволяет задать положение и размер игрового объекта, используя удобные визуальные контролы. Он вводит понятия ширины и высоты, а не только масштаб (4).

Unity Event — доработанная система событий, а конкретно компонент Event → Event Trigger который включает компоненты визуального управления вызовом событий (5).

По мере знакомства с UI я создавал для себя возможные варианты использования. Давайте на них и разберем эту всю кухню. В конце статьи вы можете найти демо-проект, на который я буду ссылаться в тексте. К сожалению, этим примерам далеко до готовых рецептов, так как они не достаточно проработаны, плюс заточены под 2D игры, хотя местами вполне подойдут и для 3D.

Пример #1 Цели:1. Тайловый фон;2. Фиксированное положение контролов в независимости от разрешения и соотнешения сторон экрана;3. Контролы должны быть пропорциональны размеру экрана.Вариант решения:1. Добавляем на сцену Canvas и выбираем режим рендера Screen space — Overlay, этот режим будет автоматически подстраивать его размер под размер камеры;2. Добавим тайловый фон, для этого нам всего-то и нужно, что добавить нашему Canvas новый UI компонент — Image, выбрать нужный спрайт и изменить поле Image Type в значение Tiled;3. Выбираем в окне Game удобное нам разрешение, например, 480×800 и добавляем на наш Canvas — контейнер необходимые контролы, выставляем им нужные позиции;4. Далее идет новая магия UI, под названием якоря! Название говорит само за себя, они позволяют закреплять ряд характеристик игрового объекта, используя компонент Rect Transform. Изменить их можно в окне редактирования сцены, включив новый режим, либо в инспекторе. Обратите внимание, что иконка в инспекторе компонента Rect Transform — кликабельна и открывает окно выбора предустановленных положений и вариантов поведения, а если зажать кнопку Shift, то еще и положение точки опоры;5. Довершает картину один из компонентов Canvas, который добавляется к нему по умолчанию Layout → Canvas Scaler, а именно один из его режимов — Scale With Screen Size. Этот режим позволяет задать Reference Resolution, в нашем случае это будет 480×800.

eb5506dc54d849048964a45366595ebd.png

Пример #2 Цели:1. Ориентация строго портретная;2. Универсальный для всех соотношений сторон фон, который всегда отображается на весь экран, а если необходимо обрезается только снизу;3. Фиксированное положение контролов в независимости от разрешения и соотнешения сторон экрана;4. Контролы должны быть пропорциональны размеру экрана.3a747e1806934d61a61960fac454e358.jpg

Вариант решения:1. Добавляем на наш Canvas — контейнер объект UI → Image, выбираем нужный спрайт и тип изображения Simple;2. Вся магия сводится к расположению якорей и точки опоры таким образом, что бы они лежили по центру верхнего ребра Canvas;3. В компонент Canvas Scaler нужно выставить значение Match равное 0.

Пример #3 Цели:1. Ориентация строго портретная;2. Тайловый фон, который не скейлится;3. Фиксированное по размеру игровое поле, например 400×400;4. Фиксированное положение контролов в независимости от разрешения и соотнешения сторон экрана;5. Контролы должны быть пропорциональны размеру экрана.3d2c8132fea24363a6d42a57aa050807.jpg

Вариант решения:1. Можно, конечно, реализовать фон как Sky Box или игровым объектом типа Quad с затайленой текстурой и размерами заведомо больше экрана. Но мы пойдем UI-ным путем и создадим Canvas, аналогичный примеру #1, только выставим тип рендера Screen Space — Camera и пропишем нашу главную камеру в поле Render Camera;2. Теперь создадим еще один Canvas с типом рендера World Space, пропишем камеру и поставим значение Order in Layer равное 1, что бы этот слой рисовался поверх предыдущего Canvas у которого это значение равно 0;3. Советую вам при рендере World Space _заранее_ ставить значение масштаба Canvas таким образом, что бы у вас не было проблем с размером шрифтов;4. Контролы раставляем уже известным нам способом.

Пример #4 Цели:1. Создать скроллер;2. Контент не должен быть виден за пределаеми скролера;3. Он должен скейлиться вместе с экраном и липнуть к нижнему краю.21a7ecda4be94850865b81f28ed3e57c.jpg

Вариант решения:1. Нам необходим игровой объект которому мы добавим компонент UI → Scroll Rect, самое важное поле которого — Content, задав которое мы указываем контейнер содержащий игровые объекты (например надцать изображений игровых уровней размером 100×100, которые заведомо не влезают в размер экрана);2. Так же нам будет полезен компонент UI → Mask (обратите внимание, что также необходимо вставлять пустой компонент Image), который клипнет контент выходящий за пределы игрового объекта, на который он добавлен;3. Можно так же создать объект UI → Scrollbar и привязать его к нашему Scroll Rect

Пример #5 Несколько мелкий приятностей:1. Как расширить список обрабатываемых событий, например обрабатывать события StartDrag, EndDrag и т.д. используя компонент Event Trigger;2. Применение элемента UI → Toggle для реализации наград в виде Звезд с удобным скриптингом вида isOn = true;3. Простейший вариант Попап окошек с использованием компонента Canvas Group и старого доброго аниматора без единой строчки кода.Конечно, эти примеры покрывают лишь малую часть возможных задач и реализаций, но я надеюсь, они помогут вам выбрать удобное направление для поисков решения или, как минимум, песочницу, в которой можно попробовать разные варианты.

Файл проекта с примерами www.dropbox.com/s/0d48cf04lekpfoe/DemoProjectUIv4_6_1.unitypackage? dl=0Сноски 1. bitbucket.org/Unity-Technologies/ui/overview2. unity3d.com/unity/whats-new/unity-4.6.13. docs.unity3d.com/Manual/class-Canvas.html4. docs.unity3d.com/Manual/class-RectTransform.html5. docs.unity3d.com/Manual/SupportedEvents.html

© Habrahabr.ru