Slick-Util Library - Part 3 - TrueType Fonts for LWJGL

Introduction

Loading Images for LWJGL - Part 1

Loading Sounds for LWJGL - Part 2

TrueType Fonts for LWJGL - Part 3

NOTES:

TrueTypeFont is marked as "deprecated" as Slick2D now uses UnicodeFont for TTF formats. You can continue to use TrueTypeFont, or you can pull Slick2D and grab its UnicodeFont support.

When to use Bitmap Fonts vs. Unicode Fonts

Most games do not require a complex set of infinitely-scalable font glyphs -- and therefore the extra performance/memory costs of using TTF fonts may be unnecessary. Most graphical libraries (such as Slick2D and TWL) have support for bitmap fonts, and generally speaking you will be much better off using simple bitmap fonts than trying to load TTF fonts. With that said, if you need dynamic sizing, or proper unicode support, the TrueTypeFont/UnicodeFont class are acceptable solutions.

Why is a Library needed for Fonts?

OpenGL has no built-in support for fonts. In order to display fonts you will need to manually implement such support. It can be pretty tricky to implements fonts correctly especially as there are many different ways and techniques to do this in OpenGL. Using bitmaps to display fonts in OpenGL is probably the most popular method.

True Type Font Format

The True Type Font Format (.ttf) is the most widely used format to store and share fonts. There are tons of sites out there which supply fonts in this format for free, e.g.:

www.dafont.com

www.1001freefonts.com

www.urbanfonts.com

Basics

Slick-Util uses Java's built in AWT Font support to load the fonts, so be sure to be familar with the AWT's Font class. You can use either the default built in java fonts or load external ttf files.

The Slick-Util library will convert the AWT Font so that it can be used with OpenGL. The fonts are stored and drawn through slick's TrueTypeFont class.

To load a True Type Font you simply do the following:

 TrueTypeFont font; TrueTypeFont font2;

public void init { // load a default java font Font awtFont = new Font("Times New Roman", Font.BOLD, 24); font = new TrueTypeFont(awtFont, false); // load font from a .ttf file try { InputStream inputStream	= ResourceLoader.getResourceAsStream("myfont.ttf"); Font awtFont2 = Font.createFont(Font.TRUETYPE_FONT, inputStream); awtFont2 = awtFont2.deriveFont(24f); // set font size font2 = new TrueTypeFont(awtFont2, false); } catch (Exception e) { e.printStackTrace; }	}

and its equally simple to render them onto the screen.

 public void render { font.drawString(100, 50, "THE LIGHTWEIGHT JAVA GAMES LIBRARY", Color.yellow); font2.drawString(100, 100, "NICE LOOKING FONTS!", Color.green); }

Below is a full working example on how to use the ttf fonts with LWJGL using slick-util.

 import java.awt.Font; import java.io.InputStream;

import org.lwjgl.LWJGLException; import org.lwjgl.opengl.Display; import org.lwjgl.opengl.DisplayMode; import org.lwjgl.opengl.GL11;

import org.newdawn.slick.Color; import org.newdawn.slick.TrueTypeFont; import org.newdawn.slick.util.ResourceLoader; public class FontExample { /** The fonts to draw to the screen */ private TrueTypeFont font; private TrueTypeFont font2; /** Boolean flag on whether AntiAliasing is enabled or not */ private boolean antiAlias = true; /**	 * Start the test */	public void start { initGL(800,600); init; while (true) { GL11.glClear(GL11.GL_COLOR_BUFFER_BIT); render; Display.update; Display.sync(100); if (Display.isCloseRequested) { Display.destroy; System.exit(0); }		}	}	/**	 * Initialise the GL display * 	 * @param width The width of the display * @param height The height of the display */	private void initGL(int width, int height) { try { Display.setDisplayMode(new DisplayMode(width,height)); Display.create; Display.setVSyncEnabled(true); } catch (LWJGLException e) { e.printStackTrace; System.exit(0); }		GL11.glEnable(GL11.GL_TEXTURE_2D); GL11.glShadeModel(GL11.GL_SMOOTH); GL11.glDisable(GL11.GL_DEPTH_TEST); GL11.glDisable(GL11.GL_LIGHTING); GL11.glClearColor(0.0f, 0.0f, 0.0f, 0.0f); GL11.glClearDepth(1); GL11.glEnable(GL11.GL_BLEND); GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA); GL11.glViewport(0,0,width,height); GL11.glMatrixMode(GL11.GL_MODELVIEW); GL11.glMatrixMode(GL11.GL_PROJECTION); GL11.glLoadIdentity; GL11.glOrtho(0, width, height, 0, 1, -1); GL11.glMatrixMode(GL11.GL_MODELVIEW); }	/**	 * Initialise resources */	public void init { // load a default java font Font awtFont = new Font("Times New Roman", Font.BOLD, 24); font = new TrueTypeFont(awtFont, antiAlias); // load font from file try { InputStream inputStream	= ResourceLoader.getResourceAsStream("myfont.ttf"); Font awtFont2 = Font.createFont(Font.TRUETYPE_FONT, inputStream); awtFont2 = awtFont2.deriveFont(24f); // set font size font2 = new TrueTypeFont(awtFont2, antiAlias); } catch (Exception e) { e.printStackTrace; }	}	/**	 * Game loop render */	public void render { Color.white.bind; font.drawString(100, 50, "THE LIGHTWEIGHT JAVA GAMES LIBRARY", Color.yellow); font2.drawString(100, 100, "NICE LOOKING FONTS!", Color.green); }	/**	 * Main method */	public static void main(String[] argv) { FontExample fontExample = new FontExample; fontExample.start; } }

You should get an output similar to the image below.



Introduction

Loading Images for LWJGL - Part 1

Loading Sounds for LWJGL - Part 2

TrueType Fonts for LWJGL - Part 3

Credit

Tutorial Credit - Ninja Cave

Kevin Glass for writing the Slick Library and initial example code.