2
\$\begingroup\$

In my 2D project, I have an object that is sometimes above or below another object.

Once the primary object comes in close proximity with the secondary object, I want the object to rotate on the z axis so that the front of the primary object is facing the secondary object.

(Here, following Unity's default setup, the z axis is the axis pointing into the screen)

\$\endgroup\$
  • \$\begingroup\$ You wrote that this is 2d and you want to rotate that on z axis too... How can that be possible...? 2d does not have Z axis I guess. \$\endgroup\$ – Shraddha Patel Nov 21 '15 at 13:16
  • 1
    \$\begingroup\$ @ShraddhaPatel - If you were to use the X and Y axis for a 2D game and wanted to rotate your object to face your mouse, it would rotate on the z axis. Picture an arrow pointed into your screen and through the centre of your object. It points in the same direction as the Z axis, therefore, rotates on the z axis. twalker22 - This video will point you in the right direction youtube.com/watch?v=CWxKLkJUxbo \$\endgroup\$ – Mike Hunt Nov 21 '15 at 14:58
  • \$\begingroup\$ I had seen what you gave here and you want that type of rotation. Right? \$\endgroup\$ – Shraddha Patel Nov 23 '15 at 10:30
3
\$\begingroup\$

I can see this question is old, but it's a fairly common issue worth a standard answer.

Quaternion.LookRotation gives us a convenient way to say "point this way" but the problem is that it wants to point the z+ axis in the given direction - usually not what we want in 2D.

Fortunately we can correct for this, taking advantage of the second argument (usually used to control the "up" vector or twist of the resulting rotation)

To point the local y+ axis toward something, keeping z+ pointing into the screen:

Vector3 offset = target.position - transform.position;

transform.rotation = Quaternion.LookRotation(
                       Vector3.forward, // Keep z+ pointing straight into the screen.
                       offset           // Point y+ toward the target.
                     );

To point the local x+ axis toward something, keeping z+ pointing into the screen:

Vector3 offset = target.position - transform.position;

// Construct a rotation as in the y+ case.
Quaternion rotation = Quaternion.LookRotation(
                          Vector3.forward,
                          offset
                      );

// Apply a compensating rotation that twists x+ to y+ before the rotation above.
transform.rotation = rotation * Quaternion.Euler(0, 0, 90);

Of course in both cases, instead of setting transform.rotation directly, you can store the target rotation and blend (Lerp/Slerp/RotateTowards) this value over multiple frames for a smoother/more controllable result.

\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.