Синусоидальный 2D трэк

Форум для самых маленьких, а так же тех, кому недосуг читать справку самостоятельно.

Синусоидальный 2D трэк

Сообщение nilex7 31 май 2016, 14:42

Всем привет,

Создаю 2D дорогу, использую LineRender для визуализации и EdgeCollider2D для физической составляющей дороги.

Все прекрасно работает только дорога прямая.

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

Имею вот какие данные:

Изначальный кусок земли (я ввожу начальную точку и конечную) в котором на "единицу" ширины строиться 5 линий, что бы плавно все выглядело. т.е. на экране дорога будет примерно из 100 отрезков(EdgeCollider2D).
Дальше я получаю кол-во точек и отрезков которые будут всего на данном куске земли. Например 100 отрезков и 101 точка.
После я забиваю координаты X = начальная точка + ширина всей дороги * i / 101 (i - это текущий индекс точки, всего точек 101)
В Y я забиваю просто верхнею координату куска земли.

И получается в итоге прямой кусок земли(линия) и прямой EdgeCollider состоящий из 101 точки и 100 отрезков

Подскажите что присвоить Y что бы получить примерно рандомный синусоид плавный?

Вот кусок рабочего кода.
Vector2[] Points = new Vector2[nodecount]; //инциализируем вектор точек
for(int i=0; i < nodecount; i++){
xpositions [i] = Left + Width * i / edgecount; //массив Х переменных
ypositions [i] = Top; //массив У переменных
MapsLine.SetPosition (i, new Vector3 (xpositions [i], ypositions [i], z)); //устанавливаем позицию для линии
Points.SetValue(new Vector2(xpositions [i], ypositions [i]),i); //устанавливаем позиции точек для коллайдера
MapsLine.GetComponent<EdgeCollider2D> ().points = Points; //Заполняем точки коллайдера

}
nilex7
UNIт
 
Сообщения: 53
Зарегистрирован: 31 май 2016, 13:45

Re: Синусоидальный 2D трэк

Сообщение MANMANA 31 май 2016, 23:44

Поскольку синус - циклическая функция, то вам необходимо менять значения для b и c в формуле y=a+bsin(cx+d) для каждого цикла https://ru.m.wikipedia.org/wiki/Синусоида
_3dbuffer.com
MANMANA
UNIверсал
 
Сообщения: 475
Зарегистрирован: 31 июл 2014, 10:32
Откуда: Moscow
  • Сайт

Re: Синусоидальный 2D трэк

Сообщение Cr0c 01 июн 2016, 02:12

Неповторяющийся - это сумма синусов с множителями угла из простого ряда чисел. Можно добавить уникальности добавляя к углу Mathf.Clamp(x, 0, max), где max рандомно генерируется для каждого синуса. Это вообще не сильно простая штука - подобрать множители и коэффициенты сдвига чтобы избежать короткой цикличности (а она будет, синус ведь), но можно её растянуть через нелинейные малоперекрывающиеся сдвиги углов и несоставные (простые) множители. И у каждого следующего синуса должен быть масштаб меньше предыдущего.
Аватара пользователя
Cr0c
Адепт
 
Сообщения: 3035
Зарегистрирован: 19 июн 2015, 13:50
Skype: cr0c81

Re: Синусоидальный 2D трэк

Сообщение nilex7 01 июн 2016, 10:57

Cr0c писал(а):Неповторяющийся - это сумма синусов с множителями угла из простого ряда чисел. Можно добавить уникальности добавляя к углу Mathf.Clamp(x, 0, max), где max рандомно генерируется для каждого синуса. Это вообще не сильно простая штука - подобрать множители и коэффициенты сдвига чтобы избежать короткой цикличности (а она будет, синус ведь), но можно её растянуть через нелинейные малоперекрывающиеся сдвиги углов и несоставные (простые) множители. И у каждого следующего синуса должен быть масштаб меньше предыдущего.


Что то не понял :)

У меня вот что получилось

Синтаксис:
Используется csharp
//Заполнение массивов физ.значений и установка позиции линии
                float a = Top;   //Oy
                float b = 0.05f;  //растяжение по Oy
                float c = 0.15f;  //растяжение по Ox
                float d = 0.0f;  //-Ox
                if (Random.Range (0.0f, 100.0f) > 50) {
                        b = 0.05f;
                        b_activ = false;
                } else {
                        b = 0.5f;
                        b_activ = true;
                }
                Vector2[] Points = new Vector2[nodecount];
                for(int i=0; i < nodecount; i++){      
                       
                        if (b_activ == false) {
                                b += 0.01f;
                        }
                        if (b_activ == true) {
                                b -= 0.01f;
                        }

                        xpositions [i] = Left + Width * i / edgecount;
                        ypositions [i] = a + b*Mathf.Sin(c*i + d);

                        if (ypositions [i] > 0.3f) {
                                b_activ = true;
                        }
                        if(ypositions[i] < -0.3f){
                                b_activ = false;
                        }

                        MapsLine.SetPosition (i, new Vector3 (xpositions [i], ypositions [i], z));
                        Points.SetValue(new Vector2(xpositions [i], ypositions [i]),i);
                        MapsLine.GetComponent<EdgeCollider2D> ().points = Points;

                }
 


MapsLine имеет LineRender это к слову.

Получается довольно интересная случайная и плавная синусоида, но резких холмов как хотелось не появляется.
Единственное если начинать менять c также как b то теряется плавность трэка и он превращается в зубчатый местами...
Ковырялся так и не смог изменения по Х нормально сделать. На видео покажу что получилось.

У кого какие идеи есть что бы улучшить модель трэка.

Еще вопрос как теперь это сделать бесконечным? Например если мы движемся вправо и достигли определенной отметки брать последние точки трэка и с них начинать строить новый справа от существующего, и тоже самое слева. И еще что бы облегчить добавить такое, если трэков создано больше 3 то крайний созданный трэк противоположный движению удалить. Так получиться все время случайно-бесконечная карта.
Или как то по другому лучше запилить?

https://youtu.be/LuAJUI2YQKA
nilex7
UNIт
 
Сообщения: 53
Зарегистрирован: 31 май 2016, 13:45

Re: Синусоидальный 2D трэк

Сообщение unk_nown 01 июн 2016, 13:51

чтобы сделать это бесконечным, стоит двигать не ГГ а саму карту вокруг него, потому что окружающий мир описан во флоате и у нас есть шанс добраться до его пределов.
unk_nown
UNITрон
 
Сообщения: 280
Зарегистрирован: 20 апр 2016, 19:31
Откуда: Москва

Re: Синусоидальный 2D трэк

Сообщение Anonymyx 01 июн 2016, 14:04

А если карта выйдет за пределы float? :)
Аватара пользователя
Anonymyx
Адепт
 
Сообщения: 1973
Зарегистрирован: 05 апр 2015, 15:55

Re: Синусоидальный 2D трэк

Сообщение unk_nown 01 июн 2016, 15:55

так, вероятно, подобное перемещение карты вокруг объекта предполагает генерацию новых ее частей и удаление старых. Разве это не очевидно? :D
unk_nown
UNITрон
 
Сообщения: 280
Зарегистрирован: 20 апр 2016, 19:31
Откуда: Москва

Re: Синусоидальный 2D трэк

Сообщение nilex7 02 июн 2016, 09:06

unk_nown писал(а):так, вероятно, подобное перемещение карты вокруг объекта предполагает генерацию новых ее частей и удаление старых. Разве это не очевидно? :D


Я именно так и написал, создавать три куска земли и по мере движения героя по земле удалять крайнию землю против движения и создавать новую землю в стороне движения, у меня так уже сделано с заднем фоном, на видео видно.
Крутить просто карту а героя оставлять на месте у меня не получиться т.к. я использую 2D физику, у меня гусенечный краб))) он хорошо ездит, обидно его лишать такой радости)))

А еще затык такой интересный, вот это не работает
Синтаксис:
Используется csharp
//Попытка определить слой, но не работает
                MapsLine.GetComponent<LineRenderer> ().sortingLayerName = NameLayer;
                MapsLine.GetComponent<LineRenderer> ().sortingOrder = NumberLayer;

                MapsMesh.GetComponent<MeshRenderer> ().sortingLayerName = NameLayer;
                MapsMesh.GetComponent<MeshRenderer> ().sortingOrder = NumberLayer;


У меня Z у всех объектов 0 кроме камеры, камера -10, но она не причем тут, просто к слову.
Вообщем слой и номер в слое не применяться...нет реакции никакой на это.
А вот на Z реакция есть, но у меня разделения по слоям сделана по имени слоя и по номеру в слое а не по Z

Вот тут Z ставлю и тут видимость меняеться. Но не охото все остальное переделывать со слоев на Z
Синтаксис:
Используется csharp
apsLine.SetPosition (i, new Vector3 (xpositions [i], ypositions [i], z));


В чем ошиибка не пойму никак...
nilex7
UNIт
 
Сообщения: 53
Зарегистрирован: 31 май 2016, 13:45

Re: Синусоидальный 2D трэк

Сообщение Cr0c 02 июн 2016, 11:11

nilex7 писал(а):
unk_nown писал(а):так, вероятно, подобное перемещение карты вокруг объекта предполагает генерацию новых ее частей и удаление старых. Разве это не очевидно? :D


Я именно так и написал, создавать три куска земли и по мере движения героя по земле удалять крайнию землю против движения и создавать новую землю в стороне движения, у меня так уже сделано с заднем фоном, на видео видно.
Крутить просто карту а героя оставлять на месте у меня не получиться т.к. я использую 2D физику, у меня гусенечный краб))) он хорошо ездит, обидно его лишать такой радости)))

Ничего не мешает каждые 100-1000 юнитов от центра перемещать весь мир в начало координат.
Аватара пользователя
Cr0c
Адепт
 
Сообщения: 3035
Зарегистрирован: 19 июн 2015, 13:50
Skype: cr0c81

Re: Синусоидальный 2D трэк

Сообщение nilex7 02 июн 2016, 11:35

Cr0c писал(а):
nilex7 писал(а):
unk_nown писал(а):так, вероятно, подобное перемещение карты вокруг объекта предполагает генерацию новых ее частей и удаление старых. Разве это не очевидно? :D


Я именно так и написал, создавать три куска земли и по мере движения героя по земле удалять крайнию землю против движения и создавать новую землю в стороне движения, у меня так уже сделано с заднем фоном, на видео видно.
Крутить просто карту а героя оставлять на месте у меня не получиться т.к. я использую 2D физику, у меня гусенечный краб))) он хорошо ездит, обидно его лишать такой радости)))

Ничего не мешает каждые 100-1000 юнитов от центра перемещать весь мир в начало координат.


физический движок мешает. Читайте руководство http://docs.unity3d.com/ru/current/Manu ... rence.html Юнити.
Перенести картинку это не проблема. Видео мое посмотрите там такое уже есть. Но перемещение физических объектов не делается через transform.position Не стоит идти против рекомендации разрабов Юнити
nilex7
UNIт
 
Сообщения: 53
Зарегистрирован: 31 май 2016, 13:45

Re: Синусоидальный 2D трэк

Сообщение unk_nown 02 июн 2016, 13:59

http://docs.unity3d.com/ru/current/Scri ... Layer.html
я так подозреваю, что те поля, которые вы используете, имеют отношение только к LineRenderer
unk_nown
UNITрон
 
Сообщения: 280
Зарегистрирован: 20 апр 2016, 19:31
Откуда: Москва

Re: Синусоидальный 2D трэк

Сообщение MANMANA 02 июн 2016, 18:03

nilex7 писал(а):Но перемещение физических объектов не делается через transform.position Не стоит идти против рекомендации разрабов Юнити

Не путайте квадратное с зеленым. Крок посоветовал вам телепортировать раз в н-ное количество юнитов всю сцену, а не "перемещать" физические объекты каждый кадр, что и имели ввиду разработчики Юнити :)
_3dbuffer.com
MANMANA
UNIверсал
 
Сообщения: 475
Зарегистрирован: 31 июл 2014, 10:32
Откуда: Moscow
  • Сайт

Re: Синусоидальный 2D трэк

Сообщение nilex7 02 июн 2016, 21:29

MANMANA писал(а):
nilex7 писал(а):Но перемещение физических объектов не делается через transform.position Не стоит идти против рекомендации разрабов Юнити

Не путайте квадратное с зеленым. Крок посоветовал вам телепортировать раз в н-ное количество юнитов всю сцену, а не "перемещать" физические объекты каждый кадр, что и имели ввиду разработчики Юнити :)


Читайте лучше комментарии, Крок посоветовал именно перемещать, слово в слово.
nilex7
UNIт
 
Сообщения: 53
Зарегистрирован: 31 май 2016, 13:45

Re: Синусоидальный 2D трэк

Сообщение Anonymyx 02 июн 2016, 21:44

Логика...
Перемещать каждый кадр != перемещать каждый 1000-ый юнит.
Перемещать каждый 1000-ый юнит == телепорт == 1 раз за какое-то время.
Аватара пользователя
Anonymyx
Адепт
 
Сообщения: 1973
Зарегистрирован: 05 апр 2015, 15:55


Вернуться в Почемучка

Кто сейчас на конференции

Сейчас этот форум просматривают: Google [Bot], Yandex [Bot] и гости: 25