question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

Bitmapfont.draw: wrap text drawn at the wrong position

See original GitHub issue

Issue details

Wrap text is drawn at the wrong position if align is set to center: image

Maybe this is releated to the issues #4425, #4970 or #4192, but I am not sure.

I noticed also some other issues:

  • dots of the german umlauts (e.g. “Ä”, “Ü”) are drawn outside the bounds for some fonts
  • the lower part of some chars (e.g. “p”, “q”, “g”) are drawn outside the bounds for all fonts (see picture)

Reproduction steps/code

public class MyGdxGame extends ApplicationAdapter {

  SpriteBatch batch;
  Texture img;
  TextureRegion texReg;
  BitmapFont font;
  GlyphLayout layout;

  @Override
  public void create() {
    batch = new SpriteBatch();
    layout = new GlyphLayout();
    img = new Texture("blank.png");
    texReg = new TextureRegion(img);
    font = new BitmapFont();
  }

  @Override
  public void render() {
    String text = "Keine Spiele für den gewählten Spielmodus gefunden";
    float targetWidth = 250;
    float xTopLeft = 100;
    float yTopLeft = Gdx.graphics.getHeight() - 5.0f;

    Gdx.gl.glClearColor(Color.WHITE.r, Color.WHITE.g, Color.WHITE.b, Color.WHITE.a);
    Gdx.gl.glClear(GL20.GL_COLOR_BUFFER_BIT);

    batch.begin();

    // draw the text:
    font.setColor(Color.BLACK);
    layout.setText(font, text, font.getColor(), targetWidth, Align.center, true);
    font.draw(batch, text, xTopLeft, yTopLeft, targetWidth, Align.center, true);

    // draw border to see the desired bounds of the text:
    batch.setColor(Color.RED);
    batch.draw(texReg, xTopLeft, yTopLeft, layout.width, 1);
    batch.draw(texReg, xTopLeft, yTopLeft - layout.height, 1, layout.height);
    batch.draw(texReg, xTopLeft, yTopLeft - layout.height, layout.width, 1);
    batch.draw(texReg, xTopLeft + layout.width, yTopLeft - layout.height, 1, layout.height);

    batch.end();
  }

  @Override
  public void dispose() {
    batch.dispose();
    img.dispose();
    font.dispose();
  }
}

Version of LibGDX and/or relevant dependencies

1.9.6 and 1.9.8

Please select the affected platforms

  • Android
  • iOS (robovm)
  • iOS (MOE)
  • HTML/GWT
  • Windows
  • Linux
  • MacOS

Hint: I only tested it on Windows and Linux, but it seems to be a genreal issue.

Issue Analytics

  • State:closed
  • Created 5 years ago
  • Comments:7 (4 by maintainers)

github_iconTop GitHub Comments

1reaction
NathanSweetcommented, Apr 5, 2018

I forget the reason why the top left corner was chosen as the origin for fonts, but I know all the options were considered and there were reasons it was chosen. It’s too late to change it now at any rate. Utility methods to draw in ways that make sense for you are good. Note that Y is up in the math world. I had the same problem long ago, but you’ll get used to it eventually!

The boxes you are drawing are using the font metrics. A font can report the descent is X but have glyphs the extend further below the baseline. I believe the font is to blame. From a GlyphLayout you can get each GlyphRun, which has an array of Glyphs, which each have positioning and size information. You can use this to find the bounding box that is accurate to a pixel. This is not normally needed for most text layout, so the work is not performed by default.

0reactions
QStormDScommented, Apr 4, 2018

Hi again, Hopefully it will be noticed as the ticket is already closed. I tried your demo code with several true type fonts. However, the bounds of the glyph runs are not exact. As you can see in the attached image there is an inaccuracy of up to 30 pixel on the right side. Furthermore, some letters like “l”, “g” or symbols like “)” are out of the bounds. Where does it come from?

font

I am using the free type font loader (everything else remains the same):

String fontname = "LiberationMono-Regular.ttf"; // paraaminobenzoic.ttf | primer print.ttf

    assetManager = new AssetManager();
    final FileHandleResolver resolver = new InternalFileHandleResolver();
    assetManager.setLoader(FreeTypeFontGenerator.class, new FreeTypeFontGeneratorLoader(resolver));
    assetManager.setLoader(BitmapFont.class, new FreetypeFontLoader(resolver));

    final FreeTypeFontLoaderParameter params = new FreeTypeFontLoaderParameter();
    params.fontFileName = Gdx.files.internal(fontname).path();
    params.fontParameters.size = 36;
    assetManager.load(fontname, BitmapFont.class, params);
    assetManager.finishLoading();
    font = assetManager.get(fontname, BitmapFont.class);

P.S.: here a result with german umlauts: font2

Read more comments on GitHub >

github_iconTop Results From Across the Web

LibGDX draw() API inconsistency - java - Stack Overflow
BitmapFont is an object with informations about text which is in it (so the text value, the glyphs textures, wrapping etc). Drawing text...
Read more >
LibGDX Letter spacing is reduced if I use GlyphLayout to draw ...
I managed to solve the problem myself but it still seems like it may be a bug. It happens because glyphLayout.setText(font, text); is ......
Read more >
The Image Gets Drawn At The Wrong Position - ADocLib
I'd like to see the interface do a better job of making it clear when the user switches ... Bitmapfont.draw: wrap text drawn...
Read more >
Work with Text | Documents for Imaging .NET Edition - GrapeCity
With GcImaging, you can add text to your graphics, trim or wrap text, change the text appearance, split the text into multiple columns,...
Read more >
bitmap-font - GitHub Pages
Draws text at the specified position. :draw^Batch batch, ^CharSequence str, ^float x, ^float y, ^float target-width, ^int halign, ^boolean wrap.
Read more >

github_iconTop Related Medium Post

No results found

github_iconTop Related StackOverflow Question

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found