2017-01-30 20 views
2
矩陣乘法完全錯誤的值

即使System.Numerics.Vectors庫通過的NuGet是獲得對視圖和投影矩陣我想要實現它自己,只是使用向量和矩陣結構自身的功能。與System.Numerics

不幸的是與(正確)視圖矩陣相乘,我的目標矢量的情況下,我已經接到了完全錯誤的結果。我用右手座標系和下列說明

具有以下功能

private static Matrix4x4 LookAt(Vector4 cameraVector4, Vector4 focusVector4, Vector4 upVector4) { 
    if (cameraVector4 == focusVector4) return Matrix4x4.Identity; 
    var z = Vector4.Normalize(cameraVector4 - focusVector4); 
    var x = Vector4.Normalize(upVector4.Cross(z)); 
    var y = Vector4.Normalize(z.Cross(x)); 

    return new Matrix4x4(
     x.X, x.Y, x.Z, -Vector4.Dot(x, cameraVector4), 
     y.X, y.Y, y.Z, -Vector4.Dot(y, cameraVector4), 
     z.X, z.Y, z.Z, -Vector4.Dot(z, cameraVector4), 
     0, 0, 0, 1); 
} 

public static class Vector4Extensions { 
    public static Vector4 Cross(this Vector4 self, Vector4 vector4) { 
     return new Vector4(
      self.Y * vector4.Z - self.Z * vector4.Y, 
      self.Z * vector4.X - self.X * vector4.Z, 
      self.X * vector4.Y - self.Y * vector4.X, 
      0); 
    } 
} 

在我的示例預期視圖矩陣以上是

vMatrix4確實具有相同的價值。乘法vMatrix4targetVector4但是應該產生<1, 0.894427, -4.91935, 1>但Visual Studio報表<1, -0.8944272, -0.4472136, 5.472136>

我的問題是,該庫是否具有計算結果數值的問題,我是否有數據類型不匹配,還是我使用不當Vector4.Transform期待它返回ViewMatrix * TargetVector


EDIT

當使用下面的自定義擴展方法

public static Vector4 ApplyMatrix(this Vector4 self, Matrix4x4 matrix) { 
    return new Vector4(
     matrix.M11 * self.X + matrix.M12 * self.Y + matrix.M13 * self.Z + matrix.M14 * self.W, 
     matrix.M21 * self.X + matrix.M22 * self.Y + matrix.M23 * self.Z + matrix.M24 * self.W, 
     matrix.M31 * self.X + matrix.M32 * self.Y + matrix.M33 * self.Z + matrix.M34 * self.W, 
     matrix.M41 * self.X + matrix.M42 * self.Y + matrix.M43 * self.Z + matrix.M44 * self.W 
    ); 
} 

呼叫targetVector4.ApplyMatrix(targetVector4)產生正確的結果。這意味着內部Vector4.Transform似乎在做一些非常意想不到的事情。

回答

0

我已經反編譯使用dotPeek的System.Numerics庫和偶然發現了這一點:

public static Vector4 Transform(Vector4 vector, Matrix4x4 matrix) { 
    return 
     new Vector4(
      (float) 
      (vector.X * (double) matrix.M11 + 
      vector.Y * (double) matrix.M21 + 
      vector.Z * (double) matrix.M31 + 
      vector.W * (double) matrix.M41), 
      (float) 
      (vector.X * (double) matrix.M12 + 
      vector.Y * (double) matrix.M22 + 
      vector.Z * (double) matrix.M32 + 
      vector.W * (double) matrix.M42), 
      (float) 
      (vector.X * (double) matrix.M13 + 
      vector.Y * (double) matrix.M23 + 
      vector.Z * (double) matrix.M33 + 
      vector.W * (double) matrix.M43), 
      (float) 
      (vector.X * (double) matrix.M14 + 
      vector.Y * (double) matrix.M24 + 
      vector.Z * (double) matrix.M34 + 
      vector.W * (double) matrix.M44)); 
} 

這種方法意味着,該庫是解釋向量作爲行向量和,而不是「通常」的矩陣從右側乘以將矩陣與列向量的左側相乘的方式。要解決此問題,您有兩種選擇:

  • 編寫一個自定義方法,以便按照需要的順序將矩陣向量相乘。
  • 應用,這可能是輕微的開銷改造前轉置矩陣。
+0

[Vector4.cs](https://github.com/dotnet/corefx/blob/master/src/System.Numerics.Vectors/src/System/Numerics/Vector4.cs),第315-329行。不需要反編譯器,這個東西是開源的。 –

+0

@JeroenMostert哦謝謝你提供的鏈接。我只是偶然發現了沒有在GitHub上實現的簽名文件。 –

相關問題