2016-08-14 5 views
0

Я работаю над 3-мя линейными 3D-играми с бесконечным бегуном, и я столкнулся с этой проблемой.Как правильно переключаться с помощью моего сценария?

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

Я пришел заметить, что ось x символа, значения точек постепенно увеличиваются. например. Если это правая полоса, она должна быть 1.0000, но после ее переключения она увеличивается постепенно 1.0045, 1.0345, 1.09585 и так далее, и наоборот. Также иногда он также прерывает движение 3 полос движения, и персонаж пытается полностью двигаться вправо или влево, не останавливаясь, поэтому я должен остановить режим воспроизведения.

Справка была бы принята с благодарностью.

Вот мой сценарий.

//Variables for Lane switching 
    private bool isChangingLane = false; 
    private Vector3 locationAfterChanginLane = Vector3.zero; 
    private Vector3 sideWayMovementDistance = Vector3.right * 2f; // This might be the case that triggers abnormal movements 
    private float sideWaySpeed = 6f; 

    public enum Lane 
    { 
     Left, 
     Right, 
     Center 
    } 

    public enum MoveDirection 
    { 
     Left, 
     Right, 
     None 
    } 

    Lane currentLane = Lane.Center; 

    void Update() 
    { 
     currentBaseState = anim.GetCurrentAnimatorStateInfo(0); 

     if (controller.isGrounded) 
     { 
      verticalVelocity = -0.5f; 
      if (currentBaseState.fullPathHash == locoState) 
      { 
       if (Input.GetButtonDown("Jump")) 
       { 
        verticalVelocity = 18f; 

        anim.SetBool("Jump", true); 
       } 
       else if (Input.GetKeyDown(KeyCode.S)) 
       { 
        anim.SetBool("Slide", true); 
       } 

      } 

      MoveLeftRight(); // This is the method to move right and left. 

      if (isChangingLane) 
      { 
       if (Math.Abs(transform.position.x - locationAfterChanginLane.x) < 0.1f) 
       { 
        isChangingLane = false; 
        moveVector.x = 0; 
       } 
      } 



     } 
    } 

    private void MoveLeftRight() 
    { 

     MoveDirection requestedMoveDirection = MoveDirection.None; 
     if (Input.GetKeyDown(KeyCode.A) && !isChangingLane) 
     { 
      requestedMoveDirection = MoveDirection.Left; 
      isChangingLane = true; 
     } 
     else if (Input.GetKeyDown(KeyCode.D) && !isChangingLane) 
     { 
      requestedMoveDirection = MoveDirection.Right; 
      isChangingLane = true; 
     } 

     switch (requestedMoveDirection) 
     { 
      case MoveDirection.Right: 
       if (currentLane == Lane.Right) 
       { 
        Debug.Log("Right Lane"); 
        break; //Do nothing when in right lane. 

       } 
       else if (currentLane == Lane.Center) 
       { 
        locationAfterChanginLane = transform.position + sideWayMovementDistance; 
        moveVector.x = +sideWaySpeed; 

        currentLane = Lane.Right; 
        Debug.Log("Center --> Right"); 
       } 
       else if (currentLane == Lane.Left) 
       { 
        locationAfterChanginLane = transform.position + sideWayMovementDistance; 
        moveVector.x = +sideWaySpeed; 

        currentLane = Lane.Center; 
        Debug.Log("Left --> Center"); 
       } 
       break; 
      case MoveDirection.Left: 
       if (currentLane == Lane.Left) 
       { 
        Debug.Log("Left Lane"); 
        break; //Do nothing when in left lane. 
       } 
       else if (currentLane == Lane.Center) 
       { 
        locationAfterChanginLane = transform.position - sideWayMovementDistance; 
        moveVector.x = -sideWaySpeed; 

        currentLane = Lane.Left; 

        Debug.Log("Center --> Left"); 
       } 
       else if (currentLane == Lane.Right) 
       { 
        locationAfterChanginLane = transform.position - sideWayMovementDistance; 
        moveVector.x = -sideWaySpeed; 

        currentLane = Lane.Center; 

        Debug.Log("Right --> Center"); 
       } 
       break; 
     } 
    } 

ответ

0

Итак, я, наконец, нашел свой ответ на вопрос, так что вот оно. Самый простой способ - использовать Clamp для решения проблемы. Вот что я реализовал.

Метод зажима внутри функции обновления.

public static float Clamp(float val, float min, float max) 
    { 
     return (val < min) ? min : (val > max) ? max : val; 
    } 

В моей MoveLeftRight() menthod,

switch (requestedMoveDirection) 
     { 
      case MoveDirection.Right: 
       if (currentLane == Lane.Right) 
       { 
        break; //Do nothing when in right lane.      
       } 
       else if (currentLane == Lane.Center) 
       { 
        locationAfterChangingLane = transform.position + sideWayMovementDistance; 
        moveVector.x = +sideWaySpeed; 

        locationAfterChangingLane.x = Clamp(locationAfterChangingLane.x, RightLaneMin, RightLaneMax); 
        currentLane = Lane.Right; 
       } 
       else if (currentLane == Lane.Left) 
       { 
        locationAfterChangingLane = transform.position + sideWayMovementDistance; 
        moveVector.x = +sideWaySpeed; 

        locationAfterChangingLane.x = Clamp(locationAfterChangingLane.x, centerLaneMin, centerLaneMax); 
        currentLane = Lane.Center; 
       } 
       break; 

      case MoveDirection.Left: 
       if (currentLane == Lane.Left) 
       { 
        break; //Do nothing when in left lane. 
       } 
       else if (currentLane == Lane.Center) 
       { 
        locationAfterChangingLane = transform.position - sideWayMovementDistance; 
        moveVector.x = -sideWaySpeed; 

        locationAfterChangingLane.x = Clamp(locationAfterChangingLane.x, leftLaneMin, leftLaneMax); 
        currentLane = Lane.Left; 
       } 
       else if (currentLane == Lane.Right) 
       { 
        locationAfterChangingLane = transform.position - sideWayMovementDistance; 
        moveVector.x = -sideWaySpeed; 

        locationAfterChangingLane.x = Clamp(locationAfterChangingLane.x, centerLaneMin, centerLaneMax); 
        currentLane = Lane.Center; 
       } 
       break; 
     } 

Там вы идете. Надеюсь, поможет. Спасибо всем за помощь. Счастливое кодирование.

2

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

if (Math.Abs(transform.position.x - locationAfterChanginLane.x) < 0.1f) 
{ 
    isChangingLane = false; 
    moveVector.x = 0; 
    transform.position = locationAfterChanginLane; //Add this line 
} 

Причина это происходит, по существу, как работает функция Update. Обновление Monobehaviour НЕ вызывается на фиксированный временной шаг (мы называем Time.deltaTime). Поэтому в большинстве случаев позиция вашего персонажа перевернута/понижает конечное значение.

+0

Отлично. Благодарю. Я приложу его и увижу на следующий день. –

+0

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

+1

Что значит «переместить»? Вернитесь как в камеру, так и назад, в направлении, в котором вы начали? –