LookAt и

Программирование на Юнити.

LookAt и

Сообщение MiniCat 31 авг 2020, 23:31

Для обычной работы камеры использую:
m_MouseLook.LookRotation(transform, m_Camera.transform);
Но порой нужно обратить внимание игрока на определенный объект, тогда использую:
m_Camera.transform.LookAt(ObjectForView); Где ObjectForView - объект наблюдения.
Всё работает хорошо, но в момент, когда мне нужно переключиться обратно с объекта наблюдения на свободный обзор, происходит слишком резкий скачок на точку, которую наблюдал персонаж до начала работы LookAt.
Понятно, что мне нужно подсунуть последние координаты, где остановился взгляд персонажа до начала работы m_MouseLook.LookRotation, но как это сделать нормально, не могу понять.
Need Help!)
Аватара пользователя
MiniCat
UNIт
 
Сообщения: 130
Зарегистрирован: 11 фев 2017, 16:50

Re: LookAt и

Сообщение 1max1 31 авг 2020, 23:40

Запомни rotation в переменную, потом лерпай к нему.
Аватара пользователя
1max1
Адепт
 
Сообщения: 5505
Зарегистрирован: 28 июн 2017, 10:51

Re: LookAt и

Сообщение MiniCat 01 сен 2020, 00:12

1max1 писал(а):Запомни rotation в переменную, потом лерпай к нему.

Так я туплю и не понимаю, rotation именно чего нужно брать.
Ведь по идее после LookAt камера должна сохранить свое положение, а не дрыгать назад, в момент когда я заставил её смотреть в определенном положении.
Аватара пользователя
MiniCat
UNIт
 
Сообщения: 130
Зарегистрирован: 11 фев 2017, 16:50

Re: LookAt и

Сообщение MiniCat 01 сен 2020, 01:13

Я может не совсем корректно объяснил что хочу.
Нужно чтобы после конца выполнения LookAt направление камеры не возвращалось к прежнему, а оставалось на месте.
Аватара пользователя
MiniCat
UNIт
 
Сообщения: 130
Зарегистрирован: 11 фев 2017, 16:50

Re: LookAt и

Сообщение MrDmitry 01 сен 2020, 06:12

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


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


Я может не совсем корректно объяснил что хочу.
Нужно чтобы после конца выполнения LookAt направление камеры не возвращалось к прежнему, а оставалось на месте.


По моему тут какое то противоречие.
MrDmitry
UNITрон
 
Сообщения: 223
Зарегистрирован: 05 авг 2017, 17:21

Re: LookAt и

Сообщение MiniCat 01 сен 2020, 09:14

MrDmitry писал(а):Чет теперь я не понял что вам нужно, в первом посте вы говорите что вам нужно убрать резкий скачек, а потом говорите что камера должна остаться на месте.


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


Я может не совсем корректно объяснил что хочу.
Нужно чтобы после конца выполнения LookAt направление камеры не возвращалось к прежнему, а оставалось на месте.


По моему тут какое то противоречие.


Окей. Еще раз по порядку объясню проблему :D
Представим что игрок идет и наблюдает красоты террайна. Например на водопад слева по движению.
Игрок заходит в зону триггера и скрипт принудительно обращает внимание с помощью LookAt на нужный объект (например записка на земле). Это происходит резко, но мне так и нужно.
Игрок смотрит на записку условные 3 секунды. После этого управление переходит LookRotation . Камера резко возвращается на тот самый водопад, на который до этого смотрел игрок. А мне нужно чтобы камера осталась на записке.
Аватара пользователя
MiniCat
UNIт
 
Сообщения: 130
Зарегистрирован: 11 фев 2017, 16:50

Re: LookAt и

Сообщение 1max1 01 сен 2020, 10:04

Очень интересно посмотреть на этот код, потому что сама по себе она бы так не сделала и там явно где-то прописан тот самый возврат, который тебе надо ВИИИРИИИЗАТЬ!!!
Аватара пользователя
1max1
Адепт
 
Сообщения: 5505
Зарегистрирован: 28 июн 2017, 10:51

Re: LookAt и

Сообщение waruiyume 01 сен 2020, 10:30

Мауслук хранит поворот в углах Эйлера, выставляя в старте или авейке то значение, которое должно быть для начального поворота. Вам этот код нужно перед активаций мауслук вызвать.
Аватара пользователя
waruiyume
Адепт
 
Сообщения: 6143
Зарегистрирован: 30 окт 2010, 05:03
Откуда: Ростов на Дону

Re: LookAt и

Сообщение MiniCat 01 сен 2020, 21:27

1max1 писал(а):Очень интересно посмотреть на этот код, потому что сама по себе она бы так не сделала и там явно где-то прописан тот самый возврат, который тебе надо ВИИИРИИИЗАТЬ!!!

Код на основе стандартного FPS контроллера. Оставил только то, что касается проблемы.
Не понимаю как в m_MouseLook подсунуть нужные сохранённые углы(
m_MouseLook.Init(transform, m_Camera.transform); не помогает.

подсовывать
m_MouseLook.m_CameraTargetRot.SetEulerRotation(m_Camera.transform.rotation.x, m_Camera.transform.rotation.y, m_Camera.transform.rotation.z);
тоже

Синтаксис:
Используется csharp
private Camera m_Camera;
[SerializeField] Transform ObjectForView;
public bool NeedToView;
 


Синтаксис:
Используется csharp

private void RotateView()
{
     m_MouseLook.LookRotation(transform, m_Camera.transform);
}

private void Update()
{
     if (NeedToView) //нужно посмотреть на объект
          m_Camera.transform.LookAt(ObjectForView);
     else
          RotateView();
}
 


Понятно только что мне сюда нужно подсунуть нужные углы...

Синтаксис:
Используется csharp
 public void LookRotation(Transform character, Transform camera)
        {
            float yRot = CrossPlatformInputManager.GetAxis("Mouse X") * XSensitivity;
            float xRot = CrossPlatformInputManager.GetAxis("Mouse Y") * YSensitivity;

            m_CharacterTargetRot *= Quaternion.Euler (0f, yRot, 0f);
            m_CameraTargetRot *= Quaternion.Euler (-xRot, 0f, 0f);

            if(clampVerticalRotation)
                m_CameraTargetRot = ClampRotationAroundXAxis (m_CameraTargetRot);

            if(smooth)
            {
                character.localRotation = Quaternion.Slerp (character.localRotation, m_CharacterTargetRot,
                    smoothTime * Time.deltaTime);
                camera.localRotation = Quaternion.Slerp (camera.localRotation, m_CameraTargetRot,
                    smoothTime * Time.deltaTime);
            }
            else
            {
                character.localRotation = m_CharacterTargetRot;
                camera.localRotation = m_CameraTargetRot;
            }

          //  UpdateCursorLock();
        }
Аватара пользователя
MiniCat
UNIт
 
Сообщения: 130
Зарегистрирован: 11 фев 2017, 16:50

Re: LookAt и

Сообщение waruiyume 02 сен 2020, 18:45

waruiyume писал(а):Мауслук хранит поворот в углах Эйлера, выставляя в старте или авейке то значение, которое должно быть для начального поворота. Вам этот код нужно перед активаций мауслук вызвать.

Добавить нечего. Показывайте полный код мауслук, попробуем найти нужную часть.
Аватара пользователя
waruiyume
Адепт
 
Сообщения: 6143
Зарегистрирован: 30 окт 2010, 05:03
Откуда: Ростов на Дону

Re: LookAt и

Сообщение MiniCat 02 сен 2020, 19:28

waruiyume писал(а):
waruiyume писал(а):Мауслук хранит поворот в углах Эйлера, выставляя в старте или авейке то значение, которое должно быть для начального поворота. Вам этот код нужно перед активаций мауслук вызвать.

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


Вот весь код. Не хватало только ClampRotationAroundXAxis.

Синтаксис:
Используется csharp
namespace UnityStandardAssets.Characters.FirstPerson
{
    [Serializable]
    public class MouseLook
    {
        public float XSensitivity = 2f;
        public float YSensitivity = 2f;
        public bool clampVerticalRotation = true;
        public float MinimumX = -90F;
        public float MaximumX = 90F;
        public bool smooth;
        public float smoothTime = 5f;
        public bool lockCursor = true;
        private string GOname;

        public Quaternion m_CharacterTargetRot;
        public Quaternion m_CameraTargetRot;
        private bool m_cursorIsLocked = true;

        public float yRot, xRot;


        public void Init(Transform character, Transform camera)
        {
            m_CharacterTargetRot = character.localRotation;
            m_CameraTargetRot = camera.localRotation;
        }


        public void LookRotation(Transform character, Transform camera)
        {
            yRot = CrossPlatformInputManager.GetAxis("Mouse X") * XSensitivity;
            xRot = CrossPlatformInputManager.GetAxis("Mouse Y") * YSensitivity;

            m_CharacterTargetRot *= Quaternion.Euler (0f, yRot, 0f);
            m_CameraTargetRot *= Quaternion.Euler (-xRot, 0f, 0f);

            if (clampVerticalRotation)
                m_CameraTargetRot = ClampRotationAroundXAxis (m_CameraTargetRot);

            if(smooth)
            {
                character.localRotation = Quaternion.Slerp (character.localRotation, m_CharacterTargetRot,
                    smoothTime * Time.deltaTime);
                camera.localRotation = Quaternion.Slerp (camera.localRotation, m_CameraTargetRot,
                    smoothTime * Time.deltaTime);
            }
            else
            {
                character.localRotation = m_CharacterTargetRot;
                camera.localRotation = m_CameraTargetRot;
            }

          //  UpdateCursorLock();
        }

        Quaternion ClampRotationAroundXAxis(Quaternion q)
        {
            q.x /= q.w;
            q.y /= q.w;
            q.z /= q.w;
            q.w = 1.0f;

            float angleX = 2.0f * Mathf.Rad2Deg * Mathf.Atan (q.x);

            angleX = Mathf.Clamp (angleX, MinimumX, MaximumX);

            q.x = Mathf.Tan (0.5f * Mathf.Deg2Rad * angleX);

            return q;
        }

    }
}
Аватара пользователя
MiniCat
UNIт
 
Сообщения: 130
Зарегистрирован: 11 фев 2017, 16:50

Re: LookAt и

Сообщение waruiyume 02 сен 2020, 22:56

m_Camera.transform.LookAt(ObjectForView)

Так делать нельзя, т.к. мауслук вращает 2 объекта: камеру по X и её родителя(видимо), по Y, поэтому и наводиться на объект интереса нужно двумя объектами.
Для тушки обнуляете Y компонент вектора направленного на цель, а потом используете Quaternion.LookRotation.
Для камеры вектор сначала нужно перевести в систему координат тушки, потом обнулить X, вернуть в мировую систему и уже потом использовать Quaternion.LookRotation.
По идеее, потом останется вызвать Init, а затем включить мауслук.
Аватара пользователя
waruiyume
Адепт
 
Сообщения: 6143
Зарегистрирован: 30 окт 2010, 05:03
Откуда: Ростов на Дону

Re: LookAt и

Сообщение MiniCat 04 сен 2020, 00:37

waruiyume писал(а):
m_Camera.transform.LookAt(ObjectForView)

Так делать нельзя, т.к. мауслук вращает 2 объекта: камеру по X и её родителя(видимо), по Y, поэтому и наводиться на объект интереса нужно двумя объектами.
Для тушки обнуляете Y компонент вектора направленного на цель, а потом используете Quaternion.LookRotation.
Для камеры вектор сначала нужно перевести в систему координат тушки, потом обнулить X, вернуть в мировую систему и уже потом использовать Quaternion.LookRotation.
По идеее, потом останется вызвать Init, а затем включить мауслук.


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

Синтаксис:
Используется csharp
private Camera m_Camera;
[SerializeField] Transform ObjectForView;
public bool NeedToView,CutSceneInit,NeedLoadRotation;
 


Синтаксис:
Используется csharp

private void RotateView()
{
     if (NeedLoadRotation) //после фокуса на объект, заново инициируем камеру
     {
         m_MouseLook.Init(transform,m_Camera.transform);
        NeedLoadRotation = false;
         CutSceneInit = false;
     }
     m_MouseLook.LookRotation(transform, m_Camera.transform);
}

private void Update()
{
     if (NeedToView) //нужно посмотреть на объект
          {
                    if (!CutSceneInit) //заходим сюда единожды, далее работают скрипты наводки на объект, а это разовая инициализация
                    {
                        //обнуляем координату у контроллера
                        transform.localRotation = Quaternion.Euler(transform.localRotation.x, 0f, transform.localRotation.z);
                        //переводим камеру в координаты контроллера
                        Vector3 cameraRelative = m_Camera.transform.InverseTransformPoint(transform.position);
                        m_Camera.transform.localEulerAngles = cameraRelative;
                        //обнуляем х камеры
                        m_Camera.transform.localRotation = Quaternion.Euler(0f, transform.localRotation.y, transform.localRotation.z);
                        //переводим в глобальную
                        Vector3 relativePoint = m_Camera.transform.TransformPoint(0, 0, 0);
                        m_Camera.transform.eulerAngles = cameraRelative;
                        //инициализируем 1 раз
                        CutSceneInit = true;
                     }
                    //следим за объектом контроллером
                    transform.rotation = Quaternion.Slerp(transform.rotation, Quaternion.LookRotation(ObjectsForView.transform.position - transform.position), 5f * Time.deltaTime);
                    //следим за объектом камерой
                    m_Camera.transform.rotation = Quaternion.Slerp(m_Camera.transform.rotation, Quaternion.LookRotation(ObjectsForView.transform.position - m_Camera.transform.position), 5f * Time.deltaTime);
                    //выставляем флаг чтобы камеру проинитить и контроллер (transform это он)
                    NeedLoadRotation = true;
          }
     else
          RotateView();
}
 
Аватара пользователя
MiniCat
UNIт
 
Сообщения: 130
Зарегистрирован: 11 фев 2017, 16:50

Re: LookAt и

Сообщение MiniCat 06 сен 2020, 15:50

Help me pls :(
Аватара пользователя
MiniCat
UNIт
 
Сообщения: 130
Зарегистрирован: 11 фев 2017, 16:50

Re: LookAt и

Сообщение waruiyume 06 сен 2020, 19:10

Описанное мной должно происходить либо каждый кадр, перед переключением на мауслук.
Аватара пользователя
waruiyume
Адепт
 
Сообщения: 6143
Зарегистрирован: 30 окт 2010, 05:03
Откуда: Ростов на Дону

След.

Вернуться в Скрипты

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

Сейчас этот форум просматривают: нет зарегистрированных пользователей и гости: 8