Home > Software engineering >  Changing direction in 3D of a given angle
Changing direction in 3D of a given angle

Time:01-30

I am working on a 3D project in Unity in which I have 3D object moving in a fixed space. The objects have a fixed velocity value, and they bounce back once they reach the space limit. What I need to add is a change of direction, to be applied once every n seconds (n given as input) of a given angle.

The problem I am facing is how to rotate a 3D vector of a given angle. In 2D is pretty easy, while in 3D I am not sure how to handle it. Can someone help me with that?

CodePudding user response:

You don't really change the direction of an angle since angles dont have directions.

You can change directions by a certain angle on a certain axis.

To change directions in 3D you can simply, but not exclusively, use a reference axis and rotate by a certain amount of degrees.

In Unity you can easily rotate an object with the Rotate method on the game object transform.

//in a script attached to the game object you want to rotate
transform.Rotate(Vector3.up, Random.Range(90,270), Space.self);

Now this is only changing the direction that the game object is facing, if you want to move this object forward in local space, use transform.forward instead of Vector3.forward.

You can also easily convert vectors from local to world space and vice versa with the transform methods on the Transform class:

//world to local
Vector3 localDirection = transform.InverseTransformDirection(Vector3.forward);

//local to world
Vector3 worldDirection = transform.TransformDirection(transform.forward);

Consider also looking at the Vector3 class methods such as Reflect and RotateTowards.

Tip: To keep a consistent speed across all directions, consider normalizing the direction vector, (0,1,1) will travel faster than (0,0,1), to keep the same speed and direction the vector would be approximately (0,0.71f,0.71f).

You can normalize any vector as follows:

Vector3 direction = Vector3.up   Vector3.forward;
direction = direction.normalized;

CodePudding user response:

In 2D this is simple...

In three 3 as well.

You can e.g. simply rotate a Vector3 about any given Euler angles via

var newVector = Quaternion.Euler(x, y, z) * oldVector;

question remains where you get those angles from and whether those are random or you are rather looking for Reflect the vector once the objects reach your defined area constraints.

You can as well simply invert the individual components like e.g.

// Note for simplicity reasons this is not an actual "distance"
// but rather the maximum of each individual axis
public float maxDistance;

private Rigidbody _rigidbody;

private void Start ()
{
    _rigidbody = GetComponent<Rigidbody>();
    _rigidbody.velocity = Random.insideUnitSphere.normalized;
}

private void FixedUpdate()
{
    var vel = _rigidbody.velocity;
    var pos = _rigidbody.position;

    if(Mathf.Abs(pos.x) >= maxDistance)
    {
        vel.x *= -1;
    }

    if(Mathf.Abs(pos.y) >= maxDistance)
    {
        vel.y *= -1;
    }

    if(Mathf.Abs(pos.z) >= maxDistance)
    {
        vel.z *= -1;
    }

    _rigidbody.velocity = vel;
}
  • Related