Новая система триггеров | День 51 🌐
Сегодня взялся за переработку системы триггеров. Всё оказалось сложнее, но не в техническом плане, а концептуальном... Похоже, нам всё-таки понадобится документация страниц на 15, чтобы объяснить все нюансы 💀
Листая прошлые посты, понял, что толком не объяснял, как всё работало раньше.
Было: Пользователь вручную запускал скрипт командой, тот начинал слушать события и жил до тех пор, пока триггеры не завершатся.
Тут всплыли две проблемы:
1) Автозапуск. Нельзя сделать так, чтобы скрипт стартовал сам, когда игрок заходит на карту. Приходилось бы делать костыли: запускать вручную и создавать отдельный скрипт для каждого игрока на сервере, даже если это условный нпс-торговец на спавне.
2) Одноразовость. Триггеры умирали после срабатывания. Хотите запретить ломать блоки? Старая система запретит сломать один блок, а дальше скрипт завершится. Если же делать их многоразовыми, то действия разных игроков начнут перезаписывать друг друга, ломая логику.
В связи с этим я решил разделить триггеры на локальные и глобальные:
1) Глобальные - это точки входа (например, "Игрок залогинился на сервер"). Они срабатывают всегда и создают отдельный экземпляр скрипта (контейнер) со своими личными переменными для каждого игрока.
2) Локальные - живут внутри этого экземпляра. Например, "Ломание блока". Они могут срабатывать многократно внутри одной сессии игрока, не мешая другим. Плюс, у них есть доступ к общим переменным контекста.
Но тут есть несколько сложных моментов:
- Когда завершать скрипт? Если локальные триггеры срабатывают бесконечно, скрипт будет висеть в памяти вечно.
Варианты решения: Завершать после выполнения глобального триггера? Добавить режим для одноразового/многоразового запуска триггера? Или дать пользователю блок "Завершить скрипт" (который 99% людей забудут поставить и положат сервер 50-ю копиями скрипта)?
- Конкурентность. Что делать, если игрок сломал блок, скрипт начал задержку на 15 секунд, а игрок тут же сломал второй блок?
Варианты решения: Отменять первое действие? Игнорировать второе, пока первое не доработает? Или запускать асинхронно? (Привет, гонка данных и баги в переменных).
В общем, идеального решения я не вижу. Каждый сценарий может потребовать своего подхода. Поэтому я решил не ограничивать Вас и реализовать все варианты с возможностью переключения 😱. Да, это дольше кодить и интерфейс станет чуть сложнее, зато система будет более гибкой. 🙃
Post #117
746
- 🤯 6
- ❤ 4