Font Rendering
10. Font Rendering
• OpenGL
OpenGl provides no font rendering capabilities
In general font rendering is window system dependent
♦ Windows
Under windows, fonts are rendered using wgl
commands
Commands include:
- wglUseFontBitmaps
- wglUseFontOutlines
♦ X Windows
Under unix, fonts are rendered using glX commands
Commands include:
- glXUseXFont
E.R. Bachmann & P.L. McDowell
MV 4202 Page 1 of 16
Font Rendering
Individual character images are referred to as glyphs
There are two basic types of fonts:
- bitmap
- stroke or true type
♦ Bitmap Characters
9 x 9 bitmap of the letter ’A’
E.R. Bachmann & P.L. McDowell
MV 4202 Page 2 of 16
Font Rendering
Bitmap characters are single-color images containing
a representation of the character
- Can be rendered quickly
- Fixed size defined in pixels
- Not suited for rendering rotated, scaled or
projected text
- Should be used when size of text relative to
viewpoint does not matter
- Text will be readable regardless of viewpoint or
orientation
♦ Stroke (True Type) Fonts
True type fonts are composed of glyphs drawn using
quadratic B-spline curves
- Can be used to draw 3D characters in the image
- Have a geometric representation unlike bitmap
fonts
- Can be rotated, scaled and projected in 3D
- Can be combined into a 3D scene
- Slower to render than bitmap glyphs
- True Type font characters may be transformed
using glTranslate*( ), glScale*( ) and glRotate*( )
- May be texture-mapped
E.R. Bachmann & P.L. McDowell
MV 4202 Page 3 of 16
Font Rendering
• Rendering Windows Fonts in OpenGL
Fonts are handled by generating an individual display
list for each character in either a bitmap or a true type
font
Steps for generating a display list of a particular font
under Windows:
1. Select the desired font characteristics
2. Select and then generate the font, using the current
DC
3. Call one of the two wgl functions to automatically
generate a sequential display list for each glyph in
the font
4. Deselect the font from the DC
E.R. Bachmann & P.L. McDowell
MV 4202 Page 4 of 16
Font Rendering
• Bitmap Fonts Under Windows
wglUseFontBitmaps() is uesed to create a set of bitmap
display lists for a specific font name
BOOL wglUseFontBitmaps(HDC hdc,
DWORD first,
DWORD count,
DWORD listBase);
where
- hdc is the device context whose font will be used
- first is the first of a run of glyphs to be turned into
bitmap display lists
- count is number of glyphs to turn into bitmap
display lists
- listBase specifies the starting display list
E.R. Bachmann & P.L. McDowell
MV 4202 Page 5 of 16
Font Rendering
Example 10.1
Creating bitmap glyph display lists
void CBitMapFont::init(CDC* m_pDC, int size,
char* fontname)
{
// Generate font display list
flatTextBase = glGenLists( 256 );
CFont* oldfont; // Pointer to old font object
if ( NULL != fontname ) {
// Create a temporary GDI font object
CFont newfont;
LOGFONT logfont;
// Specify the font height, in logical units
logfont.lfHeight
= -size;
// Average width, in logical units
logfont.lfWidth
= 0;
// angle, in tenths of degrees,
// of each line of text
logfont.lfEscapement = 0;
//Angle, in tenths of degrees,
// of each character's base line
logfont.lfOrientation = logfont.lfEscapement;
// Specifies the weight of the font
logfont.lfWeight
= FW_NORMAL;
// Specifies an italic font if set to TRUE
logfont.lfItalic
= FALSE;
E.R. Bachmann & P.L. McDowell
MV 4202 Page 6 of 16
Font Rendering
// Specifies an underlined font if set to TRUE.
logfont.lfUnderline = FALSE;
// Specifies a strikeout font if set to TRUE.
logfont.lfStrikeOut = FALSE;
// Specifies an ansi character set.
logfont.lfCharSet = ANSI_CHARSET;
// Specifies the output precision
logfont.lfOutPrecision = OUT_DEFAULT_PRECIS;
// Specifies the clipping precision.
logfont.lfClipPrecision = CLIP_DEFAULT_PRECIS;
// Specifies the output quality
logfont.lfQuality = DEFAULT_QUALITY;
// Specifies the pitch and family of the font.
logfont.lfPitchAndFamily =
FF_DONTCARE|DEFAULT_PITCH;
// Specify the typeface name of the font
lstrcpy ( logfont.lfFaceName, fontname );
// Create the requested font
newfont.CreateFontIndirect( &logfont );
// Select the font into the DC
oldfont = m_pDC->SelectObject( &newfont );
}
else {
// make the system font the device context's
// selected font
oldfont = (CFont*)m_pDC->
SelectStockObject( SYSTEM_FONT );
}
E.R. Bachmann & P.L. McDowell
MV 4202 Page 7 of 16
Font Rendering
// Create a set of display lists based on the
// glyphs of the font
if (FALSE == wglUseFontBitmaps( m_pDC->m_hDC,
0, 256, flatTextBase )){
glDeleteLists( flatTextBase, 256 );
flatTextBase
= 0;
}
else {
// Restore the old font to the DC
m_pDC->SelectObject( oldfont );
}
} // end CBitMapFont::init
E.R. Bachmann & P.L. McDowell
MV 4202 Page 8 of 16
Font Rendering
Bitmaps are drawn in terms of raster position
Positioned using glRasterPos*( )
void glRasterPos{234}{sifd}( TYPE x, TYPE y, TYPE z, TYPE w );
Sets the current raster position
- x, y, z, and w specify the coordinates of the raster
- Raster coordinates are transformed in the same
way as coordinates supplied by glVertex*( )
- Drawing at a raster position will occur after all
transformations are complete
- Only the position is transformed
- Text will be displayed starting at the current raster
position
- The current raster position is updated after each
bitmap
- If the initial raster position is outside the view
volume, none of the text will be displayed
To render text in a fixed window position:
- Push a 2D orthographic projection transformation
matrix onto the stack
- Set the raster position
- Call the appropriate display lists
E.R. Bachmann & P.L. McDowell
MV 4202 Page 9 of 16
Font Rendering
Example 10.2
Render bitmap fonts in a fixed window position
// Output bitmap text to a specified screen position
void CBitMapFont::screenTextOutput(int x, int y,
int winX, int winY, const char* const textstring)
{
GLboolean lightFlag = glIsEnabled(GL_LIGHTING);
// Store lighting mode
// Turn lighting off for bitmap text
if (lightFlag == GL_TRUE) {
glDisable(GL_LIGHTING);
}
// Set up 2D orthographic projection
glMatrixMode(GL_PROJECTION);
glPushMatrix();
glLoadIdentity();
gluOrtho2D(0.0, winX, 0.0, winY);
glMatrixMode(GL_MODELVIEW);
glPushMatrix();
glLoadIdentity();
// Set position for first letter of string
glRasterPos2i(x, y);
// Output the text
renderText(textstring);
// Restore the modelview and projection matices
glPopMatrix();
glMatrixMode(GL_PROJECTION);
glPopMatrix();
glMatrixMode(GL_MODELVIEW);
// Restore the lighting mode
if (lightFlag == GL_TRUE) {
glEnable(GL_LIGHTING); // Turn Lighting on
}
} // end CBitMapFont::screenTextOutput
E.R. Bachmann & P.L. McDowell
MV 4202 Page 10 of 16
Font Rendering
//Output text in the specified font at the current
// raster position
void CBitMapFont::renderText(const char * const
textstring)
{
// Check for valid font and string
if (0 == textstring ) {
return;
}
GLsizei size = strlen( textstring );
// Set display list base
glListBase( flatTextBase );
// Output the display lists for each character
glCallLists( size, GL_UNSIGNED_BYTE,
(const GLvoid*)textstring );
} // end CBitMapFont::renderText
E.R. Bachmann & P.L. McDowell
MV 4202 Page 11 of 16
Font Rendering
• True Type Fonts Under Windows
wglUseFontOutlines() creates polygon or line based
display lists for 3D characters based on a True Type font
BOOL wglUseFontOutlines(
HDC hdc,
DWORD first,
DWORD count,
DWORD listBase,
FLOAT deviation,
FLOAT extrusion,
int format,
LPGLYPHMETRICSFLOAT lpgmf );
where
- hdc is the device context of the font
- first is the first glyph to be turned into a display list
- count is the number of glyph display lists
- listBase is the starting display list
- deviation of the generated primitive from the
design outline of the font (equal to or greater than
zero)
- extrusion is the amount the font is extruded in the
negative z direction
- format to use in display lists; either
WGL_FONT_LINES or WGL_FONT_POLYGONS
E.R. Bachmann & P.L. McDowell
MV 4202 Page 12 of 16
Font Rendering
- lpgmf points to an array of structures that receive
the metrics of the glyphs. When lpgmf is NULL, no
glyph metrics are returned.
Example 10.3
Creating display list and rendering with a true type
font
void C3DFont::init(CDC* m_pDC, int size,
char* fontname, float extrude)
{
// Generate font display list
textBase = glGenLists(256);
// Create a temporary GDI font object
CFont newfont;
// Pointer to old font object
CFont* oldfont;
// structure defining the attributes of a font.
LOGFONT
logfont;
// lfHeight can't be used to change the font size
// Specifies the height, in logical units, of
// the font. Use glScale to change size
logfont.lfHeight
= -size;
// Average width, in logical units
logfont.lfWidth
= 0;
// angle, in tenths of degrees,
// of each line of text
logfont.lfEscapement = 0;
//Angle, in tenths of degrees, of each
// character's base line
logfont.lfOrientation = logfont.lfEscapement;
E.R. Bachmann & P.L. McDowell
MV 4202 Page 13 of 16
Font Rendering
// Specifies the weight of the font, in the
// range 0 through 1000
logfont.lfWeight
= FW_NORMAL;
// Specifies an italic font if set to TRUE
logfont.lfItalic
= FALSE;
// Specifies an underlined font if set to TRUE.
logfont.lfUnderline = FALSE;
// Specifies a strikeout font if set to TRUE.
logfont.lfStrikeOut = FALSE;
// Specifies an ansi character set.
logfont.lfCharSet = ANSI_CHARSET;
// Specifies the output precision
logfont.lfOutPrecision = OUT_TT_ONLY_PRECIS;
// Specifies the clipping precision.
logfont.lfClipPrecision = CLIP_DEFAULT_PRECIS;
// Specifies the output quality
logfont.lfQuality = DEFAULT_QUALITY;
// Specifies the pitch and family of the font.
logfont.lfPitchAndFamily =
FF_DONTCARE|DEFAULT_PITCH;
// Specify the typeface name of the font
lstrcpy ( logfont.lfFaceName, fontname );
// Create the requested font
newfont.CreateFontIndirect( &logfont );
// Select the font into the DC
oldfont = m_pDC->SelectObject( &newfont );
E.R. Bachmann & P.L. McDowell
MV 4202 Page 14 of 16
Font Rendering
//
//
//
//
//
//
if
Create a set of display lists based on the
glyphs of the TrueType font. Notice that we
really waste the first 32 spaces....
if there's a problem delete the display lists
Note that this single call takes MOST of the
initialization time for the COpenGLView class
( FALSE == wglUseFontOutlines( m_pDC->m_hDC,
0, 256, textBase, 0.0f,
extrude, WGL_FONT_POLYGONS, NULL) ) {
glDeleteLists( textBase, 256 );
textBase = 0;
}
// Restore the old font to the DC
m_pDC->SelectObject( oldfont );
} // end C3DFont::init
E.R. Bachmann & P.L. McDowell
MV 4202 Page 15 of 16
Font Rendering
//Output 3D text in the specified font
void C3DFont::renderText(const char * const
textstring)
{
GLint frontFace;
// save polygon front face mode
glGetIntegerv(GL_FRONT_FACE, &frontFace);
// Check for valid font and string
if (0 == textstring ) {
return;
}
GLsizei size = strlen( textstring );
glListBase( textBase ); // Set display list base
// Output the display lists for each character
glCallLists( size, GL_UNSIGNED_BYTE,
(const GLvoid*)textstring );
// Restore the polygon front face mode
if (frontFace == GL_CCW) {
glFrontFace(GL_CCW);
}
else {
glFrontFace(GL_CW);
}
} // end C3DFont::renderText
E.R. Bachmann & P.L. McDowell
MV 4202 Page 16 of 16
© Copyright 2026 Paperzz