ENIGMA Forums

General fluff => General ENIGMA => Topic started by: Goombert on August 06, 2013, 04:24:15 PM

Title: Default Font Glyph
Post by: Goombert on August 06, 2013, 04:24:15 PM
Some of you may not be aware as you have not much interaction with the plugin to LateralGM. canthelp discovered that the default font is rendered inside the plugin using Java AWT, you see ENIGMA uses sprite fonts, like every other game engine including Game Maker. So for there to be a default one, the plugin takes the default Java font and renders it and passes the glyphs over to ENIGMA. This is very dumb, this is done every time you compile, not that slow, but is part of the reason why compile is slow. It should be done internally by ENIGMA, otherwise ENIGMA basically depends on Java or something else to render that default font. canthelp discovered it when building the CLI that he could not call draw_text when he had no font resources. We should include a default sprite font with ENIGMA, what do you think Josh?
Title: Re: Default Font Glyph
Post by: DaSpirit on August 06, 2013, 04:37:41 PM
Everything should be done internally by ENIGMA. ENIGMA should be its own executable. I'm for it.
Title: Re: Default Font Glyph
Post by: TheExDeus on August 06, 2013, 04:49:48 PM
Well including a default sprite font for CLI would be good. But I don't think ENIGMA plugin should generate all font textures. I don't think there would be an easy cross-platform way to do it in C++ for ENIGMA plugin.
Title: Re: Default Font Glyph
Post by: Josh @ Dreamland on August 06, 2013, 06:53:23 PM
Having ENIGMA exclusively as a separate binary is asinine. Syntax checking is done frequently; in an increasing number of modern IDEs, it is done continually. Are you going to have the OS spawn a process every half second or so to check the syntax of an open script? If that isn't enough to frighten you out of that idea, what about for all open scripts? Good luck.

As far as whose job it is to generate font textures, letting the plugin do it has an advantage: the IDE can pass textures it gets from anywhere. Anything goes. The disadvantage is, of course, that all IDEs must do that. Perhaps some kind of compromise is in order (eg, an option to pass a null bitmap and have ENIGMA generate the glyphs using libttf).
Title: Re: Default Font Glyph
Post by: Goombert on August 06, 2013, 09:35:19 PM
Well I don't know, I just thought maybe you hadn't given that some thought in a while Josh, because it seems like something you would traditionally be against. But I kinda get now why it is the way that it is. I just don't like ENIGMA having to rely on Java. How big are font files anyway? I think we could pack quite a few of them in at a small size if we really wanted couldn't we?
Title: Re: Default Font Glyph
Post by: TheExDeus on August 07, 2013, 01:29:34 AM
The default one which is always included is 128x64 with about half the texture empty.
Title: Re: Default Font Glyph
Post by: ssss on August 07, 2013, 02:20:00 AM
If everyones forgotten, I found out that theres the GML function font_add that can create a font. It crashes ENIGMA right now because it never actually creates the fnt->texture, but someone should fix it for GM compatibility. That means ENIGMA has to have the ability to render a font on its own. That doesnt mean the compiler can do it though.

None of the game formats include glyph data I think, do they? Any program that reads game formats and compiles them with libcompileEGMf will have to be able to render the glyphs or the ENIGMA compiler will have to be able to render them.
Title: Re: Default Font Glyph
Post by: Goombert on August 07, 2013, 04:01:24 AM
btw everyone, ssss is canthelp on the IRC, he is building a Command Line Interface for ENIGM'R
Title: Re: Default Font Glyph
Post by: TheExDeus on August 07, 2013, 08:02:32 AM
Quote
If everyones forgotten, I found out that theres the GML function font_add that can create a font. It crashes ENIGMA right now because it never actually creates the fnt->texture, but someone should fix it for GM compatibility. That means ENIGMA has to have the ability to render a font on its own. That doesnt mean the compiler can do it though.
We know about that function and it was investigated. The problem is that there is no really painless way to do it. I guess the best bet is to use libttf: http://www.freetype.org, but previously when this was investigated (years ago) either the library didn't exist in the current form or we just didn't find it (we experimented with OS level stuff, like Windows font generation functions). I haven't investigated that though.
Title: Re: Default Font Glyph
Post by: Josh @ Dreamland on August 07, 2013, 10:32:27 PM
Quote
The default one which is always included is 128x64 with about half the texture empty.
Okay, that's gross. The rectangle packer is supposed to generate an optimal map. If half the texture is empty, it means there were just enough glyphs to require one more resize (Each resize doubles the texture atlas size, for obvious reasons).

Anyway, font_add isn't really my biggest concern, largely because it's ugly and inconsistent between platforms, and as Harri so elegantly pointed out, we pack a default font with each game. Yes, it would be nice to be able to acquire glyphs (especially Unicode glyphs) on demand, so we might invest in the matter down the road. The rectangle packer, despite its apparent issues, is capable of adding more glyphs on the fly, as it does not do any planning in advance.

That said, perhaps we could gain a more optimal solution by providing the texture size in advance, eg, by calculating a solution, halving the larger (or vertical) side, then recomputing the map. Could you upload the texture generated on your system, Harri?
Title: Re: Default Font Glyph
Post by: TheExDeus on August 08, 2013, 01:22:30 AM
Quote
Okay, that's gross. The rectangle packer is supposed to generate an optimal map. If half the texture is empty, it means there were just enough glyphs to require one more resize (Each resize doubles the texture atlas size, for obvious reasons).
Well, yeah, it didn't fit in 64x64, so it expanded to 128x64. I don't see that as a big issue taking into account how tiny the texture is. Maybe later with texture atlas we could pack several fonts together into one texture.

Quote
Anyway, font_add isn't really my biggest concern, largely because it's ugly and inconsistent between platforms, and as Harri so elegantly pointed out, we pack a default font with each game. Yes, it would be nice to be able to acquire glyphs (especially Unicode glyphs) on demand, so we might invest in the matter down the road. The rectangle packer, despite its apparent issues, is capable of adding more glyphs on the fly, as it does not do any planning in advance.
I think libttf would be quite consistent and the more I read about it the more I think that is a good solution (and it's GPL).

Quote
That said, perhaps we could gain a more optimal solution by providing the texture size in advance, eg, by calculating a solution, halving the larger (or vertical) side, then recomputing the map. Could you upload the texture generated on your system, Harri?
I think they are generated the same on all systems (or at least platforms). On Windows, for example, everyone should see this:
(https://dl.dropboxusercontent.com/u/21117924/font_texture.png)
I inverted the colors so it easier to see (normally the text is white so blending works). I think it packs quite good and maybe even too tightly, because that causes rendering artifacts. Like when you render a scaled text or something, then the texture coordinate slightly goes into the other letter. This was a massive problem with GM and I see artifacts like that in ENIGMA as well.

Also, the default font doesn't look so well and because of size and no AA the lines are not straight when they should be (like in X or Y), so we should at least turn AA on. That would probably make the font use more of the 128x64 texture, but it's empty anyway.
Title: Re: Default Font Glyph
Post by: Goombert on August 08, 2013, 02:51:51 AM
(https://dl.dropboxusercontent.com/u/21117924/font_texture.png)
Harri, I think that is why at first that draw_text was screwing up in OpenGL 3 before you fixed it, cause that whiteness kind of looked like it was just the sprites using the font texture. Just saying, its already fixed, just sayin though.
Title: Re: Default Font Glyph
Post by: TheExDeus on August 08, 2013, 03:30:32 AM
Also, the font texture interpolation bug mentioned in git is still a problem? I think maybe that is the reason why GL3 font drawing sucks to bad right now. Maybe though I just need to change floats back to ints.
Title: Re: Default Font Glyph
Post by: Goombert on August 08, 2013, 05:19:19 AM
Harri, it was that, and it was also the half pixel alignment. I can easily fix OpenGL 3 fonts, simply add a boolean flag to GmTexture struct called isFont, and check that when looping the textures in texture_set_interpolation
Title: Re: Default Font Glyph
Post by: Josh @ Dreamland on August 08, 2013, 08:35:34 AM
Sorry, Harri; that's life. There's not a damn thing I can do about the L being just big enough to not fit. Now, as for packing tightness, that's a reaaaally easy fix. You'd just need to up the width and height of the rectangles that get passed to the packing algorithm. You'd probably also need to offset the glyphs in the texture by half that margin as to avoid artifacts from clamping on the top and left edges of the texture. Interpolation gets a little ugly when that happens. The idea is that it would not matter in most games, but we've been seeing that behavior with increasing frequency...
Title: Re: Default Font Glyph
Post by: TheExDeus on August 08, 2013, 08:56:57 AM
That is not an "L", the texture is reverse. It seems it maybe could be fixed, but I doubt you wrote the packer to look for space between already packed glyphs. I will try to some packing and texture changes to clean it up later.
Title: Re: Default Font Glyph
Post by: ssss on August 09, 2013, 06:01:00 PM
I think they are generated the same on all systems (or at least platforms). On Windows, for example, everyone should see this:
(https://dl.dropboxusercontent.com/u/21117924/font_texture.png)
Enigma plugin asks AWT for a default font in EnigmaWriter.java. I assume logical fonts aren't garanteed to be always the same. Are they? Probably not if msttcorefonts isnt installed on linux.

Code: [Select]
java.awt.Font iF = new java.awt.Font(java.awt.Font.DIALOG,java.awt.Font.PLAIN,12);
Quote
Also, the default font doesn't look so well and because of size and no AA the lines are not straight when they should be (like in X or Y), so we should at least turn AA on.
It looks like you could get AA easily, the plugin just picks a glyph without AA if available:

Code: [Select]
Object aaHints[] = { RenderingHints.VALUE_TEXT_ANTIALIAS_OFF,
RenderingHints.VALUE_TEXT_ANTIALIAS_GASP,RenderingHints.VALUE_TEXT_ANTIALIAS_ON,
RenderingHints.VALUE_TEXT_ANTIALIAS_LCD_HRGB };
if (aa < 0 || aa >= aaHints.length) aa = 0;
GlyphVector gv = fnt.createGlyphVector(new FontRenderContext(null,aaHints[aa],
RenderingHints.VALUE_FRACTIONALMETRICS_OFF),String.valueOf(c));
Title: Re: Default Font Glyph
Post by: TheExDeus on August 10, 2013, 04:49:14 AM
Well AA is an option in LGM for all fonts, so I didn't think it would be hard to get it. Just that someone should maybe enable it and see if it makes it look any better.
Title: Re: Default Font Glyph
Post by: Goombert on August 10, 2013, 05:08:07 AM
TheExDeus come to think of it, you just made me think about something. How is our font antialiasing rendered? Because in the latest LGM I have font anti aliasing enabled.
Title: Re: Default Font Glyph
Post by: Josh @ Dreamland on August 10, 2013, 07:21:13 AM
Well, I thought about it, Harri, and by my algorithm, the largest amount of empty space between packed glyphs is bounded by the difference in dimension of rectangles packed in a given column or row (which I minimize by sorting up front) multiplied by the largest opposite dimension of textures in the next row or column (counter-respectively). In practice, you'll never have room for more than a 2*16 rectangle, anywhere, and that's if the sorting algorithm can do basically nothing to help the situation.

The best thing we could do to optimize space is flip the texture by 90°.
Title: Re: Default Font Glyph
Post by: TheExDeus on August 10, 2013, 09:12:39 AM
Robert, they are just rendered with Java AWT just like normal fonts. You just give it a hint just like ssss shown. And it does work for a while now. The problem is with too tight packing and/or with the drawing code.
Title: Re: Default Font Glyph
Post by: Goombert on August 13, 2013, 05:24:20 PM
Hey hey hey you guys, you'll never guess what I discovered. While I was sitting here writing up GMX loading for LGM, I discovered the new GMX format actually stores a .png of each font resource, it looks like the equivalent of drawing a floor/wall with font_get_texture in ENIGMA, just all the characters organized alphabetically on a transparent background. Or just like that font texture a few posts up from mine. Except theirs is white and not black like ours.
Title: Re: Default Font Glyph
Post by: TheExDeus on August 14, 2013, 01:24:38 AM
Ours is also white. I inverted the colors when posting here so people could actually see it. It must be white for blending to work. So GMS probably just saves the .png texture for some reason instead of the font (which could be copyrighted, so I guess it does make sense).
Title: Re: Default Font Glyph
Post by: Josh @ Dreamland on August 14, 2013, 08:25:16 AM
/facepalm
Title: Re: Default Font Glyph
Post by: popcade on August 16, 2013, 01:12:24 PM
May I recommend FreeType as:
1.It works on many platforms.
2.Same result on supported platforms.
3.Use common TTF files
4.Unicode friendly, so you can progress to UTF-8/16 as internal text engine.
5.Acceptable output quality.

You can actually draw FreeType on a frame buffer and grab it as BMP font if you wish.
Title: Re: Default Font Glyph
Post by: TheExDeus on August 16, 2013, 04:53:21 PM
Quote
May I recommend FreeType as:
Yes, that is the one we are considering (in this topic refereed to as libttf).