SDL Forum Index
SDL
Simple DirectMedia Layer Forums
Reply to topic
SDL2 + OpenGL+ SDL_ttf and rendering text question
Trev


Joined: 07 Nov 2011
Posts: 63
Reply with quote
I am porting my program from mac/windows to the iPad. Up until now, I have been using the GLUT functions for drawing text, such as:
glutBitmapCharacter (GLUT_BITMAP_HELVETICA_10,theString[i]);

But those functions are not supported on the iPad, so I am trying to use SDL_ttf for text.

There are 2 examples that demonstrate SDL_ttf.
http://lackeyccg.com/glfont.c shows how things are done with OpenGL.
http://lackeyccg.com/showfont.c shows how things are done with just SDL.
I'm not sure what is the better method for my uses.

I am using text for essentially 3 kinds of uses:

Labels for things like buttons and menus.
[img]http://lackeyccg.com/images/SDL_ttfNonDynamicText.jpg[/img]

Text for text fields.
[img]http://lackeyccg.com/images/SDL_ttfDynamicText.jpg[/img]

And text labels that appear in 3D space. (The text itself is flat, but it appears in 3D OpenGL space.)
[img]http://lackeyccg.com/images/SDL_ttf3DText.jpg[/img]

If I understand things correctly, with SDL_ttf, fonts are loaded and then you can use those fonts to create surface images, or load those images into opengl which you can refer to later by the texture id. In either case, it seems like you need to store a unique image in memory for each unique bit of text. Alternatively, you can generate this image every time you display the text, but it seems like generating the image every display cycle, while simpler to implement, would be a drag on the system. Is that correct, or could I simply generate everything I need every display cycle and not suffer a performance hit?
What I think might be the best thing to do is create some persistent record of all text images. Whenever a new word or phrase is needed (or with different style, like italics or bold) then a new entry to the record is added for that surface image (or opengl texture id). This is pretty straight-forward for something like a button label, but a text field seems to be more complicated. I think the best approach for a text field would be to store in the record only those lines of the text field that are currently visible, and have a separate entry for each line.

Another idea is to persistently store the images for all of a font's glyphs, and then generate any needed word or phrase by cobbling them together. I would hope that SDL_ttf does this for me somehow to save me all the work. I would love to be able to just call a function, passing it a string to display, its X,Y,Z coordinates, it's color, and size, and it would just draw it to the screen with all of the complex stuff like memory management and kerning all done behind the scenes. Does anyone know if anything like that already exists? All I can currently find is functions likeTTF_RenderText_Solidthat create a surface image that I then have to manage in a complex way as stated above.

As far as the text labels that appear in 3D space, I am not sure but I think this requires the opengl method like in theglfont.cexample instead of the pure SDL method.

Does anyone have any suggestions for me? Do you think I am thinking about things in the right manner? How have you handled rendering both non-dynamic and dynamic text with SDL_ttf?

Any insight you have on this subject would be helpful.

Thanks in advance.

-Trevor
View user's profileSend private messageVisit poster's websiteAIM Address
SDL2 + OpenGL+ SDL_ttf and rendering text question
gabomdq


Joined: 28 Jul 2011
Posts: 469
Location: Argentina
Reply with quote
2012/5/24 Trev
Quote:
I am porting my program from mac/windows to the iPad. Up until now, I have been using the GLUT functions for drawing text, such as:
glutBitmapCharacter (GLUT_BITMAP_HELVETICA_10,theString[i]);

But those functions are not supported on the iPad, so I am trying to use SDL_ttf for text.

There are 2 examples that demonstrate SDL_ttf.
http://lackeyccg.com/glfont.c shows how things are done with OpenGL.
http://lackeyccg.com/showfont.c shows how things are done with just SDL.
I'm not sure what is the better method for my uses.





Both methods basically do the same, even though the SDL method does it behind the scenes with SDL_CreateTextureFromSurface, they create a "software" surface where SDL_ttf renders the text, then copy it to a "hardware" texture and render that.

Quote:
As far as the text labels that appear in 3D space, I am not sure but I think this requires the opengl method like in theglfont.cexample instead of the pure SDL method.

Does anyone have any suggestions for me? Do you think I am thinking about things in the right manner? How have you handled rendering both non-dynamic and dynamic text with SDL_ttf?





I generally render the text to a software surface, copy it to a texture and render it using SDL, I don't think there's a way around it because SDL_ttf is fundamentally CPU centered and rendering GPU centered, and you have to bridge those eventually...if there's a lot of text or it is constantly changing, maybe you can do the glyphs thing (uploading all symbols to a texture and render them "by hand"), but it really depends on the application you are developing. You could, in theory, render fonts using only geometry or shaders, but it seems the technology is not there yet:http://stackoverflow.com/questions/5262951/what-is-state-of-the-art-for-text-rendering-in-opengl-as-of-version-4-1



--
Gabriel.

_________________
Gabriel Jacobo
mdqinc.com
View user's profileSend private messageVisit poster's website
SDL2 + OpenGL+ SDL_ttf and rendering text question
Chris Bush
Guest

Reply with quote
You're right that generating the textures for each new string every cycle will not perform well. Preloading the glyphs from a font to a texture set and assembling on the fly instead seems to work alright for me. The relevant parts I've mashed into the example program below (c++/sdl2). But this approach is only for game text. It's not great for regular applications where the standard OS widgets are familiar, complete and comfortable for people. So, for the text areas and things, you might want to be using a GUI library such as GTK+... but if you do choose to render letters as individual textures, feel free to have at the code here (note the paths to fonts at lines 102-105).

http://codepad.org/QS26ciMD




On Thu, May 24, 2012 at 10:56 PM, Trev wrote:
Quote:
I am porting my program from mac/windows to the iPad. Up until now, I have been using the GLUT functions for drawing text, such as:
glutBitmapCharacter (GLUT_BITMAP_HELVETICA_10,theString[i]);

But those functions are not supported on the iPad, so I am trying to use SDL_ttf for text.

There are 2 examples that demonstrate SDL_ttf.
http://lackeyccg.com/glfont.c shows how things are done with OpenGL.
http://lackeyccg.com/showfont.c shows how things are done with just SDL.
I'm not sure what is the better method for my uses.

I am using text for essentially 3 kinds of uses:

Labels for things like buttons and menus.
[img]http://lackeyccg.com/SDL_ttfNonDynamicText.jpg[/img]

Text for text fields.
[img]http://lackeyccg.com/SDL_ttfDynamicText.jpg[/img]

And text labels that appear in 3D space. (The text itself is flat, but it appears in 3D OpenGL space.)
[img]http://lackeyccg.com/SDL_ttf3DText.jpg[/img]

If I understand things correctly, with SDL_ttf, fonts are loaded and then you can use those fonts to create surface images, or load those images into opengl which you can refer to later by the texture id. In either case, it seems like you need to store a unique image in memory for each unique bit of text. Alternatively, you can generate this image every time you display the text, but it seems like generating the image every display cycle, while simpler to implement, would be a drag on the system. Is that correct, or could I simply generate everything I need every display cycle and not suffer a performance hit?
What I think might be the best thing to do is create some persistent record of all text images. Whenever a new word or phrase is needed (or with different style, like italics or bold) then a new entry to the record is added for that surface image (or opengl texture id). This is pretty straight-forward for something like a button label, but a text field seems to be more complicated. I think the best approach for a text field would be to store in the record only those lines of the text field that are currently visible, and have a separate entry for each line.

Another idea is to persistently store the images for all of a font's glyphs, and then generate any needed word or phrase by cobbling them together. I would hope that SDL_ttf does this for me somehow to save me all the work. I would love to be able to just call a function, passing it a string to display, its X,Y,Z coordinates, it's color, and size, and it would just draw it to the screen with all of the complex stuff like memory management and kerning all done behind the scenes. Does anyone know if anything like that already exists? All I can currently find is functions like TTF_RenderText_Solid that create a surface image that I then have to manage in a complex way as stated above.

As far as the text labels that appear in 3D space, I am not sure but I think this requires the opengl method like in the glfont.c example instead of the pure SDL method.

Does anyone have any suggestions for me? Do you think I am thinking about things in the right manner? How have you handled rendering both non-dynamic and dynamic text with SDL_ttf?

Any insight you have on this subject would be helpful.

Thanks in advance.

-Trevor


_______________________________________________
SDL mailing list

http://lists.libsdl.org/listinfo.cgi/sdl-libsdl.org

Re: SDL2 + OpenGL+ SDL_ttf and rendering text question
Trev


Joined: 07 Nov 2011
Posts: 63
Reply with quote
Chris Bush wrote:
You're right that generating the textures for each new string every cycle will not perform well. Preloading the glyphs from a font to a texture set and assembling on the fly instead seems to work alright for me. The relevant parts I've mashed into the example program below (c++/sdl2). But this approach is only for game text. It's not great for regular applications where the standard OS widgets are familiar, complete and comfortable for people. So, for the text areas and things, you might want to be using a GUI library such as GTK+... but if you do choose to render letters as individual textures, feel free to have at the code here (note the paths to fonts at lines 102-105).

http://codepad.org/QS26ciMD
That seems like a great example code and is pretty close to exactly what I am looking for.

I have a minor tweak that I think is an improvement. If you pass some RGB values to void Text_ure::write(float x, float y, float lh, float r,float g,float b), then you can dynamically change the color of the font without having to reload it. You just need to add glColor4f(r,g,b,1.0); right before "glBegin(GL_QUADS);".
Just make sure you pass a white color to TTF_RenderText_Blended when the glyph images are being created initially. And you can pass RGB values to write_left_aligned so it in turn can pass them to Text_ure::write. That leaves you with:
Code:
void write_left_aligned(  // write
  Text_ure *Lettercase[], // with letter case
  const char* s,          // input C string
  float top, float left,  // upper left corner
  float fontsize,         // size
  float lineheight,       // line height factor - 1 is normal
  float kerning,          // letter spacing factor - 1 is normal
  float width,             // column width,
  float r,float g,float b) //Font color

And that one function is all you need from that point on.

Now all I need is to convert that code to an OpenGL ES safe version and I think I'll be all set for rendering text on the iPad.
View user's profileSend private messageVisit poster's websiteAIM Address
SDL2 + OpenGL+ SDL_ttf and rendering text question
Chris Bush
Guest

Reply with quote
Oh, yes... the function could be improved in many ways. However, you could just use glColor4f(r, g, b, a); prior to calling the write_left_aligned function. The color will be as set without needing to reload the textures.



On Fri, May 25, 2012 at 5:15 PM, Trev wrote:
Quote:



Chris Bush wrote:

You're right that generating the textures for each new string every cycle will not perform well. Preloading the glyphs from a font to a texture set and assembling on the fly instead seems to work alright for me. The relevant parts I've mashed into the example program below (c++/sdl2). But this approach is only for game text. It's not great for regular applications where the standard OS widgets are familiar, complete and comfortable for people. So, for the text areas and things, you might want to be using a GUI library such as GTK+... but if you do choose to render letters as individual textures, feel free to have at the code here (note the paths to fonts at lines 102-105).

http://codepad.org/QS26ciMD



That seems like a great example code and is pretty close to exactly what I am looking for.

I have a minor tweak that I think is an improvement. If you pass some RGB values to void Text_ure::write(float x, float y, float lh, float r,float g,float b), then you can dynamically change the color of the font without having to reload it. Just make sure you pass a white color to TTF_RenderText_Blended when the glyph images are being created initially. And you can pass RGB values to write_left_aligned so it in turn can pass them to Text_ure::write. That leaves you with:


Code:

void write_left_aligned( // write
Text_ure *Lettercase[], // with letter case
const char* s, // input C string
float top, float left, // upper left corner
float fontsize, // size
float lineheight, // line height factor - 1 is normal
float kerning, // letter spacing factor - 1 is normal
float width, // column width,
float r,float g,float b) //Font color



And that one function is all you need from that point on.


_______________________________________________
SDL mailing list

http://lists.libsdl.org/listinfo.cgi/sdl-libsdl.org

Re: SDL2 + OpenGL+ SDL_ttf and rendering text question
Trev


Joined: 07 Nov 2011
Posts: 63
Reply with quote
Chris Bush wrote:
Oh, yes... the function could be improved in many ways. However, you could just use glColor4f(r, g, b, a); prior to calling the write_left_aligned function. The color will be as set without needing to reload the textures.


I tried my hand at making the code more easy to use. I appreciate suggestions for improvement.
http://forums.libsdl.org/viewtopic.php?t=8194
View user's profileSend private messageVisit poster's websiteAIM Address
SDL2 + OpenGL+ SDL_ttf and rendering text question
Chris Bush
Guest

Reply with quote
It's neat. I like the prospective alignment feature. One might go in the direction of creating something like a paragraph class that you can create, position on the plane, set the typeface and kerning and so on, and fill and refill with text. I think setting the color in the glyph drawing function might not be optimal, since for a given input to DrawText you must pass and set the colors to each letter. Anyway, it looks useful. Thanks for leaving the credit.

Chris



On Sat, May 26, 2012 at 8:39 AM, Trev wrote:
Quote:



Chris Bush wrote:

Oh, yes... the function could be improved in many ways. However, you could just use glColor4f(r, g, b, a); prior to calling the write_left_aligned function. The color will be as set without needing to reload the textures.




I tried my hand at making the code more easy to use. I appreciate suggestions for improvement.
http://forums.libsdl.org/viewtopic.php?t=8194


_______________________________________________
SDL mailing list

http://lists.libsdl.org/listinfo.cgi/sdl-libsdl.org

SDL2 + OpenGL+ SDL_ttf and rendering text question
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum
All times are GMT  
Page 1 of 1  

  
  
 Reply to topic