欧拉四元数和旋转矩阵

时间:2020-11-11 01:10:33

标签: matrix 3d quaternions euler-angles

我正在尝试在简单的Metal应用程序中实现四元数,但遇到了问题。我仔细检查了所有内容,从数学角度看似乎是正确的,但结果根本不正确。

所以基本上,这应该产生一个转换矩阵,我将其应用于顶点

static func FromEuler(_ eul: simd_float3) -> simd_quatf{
        
        let yaw = eul[0]
        let pitch = eul[1]
        let roll = eul[2]
        
        let cy = cos(yaw * 0.5);
        let sy = sin(yaw * 0.5);
        let cp = cos(pitch * 0.5);
        let sp = sin(pitch * 0.5);
        let cr = cos(roll * 0.5);
        let sr = sin(roll * 0.5);
        
        let qw = cr * cp * cy + sr * sp * sy;
        let qx = sr * cp * cy - cr * sp * sy;
        let qy = cr * sp * cy + sr * cp * sy;
        let qz = cr * cp * sy - sr * sp * cy;
        
        return simd_quatf(ix:qx, iy:qy, iz:qz, r:qw)
    }
    
    func ToMat4x4()-> matrix_float4x4{
        
        let qx = self.imag.x
        let qy = self.imag.y
        let qz = self.imag.z
        let qw = self.real
        
        return matrix_float4x4(rows: [
            simd_float4(1 - 2*qy*qy - 2*qz*qz, 2*qx*qy - 2*qz*qw, 2*qx*qz + 2*qy*qw, 0),
            simd_float4(2*qx*qy + 2*qz*qw, 1 - 2*qx*qx - 2*qz*qz, 2*qy*qz + 2*qx*qw, 0),
            simd_float4(2*qx*qz - 2*qy*qw, 2*qy*qz - 2*qx*qw, 1 - 2*qx*qx - 2*qy*qy, 0),
            simd_float4(0, 0, 0, 1)
        ])
    }

这是我的变换矩阵

func Transform() -> matrix_float4x4{
        
        //Perform Translation matrix
        let translate : matrix_float4x4 = matrix_float4x4(rows: [
            simd_float4(1, 0, 0, self.position[0]),
            simd_float4(0, 1, 0, self.position[1]),
            simd_float4(0, 0, 1, self.position[2]),
            simd_float4(0, 0, 0, 1)
        ])
        
        //Scale matrix
        let scale : matrix_float4x4 = matrix_float4x4(rows: [
            simd_float4(self.scale[0], 0, 0, 0),
            simd_float4(0, self.scale[1], 0, 0),
            simd_float4(0, 0, self.scale[2], 0),
            simd_float4(0, 0, 0, 1)
        ])
        
        
        //Rotation
        //Get quaternion from euler
        let quaternion = simd_quatf.FromEuler(self.rotation)
        
        
        return translate * quaternion.ToMat4x4() * scale
    }

然后在着色器中,我只需执行Matrix * VertexPosition The Triangle rotated 90 degrees z axis变成了飞机!

0 个答案:

没有答案