Note: to use the D3DX functions you must include the header d3dx9.h and link with d3dx9d.lib (in debug build) or d3dx9.lib (in release mode).
Direct3D comes with a set of interfaces to help you easily draw text to the screen. It is worth knowing how it does it before using it. This is the traditional method used by games developers:
Direct3D provides a set of interfaces that can do all this for you. It may not be the fastest method in the world so developers do normally create there own (as described above) but it will do perfectly well to start with.
As usual you must declare a pointer to the interface object:
LPD3DXFONT m_font;
or
ID3DXFont *m_font;
The D3DXCreateFont function creates a Windows 32 font and uses that to create its characters. This means there are a lot of parameters to this function call allowing a font to be specified. You can look in the DirectX help and at the Windows 32 CreateFont function for the list of parameters. Below is an example of creating a font with 20 point high characters, in bold and using the Arial typeface:
// Create a D3DX font object
D3DXCreateFont( gD3dDevice, 20, 0, FW_BOLD, 0, FALSE, DEFAULT_CHARSET, OUT_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | FF_DONTCARE, TEXT("Arial"), &m_font );
Now that you have created the font interface object you can use it, so in your render loop after calling BeginScene you could call a function to draw the text e.g.
void DisplaySomeText()
{
// Create a colour for the text - in this case blue
D3DCOLOR fontColor = D3DCOLOR_ARGB(255,0,0,255);
// Create a rectangle to indicate where on the screen it should be drawn
RECT rct;
rct.left=2;
rct.right=780;
rct.top=10;
rct.bottom=rct.top+20;
// Draw some text
m_font->DrawText(NULL, "Hello World", -1, &rct, 0, fontColor );
}
The format of the draw call is:
int DrawText( LPD3DXSPRITE pSprite, LPCTSTR pString, INT Count, LPRECT pRect, DWORD Format, D3DCOLOR Color );
As always you must release the D3DX interface before your program exits or on a device reset:
m_font->Release();
The third parameter to the DrawText function is a flag that allows you to specify justification etc. There is also a very useful flag: DT_CALCRECT that causes DrawText to set the passed rectangle to the size required to display the text. When using this flag DrawText will not actually draw anything, it is purely a way of obtaining the size of the text.
Text drawing can be slow and so there are a couple of optimisations provided by the font interface. Unfortunately these are not very well documented so I decided to carry out some tests of my own to determine some real world values.
I found that passing a sprite object as the first parameter to DrawText improved rendering speeds by up to 4 times - quite a significant improvement.
The sprite interface also provides a function to allow you to preload a text string into video card memory - PreloadText. This should theoretically improve performance as the function would not need to assemble the characters each time and upload them to the graphic card. However from my test results I found little speed improvement.