6

我一直在关注 The Hazy Mind 的 XNA 教程我有一个基础对象,它有一个位置(Vector3)和一个旋转(四元数)。对象模型如下所示 类图

从教程中的相机实现中,我复制了 Rotation 和 Revolve 方法并在 Object 上实现了它们

public virtual void Rotate(Vector3 axis, float angle)
{
    axis = Vector3.Transform(axis, Matrix.CreateFromQuaternion(Rotation));
    Rotation = Quaternion.Normalize(Quaternion.CreateFromAxisAngle(axis, angle) * Rotation);
}

public virtual void Revolve(Vector3 target, Vector3 axis, float angle)
{
    Vector3 revolveAxis = Vector3.Transform(axis, Matrix.CreateFromQuaternion(Rotation));

    Quaternion rotate = Quaternion.Normalize(Quaternion.CreateFromAxisAngle(revolveAxis, angle));

    Position = Vector3.Transform(Position - target, Matrix.CreateFromQuaternion(rotate)) + target;

    Rotate(axis, angle);
}

我的 Block 对象创建了 6 个 Quad 实例并在每个 Quad 对象上调用 render 方法,我在每个 Quad 上分配了偏移和旋转,以形成如下所示的纹理块: 由 6 个 Quad 对象渲染的块

现在我们遇到了实际问题,在我的 Block 对象上调用 Rotate 会导致对象本身改变旋转,而我的 Quad 对象不会旋转,因此我在 Block 对象上实现了一个新的 Rotate 函数。

public override void Rotate(Vector3 axis, float angle)
{
    for (int i = 0; i < mySides.Length; i++)
    {
        Quad side = mySides[i];
        side.Revolve(this.Position, axis, angle);
    }
}

然而,这并没有给我预期的结果,如下所示:

块对象旋转

错误的解决方案

以下解决方案将起作用,但不会很通用并且会受到限制:一堆 if 语句检查我想要围绕哪个轴旋转,然后以正确的方式旋转每一侧(Quad 对象)。

正确的解决方案

或者,我可以根据块对象(它们的父对象)的旋转来渲染 Quad 对象,但我不确定如何执行此操作。

第三个也是最后一个选项是让 Rotate 方法将每个 Quad 对象的旋转和位置更新为正确的值,我也不确定如何做。

问题

所以我要求的是对此的一些想法或想法,也许是一些链接和/或教程,解释如何在 XNA 中使用四元数,最好以视觉方式。

干杯,期待您的意见:)

4

1 回答 1

2

您应该做什么,并且您提到了这一点,使 Quad 对象的渲染依赖于父对象的旋转。

使用像您这样的分层系统很容易做到这一点。当你的渲染器去渲染块时,它应该将块的转换存储在一个矩阵中,我们称之为BlockWorld。当你去渲染每个 Quad 时,将 Quad 的局部变换乘以BlockWorld

于 2011-10-25T21:26:18.530 回答