How to draw text in some determined area, doing auto wrap

Hello,

I’m working in a project called FreeVO(http://freevo.sf.net), that
uses SDL with python to do the graphics.

We want to build a widget that will act like a frame: we say its
width/height, the text and font(ttf) to use. Then it should be able to
arrange the text into the specified area, breaking lines if it doesn’t
fit (preferable in white spaces) and if the hole text overflows the
area capacity, should appear “…” after the last part visible.

I don’t know any technique to do that, but they must exit (any
toolkit do that). I want to know what is the best way to do that.

PS: We use python+SDL and pygame. So solutions using them are
preferable :slight_smile:

Gustavo_______________________________________________________________________
Yahoo! PageBuilder
O super editor para cria??o de sites: ? gr?tis, f?cil e r?pido.

I don’t know any technique to do that, but they must exit (any
toolkit do that). I want to know what is the best way to do that.

I do this in Tux Paint, in the “draw_tux_text()” function
(or one that it calls)

PS: We use python+SDL and pygame. So solutions using them are
preferable :slight_smile:

I’m doing it in C. I’ve never used Python, so I don’t
know how its string handling works. Sorry :wink:

Good luck!

-bill!On Thu, Sep 05, 2002 at 03:08:46PM -0300, Gustavo Sverzut Barbieri wrote:

PS: We use python+SDL and pygame. So solutions using them are
preferable :slight_smile:

Well, the only real way to do this is manually by calculating how many
characters can fit into a rectangle. I’ll tell you now: skip the TTF
font stuff and use monospace bitmap fonts. Non-monospace fonts require
a bit more calculation.

Basically, you step through the string character by character and print
away, then add the width of the font to your current X coordinate. If
you’re out of bounds, drop back to the beginning of the line and then
drop down by adding to the y coordinate. It’s a pretty simple thing to
do with a monospace font. A variable-width font requires you to check
the sizes of individual characters.

Does this help?

  • Charles__________________________________________________
    Do You Yahoo!?
    Yahoo! Finance - Get real-time stock quotes
    http://finance.yahoo.com

Well, kinda. If you use proportionally-spaced fonts, you can just use
SDL_TTF to render one word at a time:

The
quick
brown
fox.

For each word, examine whether we’ll be going off the edge if we draw that
word at the current cursor position. If not, draw the word, and move
the cursor’s X position over that far.

If it will, first reset the cursor’s X position to the left edge,
and move the cursor’s Y position down one line. THEN draw the word,
and move the cursor’s X position over that far.

The one special case is when a SINGLE particular word is too long to
fit on one line:

supercalifragolisticexpialadocious [no idea how to spell that ;^) ]

In that case, you could have some ‘special case’ where it then draws the
word one letter at a time, and breaks it up when one of the LETTERS would
be past the right edge.

The difference between doing this ‘one word at a time’ word-wrap vs.
just blitting the entire word is how many times you blit.
(Once you’ve blit a word, you WILL end up using it, unless you’ve gone
below the bottom boundary of where you want your text to go…
then you’re just screwed! :slight_smile: )

If you don’t think your text will be longer than one line most of the
time, you can just render it all as one sentence first:

The quick brown fox.

If that’s too wide to fit, THEN you try doing it one… word… at… a… time.

-bill!On Thu, Sep 05, 2002 at 02:19:03PM -0700, Charles Wardlaw wrote:

PS: We use python+SDL and pygame. So solutions using them are
preferable :slight_smile:

Well, the only real way to do this is manually by calculating how many
characters can fit into a rectangle. I’ll tell you now: skip the TTF
font stuff and use monospace bitmap fonts. Non-monospace fonts require
a bit more calculation.

Charles Wardlaw escribi?:

PS: We use python+SDL and pygame. So solutions using them are
preferable :slight_smile:

Well, the only real way to do this is manually by calculating how many
characters can fit into a rectangle. I’ll tell you now: skip the TTF
font stuff and use monospace bitmap fonts. Non-monospace fonts require
a bit more calculation.

Basically, you step through the string character by character and print
away, then add the width of the font to your current X coordinate. If
you’re out of bounds, drop back to the beginning of the line and then
drop down by adding to the y coordinate. It’s a pretty simple thing to
do with a monospace font. A variable-width font requires you to check
the sizes of individual characters.

GetTextExtentPoint32 is a Windows API call. It gives the exact width and
height of a string in points for an arbitrary string, font face and size.

Doesn’t SDL_TTF have a similar function?

Regards,
Wizord.

— Charles Wardlaw escreveu: > > PS: We use
python+SDL and pygame. So solutions using them are

preferable :slight_smile:

Well, the only real way to do this is manually by calculating how
many
characters can fit into a rectangle. I’ll tell you now: skip the TTF
font stuff and use monospace bitmap fonts. Non-monospace fonts
require
a bit more calculation.

Basically, you step through the string character by character and
print
away, then add the width of the font to your current X coordinate.
If
you’re out of bounds, drop back to the beginning of the line and then
drop down by adding to the y coordinate. It’s a pretty simple thing
to
do with a monospace font. A variable-width font requires you to
check
the sizes of individual characters.

Does this help?

  • Charles

Kind of… We must do this work with all type of fonts. It’s an
eye-candy program.
But that was the idea we had before.

Thanks,

Gustavo_______________________________________________________________________
Yahoo! PageBuilder
O super editor para cria??o de sites: ? gr?tis, f?cil e r?pido.

— nbs escreveu: > On Thu, Sep 05, 2002 at 02:19:03PM
-0700, Charles Wardlaw wrote:

PS: We use python+SDL and pygame. So solutions using them are
preferable :slight_smile:

Well, the only real way to do this is manually by calculating how
many
characters can fit into a rectangle. I’ll tell you now: skip the
TTF
font stuff and use monospace bitmap fonts. Non-monospace fonts
require
a bit more calculation.

Well, kinda. If you use proportionally-spaced fonts, you can just
use
SDL_TTF to render one word at a time:

The
quick
brown
fox.

For each word, examine whether we’ll be going off the edge if we draw
that
word at the current cursor position. If not, draw the word, and move
the cursor’s X position over that far.

If it will, first reset the cursor’s X position to the left edge,
and move the cursor’s Y position down one line. THEN draw the word,
and move the cursor’s X position over that far.

The one special case is when a SINGLE particular word is too long to
fit on one line:

supercalifragolisticexpialadocious [no idea how to spell
that ;^) ]

In that case, you could have some ‘special case’ where it then draws
the
word one letter at a time, and breaks it up when one of the LETTERS
would
be past the right edge.

The difference between doing this ‘one word at a time’ word-wrap vs.
just blitting the entire word is how many times you blit.
(Once you’ve blit a word, you WILL end up using it, unless you’ve
gone
below the bottom boundary of where you want your text to go…
then you’re just screwed! :slight_smile: )

If you don’t think your text will be longer than one line most of
the
time, you can just render it all as one sentence first:

The quick brown fox.

If that’s too wide to fit, THEN you try doing it one… word… at…
a… time.

-bill!

Those ideas give me kind of light. I like the “per word” calculation,
the others I think is too many specific.
I think we will cache up every letter measured as it needs, but your
approach give me some ideas on how to break lines.

Gustavo_______________________________________________________________________
Yahoo! PageBuilder
O super editor para cria??o de sites: ? gr?tis, f?cil e r?pido.