Хитроумные способы рисовать звездное поле

Я работаю над игрой, и у меня есть довольно интересная проблема: умные способы рисовать звездные поля.

Это 2D-игра, поэтому действие может прокручиваться в направлениях X и Y. Кроме того, мы можем настроить масштаб, чтобы показать более или менее область воспроизведения. Мне также хотелось бы, чтобы звездное поле имело поддельный параллакс, чтобы произвести впечатление глубины.

Сейчас я делаю это традиционным способом, имея большой массив звезд, каждый из которых помечен "глубинным" фактором. Чтобы рисовать, я переводил каждую звезду в соответствии с положением камеры, умноженным на "глубину", поэтому некоторые звезды двигаются много, а некоторые немного двигаются. Все это прекрасно работает, но, конечно, поскольку у меня есть конечное число звезд в моем массиве, у меня возникают проблемы, когда камера слишком далеко перемещается или мы слишком сильно уменьшаем масштаб. Это все будет работать, но связано с большим количеством кода и особых случаев.

Это оскорбляет мое чувство элегантности. Там был лучший способ добиться этого.

Я рассмотрел процесс создания моих звезд, что позволяет мне иметь неограниченное число: например. используя фиксированное семя и PRNG для определения координат. Мне нужно было бы разделить небо на плитки, генерировать семя, хэшируя координаты плитки, а затем нарисуйте, скажем, 100 звезд на плитку. Это позволяет мне неограниченно расширять свое звездное поле во всех направлениях, в то время как все еще нужно учитывать только видимые плитки, но это не работает с коэффициентом "глубина", так как это позволяет звездам отклониться от своей плитки. Я мог бы просто использовать несколько многоуровневых звездных полей без параллакса, используя этот алгоритм, но это меня поражает.

И, конечно, мне нужно делать все это в каждом кадре, поэтому он должен быть быстрым.

Что вы все считаете?

Ответы

Ответ 1

Есть несколько слоев звезд.

Для каждого слоя используйте генератор случайных чисел с посевом (или просто массив), чтобы сгенерировать количество пробелов между звездой и следующей (пуассоновское распределение, если вы хотите быть разборчивым). Вы хотите, чтобы звезды были довольно разреженными, поэтому пустое пространство часто будет больше, чем целая строка. Очевидно, что задние слои будут более плотными, чем передние.

Используйте это, чтобы дать себе несколько фрагментов, каждый из которых (скажем) на двух экранах. Прокрутите звездочку, отслеживая, где эта "первая" звезда для каждого слоя.

Игрок не заметит плитки, потому что вы прокручиваете плитки с разной скоростью для каждого слоя, особенно если вы используете несколько слоев, которые кажутся довольно разреженными.

Ответ 2

Как звезды в фоновом режиме не перемещаются так быстро, как на переднем плане, вы можете сделать многослойные плитки для фона и заменить их однослойными, когда у вас есть время для этого. О, и как насчет повторяющихся узоров в фоновых слоях? Это могло бы позволить вам воссоздать все фоновые фрагменты - вы все равно можете сдвинуть их по высоте и наложить несколько с произвольными смещениями или так, чтобы они выглядели случайными.

Ответ 3

Есть ли что-то не так, если обернуть звездообразное поле вокруг X и Y? Из-за вашей глубины расстояние от поверхности должно зависеть от глубины, но вы можете это сделать. Каждая записанная звезда в точке (x, y, depth) должна появляться во всех точках

[x + j * S * глубина, y + k * S * глубина]

для всех целых чисел j и k. S является параметром wraparound. Если S равно 1, то обрыв происходит немедленно, и все звезды всегда отображаются где-то. Если S выше, то обрыв не происходит сразу, а некоторые звезды отображаются с экрана. Вероятно, вы захотите S достаточно большой, чтобы не было повторений при максимальном уменьшении.

Ответ 4

Каждый кадр отображает звезды на одном растровом/слое. Они - только точки, и поэтому они будут быстрее, чем использование любого алгоритма с несколькими слоями.

Теперь вам нужна бесконечная 2D-сетка 3D-боксов, заполненная конечным числом звезд. Для каждого окна вы можете определить индивидуальное значение RANDOM_SEED, используя его координаты сетки. Звезды в каждой коробке могут быть созданы на лету.

Не забудьте корректировать перспективу при масштабировании: каждый 3D-бокс имеет прямоугольник (передняя сторона) и прямоугольник. Вы увидите больше звезд соседних ящиков, каждый раз, когда прямоугольник или прямоугольник сжимаются в вашем представлении.

Ваши дальние прямоугольники никогда не должны быть меньше половины ширины прямоугольников, иначе это может быть проблематично: вам, возможно, придется сканировать огромные списки звезд, где большинство из них находятся вне пределов. Вы можете реализовать звезды за дальними прямоугольниками через дополнительные 2D-сетки 3D-боксов с другими размерами и глубинами.

Ответ 5

Почему бы не объединить координаты 3D-полей звездного поля с образованием семени случайных чисел? Используйте глобальную "настройку", если вы хотите создать разные юниверсы. Таким образом, вам не нужно отслеживать поля, которые вы не видите, поскольку содержимое фиксируется по их местоположению.