Question about bitmap font


Curious to know how to calculate the width of a text (single-line text) in bitmap font?

Accumulating xAdvance of all letters?


Accumulating xAdvance + xOffset of all letters?

or another way?

next question, if we have xOffset and xAdvance of characters how do we find the x position of the next character? (In both left-to-right and right-to-left fonts)

Thanks in advance!

The way the code does it now.

I’d have to reread the code and all of the comments I left in it to answer this. At one time, I went through a fairly extensive process of rendering annotated bitmap texts and annotated Swing text and compared them… then I left comments in the code about why things are the way they are.

The biggest thing you left out in your question was kerning, by the way. You need to know that for ‘next character’.

Have you used Swing FontMetrics before or similar? Without familiarity with standard font terms then this could be a very long conversation. There are various parameters that relate a character’s ‘position’ to its extents to its ‘next position’. And while angelcode font and JME’s implementation use different terms for these sometimes, most of the important bits are represented.

1 Like


I have no idea what is kerning. I need to read about it.

Nope. I will take a look at it.

So far JME BitmapText caused lots of confusion to me. So I am more about to understand it from somewhere else than JME :wink:

Note: it can also be helpful to look at images of the letter with its letter quad edges showing and then look at the line in the fnt file to understand what the different numbers are saying. Even if you don’t take the time to write an app to visualize that stuff, a mental picture can be formed sometimes just by looking at the numbers.

Edit: fonts are one of those computer science topics that always seem like “this should be easy” and then turns out to be a lot more complicated than expected. Similar to things like time/date handling (so much trouble), color spaces, etc… (In the GIS world, datum-conversion is my favorite to point to because so many pros get it wrong, too.) So be patient with yourself as you try to figure it out.

1 Like

I read about kerning. Suppose kerning is 0 for all characters. By this assumption can we still tell which one is correct for calculating the line width?

The one the code is doing.

It would be maybe more productive if you ask questions about the code that seems to break your understanding.

JME uses the first one I believe. Only accumulating xAdvances.


so far so good!

The below part is where I do not understand

why xOffset is used only for the first character and not all characters?

Because of why the comment says. But this is what I was talking about as the difference between letter quad and letter position, etc…

Basically, the letter quads overlap. The first letter sticks out to the left of the text position. So if you want to know the text width then you have to include that bit.

What’s fun is to create a visualization where you put a marker at each character position and render the outlines of the quads of the letters. Things become much clearer, I think.

Hmm, I thought they overlap only when the offset is negative. Do they overlap even if the offset is positive?

Also this line

Isn’t xAdvance meant to be a fixed amount?

The comment says exactly why.

Since x0 will have offset baked into it then we

              // need to counteract that in xAdvance.  This is better

              // than removing it in getNextX() because we also need

              // to take kerning into account below... which will also

              // get baked in.

              // Without this, getNextX() will return values too far to

              // the left, for example.

I’m not sure how to state the differently. If you look even a few lines above you will see that xAdvance is reset to this letter’s advance before these lines happen. So each letter sets xAdvance and then we adjust it based on where the real next letter should go.

If you want to know where the next x is and are going to add xAdvance then you need to subtract the offset from xAdvance because the current x already includes that. But now I’m just restating the comment in different words.

Write a visualization or step through the debugger… else probably we can play the “me restating the comments I already wrote” a few times. I don’t mind but I feel like you will find this even more tedious than I do.

Edit: perhaps it’s important to remember the x0 is not the “text position” from a user’s perspective but the actual x position of the letter quad… which may extend left of the “text position”.

1 Like

I see. I think this clears my misunderstanding a bit. Actually I was thinking the correct way is to add the xadvance (the same value that we read from the font file) to the current x0 position no matter if we have offsetted it or not.

Thanks for your help and patience :slightly_smiling_face:

xAdvance says how to get from this text position to the next text position. Text position is not the same as x0.

1 Like