Scratch – это интуитивно понятная визуальная среда программирования, разработанная для обучения детей и новичков основам кодирования. Хотя Scratch изначально предназначен для создания 2D-игр и анимации, с помощью некоторых хитростей и математических концепций можно имитировать 3D-пространство и создавать увлекательные 3D-игры. В этой статье мы подробно рассмотрим, как это сделать.
Оглавление
Что такое Scratch и почему он подходит для начала?
Scratch использует подход «перетащи и отпусти» блоков кода, что делает процесс программирования похожим на сбор конструктора LEGO. Это позволяет сосредоточиться на логике и концепциях без необходимости изучать сложный синтаксис. Для создания 3D-эффектов в Scratch мы будем использовать принципы перспективы и масштабирования, чтобы имитировать глубину на двухмерном экране.
Основные принципы имитации 3D в Scratch
Имитация 3D в Scratch основываеться на нескольких ключевых идеях:
- Перспектива: Объекты, находящиеся дальше, кажутся меньше. Мы будем использовать изменение размера спрайтов для создания этого эффекта.
- Глубина (Z-координата): Мы будем использовать переменную для каждого спрайта, чтобы имитировать его положение по оси Z. Чем больше значение Z, тем дальше объект.
- Порядок слоев: Объекты, которые находятся ближе к «камере», должны отображаться поверх объектов, которые находятся дальше. Это достигается с помощью блока «перейти на передний/задний слой».
- Движение: Движение «камеры» или игрока будет влиять на кажущееся положение всех объектов в 3D-пространстве.
Шаг 1: Подготовка сцены и основных спрайтов
1.1 Создание базовой сцены
Для начала, давайте создадим простую сцену. Вы можете выбрать любой фон, но для демонстрации 3D-эффекта лучше использовать однотонный фон или фон с горизонтальными линиями, чтобы было легче ориентироваться в «глубине».
1.2 Создание спрайта «игрока» (или «камеры»)
Нам нужен спрайт, который будет представлять игрока или камеру, управляющую видом. Это может быть простой квадрат или любая другая форма. На самом деле, этот спрайт может быть невидимым, так как он будет служить только для отслеживания позиции в 3D-пространстве.
Создайте переменные для этого спрайта, например:
PlayerX: Позиция игрока по оси X.PlayerY: Позиция игрока по оси Y.PlayerZ: Позиция игрока по оси Z (глубина).
При запуске игры установите эти переменные в начальные значения (например, PlayerX = 0, PlayerY = 0, PlayerZ = 0).
1.3 Создание спрайтов «3D-объектов»
Теперь создадим спрайты, которые будут представлять объекты в нашем 3D-мире. Допустим, это будут несколько кубов.
Для каждого «3D-объекта» нам понадобятся переменные, чтобы хранить его фиксированное положение в 3D-мире:
ObjectX: Исходная позиция объекта по X.ObjectY: Исходная позиция объекта по Y.ObjectZ: Исходная позиция объекта по Z (глубина).
Важно: Эти переменные должны быть «Только для этого спрайта», если вы хотите иметь несколько разных объектов. Если все объекты одинаковые (клоны), то можно использовать общие переменные.
Шаг 2: Реализация 3D-проекции
Это самый важный шаг. Мы должны рассчитать, как объекты должны отображаться на 2D-экране, исходя из их 3D-координат и положения «камеры».
2.1 Переменные для расчета проекции
В каждом спрайте «3D-объекта» нам понадобятся временные переменные для хранения расчетов:
RenderX: Рассчитанная позиция на экране по X.RenderY: Рассчитанная позиция на экране по Y.RenderSize: Рассчитанный размер спрайта.
2.2 Алгоритм расчета проекции
В цикле «всегда» каждого спрайта «3D-объекта» выполните следующие действия:
2.2.1 Относительные координаты
Сначала вычислим относительное положение объекта относительно игрока/камеры. То есть, насколько далеко объект находится от игрока по каждой из осей.
когда нажат флажок
всегда
установить [RelX v] в ((ObjectX) ⎯ (PlayerX))
установить [RelY v] в ((ObjectY) ‒ (PlayerY))
установить [RelZ v] в ((ObjectZ) ‒ (PlayerZ))
Здесь RelX, RelY, RelZ – это временные переменные «Только для этого спрайта».
2.2.2 Расчет масштаба (эффект перспективы)
Объекты, которые находятся дальше (больше RelZ), должны быть меньше. Мы используем простую формулу для масштаба. Чем больше делитель (RelZ), тем меньше размер.
Важно: Избегайте деления на ноль или отрицательные значения RelZ, если объект находится «за» камерой. Можно добавить проверку: если RelZ меньше определенного минимального значения (например, 1), присвойте ему это минимальное значение, чтобы избежать ошибок и сделать объекты слишком большими.
если <(RelZ) < [1]> тогда
установить [RenderScale v] в (100) // или другое максимальное значение
иначе
установить [RenderScale v] в ((500) / (RelZ)) // 500 ‒ это "расстояние фокуса", настройте его
конец
Значение 500 (или любое другое) определяет «fov» (field of view) или угол обзора. Чем больше это значение, тем меньше искажения перспективы.
2.2.3 Расчет экранных координат (RenderX, RenderY)
Теперь, используя относительные координаты и масштаб, рассчитаем, где спрайт должен быть на экране.
установить [RenderX v] в ((RelX) * (RenderScale) / (100))
установить [RenderY v] в ((RelY) * (RenderScale) / (100))
Мы делим на 100, потому что RenderScale обычно выражается в процентах. Теперь эти RenderX и RenderY являются смещениями от центра экрана. Scratch использует диапазон от -240 до 240 по X и от -180 до 180 по Y. Поэтому нам нужно добавить смещение:
перейти в x: ((RenderX) + [0]) y: ((RenderY) + [0])
установить размер в ((RenderScale)) %
Значения 0 в скобках после RenderX и RenderY – это смещение центра экрана. Если ваш спрайт игрока/камеры находится в центре, то это будут нули.
2.2.4 Управление слоями
Объекты, которые находятся дальше (больше RelZ), должны быть на заднем плане. Объекты, которые ближе, на переднем. Это можно сделать, отправляя спрайты на слои в зависимости от их RelZ.
перейти на слой (RelZ)
Scratch автоматически сортирует спрайты по их числовому значению слоя (переменной). Чем больше значение, тем дальше спрайт.
Важно: Для правильной работы слоев, каждый спрайт «3D-объекта» должен иметь свою собственную переменную RelZ (или другую переменную, отвечающую за глубину), «Только для этого спрайта», и затем использовать эту переменную в блоке «перейти на слой [переменная]».
Шаг 3: Добавление движения
3.1 Управление игроком/камерой
Теперь давайте добавим управление для «камеры» (спрайта игрока). Используйте стрелки или клавиши WASD для изменения PlayerX, PlayerY и PlayerZ.
когда клавиша [стрелка вверх v] нажата
изменить [PlayerZ v] на (10) // Движение вперед
когда клавиша [стрелка вниз v] нажата
изменить [PlayerZ v] на (-10) // Движение назад
когда клавиша [стрелка вправо v] нажата
изменить [PlayerX v] на (10) // Движение вправо
когда клавиша [стрелка влево v] нажата
изменить [PlayerX v] на (-10) // Движение влево
// Для движения вверх/вниз
когда клавиша [W v] нажата
изменить [PlayerY v] на (10) // Движение вверх
когда клавиша [S v] нажата
изменить [PlayerY v] на (-10) // Движение вниз
Когда вы будете двигать игрока, все «3D-объекты» будут пересчитывать свои положения и размеры, создавая иллюзию движения в 3D-пространстве.
Шаг 4: Расширенные возможности (по желанию)
4.1 Вращение
Вращение объектов или камеры значительно сложнее, так как требует применения матриц вращения или тригонометрических функций (sin/cos). Если вы хотите добавить вращение, вам придется вращать относительные координаты RelX и RelY вокруг оси, прежде чем применять проекцию.
4.2 Пол
Создание пола в 3D-мире Scratch может быть выполнено путем создания множества маленьких спрайтов, имитирующих плитки, и применения к ним тех же принципов 3D-проекции.
4.3 Коллизии (столкновения)
Для обнаружения столкновений вам нужно будет проверять, находятся ли 3D-координаты игрока и объекта близко друг к другу. Учитывайте их размеры в 3D-пространстве.
4.4 «Стена» из клонов
Для создания повторяющихся объектов (например, стен или дороги) вы можете использовать клоны. Создайте один спрайт «3D-объекта» и сделайте множество его клонов, каждый с уникальными значениями ObjectX, ObjectY, ObjectZ.
Советы и рекомендации
- Начинайте с простого: Сначала сделайте один движущийся объект и камеру, а затем добавляйте больше объектов и функций.
- Тестируйте часто: Изменяйте значения, смотрите, как это влияет на проекцию, и учитесь на практике.
- Используйте функции: Если у вас есть повторяющийся код (например, расчет проекции), создайте «Мой блок», чтобы сделать код чище.
- Ограничьте движение: Добавьте условия, чтобы игрок не мог уйти слишком далеко или пройти сквозь объекты.
- Оптимизация: Для сложных сцен с большим количеством спрайтов производительность Scratch может снизиться. Постарайтесь минимизировать количество вычислений в каждом кадре.
Создание 3D-игры в Scratch – это увлекательный проект, который демонстрирует, как с помощью базовых математических принципов можно имитировать сложные визуальные эффекты. Это отличный способ углубить понимание перспективы, координат и алгоритмического мышления. Удачи в ваших экспериментах с 3D в Scratch!
