📄 dxfont.cpp
字号:
#include "DXFont.h"
ID3DXSprite* CDXFont::m_pSprite = 0;
CDXFont::CDXFont()
{
// Initialize the variables
m_pFont = NULL;
m_pD3DDevice = NULL;
// Set the default color to white
m_dwColor = 0xFFFFFFFF;
m_bSpriteDeleted = false;
}
CDXFont::~CDXFont()
{
// Simply destroy it
DestroyFont();
}
bool CDXFont::InitializeFont(IDirect3DDevice9* pDevice, char* strFontName, int iFontSize)
{
// First make sure we have a valid device
if((m_pD3DDevice = pDevice) == NULL)
return false;
// If our sprite interface hasn't been initialized, then
// initialize it. If it HAS been initialized, then AddRef
// it
if(!m_pSprite)
{
if(FAILED(D3DXCreateSprite(m_pD3DDevice, &m_pSprite) ))
return false;
}
else
m_pSprite->AddRef();
// Then make sure the font name is good. If it isnt
// specify one yourself
if( strFontName == NULL )
strFontName = "Ariel";
// Then make sure teh font size is good
if( iFontSize == 0 )
iFontSize = 15;
// Now we need to fill out a structure called D3DXFONT_DESC
D3DXFONT_DESC fd;
// Clear the structure
ZeroMemory(&fd, sizeof(D3DXFONT_DESC));
// Now fill it in with stuff.
strcpy(fd.FaceName, strFontName); // Copy the font name into the appropriate
// place. FaceName is what type of font you
// want to create ie: ariel, tahoma, etc...
fd.Height = -(iFontSize); // For this you have to give it a negative
// number of the font size that you want
// If you want font size 10, then pass in -10
// Ok that's all we're going to be filling. So now we create teh font object. There
// is a lot more to this LOGFONT structure then what I've went over. You should
// experiment with it. Set teh italics member, the boldness, and a few other things
// and see what happens.
if(FAILED(D3DXCreateFontIndirect(m_pD3DDevice, // Just give it the device for it's
// own internal use
&fd, // Pass in the LOGFONT structure
// that we (kinda) filled out
&m_pFont))) // The address of our font interface
// that is going to be initialized
// for us
return false;
// If we've reached here, then we have a valid font interface and we can start drawing
return true;
}
void CDXFont::DestroyFont()
{
if( m_pFont != NULL )
{
m_pFont->Release();
m_pFont = NULL;
}
if( !m_bSpriteDeleted && m_pSprite )
{
m_pSprite->Release();
m_bSpriteDeleted = true;
}
// DO NOT release the device, because the rest
// of the application might still be using it.
// The device DOES NOT belong to this class. It
// belongs to the base class (CMyApplication)
// and we just have a pointer to the device.
// so be careful with what you do with the device
// If you release teh device from over here
// then your application will probably crash on exit
// Incfact, Im going to get rid of the device
// pointer in the next app.
}
bool CDXFont::Begin()
{
// You *should* call this before drawing text, but you
// dont have to becayse the DrawText() function calls it,
// and End(), internally. But that would cost a performance
// hit if your calling *our* Print() function more then
// once per frame. By the way, we're calling the sprite iterface
// begin because the font interface is drawn using the sprite
// interface.
if( FAILED( m_pSprite->Begin(D3DXSPRITE_ALPHABLEND | D3DXSPRITE_SORT_TEXTURE ) ) )
return false;
return true;
}
void CDXFont::End()
{
// End the scene when you're finished drawing
m_pSprite->End();
}
// You must call this method between m_pD3DDevice->BeginScene() and
// m_pD3DDevice->EndScene() otherwise it will fail
bool CDXFont::Print( char* strText, int iXPos, int iYPos )
{
// Make sure the fnt interface is good
if( !m_pFont )
return FALSE;
// Now we have to declare a RECT structure and fill it, because that is what
// the DrawText() fuinction takes to know which area to draw teh text in. So
// we'll fill it in depending on teh x,y position that was specified during
// this function call
RECT box;
box.bottom = iYPos + 2000; // Make the rectangle wide enough to take up
// the whole screen
box.left = iXPos; // Text's X-Position
box.right = iXPos + 2000; // High enough for teh whole screen
box.top = iYPos; // Text's Y-Position
// So now all we do is call DrawText to get the text on screen
if(FAILED(m_pFont->DrawText(m_pSprite, // Pointer to the sprite interface we want to
// to use to draw the text
strText, // This is the text you want to print
-1, // This paarameter tells DirectX the length
// of our string. If we use -1, then DX will
// assume that it si a null terminated string
&box, // Address of our previously filled our
// RECT structure that tells DirectX which
// Area of eh screen to draw in.
DT_LEFT, // This param tells DirectX how the text is
// to be formatted. I have specified LEFT, so
// that te text stays on teh left. You can use
// CENTER or anything else. Check the docs for a
// full list of valid formats. Also you can
// add a parameter to this function to specify
// the format at run time. I have only chosen
// to specify, x, y coordinates and the actual
// string of text that you want printed
m_dwColor))) // Color of the text!!
return false;
return true;
}
void CDXFont::SetFontColor(DWORD dwColor)
{
// Simply set the color.
m_dwColor = dwColor;
}
bool CDXFont::Invalidate()
{
// This is easy just call this function and the
// font is invalidated. DX takes care of it
if( FAILED(m_pFont->OnLostDevice() ) )
return false;
return true;
}
bool CDXFont::Restore()
{
// Again DX handles everything for you by simply
// calling this one function
if( FAILED( m_pFont->OnResetDevice() ) )
return false;
return true;
}
bool CDXFont::RestoreFontSprite()
{
if(FAILED(m_pSprite->OnResetDevice()))
return false;
return true;
}
bool CDXFont::InvalidateFontSprite()
{
if(FAILED(m_pSprite->OnLostDevice()))
return false;
return true;
}
/*
**Drawing Fonts**
This is very simple and straight forward. Granted it's not the best way to
write text to the screen using DirectX, there are better ways. If you made a bitmap
with all the letters in it, then you can have a font class that draws a portion of
that bitmap on request. Your bitmap would look something like this
-------------------
|A|B|C|D|E|F|G|H|I|
-------------------
|J|K|L|M|N|O|P|Q|R|
-------------------
|S|T| etc...
So if you wanted to write "ALI" you would access the 1st, 12th, and 9th tiles of the
bitmap, and have them texture mapped to three squares made from a vertex buffer, then
you just DrawPrimitive the square, with using SetTexture(FontBitmapTexture).
That way would be better then using the D3DX interface, but also more of a hassle.
Using the d3dx font interface is VERY simple, so that's what we'll use, maybe some other
time Ill make a proper font engine.
*/
//////////////////////////////////////////////////////////////////////////////////////////////
// This file is copyright
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -