Вектор направления вокруг поверхности сетки - PullRequest
0 голосов
/ 07 марта 2019

Как лучше всего описать вектор направления для перемещения объекта влево (или вправо / вверх / вниз) из его текущего положения, с учетом перспективы текущего вида в уравнение?

Например, представьте себе прямоугольникизображен на следующем рисунке, размещен в начале координат (0,0,0).Если бы я хотел переместить точку сверху окна влево, мне пришлось бы сделать шаг в (-1,0,0) направлении (т.е. currentPos = currentPos + Vector3.left).

Vector Left(-1,0,0) when viewing from front

Если бы я посмотрел на коробку сзади, мне пришлось бы сделать шаг в (1,0,0) направлении, чтобы продолжить движение в том же направлении.

т.е. когда я смотрю на это поле, помещаю его в начало координат и нажимаю кнопку ввода ВЛЕВО, мне нужно, чтобы точка двигалась влево и продолжала двигаться в этом направлении до тех пор, пока я продолжаю нажимать кнопку,В конечном итоге он оборачивается вокруг поверхности, т. Е. Если я продолжу нажимать только ВЛЕВО, точка обернется вокруг куба и снова появится, так сказать.

Vector Left(1,0,0) when viewing from behind

Ответы [ 2 ]

2 голосов
/ 07 марта 2019

Чтобы бесконечно отследить декаль вокруг куба:

private Transform Cube;
private Transform Decal;


void Update() {


    Vector3 moveLocal = Vector3.zero;

    // Set moveLocal from User Input
    moveLocal += Vector3.left * Input.GetAxis("Left"); // etc

    if (moveLocal.sqrMagnitude > 0) {

        var decalDirection = (Decal.position - Cube.position).normalized;
        var angle = Vector3.SignedAngle(Cube.forward, decalDirection, Cube.up);


        // Align decal to correct cube face
        if (angle < -135 || angle > 135) { // Rear face
            Decal.forward = -Cube.forward;
        }
        else if (angle < -45) { // Left face
            Decal.forward = -Cube.right;
        }
        else if (angle > 45) { // Right face
            Decal.forward = Cube.right;
        }
        else { // Front Face
            Decal.forward = Cube.forward;
        }

        // Now move decal in it's local space:
        Decal.Translate(moveLocal, Space.Self);
    }
}

По общему признанию, это только вращает Влево / Вправо, но я надеюсь, что вы поняли =)

1 голос
/ 07 марта 2019

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

private Vector3 normal;
private Vector3 contact;
private Vector3 direction;
private GameObject obj;

void Start () {

}

void Update () {
    if (obj == null)
        return;
    if( Input.GetKey(KeyCode.LeftArrow))
    {
        obj.transform.position += direction * Time.deltaTime;
    }
    if (Input.GetKey(KeyCode.RightArrow))
    {
        obj.transform.position -= direction * Time.deltaTime;
    }
}

void OnCollisionEnter(Collision collision)
{
    Debug.Log("Collided");

    Debug.Log("If works");
    obj = collision.gameObject;
    normal = collision.contacts[0].normal;
    contact = collision.contacts[0].point;

    //Cross product of normal and up gives direction Right. 
    //This up can be cube's up as well in cases it is tilted
    direction = (-Vector3.Cross(Vector3.up, normal));

}

Вы также можете увидеть, как он работает, из изображений ниже:

enter image description hereenter image description here

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