在 ThreeJS 中 Object3D.applyMatrix4 是不连续的
In ThreeJS Object3D.applyMatrix4 is not continuous
我正在使用 Object3D.applyMatrix4 转换具有矩阵 A
的对象,我发现它在某一点上没有保留特征向量的方向。
所以我尝试在单位矩阵 I
和 A
之间设置动画插值,我发现了这个:
转化怎么会不连续呢?
旋转矩阵的线性插值在数学上并不可靠。组成旋转矩阵的向量需要是单位长度..或者至少保持一致的长度。
想象一个时钟,指针在 12 点,指针在 6 点。
如果将 12 点钟指针尖端的点线性插值到 6 点钟指针的尖端,则该点从时钟顶部到底部沿直线移动。
要对 4x4 矩阵表示的旋转进行插值,您可以将矩阵的旋转转换为四元数,并在这些四元数之间进行 .slerp(球形线性插值),然后再转换回矩阵。
然后对object.position进行线性插值。 (虽然再次......这假设关键帧之间的线性运动)。
现在在旋转很小的情况下,您可以通过线性插值矩阵来逃避,但您需要在每一步对其进行正交化,以将网格重塑为具有一致长度正交向量的网格对彼此。这并不难.. 你使用点积的组合,形成矩阵行(或列,我忘记了)的向量的乘法和加法来对矩阵进行正交化。但它比仅使用四元数和 .slerp 更痛苦,而且更不准确。
@manthrax 的回答指出了线性插值矩阵的基本问题,我当时并没有意识到这一点,他是对的。但真正的问题是 Object3D.applyMatrix4
不是显式定义局部矩阵的正确函数。我尝试直接设置 Object3D.matrix
属性 并且有效。并且线性插值(虽然我不应该这样做)变得连续。
我正在使用 Object3D.applyMatrix4 转换具有矩阵 A
的对象,我发现它在某一点上没有保留特征向量的方向。
所以我尝试在单位矩阵 I
和 A
之间设置动画插值,我发现了这个:
转化怎么会不连续呢?
旋转矩阵的线性插值在数学上并不可靠。组成旋转矩阵的向量需要是单位长度..或者至少保持一致的长度。
想象一个时钟,指针在 12 点,指针在 6 点。 如果将 12 点钟指针尖端的点线性插值到 6 点钟指针的尖端,则该点从时钟顶部到底部沿直线移动。
要对 4x4 矩阵表示的旋转进行插值,您可以将矩阵的旋转转换为四元数,并在这些四元数之间进行 .slerp(球形线性插值),然后再转换回矩阵。
然后对object.position进行线性插值。 (虽然再次......这假设关键帧之间的线性运动)。
现在在旋转很小的情况下,您可以通过线性插值矩阵来逃避,但您需要在每一步对其进行正交化,以将网格重塑为具有一致长度正交向量的网格对彼此。这并不难.. 你使用点积的组合,形成矩阵行(或列,我忘记了)的向量的乘法和加法来对矩阵进行正交化。但它比仅使用四元数和 .slerp 更痛苦,而且更不准确。
@manthrax 的回答指出了线性插值矩阵的基本问题,我当时并没有意识到这一点,他是对的。但真正的问题是 Object3D.applyMatrix4
不是显式定义局部矩阵的正确函数。我尝试直接设置 Object3D.matrix
属性 并且有效。并且线性插值(虽然我不应该这样做)变得连续。