Chad Vernon
  • Home
  • Reel/Resume
  • Work
  • Resources
  • About
  • Contact
sideBar

Search

Categories

  • CG
  • cvxporter
  • Maya
    • API
    • Plug-ins
  • Personal

Archives

  • May 2012
  • March 2012
  • September 2011
  • June 2011
  • March 2011
  • December 2010
  • November 2010
  • September 2010
  • August 2010
  • July 2010
  • May 2010
  • April 2010
  • March 2010
  • December 2009
  • October 2009
  • September 2009
  • August 2009
  • July 2009
  • June 2009
  • May 2009
  • April 2009
  • March 2009
  • February 2009
  • January 2009
  • December 2008
  • November 2008
  • October 2008
  • September 2008
  • August 2008
  • July 2008
  • June 2008
  • May 2008
  • April 2008
  • March 2008
  • February 2008
  • January 2008
  • December 2007
  • November 2007
  • October 2007
  • September 2007
  • August 2007

Rss

  • Main Entries RSS
  • Comments RSS
Home » Resources » DirectX 9 » Transformations

Transformations

  CU_Transformations.zip (34.0 KiB, 2,075 hits)

Recommended reading for this tutorial:

  • Real-Time Rendering, Section 3.1: Basic Transforms
  • MSDN: Transforms

In 3D graphics, there are three basic transformations: translation, rotation, and scale. To transform our geometry, we have to manipulate the world matrix before rendering each separate piece of geometry. The specific manipulations required are described in any beginning graphics book or article such as the ones listed above.

To make things easier, I have created a class, CWorldTransform, that will handle all the transformations with simple method calls. In the future, other classes can derive from this class if they need their own world matrix to transform, rotate, and scale.

#ifndef CWORLDMATRIX_H 
#define CWORLDMATRIX_H 
#include "stdafx.h" 

class CWorldTransform 
{ 
public: 
    CWorldTransform(); 
    ~CWorldTransform() { Reset(); } 

    void Reset(); 
    void TranslateAbs( float x, float y, float z ); 
    void TranslateRel( float x, float y, float z ); 
    void RotateAbs( float x, float y, float z ); 
    void RotateRel( float x, float y, float z ); 
    void ScaleAbs( float x, float y, float z ); 
    void ScaleRel( float x, float y, float z ); 

    D3DXMATRIX* GetTransform(); 
    float GetXPosition() { return m_translate._41; } 
    float GetYPosition() { return m_translate._42; } 
    float GetZPosition() { return m_translate._43; } 
    float GetXRotation() { return m_rotationX; } 
    float GetYRotation() { return m_rotationY; } 
    float GetZRotation() { return m_rotationZ; } 
    float GetXScale()    { return m_scale._11; } 
    float GetYScale()    { return m_scale._22; } 
    float GetZScale()    { return m_scale._33; } 

protected: 
    D3DXMATRIX m_translate; 
    D3DXMATRIX m_rotate; 
    D3DXMATRIX m_scale; 
    D3DXMATRIX m_transform; 
    float m_rotationX, m_rotationY, m_rotationZ; 
}; 
#endif

Since a world transformations matrix is composed of three concatenated transformation matrices, the CWorldTransform class will store these matrices separately so we can manipulate them independantly. These matrices are the transformation matrix, the rotation matrix, and the scaling matrix. All the transformation methods above will manipulate these matrices.

#include “..\include\stdafx.h”
#include “..\include\CWorldTransform.h”

/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
Summary: Default Constructor
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
CWorldTransform::CWorldTransform() Toggle

{

Reset();

}

/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
Summary: Reset the matrices to default position.
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
void CWorldTransform::Reset() Toggle

{

D3DXMatrixIdentity( &m_translate );
D3DXMatrixIdentity( &m_rotate );
D3DXMatrixIdentity( &m_scale );
D3DXMatrixIdentity( &m_transform );
m_rotationX = m_rotationY = m_rotationZ = 0.0f;

}

/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
Summary: Absolute translation
Parameters:
[in] x – X position
[in] y – Y position
[in] z – Z position
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
void CWorldTransform::TranslateAbs( float x, float y, float z ) Toggle

{

m_translate._41 = x;
m_translate._42 = y;
m_translate._43 = z;

}

/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
Summary: Relative translation
Parameters:
[in] x – X amount
[in] y – Y amount
[in] z – Z amount
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
void CWorldTransform::TranslateRel( float x, float y, float z ) Toggle

{

m_translate._41 += x;
m_translate._42 += y;
m_translate._43 += z;

}

/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
Summary: Absolute rotation
Parameters:
[in] x – X radians
[in] y – Y radians
[in] z – Z radians
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
void CWorldTransform::RotateAbs( float x, float y, float z ) Toggle

{

m_rotationX = x;
m_rotationY = y;
m_rotationZ = z;
D3DXMatrixRotationYawPitchRoll( &m_rotate, y, x, z );

}

/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
Summary: Relative rotation
Parameters:
[in] x – X radians
[in] y – Y radians
[in] z – Z radians
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
void CWorldTransform::RotateRel( float x, float y, float z ) Toggle

{

m_rotationX += x;
m_rotationY += y;
m_rotationZ += z;
D3DXMatrixRotationYawPitchRoll( &m_rotate, m_rotationY, m_rotationX, m_rotationZ );

}

/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
Summary: Absolute scale.
Parameters:
[in] x – X size
[in] y – Y size
[in] z – Z size
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
void CWorldTransform::ScaleAbs( float x, float y, float z ) Toggle

{

m_scale._11 = x;
m_scale._22 = y;
m_scale._33 = z;

}

/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
Summary: Relative scale.
Parameters:
[in] x – X size
[in] y – Y size
[in] z – Z size
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
void CWorldTransform::ScaleRel( float x, float y, float z ) Toggle

{

m_scale._11 += x;
m_scale._22 += y;
m_scale._33 += z;

}

/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
Summary: Get the transformation matrix
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
D3DXMATRIX* CWorldTransform::GetTransform() Toggle

{

m_transform = m_scale * m_rotate * m_translate;
return &m_transform;

}

The CWorldTransform class contains methods to translate, rotate, and scale to either absolute values or relative to the current transformation. The translation and scaling values are the easiest to set because they can be put straight into their corresponding matrices. The rotation values, on the other hand, cannot be put directly into the rotation matrix. We need to create a rotation matrix by calling D3DXMatrixRotationYawPitchRoll.

The GetTransform method concatenates the 3 matrices together and returns the result. The order of the concatenation is important because matrix multiplication is noncommutative. The scaling matrix should be applied first, followed by the rotation matrix, and then the translation matrix.

/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
Summary: Updates the current frame.
Parameters:
[in] pDevice – Pointer to a DIRECT3DDEVICE9 instance
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
void CGameApp::OnUpdateFrame( LPDIRECT3DDEVICE9 pDevice )
{

// Translation
m_transform.TranslateRel( g_Xdirection, g_Ydirection, 0.0f );
if ( m_transform.GetXPosition() > 3.0f || m_transform.GetXPosition() < -3.0f )
{

g_Xdirection *= -1.0f;

}
if ( m_transform.GetYPosition() > 4.0f || m_transform.GetYPosition() < -4.0f )
{

g_Ydirection *= -1.0f;

}

// Rotation
m_transform.RotateRel( 0.0f, 0.0f, 0.001f );

// Scale
m_transform.ScaleRel( g_scale, g_scale, g_scale );
if ( m_transform.GetXScale() > 2.0f || m_transform.GetXScale() < 0.5f )
{

g_scale *= -1.0f;

}

}

Transforming geometry is made easy with the CWorldTransform class. Each frame, I update the transform by applying a translation, rotation, and a scale.

/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
Summary: Renders the current frame.
Parameters:
[in] pDevice – Pointer to a DIRECT3DDEVICE9 instance
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
void CGameApp::OnRenderFrame( LPDIRECT3DDEVICE9 pDevice )
{

pDevice->Clear( 0, 0, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, D3DCOLOR_XRGB( 0, 0, 0 ), 1.0f, 0 );
pDevice->BeginScene();

pDevice->SetTransform( D3DTS_WORLD, m_transform.GetTransform() );
m_VB.Render( pDevice, 2, D3DPT_TRIANGLELIST );

pDevice->EndScene();
pDevice->Present( 0, 0, 0, 0 );

}

When we render the geometry, we need to set the world transform of the device to the matrix created by the CWorldTransform class.

The square will transform at different speeds depending on how powerful your computer is. In the next tutorial, we will create a timer that will be used to keep a consistent animation speed.

No Responses to “Transformations”

Subscribes to this topic Comment RSS or TrackBack URL

Leave A Reply

Allowed tag : <blockquote>, <p>, <code>, <em>, <small>, <ul>, <li>, <ol>, <a href=>..

 Username

 Email Address

 Website

Sticky: Always double check your comment before posting Please Note: Comment Moderation Maybe Active So There Is No Need To Resubmit Your Comments
Home » Resources » DirectX 9 » Transformations

© 2011 Chad Vernon