This topic is now archived and is closed to further replies.


Stupid question about D3DX matrices

Recommended Posts

I feel stupid even asking this question, but anyway.. I am implementing an engine that aims to be API independent, and am trying to finish off my Matrix class.. I have a method that is called BuildPerspectiveLH(), that builds a left handed projection matrix from a field of view (fov), aspect, near and far Z values.. Now I grabbed the formula from the Directx 8.1 SDK docs for the D3DXMatrixPerspectiveFovLH() function. The docs define the matrix as:
h = cos(fov/2) / sin(fov/2);
w = h / aspect;
And then the matrix as:
 2 * zNear/w       0                0                   0
     0         2 * zNear/h          0                   0
     0             0         zFar/(zFar-zNear)          1
     0             0         zNear*zFar/(zNear-zFar)    0
The problem is, when I call the D3DX function with fov=pi/4, aspect = 1.3333 and a z near and far of 0.1 and 100.0, I get a different matrix than if I use my own function which implements that exact formula.. I am supplying the FOV in radians, which is what the standard libraries expect, as does the D3DX function.. I can''t think what else I am doing wrong... Of course, the elements m(3,3) and m(4,3) are correct, they just involve the near and far terms, but elements (1,1) and (2,2) are inconsistent with what D3DX calculates.. Any ideas!?!?

Share this post

Link to post
Share on other sites
Darrell L    122
Here''s MS''s DX7 framework function for calculating the projection matrix:

// Name: D3DUtil_SetProjectionMatrix()
// Desc: Sets the passed in 4x4 matrix to a perpsective projection matrix built
// from the field-of-view (fov, in y), aspect ratio, near plane (D),
// and far plane (F). Note that the projection matrix is normalized for
// element [3][4] to be 1.0. This is performed so that W-based range fog
// will work correctly.
HRESULT D3DUtil_SetProjectionMatrix( D3DMATRIX& mat, FLOAT fFOV, FLOAT fAspect,
FLOAT fNearPlane, FLOAT fFarPlane )
if( fabs(fFarPlane-fNearPlane) < 0.01f )
if( fabs(sin(fFOV/2)) < 0.01f )

FLOAT w = fAspect * ( cosf(fFOV/2)/sinf(fFOV/2) );
FLOAT h = 1.0f * ( cosf(fFOV/2)/sinf(fFOV/2) );
FLOAT Q = fFarPlane / ( fFarPlane - fNearPlane );

ZeroMemory( &mat, sizeof(D3DMATRIX) );
mat._11 = w;
mat._22 = h;
mat._33 = Q;
mat._34 = 1.0f;
mat._43 = -Q*fNearPlane;

return S_OK;

Share this post

Link to post
Share on other sites