http://www.5178c.cn/article/6/2006/200605173892.html9 z4 K5 y# i) i0 z
2 |9 L4 t8 g3 q& U' H- C
在DirectX 9.0中渲染文字
$ I4 r, G5 G L3 w+ H* I. M作者:佚名 来源:不详 发布时间:2006-5-17 12:27:04 发布人:admin
) f; J: x9 q0 T3 c减小字体 增大字体 ' @% o( b! j+ ]+ n- C
4 a- F- f& |' ~* [4 e) ?
2 C; i. Y' r2 d( W$ ?) g( I
* f ~3 }' A( x1 b* n6 l
! X% Z3 |2 ?- [ F8 [$ @7 \+ s
* k) ?/ s4 O9 R& D/ K. k: I1 [
7 n) [5 N' }1 }+ z5 M- r9. 字体
' A3 B3 Y5 a& E7 i本文翻译自《Introduction to 3D Game Programming with DirectX 9.0》第九章“Fonts”,敬请斧正!XML:namespace prefix = o ns = "urn:schemas-microsoft-com:Office:office" />
) `9 `3 N# ~$ V% E4 u ?" Y" c9 Z4 G$ }; g
" j+ ?6 \9 N5 W3 @5 o
# `& z1 U! R! A$ y$ a- T* v# O+ E在游戏中,文字信息的显示是必不可少的。本章将讨论在D3D中使用的三种显示字体的方法。同样,这里只列出每种方法的演示程序的主体框架。学完本章将达到如下目标:
% }" @3 m5 y4 O& F O R; _ F% u& W
l 学习如何使用ID3DXFont接口渲染文字
# q! C* \ P; ~4 z2 _
- V+ s: _: P8 {* B4 J" _. Il 学习如何使用CD3DFont类渲染文字; d6 {/ A8 S/ U" d+ K. K. L% M7 b
. m, X ] U$ U" c5 m; Sl 学习计算游戏帧速度的方法
' ]) N7 m4 G* i0 Y. Y) ^+ }
4 Q% t% h9 a5 Y9 vl 学习使用D3DXCreateText函数创建3D文字
) n3 N/ u! f- Y7 p7 F0 C3 b' Q$ O8 `4 T, s$ _
9.1. ID3DXFont
6 B5 [; A) ^ s6 |9 g4 i要在D3D程序输出文字,使用D3DX库提供的ID3DXFont接口很方便。其实该接口是使用GDI实现的,所以,其执行效率有所降低,但是它可以很方便地处理复杂的字体和格式。
- V5 u8 a# i3 p$ @
: |: x/ h+ @6 w& p. E, x9.1.1. 创建一个ID3DXFont- }$ V; o/ k8 d0 `
可使用D3DXCreateFontIndirect函数创建ID3DXFont:
) g. G* y c# n* ^) a9 k! ~# U8 J7 g9 e; M& q L# \4 W6 }
HRESULT WINAPI D3DXCreateFontIndirect(( F& l# p1 ?7 _( y" _
& g+ n5 F, S5 _2 W4 q- M
LPDIRECT3DDEVICE9 pDevice,6 P6 u5 G' C# E+ Z
7 N4 K. N N2 d/ A0 P, y. p CONST D3DXFONT_DESC *pDesc,& Q1 [8 ?1 O& @9 p' z
) V7 R3 I- c8 r$ y+ y$ L2 j- x- ^ LPD3DXFONT *ppFont
3 k, R9 a+ U' Y' z% k. V7 l& L! s2 ^: `, p: }0 P
);/ S# E; ]( A- R5 S
+ _7 [6 D: x) u" U
, ~1 Q' Z+ I; F! ~) T7 J
译者注:我所使用的DirectX SDK是Microsoft DirectX 9.0 SDK Update (Summer 2004),也就是使用DirectX 9.0c的那个版本,在较早的版本里,该函数的原型有所不同:第二个参数为CONST LOGFONT *pLogFont,它是GDI中的结构。以后,如无特别说明,将以DirectX 9.0 SDK Update (Summer 2004)中声明的函数原型为准,特此声明!
( o1 u5 I1 O3 v+ C/ H1 o" N- U, p; G; c( `9 s3 d
使用这个函数时,需要一个D3DXFONT_DESC结构:. T8 C. x5 s+ P
8 W; `4 h6 G2 m# u# a5 k8 o
D3DXFONT_DESC d3dFont;
' @& q. M' N( j( N. t! r) [% @5 p
) P4 z6 x- F- `, bmemset(&d3dFont,0,sizeof(d3dFont));
+ q6 S4 \6 G: {& T/ H! Z! B# W; x
7 h. D# z) r F: K5 M6 Ud3dFont.Height=25; // in logical units( A1 n' v7 @* {- k& Q' n
2 a* ?) w6 `: p. td3dFont.Width=12; // in logical units
2 {, [4 U0 s( J3 l
) K8 P9 j9 M! u5 a- Fd3dFont.Weight=500;// boldness, range 0(light) - 1000(bold)4 @/ r2 G0 d- h( z" x6 o$ R/ ~) a5 j
6 m0 Y' ?0 ~/ q7 h/ D
d3dFont.Italic=FALSE;& y- T s/ `' n* J& F' K5 G
3 X- Q) R! M, z/ p
d3dFont.CharSet=DEFAULT_CHARSET;
; V5 s, {" R+ g$ x) T, i8 b3 v. J1 P/ K& m. A9 w, S
strcpy(d3dFont.FaceName,"Times New Roman");6 e( m4 D0 `3 g) ~' ?
' K% W$ A$ Y ]5 Q5 s" v
ID3DXFont* font=0;9 B6 ^3 g2 w8 n
9 _$ a( E. d% u* B6 k: l
D3DXCreateFontIndirect(Device,&d3dFont,&font);. D( H% E3 C. p0 @! U6 i
1 M6 e. l& G) G0 c' v2 e# l7 H# ]$ a, z! d8 ^1 I
如果你使用的是LOGFONT结构,则:
8 o" o5 Y! O1 o7 D7 A# H- x* z
1 f. g6 b' Y- |1 b$ RLOGFONT lf;: X. h& [ @2 l. g1 A; Z
4 n9 e3 n" y- F8 r% nZeroMemory(&lf, sizeof(LOGFONT));
: e# D- f% m" O3 c( E: y
0 Q: ]8 ~4 i! F8 t9 N4 s+ R" X3 blf.lfHeight = 25; // in logical units
' O2 Y* g" p1 d3 m, ^' x5 h0 e$ ~# e( t; c9 J5 S; M, b6 x
lf.lfWidth = 12; // in logical units
1 Z) `+ M8 @* `# n1 h; k. S/ g7 p8 b( T0 _
lf.lfWeight = 500; // boldness, range 0(light) - 1000(bold)
+ A3 y2 T8 y1 T4 i' v$ B9 t8 [0 ~
) {7 G8 n I; q9 \lf.lfItalic = false;
5 T$ H- v7 J" d4 d6 i0 M7 B% x! ?& `- d1 C
lf.lfUnderline = false;4 }& G3 ]9 T; a+ H( N! w6 j
( ^ c5 m! ^5 T! R6 U
lf.lfStrikeOut = false;! ]* y! R! `0 I$ C
3 N" ]5 z5 O c' g. k7 Rlf.lfCharSet = DEFAULT_CHARSET;
' @# k7 w6 |3 m( k, r% O& W }- Q2 J% C# i
strcpy(lf.lfFaceName, "Times New Roman"); // font style0 F$ C+ }1 @% a: n$ a9 `
n" {" }, @8 z3 c2 r- C# QID3DXFont* font = 0;5 p2 x, Q8 L* W: d& ~9 z& S
$ Y- j/ |% o5 }: TD3DXCreateFontIndirect(Device, &lf, &font);& R0 l- P2 R+ S6 b4 @
1 n" v. W% w( y* c! F- d X1 ~( L! _) _
另外,还可以使用D3DXCreateFont函数创建ID3DXFont的对象。2 Q; C5 e, l" j
' L, e( E, `( v: u
9.1.2. 绘制文字
5 O- h+ _0 V R! ~& A3 x9 [得到ID3DXFont接口后,绘制文字就很简单了,只需要调用ID3DXFont::DrawText方法:
$ c. I4 y1 E+ R# ?* }% _2 _8 d' f" N) ^. Y9 `( w
INT ID3DXFont::DrawText(/ g. E! S: v( I
% D0 s N3 V8 l. ^5 `1 A8 ^7 U7 P
LPD3DXSPRITE pSprite,8 D/ l j1 u6 ]7 v' _
/ @3 ^) o0 C" Y( Q5 e' s2 z LPCTSTR pString,
: C6 O; n: C6 z: u7 g4 w6 g: M9 }7 `
INT Count,5 ~5 `0 k1 K$ i! i$ B: Y
7 w; I1 ]0 w' }2 f
LPRECT pRect,' L' D# @4 G' q% p
6 t9 N" l; {7 j+ z# {2 Q DWORD Format,
6 i0 ^. l1 S. W6 G2 K; \" o& I* @0 x* ]: D
D3DCOLOR Color; H1 U8 p: j# ` ]9 Y
; S9 p! [8 i$ Z) q3 K+ g0 @);3 K8 z9 q3 |& K- g3 h
/ X: K1 c0 \/ ]' j5 c" i/ `
. u+ J3 f" d( R# E4 c' O1 {
l pSprite –输出目标,为ID3DXSprite对象指针,可以为NULL值,此时字符串输出到默认对象# ?. _/ V' \" g4 w) i: _( L
G. ~1 }& F! jl pString –需要输出的字符串' z' m! h/ m2 i
6 N; O* g7 o" a8 B" Z. F6 E
l Count –字符串的字符数,如果为-1,则以0字符为结束标志2 B e' j& l3 b/ D2 r1 n! E5 S
8 y l/ h$ E0 Il pRect –绘制字符串的区域
! P R& a. u1 M
$ [/ R6 T+ L1 g% n* v; Y$ p- gl Format –文字的输出格式$ A2 K5 y: I) C
4 F3 ?8 D2 W# u$ g7 @
l Color –文字颜色0 ^% v& `/ i4 v5 N
$ g4 H* u8 Q4 T q. [; C r/ z
例如,可以这样使用该方法:0 Q7 p8 ^; N" [4 `
, f( H" H1 w+ g/ a9 qFont->DrawText(NULL, Z4 n3 e- `2 v
5 o# u& F9 J9 I6 I& O1 U
"Hello World", // String to draw.
0 l7 z5 B8 p0 r" K' Y4 p% e5 `# C% s3 S+ j& N1 i* j2 o h! X
-1, // Null terminating string.
! z( @- o1 n1 h( ^3 _6 E6 v. a3 w
8 d- c9 p! P; [4 a. d0 t &rect, // Rectangle to draw the string in.
) T9 F- p; M8 f6 Q; T6 L
R7 W* o. X: Z& S9 ]+ l) Q) D DT_TOP | DT_LEFT, // Draw in top-left corner of rect.( L4 }, n5 s9 d. j& l9 g9 f" u
/ A8 z2 O, F" p! B2 V 0xff000000); // Black./ H( g5 P' u3 ~3 }
$ n% B& `. M9 ?4 [' i4 |
/ u7 X6 q5 ]/ l( \% }$ V, A8 {4 i9.1.3. 计算帧速率3 q( B8 y# B2 J
帧速率用FPS(Frame per Second)表示。首先声明三个全局变量:4 V: k+ M; n2 ^( t
* P% D+ f. n8 x/ O
DWORD FrameCnt; // The number of frames that have occurred.- U r3 I* C5 L( p0 K& P' c' d
, r4 ?7 q/ ]6 ~) {! p; y2 m- ` z
float TimeElapsed; // The time that has elapsed so far.
# h. E5 v1 x9 D+ h" d5 ~+ z; {% b# b1 ~: I) R! S
float FPS; // The frames rendered per second.! U2 P+ d: q/ q& ?9 V* r) {. ?
/ j/ p) p% a( h% W( f/ U1 L/ `
% X, f# l/ A# I+ X' I每秒计算一次FPS,这里计算的是平均值。我们也可以有足够的时间去读FPS值,而不至于因FPS的快速变化而产生较大误差。
( H% V, i; |: F, P. f8 Z1 A9 u, F( T& l
: `! b+ c2 C# I8 f2 ^每渲染一帧,累加一次帧数和所用的时间值:! E# v. C% J# f7 p. i2 T
9 j+ F( x3 N/ v Z; {! m5 B, d J/ W# TFrameCnt++;9 d0 T9 q' U7 P1 N5 W0 J6 p
' l1 A$ a: q/ m" E) L. |3 w3 LTimeElapsed += timeDelta;6 o) _0 F7 U( Q" P9 {: _) q
' O, g# x E; u" l% C7 @+ i* D" T
: D1 R# }) J) o T* B, H5 Y
这里的timeDelta表示两帧间的时间间隔。每过去一秒,就可以使用下面的公式计算FPS了:) _% B1 o$ ~0 f2 ?6 E+ ?# D
+ P0 K1 H/ {( F6 p7 w+ wFPS = (float)FrameCnt / TimeElapsed;
+ J& p6 _4 C2 o) R5 X* C6 H
* [5 a; o4 U& A
5 m/ U& S7 c) W# N P5 z计算完成后,需要将FrameCnt和TimeElapsed重新置0,这样下一次的计算结果才正确:4 H1 c$ M0 D ?- r
o2 m; L% ]3 _+ Y5 _/ ?void CalcFPS(float timeDelta)7 ?! ]0 ^7 c5 X* u
1 |; g& b7 l o6 x2 X! h6 ~; i( D{% b2 s0 S1 { W/ W/ p! P
/ V5 K. i- {! u% Z0 ` FrameCnt++;
! N8 S& A( I" V( O' K; l
7 g, Y M7 x. w% L. z2 r W2 T TimeElapsed += timeDelta;6 j9 N; Y$ w/ \0 A
1 K% L3 D2 W1 a; {; ]
if(TimeElapsed >= 1.0f)
& q% m6 F1 b0 i" j3 }/ W) S& o4 ` N; k
{& n6 A% E9 r; ^& ?) p$ l: b
J+ z6 L7 R( A" k FPS = (float)FrameCnt / TimeElapsed;, N2 k- G% g6 ~, u d9 r- T. N
' O- D5 ~4 S( _6 _- T9 |9 n1 v TimeElapsed = 0.0f;3 ?1 B+ u; p& f3 ^) U( E
' o# }7 n2 ?( y+ F0 z5 j! z6 F
FrameCnt = 0;
0 t. L( v7 W- [
$ g+ i# ~( L0 I, k3 X! l. x }
6 ^1 W3 h$ b( f' W5 V: U k+ x6 m- D' X+ @
}: b/ L- I' q) g Q- R/ D6 v$ x s* h
1 C% M! ]. X, i' [1 u$ y ^ Z- Q! ]2 Z4 V6 p9 V0 F: `6 V% `* U
9.2. CD3DFont
}/ i1 q" g8 L) k) |在DirectX SDK的安装目录下,提供了很多有用的代码CD3DFont类就位于其中。该类使用纹理三角形和Direct3D渲染文字,而不是通过GDI渲染,所以,其效率高于ID3DXFont。但是,CD3DFont不支持复杂的字体和文本格式,如果只需要高速渲染简单的字体,CD3DFont应是首选。
I1 }1 u0 t) O6 W w$ h5 f/ o( d- C5 f0 H- @" r/ Y- }& [
使用CD3DFont类时,需要加入以下源文件:d3dfont.h,d3dfont.cpp,d3dutil.h,d3dutil.cpp,dxutil.h,dxutil.cpp。这些文件可在DirectX SDK的安装目录下找到。在DirectX 9.0 SDK Update (Summer 2004)中,该类却消失了,所以,该节内容只适用于较早的DirectX 9.0 SDK版本!
9 \* C/ t; q! V4 V9 G8 R9 t. ?- ?5 o8 v1 R) U( n& P# I# W
9.2.1. 创建CD3DFont对象
# [% U* G$ h# A创建CD3DFont的对象,就像创建一个普通的C++对象一样,其构造函数如下:
) s& ~# }- Y/ ~! g) S3 A' a8 p: N% B- {* ]! W7 W, d `
CD3DFont(const TCHAR* strFontName, DWORD dwHeight, DWORD dwFlags=0L);
( K! Y. N, J& w2 @6 O 7 ?) N! j1 C S
: E2 L4 |: N/ A `% Tl strFontName –所使用的字体名称
- N7 R+ u; h' X z/ \* s
9 Y4 b3 o9 G/ P; R9 J8 i+ K9 R( L& Ul dwHeight –字体高度' ^* R7 ?) O* v" x% z
( i0 z$ U: o$ U2 K8 E
l dwFlags –可选的标志,如D3DFONT_BOLD、D3DFONT_ITALIC、D3DFONT_ZENABLE等。
, C6 s7 v F' N- z" x5 O$ P
4 j& o& c. d$ C- k) J) ~得到CD3DFont对象后,还需按顺序进行初始化,如:
8 f9 w5 L* G- |% B Y- r: J A* r, `; z1 I4 {
Font = new CD3DFont("Times New Roman", 16, 0); // instantiate" n& q. c L1 v( k( f
- w! O3 x( |7 O+ f" o7 g
Font->InitDeviceObjects( Device );
3 X& |/ s- M$ Z+ x" v3 L4 i2 P: a% t. ?! H
Font->RestoreDeviceObjects();
1 F" S( I% y( q9 _$ a6 } & I( D3 W' n7 b% R
/ b/ n1 u$ j: c- v+ ~ {4 ~3 Q1 L: q9.2.2. 绘制文字 A- v$ p' K6 }
使用CD3DFont对象的如下方法渲染文字:8 p- }& k1 r6 [7 L% a
) J1 s% {3 `$ N) f% k* Y. p
HRESULT CD3DFont::DrawText(FLOAT x, FLOAT y, DWORD dwColor,- r& x; p: {3 x. Y! r' [7 B( Y8 h4 m
/ ~' T+ s) K A3 L4 w! X# k const TCHAR* strText, DWORD dwFlags=0L);4 \; s8 \9 E) \2 ]4 p, ]
# K3 o/ [: D+ S: ~: i8 c
! E/ q% j; k- [0 T3 z5 m. ul x –屏幕的x坐标) c! i5 J; c6 E! f; ^
5 B$ O7 L& ]# m/ U7 al y –屏幕的y坐标9 j) Y/ O0 e5 p" c7 E9 ?
+ E" J. {. P" k- L7 Bl dwColor –文字的颜色
/ L& [' N* U/ |' B4 K; l
- y; K& l9 j$ O% e0 \: sl strText –要绘制的字符串
. M# Z* D M/ Y% m" T8 g' g
6 D; Q. \! T% f4 q- Xl dwFlags –可选的渲染标志,可为0或下面的值:D3DFONT_CENTERED、D3DFONT_TWOSIDED、D3DFONT_FILTERED。( V. m2 n* p5 I
2 Y4 G8 h% ?0 J* K% e* D7 T$ y+ J
例如:
4 }0 p! O5 [* e/ }4 d5 o( A& U& m: v1 U
Font->DrawText(20, 20, 0xff000000, “Hello, World”);6 X) Q" X, F3 H' K3 l1 { X
) L1 Q/ Y% K) Q3 e2 k8 P
* e" i5 _$ a6 b }: x. A/ A9.2.3. 资源清除
$ z: ]( `; Z6 m Z3 z在删除CD3DFont对象前,还需作一些清除的工作:; F6 w! F& s( Z5 C
/ h$ A4 g0 M! X5 g" K! YFont->InvalidateDeviceObjects();: O7 M7 N. V5 N; L% z" O
$ p1 s- j- o ]$ Y# k9 ~% n2 XFont->DeleteDeviceObjects();
4 t& j9 Y; Q! b N; n
6 e& a5 p$ y- o+ W' B0 V L, tdelete Font;3 K" _% U9 |& N7 O, o
5 g% l3 Q V+ ~9 q D7 |" k" t. p' w5 X1 Q
9.3. 函数D3DXCreateText
& x6 S4 _6 V1 |& Q/ V$ q8 X该函数用于创建3D文字Mesh,原型如下:
( V' ?! `8 `" U$ g! K' m
7 @* V% I7 R- G9 X5 YHRESULT WINAPI D3DXCreateText(/ [# W( A4 N( h2 ^& [9 C: K9 t
& o4 r: K- w5 Q7 i* m
LPDIRECT3DDEVICE9 pDevice,8 G9 d: D* P% {
, Z' Z B1 {# k/ J
HDC hDC,
6 v0 s2 `' i8 g1 m2 X8 W P' D7 @% \3 u9 c( l4 w% q8 y3 f8 ]9 d
LPCTSTR pText,/ U% o2 C8 Z9 N
% u! s) P" E0 { FLOAT Deviation,
7 P: T# [# _3 t: n. B0 }$ |2 {
FLOAT Extrusion,, v" _4 g, G' F/ h1 ~
' z; E/ n& a0 I' O3 o
LPD3DXMESH *ppMesh,# @) z7 u0 S8 F# r# l* f1 d
$ ?# i# V9 u5 U, `" m- }: ^3 E
LPD3DXBUFFER *ppAdjacency, r. I: l O- U5 v+ o% L
/ ?+ R" A0 P+ q) J LPGLYPHMETRICSFLOAT pGlyphMetrics: w; L% J5 @2 A- O4 c( S J. t
% [) E: }0 o7 ]+ {! d g
);
+ K k- o' v) [2 F1 H' V . U) m n$ n) E: ]
% P$ k3 A9 C1 w5 `6 p0 Nl pDevice –D3D设备
! A! d& c' c! r2 m( k0 R+ y- @% g4 P, G. m; I( z( E; h# J
l hDC –描述字体的设备上下文句柄- n6 L6 |5 K6 }7 D N0 |4 _: x
& ?. m" |8 c' ], t0 u nl pText –要渲染的字符串4 _! N( g: [" F7 u7 c2 T+ k# V7 G
}5 [3 @9 @* Q/ ?% E( Il Deviation –TrueType字体的一个属性,该值不能小于0。如果为0,则使用字体的默认值- C0 d z6 E1 M. c
7 J) v) C, M: K; B* D
l Extrusion –字体的深度,相对于Z坐标轴
8 x; |) @, H/ \7 b
/ W9 @' }1 a- Ml ppMesh –返回生成的Mesh对象指针
% V, j& @6 C. G/ |6 c6 t( W/ f$ x9 q( i* k) M) t8 M8 t5 U
l ppAdjacency –返回邻接信息。如果不需要该信息,可使用NULL指针; H9 A: f$ }! D6 g# K/ z
9 s, P; g3 X( `: U* yl pGlyphMetrics –结构GLYPHMETRICSFLOAT的数组,返回轮廓矩阵数据。如果不需要该数据,可以设该参数为NULL
, s0 p4 p$ w- j e, b, `
) y4 \' C: F1 n, E0 y6 E* n下面就举例说明如何使用该函数创建3D文字的Mesh对象。
X, }/ c( d, O& j& C
% C; c3 `9 R- p. U4 M/ j// Obtain a handle to a device context.; {( H' I- {- j0 u! |
4 }2 h# t( H% Z% y$ \1 i IHDC hdc = CreateCompatibleDC( 0 );# C3 T; v! C% g5 X. T) O. s
5 \( B) D1 E$ R+ X// Fill out a LOGFONT structure that describes the font’s properties.( Z+ d4 c: G9 A+ o0 J
& ~& @) o' H1 a+ XLOGFONT lf;+ @* C( B# W) I; {. S
+ e0 {6 F7 q. s* n, ?5 p$ M& r
ZeroMemory(&lf, sizeof(LOGFONT));. I" K$ E& x0 k7 D& }/ s
8 E) y% Z( r6 Z, D7 Jlf.lfHeight = 25; // in logical units: y2 {1 B1 k# W1 T4 @
3 ]# V B- o% l8 _5 O* |2 Llf.lfWidth = 12; // in logical units
) D7 {! ?0 Y }4 n% B: C8 z" Q* b
2 V! X+ U% P0 ~" ?& g5 N* Ulf.lfWeight = 500; // boldness, range 0(light) - 1000(bold)) z" g. a( O3 n! `( q( W
6 ]2 X# N# w+ ~* [) b% H% Tlf.lfItalic = false;2 _4 T7 T6 C& d$ w) d: a# n4 j
2 _2 j0 S! S; G+ w0 L, Slf.lfUnderline = false;
7 W/ t# l* ~" {2 r }! e8 v' v2 ]" i( `
lf.lfStrikeOut = false;
, o+ J) s6 f* T' Q2 v8 ]- t- h! C$ x8 e$ ^5 O4 \3 h
lf.lfCharSet = DEFAULT_CHARSET;& o& b+ a& q- z" a3 l
8 a" {6 h) j/ d9 m1 K3 [
strcpy(lf.lfFaceName, "Times New Roman"); // font style: D0 e" O: a1 R |4 Q0 ]
# h' e) f5 Q* }2 H" x* G// Create a font and select that font with the device context.3 W& S$ Y6 r$ i9 W0 f/ k7 k( \
5 W. i8 d& h. `$ `' i' {
HFONT hFont;) }# g5 _* F( |: A2 Y
/ \( W' z4 M8 ~; e2 t4 u9 r
HFONT hFontOld;+ P2 @1 l# A ]3 Z7 z. T: }$ |- |
, ]# i( v' Q0 `- c# J7 K9 w
hFont = CreateFontIndirect(&lf);, M# K$ m& K: S
j/ J9 C- o% _- @( i. w% n
hFontOld = (HFONT)SelectObject(hdc, hFont);
5 q1 ? P# i6 n4 b" o% y2 i: `/ Z7 c/ C- d- n, K) R1 D
// Create the 3D mesh of text.
7 T n9 ]( A7 X& O5 K1 r( K
R/ \% U/ K) x, o' k4 nID3DXMesh* Text = 0;
+ p7 |6 L& A& W& Y
1 d/ h& u" \, W6 {4 z- ^# F# f4 jD3DXCreateText(_device, hdc, "Direct3D", 0.001f, 0.4f, &Text, 0, 0);+ p* I! l9 A) C% H7 X
2 [! N8 d$ i) Z' D8 z! w// Reselect the old font, and free resources.
! w1 H$ S$ q$ L X+ G2 u! @ ^/ e# o, L" |1 o
SelectObject(hdc, hFontOld);+ B) w+ K6 l4 j M: e: p
8 [- s: x+ \* r9 NDeleteObject( hFont );
, p8 W8 k* Y& h. O5 ^
7 c/ b4 I4 ^: a& @5 g) E {6 w1 ]DeleteDC( hdc );7 p" m* q) K, L |+ M, l Q: `
2 Q- ^* t+ x) i# F( S7 ?' P5 C# h' M* k+ p
这时,Mesh对象已经得到了。最后,直接使用DrawSubset方法渲染即可:! S7 |4 |+ Z, _, `
, W% \1 x* A( dText->DrawSubset( 0 );
& x4 ?. y. W8 Y - G8 C4 i* r: k$ x- |" Z2 f/ E w
4 e/ Q6 ~9 Z& f1 b
译者注:上面的例子代码,使用的是较早的DirectX 9.0 SDK,不是Summer 2004版本。( i6 b9 U7 I) X2 p# r1 x
/ p& G" }' S. t( B& B# R9.4. 总结
5 n* J" a& p# w7 |( ql 如果需要渲染较复杂的字体和格式,使用ID3DXFont接口会很方便。但是该接口是使用GDI实现的,故效率较低。
! E1 O9 q! V2 Z( A! w! y
+ F* {# p9 F3 \/ Ol CD3DFont类可以快速的渲染简单的字体。该类实用D3D的纹理三角形渲染文字,故速度较ID3DXFont为快。/ O; _4 V2 o8 _, j7 b
2 w7 f- F0 m# u- t) J il 使用D3DXCreateText函数可以创建文字的3D网格模型。 |