在这种情况下,为什么我不能将“Mouse Y”(来自Input.GetAxis("Mouse Y"))直接传递到X轴变换旋转?(想了解更多关于C#的知识)

问题描述 投票:0回答:1

这里是菜鸟/初学者。我已经搜索过这个问题,但我自己没有找到任何内容(如果这个问题已经在这里解决/回答,我深表歉意)。我正在按照本教程制作一个超级基本的 FP 角色控制器 (https://www.youtube.com/watch?v=PmIPqGqp8UY)。这太棒了,我已经让它工作了,但我一路上遇到了一些问题,我真的很想知道为什么。最终的脚本如下所示(缺少一些将鼠标锁定到屏幕中心的代码):

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class PlayerMovementScript_V3 : MonoBehaviour
{
    [SerializeField] Transform playerChar_FP_POV = null;
    [SerializeField] float mouseSensitivty = 3.5f;
    float cameraPitch = 0.0f;

    // Start is called before the first frame update
    void Start()
    {
    
    }

    // Update is called once per frame
    void Update()
    {
       PlayerCameraControl(); 
    }

    public void PlayerCameraControl()
    {
        Vector2 mouseDelta = new Vector2(Input.GetAxis("Mouse X"), Input.GetAxis("Mouse Y"));

        cameraPitch -= mouseDelta.y;
        cameraPitch = Mathf.Clamp(cameraPitch, -90.0f, 90.0f);

        playerChar_FP_POV.localEulerAngles = Vector3.right * cameraPitch;
        transform.Rotate(Vector3.up * mouseDelta.x * mouseSensitivty);
    }
}

其中 SerializeField 变换“playerChar_FP_POV”是一个已将相机(“PlayerChar_Body”的子对象)拖入其中的字段,因此可以从脚本访问其变换(请参见附图 1显示序列化字段变换的图像附于

在实验时,我发现无法将“mouseDelta.y”直接传递到“PlayerChar_FP_POV”X 旋转变换(上面脚本的倒数第二行),就像将 mouseDelta.x 传递到“PlayerChar_Body”Z 旋转一样转换(上面脚本的最后一行)。我首先必须创建一个浮点“cameraPitch”,然后将其值分配给 mouseDelta.y 的倒数(cameraPitch -= mousedelta.y),然后使用 Mathf.Clamp 限制“cameraPitch”的范围(上面的脚本 - 在最后一个方法中) )。然后,也只有这样,我才能成功地将值传递给“player_FP_Pov”以更改其 X 旋转变换。如果我尝试像这样将 mousedelta.y 直接传递到“playerChar_FP_POV”的 X 变换中(查看最后一个方法):

    public void PlayerCameraControl()
    {
        Vector2 mouseDelta = new Vector2(Input.GetAxis("Mouse X"), Input.GetAxis("Mouse Y"));

        playerChar_FP_POV.localEulerAngles = Vector3.right * mouseDelta.y;
        transform.Rotate(Vector3.up * mouseDelta.x * mouseSensitivty);
    }

(将 mouseDelta.y 直接传递到“playerChar_FP_POV”X 旋转变换;省略夹紧相机范围和反转输入)

“PlayerChar_FP_POV”(玩家相机)的 X 旋转变换被锁定到位,并且不响应鼠标 Y 轴移动(见图)。 父对象可以在其 Z 轴上跟随鼠标 x 轴,子对象不能在其 x 轴上跟随鼠标 Y 轴

再次,我的控制器工作正常。但纯粹从教育角度来看,我试图找出为什么后一个代码块不起作用。我觉得理解这会进一步加深我的理解。我希望这足够清楚,不想浪费人们的时间!

Unity版本:2022.3.22f1

为阅读本文干杯!

上面解释的问题,本节并不完全适用。

c# unity-game-engine visual-studio-code game-development unityscript
1个回答
0
投票

这是因为

Input.GetAxis("Mouse Y")
又名
mouseDelta.y
是自上一帧以来鼠标垂直移动的距离,也就是说,上一次
Update
被调用。


在第一个示例中,

cameraPitch
充当记录前一帧上的旋转状态的方式:

cameraPitch -= mouseDelta.y;
// clamping goes here... omitting for clarity
playerChar_FP_POV.localEulerAngles = Vector3.right * cameraPitch;

通过这种方式,它被用来对基于前一帧的旋转进行更改,这与

mouseDelta.y
本身是基于前一帧的更改是一致的。

为了让这个想法更清晰,你可以这样想:

// this doesn't actually change anything because this is already true based on
// what happened the last time PlayerCameraControl() was called
cameraPitch = playerChar_FP_POV.localEulerAngles.x; 
cameraPitch -= mouseDelta.y;
// clamping goes here... omitting for clarity
playerChar_FP_POV.localEulerAngles = Vector3.right * cameraPitch;

在第二个示例中,尝试将其单独用作旋转的绝对度量。请注意,前一帧中的旋转没有任何涉及,它只是被完全覆盖:

playerChar_FP_POV.localEulerAngles = Vector3.right * mouseDelta.y;

进一步说明的一个小比喻...

鲍勃一开始有 90 个苹果。每天,爱丽丝都会给鲍勃一定数量的苹果,或者拿走一定数量的苹果。每天,你可以问爱丽丝她给了鲍勃多少个苹果,或者她拿走了多少个。

如果您需要预测鲍勃目前每天结束时有多少个苹果……您不能只使用爱丽丝告诉您的数量,对吧?您需要记住鲍勃一开始有多少,然后根据爱丽丝拿走或给予的金额更新该金额。

您基本上是在这样做,但是鼠标在旋转中“给予”或“获取”的程度不同。

© www.soinside.com 2019 - 2024. All rights reserved.