Код: https://github.com/lucamug/elm-playground-3d
Демо: https://elm-playground-3d.netlify.com/
Пример: https: //elmjapan.org/
Вяз-площадка-3д - экспериментальная библиотека, построенная на базе Вяза-детской площадки. Итак, позвольте мне сначала представить вам эту библиотеку ...
вяз-детская площадка
Вяз-площадка - отличная библиотека для создания картинок, анимации и игр с Вязом. В то же время он прост в использовании, поэтому новичок может изучить основы программирования, а также мощный для создания сложных приложений.
Он является оболочкой The Elm Architecture, предоставляя простые директивы для рисования объектов на экране (квадрат, круг, треугольник и т. Д.) И их преобразования (перемещения, поворота, масштабирования).
Она имеет
- Три уровня сложности, которым вы можете следовать в процессе обучения: картинка, анимация, игра.
- Информация об экране, мыши и клавиатуре для создания интерактивного приложения
- Крючки для перемещения объекта, такие как вращение, волна, зигзаг
Библиотека поддерживает двухмерные формы, но мне нужно было создать простую трехмерную композицию, и я хочу сохранить все функции, которые предоставляет elm-Playground, сохраняя тот же уровень простоты.
Поехали в 3D!
Итак, я построил простой трехмерный слой над детской площадкой из вяза. Это сравнение использования 2D и 3D версий:
2D
main =
picture
[ square purple 500
|> fade 0.8
|> move 200 0
]
3D
main =
picture
[ cube darkPurple purple lightPurple 500
|> fade3d 0.8
|> move3d 200 0 0
|> shape3dto2d camera1
]
Как видите, эти два процесса следуют одной и той же логике. Тонкие различия заключаются в следующем:
- По возможности функции в 2D имеют аналоги в 3D с суффиксом «3d» в названии. Суффикс позволяет импортировать все из 3D-библиотеки, не создавая конфликтов с функциями из 2D-библиотеки.
- Для функций в 3D могут потребоваться дополнительные аргументы, такие как
move3d
, для которых требуется дополнительная координата Z. - Трехмерные формы необходимо преобразовать в двухмерные с помощью
shape3dto2d
перед их обработкой с помощью функций 2D (например,picture
).
Волшебство творится функцией shape3dto2d
. То, что он делает, называется 3D-проекцией. Я использовал перспективную проекцию с помощью ianmackenzie / elm-3d-camera. Для преобразований в трехмерном пространстве я использовал ianmackenzie / elm-geometry.
Это расширенная библиотека для 3D-преобразований, и вам обязательно стоит взглянуть на них, если вы хотите заняться чем-то серьезным с 3D-рендерингом. Для этой библиотеки я их упростил, заменив несколько аргументов значениями по умолчанию.
Ниже приведены три примера, отсортированные по сложности (picture
, animation
, game
).
Пример 1 - Изображение
Демо: https://elm-playground-3d.netlify.com/example1-picture.html
В этом примере собраны вместе двухмерные и трехмерные элементы.
main =
picture
[ group3d
[ cube darkPurple purple lightPurple 600
|> fade3d 0.5
, words3d darkPurple "3D"
|> scale3d 5
]
|> shape3dto2d camera1
|> moveLeft 180
, group
[ square darkPurple 300
|> fade 0.5
, words darkPurple "2D"
|> scale 5
]
|> moveRight 180
]
Пример 2 - Анимация
Демо: https://elm-playground-3d.netlify.com/example2-animation.html
Здесь мы добавляем действие
main = animation view
view time = [ group3d [ cube lightPurple purple darkPurple 600 |> fade3d 0.5 , words3d darkPurple "3D" |> scale3d 5 |> move3d 300 300 0 ] |> rotate3d 0 0 (spin 3 time) |> shape3dto2d camera1 |> rotate (spin 3 time) |> moveLeft 180 , group [ square darkPurple 300 |> fade 0.5 , words darkPurple "2D" |> scale 5 ] |> rotate (spin 3 time) |> moveRight 180 ]
Пример 3 - Игра
Демо: https://elm-playground-3d.netlify.com/example3-game.html
Этот другой пример добавляет взаимодействия:
- Горизонтальные движения мыши вращают все объекты на экране. Это получается добавлением координаты мыши к преобразованию
rotate3d
:
rotate3d 0 0 (computer.mouse.x / 3)
- Маленький кубик управляется по горизонтали с помощью клавиш со стрелками и по вертикали с помощью мыши, это достигается с помощью
move3d (500 - x * 30) (500 - y * 30) (500 + computer.mouse.y * 2)
Откуда приходят x
и y
update : Computer -> Memory -> Memory
update computer ( x, y ) =
let
( dx, dy ) =
toXY computer.keyboard
in
( x + dx, y + dy )
как объяснено в документации на вязаную площадку
- Дополнительные модификации, основанные на нажатой кнопке. Чтобы определить, нажата ли кнопка:
if Set.member "s" computer.keyboard.keys then
...
Толкаем конверт
Из этих простых блоков можно построить довольно сложную композицию, например плавучий город на https://elmjapan.org/:
В этом случае мы не только анимируем объект, но и постоянно анимируем камеру, создавая эффект плавания.
Со временем я опубликую исходный код этого веб-сайта, следите за обновлениями!
Выводы
Эта библиотека все еще находится на ранней стадии, и в ней отсутствуют многие функции, которые должна поддерживать «серьезная» 3D-библиотека.
Как новичок в области 3D-рендеринга, это было очень весело, а также оказалось проще, чем я ожидал.
Для более серьезных 3D-вещей в Elm, взгляните на
- Янмакензи / вяз-3d-сцена
- Вяз-исследования / webgl
- Unsoundscapes / кубик
- W0rm / elm-Physics
- 3D векторные анимации
- Обсуждение:« Движок 3D-рендеринга для Elm Иэна Маккензи»
- Беседа:« Борьба с законом физики с помощью вяз Андрея Кузьмина»
- Разговор:« Развлекаемся в графическом программировании Андрея Кузьмина»
- Беседа:« Отрисовка текста с помощью WebGL Андрея Кузьмина»