微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

如何正确夹紧相机旋转轴?

如何解决如何正确夹紧相机旋转轴?

我正在尝试夹紧相机的 X 轴和 Y 轴,我已经设法做到了。但是,当钳位值达到 MAX 阈值时,它将跳回到 MIN 阈值! 知道是什么导致我的代码出现这种情况吗?

 private void climbingLookRotation()
    {
        if (input.mouseX != 0 || input.mouseY != 0f)
        {
            orientation.rotation *= Quaternion.AngleAxis(input.mouseX,Vector3.up);
            orientation.rotation *= Quaternion.AngleAxis(input.mouseY,Vector3.right);
        }

        var rotX = orientation.eulerAngles.x;
        var rotY = orientation.eulerAngles.y;

        rotX = Mathf.Clamp(rotX,1,25);
        rotY = Mathf.Clamp(rotY,200,355);            

        orientation.eulerAngles = new Vector3(rotX,rotY,0);
    }

任何帮助将不胜感激! 谢谢。

解决方法

您可以将欧拉角围绕中心值重新居中,然后缩小差异:

float centralX = 13f;
float extentX = 12f;

float centralY = 277.5f;
float extentY = 77.5f;

private static float ClampEuler(float val,float center,float extent)
{
    return center + Mathf.Clamp((val - center + 360f) % 360f,-extent,extent);
}

private void ClimbingLookRotation()
{
    if (input.mouseX != 0 || input.mouseY != 0f)
    {
        orientation.rotation *= Quaternion.AngleAxis(input.mouseX,Vector3.up);
        orientation.rotation *= Quaternion.AngleAxis(input.mouseY,Vector3.right);
    }

    var rotX = orientation.eulerAngles.x;
    var rotY = orientation.eulerAngles.y;

    rotX = ClampEuler(rotX,centralX,extentX);
    rotY = ClampEuler(rotY,centralY,extentY);

    orientation.eulerAngles = new Vector3(rotX,rotY,0);
}

顺便说一下,您可能想要执行 orientation.rotation *= Quaternion.AngleAxis(input.mouseY,orientation.right); 来围绕局部右侧而不是全局右侧旋转。随着时间的推移,围绕全局右侧旋转可能会产生您可能不想要的滚动效果。

,

我发现了一些效果很好的东西,所以我想我会回答,以防它对任何人有帮助!

 public static float ClampAngle(float angle,float min,float max)
    {   //Normalises angle value passed in between -180 to 180 to make the angle clampable
        angle = NormalizeAngle(angle);
        if (angle > 180)
        {
            angle -= 360;
        }
        else if (angle < -180)
        {
            angle += 360;
        }

        min = NormalizeAngle(min);
        if (min > 180)
        {
            min -= 360;
        }
        else if (min < -180)
        {
            min += 360;
        }

        max = NormalizeAngle(max);
        if (max > 180)
        {
            max -= 360;
        }
        else if (max < -180)
        {
            max += 360;
        }

        return Mathf.Clamp(angle,min,max);
    }

    public static float NormalizeAngle(float angle)
    { //If the angle is above or below 360 degrees,normalise it
        while (angle > 360)
            angle -= 360;
        while (angle < 0)
            angle += 360;
        return angle;
    }

然后只需在需要限制值的地方调用 ClampAngle 方法,例如:

private void ClimbingLookRotation()
    {
        if (input.mouseX != 0 || input.mouseY != 0f)
        {
            orientation.rotation *= Quaternion.AngleAxis(input.mouseX,Vector3.up);
            orientation.rotation *= Quaternion.AngleAxis(input.mouseY,Vector3.right);
        }

        var rotX = orientation.eulerAngles.x;
        var rotY = orientation.eulerAngles.y;

        rotX = HelperFunctions.ClampAngle(rotX,-10,25); //Here
        rotY = HelperFunctions.ClampAngle(rotY,200,340); //And here

        orientation.eulerAngles = new Vector3(rotX,0);
    }

我在我的相机旋转函数中调用了它来钳制 rotX 和 rotY,这后来被应用于我的方向游戏对象的旋转。

再次感谢 Ruzihm 之前的帮助 :)

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。