Skip to main content
Updating now that the question has been clarified.
Source Link
DMGregory
  • 140.8k
  • 23
  • 257
  • 401

Given that you're lockingIt sounds like you want to project the mouse cursor:

Cursor.lockState =  CursorLockMode.Locked;

...it looks like you're trying onto the horizontal plane, and rotate to implement FPS-style controlsface that. You couldWe can do that like soeasily:

public class Move : MonoBehaviour
{
    public float pitchSpeed = 1f;
    public float yawSpeed = 1f;
    public float maxPitch = 90f;

  // Update Vector2is _angles;called once per 
 frame
    void StartUpdate()
    {  
        // Record our initial orientation.
Get the position of the mouse on the _anglesscreen, =in transformpixels.localEulerAngles;

        Cursor.lockStateVector2 =screenPosition = CursorLockModeInput.Locked;mousePosition;

        // UsuallyCast we'dthis hidepoint through the cursorcamera whileviewpoint/projection
 locked, but I'll leave this as-is.
  // to form a ray shooting Cursor.visiblethrough =world true;space.
    }

    //Ray UpdateworldRay is= calledCamera.main.ScreenPointToRay(screenPosition);

 once per frame
    void Update()
// Form a horizontal plane through {this object's origin.
        //Plane AccumulateworldPlane our= yawnew Plane(left-right rotation)Vector3.up, and wrap aroundtransform.position);

        _angles.y// =Check (_angles.yif +the yawSpeedray *from Input.GetAxis("Mousethe X"))cursor %hits 360this plane.0f;

        // Accumulate our pitch (up-downIf rotation)not, and clamp at theskip polesit.
        _angles.x =if Mathf(worldPlane.ClampRaycast(
  worldRay, out float distance) {

            _angles.x// -If pitchSpeedwe *got Input.GetAxis("Mousea Y")hit,
  get the world space coordinates
            -maxPitch,
// of the point on the plane where the cursor ray hits.
       maxPitch
     var worldPosition = worldRay.GetPoint(distance);
 
        // Apply these rotation angles// Rotate to thislook transformtoward that point.
            transform.localEulerAnglesLookAt(worldPosition);
 = _angles;      }
    }
}

Given that you're locking the cursor:

Cursor.lockState =  CursorLockMode.Locked;

...it looks like you're trying to implement FPS-style controls. You could do that like so:

public class Move : MonoBehaviour
{
    public float pitchSpeed = 1f;
    public float yawSpeed = 1f;
    public float maxPitch = 90f;

    Vector2 _angles;   
 
    void Start()
    {
        // Record our initial orientation.
        _angles = transform.localEulerAngles;

        Cursor.lockState =  CursorLockMode.Locked;
        // Usually we'd hide the cursor while locked, but I'll leave this as-is.
        Cursor.visible = true;
    }

    // Update is called once per frame
    void Update()
    {  
        // Accumulate our yaw (left-right rotation), and wrap around.
        _angles.y = (_angles.y + yawSpeed * Input.GetAxis("Mouse X")) % 360.0f;

        // Accumulate our pitch (up-down rotation), and clamp at the poles.
        _angles.x = Mathf.Clamp(
                  _angles.x - pitchSpeed * Input.GetAxis("Mouse Y"),
                  -maxPitch,
                  maxPitch
        );

        // Apply these rotation angles to this transform.
        transform.localEulerAngles = _angles;
    }
}

It sounds like you want to project the mouse cursor onto the horizontal plane, and rotate to face that. We can do that easily:

public class Move : MonoBehaviour
{  
    // Update is called once per frame
    void Update()
    {  
        // Get the position of the mouse on the screen, in pixels.
        Vector2 screenPosition = Input.mousePosition;

        // Cast this point through the camera viewpoint/projection
        // to form a ray shooting through world space.
        Ray worldRay = Camera.main.ScreenPointToRay(screenPosition);

        // Form a horizontal plane through this object's origin.
        Plane worldPlane = new Plane(Vector3.up, transform.position);

        // Check if the ray from the cursor hits this plane.
        // If not, skip it.
        if (worldPlane.Raycast(worldRay, out float distance) {

            // If we got a hit, get the world space coordinates
            // of the point on the plane where the cursor ray hits.
            var worldPosition = worldRay.GetPoint(distance);
 
            // Rotate to look toward that point.
            transform.LookAt(worldPosition);
        }
    }
}
Source Link
DMGregory
  • 140.8k
  • 23
  • 257
  • 401

This code fundamentally misunderstands the different coordinate systems it's attempting to bodge together.

  • Input.GetAxis("Mouse X"); returns the change in the mouse's screen position (in the horizontal direction, or vertical for "Mouse Y") since the previous frame, measured in pixels.

  • transform.rotation and new Quaternion expect a unit quaternion: a vector in a four dimensional space with three imaginary components and one real component, whose squares sum to one. This has no meaning as a position in 3D space.

  • transform.LookAt expects a position in world space as its first argument (measured in world units), and an upward direction as its second argument.

So this code is meaningless gobbledygook:

mouseX = Input.GetAxis("Mouse X");
mouseY = Input.GetAxis("Mouse Y");
Vector3 mousePosition = new Vector3(
              mouseX /* displacement in screen pixels */,
              mouseY /* displacement in screen pixels */,
              transform.rotation.z /* imaginary number, 
              sine of half of rotation angle
              times z component of rotation axis*/
);

transform.LookAt(
               mousePosition /* position in the world? Definitely not!*/,
               Vector3.forward
 );

None of the three inputs you've passed to the Vector3 constructor represent positions, distances, or even directions in world space.

Given that you're locking the cursor:

Cursor.lockState =  CursorLockMode.Locked;

...it looks like you're trying to implement FPS-style controls. You could do that like so:

public class Move : MonoBehaviour
{
    public float pitchSpeed = 1f;
    public float yawSpeed = 1f;
    public float maxPitch = 90f;

    Vector2 _angles;   

    void Start()
    {
        // Record our initial orientation.
        _angles = transform.localEulerAngles;

        Cursor.lockState =  CursorLockMode.Locked;
        // Usually we'd hide the cursor while locked, but I'll leave this as-is.
        Cursor.visible = true;
    }

    // Update is called once per frame
    void Update()
    {  
        // Accumulate our yaw (left-right rotation), and wrap around.
        _angles.y = (_angles.y + yawSpeed * Input.GetAxis("Mouse X")) % 360.0f;

        // Accumulate our pitch (up-down rotation), and clamp at the poles.
        _angles.x = Mathf.Clamp(
                  _angles.x - pitchSpeed * Input.GetAxis("Mouse Y"),
                  -maxPitch,
                  maxPitch
        );

        // Apply these rotation angles to this transform.
        transform.localEulerAngles = _angles;
    }
}