• Welcome to Final Fantasy Hacktics. Please login or sign up.
 

How to create and export bitmap fonts for Panda3d

Started by Kivutar, October 08, 2011, 01:09:25 pm

Kivutar

October 08, 2011, 01:09:25 pm Last Edit: October 08, 2011, 02:11:21 pm by Kivutar
This is a tutorial about font making for Tethical.

For this, we'll take as exemple the fonts used to display the cursor's height during the battle (called fftcoords):

1) Screenshots

The first step is to take a lot of screenshot from FFT. Use an emulator with no aliasing, with a 320x240 or 256x240 resolution.

2) Analyse!

Put all the characters in a single bitmap file, and start to analyse them.

What is the best height to use? Align the characters as you want to display them in game, and look at the top and bottom pixels.
Our fftcoords uses a 32 px height (don't have to be power of two).

What width to use for each character?
This an vary a lot. You must also take care of this in the 3rd question:

How much pixels are used to space the characters? This setting can change for each character! You can also use negative margins to fix some special cases
Our fftcoords was a real nightmare for spacing. It uses negative margins, but the emulation is still not complete. However, normal people won't be able to notice it, so no problem.

Which alignment do you need for the words that will result from the combination of the characters, left, right, both?
fftcoords will be used to display right aligned words of the form "12.5h" only. The "h" must not move. This may lead you to use left margins instead of right margins.

What characters are available in this font? What special characters? How will you handle it in your code?
This font have a special character: there is two "5", and one is smaller than the others characters.
There I had to choose beetween ["1","2","3","4","5","6","7","8","9",".5","h"] and ["1","2","3","4","5","6","7","8","9",".","h"] where ".5" is a special character used instead of "a".
I choose the first solution because it was easier to code. I just have to write "12ah" to display "12.5h" with the small "5".

3) Fontforge

The software I use to modelize the font is called Fontforge and is free and opensource. It uses SFD as internal format, and you can find some .sfd in the font folder of Tethical's client to get started.
Yes Fontforge is ugly, but very complete.

So let's open our FFTCoordinates.sfd and see what it look like:



The cells with a red cross are disabled cells. The others are for used characters. You can note the A is used (for the .5 special char).

Click on a cell to open the character editor. You may be surprised to discover that I did not draw the real character in Fontforge. It is because Fontforge (and almost all known font formats) does not handle more than one color for the pixel fonts. So all this Fontforge step will be only usefull to setup the height, widths, and margins of our characters.

Once in the character editor, you can type CTRL+SHIFT+L to set the "case", which means the width of the current character.
You can increment the case to create a positive margin. Let's say that all our characters will have one more pixel on the same side to be displayed spaced.
You can draw outside the case border to fake a negative margin.

4) Exporting to BDF

BDF is a pixel font format. Fontforge can export to BDF. And Panda3d egg_mkfont utility can import BDF.

In Fontforge main window, type CTRL+SHIFT+G to generate the font. A setting popup will appear. Choose BDF for the pixel format, no vectorial formats, and set 12 for the size of the font, this is arbitrary number, but remember it because we will pass it to egg_mkfont in a later step.

You don't have to change the name of the font with the *. You will obtain a FFTCoordinates-12.bdf file.

Note that you can open back this bdf with Fontforge. Almost no data is lost. You could even stop using your SFD file after this step.

5) BDF to EGG

Panda likes eggs. It also supplies an small utility called egg-mkfont to convert fonts to egg+png. If you open the already existing fftcoords.egg, you will find this comment in the first line:

egg-mkfont -noaa -sf 1 -o fftcoords.egg FFTCoordinates-12.bdf -ps 20 -ppu 12

This is the command line I used to export the font.
-noaa means no anti aliasing
-sf 1, I don't remember
-ps 20, I don't remember
-ppu 12, 12 pixel per unit, our arbitrary number

You will obtain two files, fftcoords.egg and fftcoords_1.png.

Note: since I updated my Panda on Arch Linux, I can no more pass this step. I get this error:
:pnmtext(warning): Unable to set  to 10pt at 432 dpi.

6) Fix your egg

Open you egg with a text editor, and use search and replace to make your texture use the following options:

<Texture> fftcoords104 {
 fftcoords_1.png
 <Scalar> minfilter { nearest }
 <Scalar> magfilter { nearest }
 <Scalar> anisotropic-degree { 0 }
 <Scalar> quality-level { best }
 <Transform> {
   <Matrix3> {
     0.140625 0 0
     0 0.28125 0
     0.664062 0.460938 1
   }
 }
}


I changed the filters, and removed another thing that was locking colors.

Note: egg-mkfont may have some new options to automatise this step.

7) Fix your png

Open your PNG with an image editor. Change the mode to RGB. Add an alpha chanel. Remove all this black and white, and paste the characters from you screenshots in the right places.

8) Test your font in Panda

Using this script:

from Config import *
from direct.directbase.DirectStart import *
from pandac.PandaModules import *
import GUI

v = 1.0/120.0
scale = 2*12.0/240.0
coordsfont = loader.loadFont(GAME+'/fonts/fftcoords')

GUI.Test('test_menu2')

coordstn = TextNode('tn')
coordstn.setFont(coordsfont)
coordstn.setAlign(coordstn.ARight)
coordstn.setTextColor(1,1,1,1)
tnp = aspect2d.attachNewNode(coordstn)
tnp.setScale(scale)
tnp.setPos(v*112, 0, v*66)
coordstn.setText('23ah')

run()
Tethical, an online FFT clone