1

I'm creating a game in libGDX. I want to create some UI elements (buttons and stuff), because of my app design, I would like to draw them in the world space, as other game objects.

I'm using Freetype generator that generates a bitmap font from true type font files(.ttf). The problem is that the dimension of the font is in pixels.

Orthographic camera that I use to to render the world, has viewport size of approximately 10x10, so when I generate a font at the size of 10, it covers almost whole screen(too big) and also looks very ugly because generated bitmap for the font is too small (too few pixels).

What I want is to create sprite, draw it at same size(world space) and draw text over it, and basicly create a button.

Is there some well established way how to deal with this?

Jerry Lundegaard
  • 198
  • 1
  • 12
  • I've had this exact same problem and I found it much easier to use a separate stage for something like this. There probably is a way to map the coordinates from your game stage to another stage if you choose to go that route. But trust me, trying to draw a font onto a stage with dimensions of something as small as 10x10 does not work out without some hacky solution. In my game, I kept the UI stage and game stage completely separate. However I never had to draw text in world coordinates so I can't help much there. – retodaredevil Jan 02 '19 at 03:36
  • setUseIntegerPositions(false) on the font and set a smaller scale than 1. But it might be cleaner/easier to use a separate camera for your text that uses a ScreenViewport. You'd have to use your game's Viewport to project to screen coordinates and then unproject to the text layer's Viewport to figure out where to draw it. But beware of a LibGDX gotcha: one of those two methods (project/unproject) flips Y coordinates and the other doesn't so you will have to manually flip the Y of your screen coordinates before projecting to the text layer. – Tenfour04 Jan 02 '19 at 05:24
  • @Tenfour04 Using separate viewport seems to work. But how to determine correct size? Example: if the desired with of entire text is 100px, string is "HelloWorld", how to calculate the font size that will make rendered text exactly 100px wide? – Jerry Lundegaard Jan 02 '19 at 15:29
  • I don't know of a way to do that exactly. But if *approximately* 100 px is okay, I would calculate ahead of time average character width for this particular font in units of pixels per font point size. Then simple arithmetic at runtime will give you the point size to use. – Tenfour04 Jan 02 '19 at 15:54

1 Answers1

1

Thanks to clarifying comments, I've came up with the solution.

I took a point at which I wanted to draw the text, projected it to the screen space by my world camera. Then I flipped y axis by:

point.y = viewportHeight - point.y;

Then I unprojected it with ScreenViewport (separate viewport for drawing the text, is uses camera of the size of the screen so 1unit == 1pixel). Now I can draw text in projection where 1unit = 1pixel, on the point that is at the same place on the screen as previously chosen point in world space.

I also wanted to be able to draw text inside rectangular boundaries. For this I chose another point. At this point text should end. Did the same procedure as with start point, and then calculated width

targetWidth = endpoint.x - startpoint.x;

Then I used GlypthLayout class to get actual width of my text at some(generated) font size.

actualWidth = glyphLayout.width;

And when I scaled font like this

font.getData().setScale(targetWidth / actualWidth);

my font get scaled so drawed text is wide as target width.

But be aware of another problem! When I generate bimap font via FreetypeGenerator with size bigger when approximately 300, some letters don't draw, and are missing. (probably bug).

Jerry Lundegaard
  • 198
  • 1
  • 12