Поля UnityEvent
Часть раздела Архитектура игр в Unity путешествия по Unity на Coddy. Урок 14 из 64.
Поле On Click () у кнопки — это поле UnityEvent, и в собственных скриптах у тебя тоже может быть такое поле. Публичное поле UnityEvent отображается в Inspector в виде такого же списка, а скрипт вызывает его с помощью Invoke(), не зная, что с ним связано. Этот обратный отсчёт отсчитывает секунды:
using UnityEngine;
using UnityEngine.Events;
public class Countdown : MonoBehaviour
{
public int seconds = 3;
public UnityEvent<int> onTick;
public UnityEvent onFinished;
void Start()
{
InvokeRepeating("Tick", 1f, 1f);
}
void Tick()
{
seconds--;
onTick.Invoke(seconds);
if (seconds == 0)
{
CancelInvoke("Tick");
onFinished.Invoke();
}
}
}В Inspector в разделе On Finished () можно добавлять строки, как у кнопки: в одной строке запускается ракета, в другой открываются ворота. На другом уровне тот же Countdown используется с другими строками, и никому не приходится писать новый скрипт. UnityEvent<int> передаёт значение. В раскрывающемся списке метод, принимающий int, находится в разделе Dynamic int, а строка получает значение, переданное в Invoke, — в данном случае количество оставшихся секунд. Тот же метод в разделе Static Parameters получает число, введённое непосредственно в строку, а также можно связать методы без параметров.
Unity создаёт поле UnityEvent при загрузке скрипта, поэтому onTick никогда не равно null, и ему не нужен ?.; код также может добавлять обработчики с помощью onTick.AddListener(ShowSeconds). Выбирай UnityEvent, если реакция различается для разных объектов и настраивается в Inspector тобой или дизайнером, который никогда не открывает скрипт. Выбирай событие C#, если обработчики задаются в коде: компилятор проверяет имена методов, поэтому переименование приводит к ошибке сборки, а не оставляет незаметную строку <Missing>, и событие C# никогда не отображается в Inspector.
Задание
ЛегкоДобавь к FinishLine события, к которым подключены строки сцены.
- Добавь
using UnityEngine.Events;,public UnityEvent<int> onLap;,public UnityEvent onRaceOver;и приватное целое число для количества пройденных кругов. - В
OnTriggerEnter, когда уotherтегPlayer, засчитай круг и вызовиonLap.Invoke, передав количество пройденных кругов. - Когда будет достигнуто значение
laps, вызовиonRaceOver.Invoke(); после этого пересечение финишной линии ничего не делает.
Нажми «Играть» и проедь три круга. Затем нажми «Проверить».
Попробуйте сами
using UnityEngine;
public class FinishLine : MonoBehaviour
{
public int laps = 3;
void OnTriggerEnter(Collider other)
{
// машина пересекла финишную черту: пройден ещё один круг
}
}
Все уроки раздела Архитектура игр в Unity
1Компоненты, а не иерархии
Небольшие компонентыБазовый скрипт врагаАбстрактные компонентыКомпоненты работают вместеПовторение: модульная турельПовторение: спаренная пушка4Сериализованные данные
Сериализуемые классыСписки в инспектореПеречисления в инспектореПовторение: таблица добычиПовторение: определяем добычу2Интерфейсы в Unity
IDamageableИнтерфейсы и TryGetComponentGetComponentsПовторение: клавиша взаимодействияПовторение: ближайший в пределах досягаемости5ScriptableObjects
Ресурсы данныхХарактеристики оружияОбщие настройкиСохраняем ветерВолны как данныеПовторение: база предметовПовторение: покупка в магазинеПотренируйтесь самостоятельно: Песочница Unity