Click here to Skip to main content
Licence CPOL
First Posted 23 Mar 2010
Views 11,825
Bookmarked 5 times

OpenGL String (printw)

By | 2 Apr 2010 | Technical Blog
Make drawing text in your OpenGL app as simple as calling printf
A Technical Blog article. View original blog here.[^]

There are many ways for displaying text in OpenGL. In this post, I'll use the glutBitmapCharacter function to draw characters, and then will extend it to a more generic function (printw), which will make drawing a string in OpenGL as simple as using printf.

First, I will start by defining the font to be used by the glutBitmapCharacter function. I will choose a 24-point proportional spaced Times Roman font as shown below:

//  A pointer to a font style..
//  Fonts supported by GLUT are: GLUT_BITMAP_8_BY_13,
//  GLUT_BITMAP_9_BY_15, GLUT_BITMAP_TIMES_ROMAN_10,
//  GLUT_BITMAP_TIMES_ROMAN_24, GLUT_BITMAP_HELVETICA_10,
//  GLUT_BITMAP_HELVETICA_12, and GLUT_BITMAP_HELVETICA_18.
GLvoid *font_style = GLUT_BITMAP_TIMES_ROMAN_24;

To draw a character, simply define the raster position using glRasterPos3f (x, y, z), then draw it using glutBitmapCharacter(font_style, character). To extend this to drawing a string at certain coordinates, loop over each character in the string and draw it with glutBitmapCharacter. The additional logic that goes below is in making this as pretty as printf.

This can be done by using C’s va_list type, which is C’s approach to defining functions with variables number of arguments.

  • In the function prototype, place ellipsis (…) as the last argument
  • Define a variable argument list: va_list args;
  • Call va_start on the args list and the first real argument in the function prototype preceding the ellipsis: va_start(args, format);
  • Use _vscprintf to get the number of characters that would be generated if the string pointed to by the list of arguments was printed using the specified format
  • Allocate memory for a string with the specified number of characters
  • Call vsprintf_s to build the string we want from the list of arguments
  • Call va_end to end the use of the variables argument list
  • Draw our beautified string
  • Free allocated memory

Function implementation with full comments are shown below:

//-------------------------------------------------------------------------
//  Draws a string at the specified coordinates.
//-------------------------------------------------------------------------
void printw (float x, float y, float z, char* format, ...)
{
    va_list args;   //  Variable argument list
    int len;        // String length
    int i;          //  Iterator
    char * text;    // Text

    //  Initialize a variable argument list
    va_start(args, format);

    //  Return the number of characters in the string referenced the list of arguments.
    // _vscprintf doesn't count terminating '\0' (that's why +1)
    len = _vscprintf(format, args) + 1;

    //  Allocate memory for a string of the specified size
    text = malloc(len * sizeof(char));

    //  Write formatted output using a pointer to the list of arguments
    vsprintf_s(text, len, format, args);

    //  End using variable argument list
    va_end(args);

    //  Specify the raster position for pixel operations.
    glRasterPos3f (x, y, z);

    //  Draw the characters one by one
    for (i = 0; text[i] != '\0'; i++)
        glutBitmapCharacter(font_style, text[i]);

    //  Free the allocated memory for the string
    free(text);
}

Now that printw is defined, using it is similar to printf:

printf(         "char: %c, decimal: %d, float: %f, 
		string: %s", 'X', 1618, 1.618, "text");
printw(x, y, z, "char: %c, decimal: %d, float: %f, 
		string: %s", 'X', 1618, 1.618, "text");

Libraries to include before copying the function are: ;)

#include <stdio.h>    //  Standard Input\Output C Library
#include <stdarg.h>   //  To use functions with variables arguments
#include <stdlib.h>   //  for malloc
#include <gl/glut.h>  //  Include GLUT, OpenGL, and GLU libraries

Here is a sample source code that contains the printw function. If you have any issues compiling or running the app, check out this section for details about compiling and running an OpenGL app that uses the GLUT library. Below is a screen shot of the demo app:


Filed under: C, OpenGL Tagged: glRasterPos, glutBitmapCharacter, GLUT_BITMAP_HELVETICA, GLUT_BITMAP_TIMES_ROMAN, OpenGL string, OpenGL Text, printw, va_end, va_list, va_start, vsprintf_s, _vscprintf

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)

About the Author

Ali BaderEddin

Software Developer
Microsoft
United States United States

Member

http://mycodelog.com/about/

Sign Up to vote   Poor Excellent
Add a reason or comment to your vote: x
Votes of 3 or less require a comment

Comments and Discussions

 
You must Sign In to use this message board. (secure sign-in)
 
Search this forum  
 FAQ
    Noise  Layout  Per page   
  Refresh
JokeWon't you... PinmemberTim Craig13:52 25 Mar '10  
GeneralRe: Won't you... PinmemberAli BaderEddin15:16 25 Mar '10  
GeneralRe: Won't you... PinmemberW. Kleinschmit0:41 30 Mar '10  
GeneralRe: Won't you... PinmemberTim Craig7:45 30 Mar '10  

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Rant Rant    Admin Admin   

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.

Permalink | Advertise | Privacy | Mobile
Web02 | 2.5.120517.1 | Last Updated 3 Apr 2010
Article Copyright 2010 by Ali BaderEddin
Everything else Copyright © CodeProject, 1999-2012
Terms of Use
Layout: fixed | fluid