【问题标题】:Unity Quaternion reset base orientationunity Quaternion 重置基本方向
【发布时间】:2016-10-22 07:23:09
【问题描述】:

我在旋转游戏对象时遇到问题。 我能够沿另一个游戏对象的方向/角度旋转对象。 但是在第一次旋转之后,我根据源游戏对象的增量旋转来旋转游戏对象它开始向不同的方向旋转,因为我猜它已经旋转了一次。

那么有没有办法在第一次旋转后我可以重置旋转,以便它在另一个对象旋转的角度/方向上再次移动?

下面是我当前的代码,我不是数学专家,所以我可能做错了.. 所以我想要的基本事情是第二个游戏对象以与基础游戏对象旋转相同的方向旋转,但我不希望旋转值相等,旋转值不必相同,它只有以与基础游戏对象旋转相同的角度/方向旋转。 TiltAgainstObject 是源游戏对象。 该脚本附加到第二个游戏对象。

欢迎任何帮助:)。

public class Tilt : MonoBehaviour {

public GameObject TiltAgainstObject;
private float rotX;
private float rotY;
private float rotZ;
private float rotW;
private float deltaX;
private float deltaY;
private float deltaZ;
private float deltaW;

// Use this for initialization
void Start () {

    rotX = TiltAgainstObject.transform.rotation.x;
    rotY = TiltAgainstObject.transform.rotation.y;
    rotZ = TiltAgainstObject.transform.rotation.z;
    rotW = TiltAgainstObject.transform.rotation.w;
}

// Update is called once per frame
void Update () {

    if(OVRInput.Get(OVRInput.Button.One))
    {
        deltaX = TiltAgainstObject.transform.rotation.x - rotX;
        deltaY = TiltAgainstObject.transform.rotation.y - rotY;
        deltaZ = TiltAgainstObject.transform.rotation.z - rotZ;
        deltaW = TiltAgainstObject.transform.rotation.w - rotW;
        gameObject.transform.localRotation = new Quaternion(gameObject.transform.rotation.x + deltaX,
                                                       gameObject.transform.rotation.y + deltaY,
                                                       gameObject.transform.rotation.z + deltaZ,
                                                       gameObject.transform.rotation.w + deltaW);
    }
    rotX = TiltAgainstObject.transform.rotation.x;
    rotY = TiltAgainstObject.transform.rotation.y;
    rotZ = TiltAgainstObject.transform.rotation.z;
    rotW = TiltAgainstObject.transform.rotation.w;
}

}

【问题讨论】:

    标签: math unity3d rotation quaternions euler-angles


    【解决方案1】:

    这个问题似乎有点令人困惑,如果你想让第二个游戏对象(你的脚本所在的位置)与第一个对象的旋转方向相同,你应该这样做:

    public class Tilt : MonoBehaviour {
    
    public GameObject TiltAgainstObject;
    private float rotX;
    private float rotY;
    private float rotZ;
    private float rotW;
    private float deltaX;
    private float deltaY;
    private float deltaZ;
    private float deltaW;
    
    // Use this for initialization
    void Start () {
    
        rotX = TiltAgainstObject.transform.rotation.x;
        rotY = TiltAgainstObject.transform.rotation.y;
        rotZ = TiltAgainstObject.transform.rotation.z;
        rotW = TiltAgainstObject.transform.rotation.w;
    
        deltaX = 0;
        deltaY = 0;
        deltaZ = 0;
        deltaW = 0;
    
    }
    
    // Update is called once per frame
    void Update () {
        rotX = TiltAgainstObject.transform.rotation.x;
        rotY = TiltAgainstObject.transform.rotation.y;
        rotZ = TiltAgainstObject.transform.rotation.z;
        rotW = TiltAgainstObject.transform.rotation.w;
    
        this.gameObject.transform.localRotation = new Quaternion(rotX + deltaX,
                                                           rotY + deltaY,
                                                           rotZ + deltaZ,
                                                           rotW + deltaW);
    
    
    }
    

    这样,第二个对象将沿第一个对象的相同方向旋转,如果您想更改旋转速度,只需修改增量即可。

    如果您希望仅在按下按钮时发生旋转。只需将其放入 if 语句中即可:

    if(OVRInput.Get(OVRInput.Button.One))
        {
          this.gameObject.transform.localRotation = new Quaternion(rotX + deltaX,
                                                           rotY + deltaY,
                                                           rotZ + deltaZ,
                                                           rotW + deltaW);
        }
    

    【讨论】:

    • 抱歉这个令人困惑的问题,我在示例中的逻辑“有效”但仅适用于第一次轮换。我第二次旋转它,它不再沿同一方向旋转,只有第一次旋转。我想这是因为您第二次旋转第二个对象的旋转欧拉角不再是 0,0,0 了?知道如何使您第二次按下按钮旋转第二个对象也正确地沿相同方向旋转吗?。
    【解决方案2】:

    我认为问题在于您将世界坐标rotation 分配给您的本地坐标localRotation,可能是拼写错误?除此之外,我不确定为什么要直接编辑四元数的组件,通常最好将它们加在一起并使用 Unity 的函数,因为处理 4 维通常容易出错。你可以试试这样的:

    public class Tilt : MonoBehaviour {
    
      public GameObject TiltAgainstObject;
      private Quaternion prevRotation;
      private Quaternion currentRotation;
    
      void Start()
      {
        prevRotation = TiltAgainstObject.transform.rotation;
      }
    
      void Update()
      {
        currentRotation = TiltAgainstObject.transform.rotation;
        if (OVRInput.Get(OVRInput.Button.One))
          gameObject.transform.rotation *= Quaternion.RotateTowards(prevRotation, currentRotation, 1000f);
        prevRotation = currentRotation;
      }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-06-01
      • 1970-01-01
      • 2010-11-24
      • 1970-01-01
      相关资源
      最近更新 更多