Page 1 of 1

Render space or characters with background color in SSFN

Posted: Sat Mar 20, 2021 6:28 am
by prajwal
[@bzt]

I recently ported SSFN library into my OS. The default config is to render characters in the white foreground and black background. I used Unicode font and found that <space> character doesn't render at all. Also, characters with color backgrounds (like green, white, or any) render only the character but not the background.

I use ssfn_render function.

I debugged through the code and found that there is this condition with a magic number

Code: Select all

if (sA > 15) 
Only if sA > 15, it will write the character to the framebuffer. If I remove this "if condition", the issue is resolved. May I know why and what this "if condition" is about?

Regards
Prajwal

Re: Render space or characters with background color in SSFN

Posted: Sat Mar 20, 2021 10:34 am
by bzt
prajwal wrote:[@bzt]

I recently ported SSFN library into my OS. The default config is to render characters in the white foreground and black background. I used Unicode font and found that <space> character doesn't render at all. Also, characters with color backgrounds (like green, white, or any) render only the character but not the background.
Yes, that's intentional. Note that not all font's cover the entire area, most notably outline fonts don't store every pixel. But bitmaps can't either, because they are compressed, so for example รก is stored in two fragments vertically, an ' acute, then a gap, and then the 'a'. The area between the fragments never drawn with ssfn_render, and ssfn_putc implements a special filler to cover the gap.

From the API documentation
This [ssfn_render] renderer never clears the background. If dst.bg is zero, then the alpha-blending will be calculated against the pixels already in the buffer. With a color given as background, that will be used to calculate gradients of anti-aliased edges.
This is in contrast to ssfn_putc, which was designed to be usable for a console, so it can clear the background if you want it to:
With ssfn_dst.bg being full 32 bit wide zero, ssfn_putc will operate in transparent background mode: it will only modify the destination buffer where the font face is set. To clear the glyph's background, set ssfn_dst.bg to some value where the most significant byte (alpha channel for true-color mode) is 255, like 0xFF000000. This will fill the background with the index 0 (palette) or full black (hicolor and truecolor modes).
prajwal wrote:Only if sA > 15, it will write the character to the framebuffer. If I remove this "if condition", the issue is resolved. May I know why and what this "if condition" is about?
The purpose of the userland ssfn_render function is to draw text on pre-rendered UI elements (buttons, gradiented status bars, progress bars etc.) For that sA !=0 would do, but sA > 15 is to speed up rendering, as it will leave the background untouched when alpha is small, because there's no need to do the expensive alpha-blending when the result would be negligable. Plus without ssfn_render would black out the background even when you don't want it to :-)

To clear the background, I'd suggest to draw a filled box before you render text. Or if you really really never want to write text on pre-drawn buttons or other UI elements with nice gradients, then feel free to remove the if sA > 15 condition.


I've added some images to the API documentation to demonstrate the difference between the two:

ssfn_putc without and with green background (designed for consoles)
Image

ssfn_render without and with green background (designed for UI)
Image

Cheers,
bzt

Re: Render space or characters with background color in SSFN

Posted: Sat Mar 20, 2021 5:14 pm
by prajwal
bzt,

Thank you so much for the detailed explanation - very helpful!!

ssfn_render is doing the right thing for its purpose. We can use ssfn_putc for the other scenario. I am also thinking to make ssfn_render work in scenarios where we need the rendered to fill the background by passing an optional boolean parameter.

Regards
Prajwal

Re: Render space or characters with background color in SSFN

Posted: Sun Mar 21, 2021 5:05 am
by bzt
prajwal wrote:bzt,

Thank you so much for the detailed explanation - very helpful!!
You're welcome!
prajwal wrote:I am also thinking to make ssfn_render work in scenarios where we need the rendered to fill the background by passing an optional boolean parameter.
Don't forget that rendering the background doesn't necessarily cover everything, depends on the font too. For a demonstration, take a look at SSFN 1.0's feature demo (the one at the bottom left), as it could return the outlines, you could see the fragments.
features.png
features.png (4.84 KiB) Viewed 1317 times
Notice how the "outline" for the bitmap font lacks the top (smaller than the third box), vector font outlines does not cover a box at all, and that pixel font was made up of two fragments (that's because the top of the "head" of the smilely face shared with multiple glyphs, so it was deduplicated. It's not the case here, but there could be a gap between the two fragments easily.)

Just for the records, SSFN 2.0 does not return the outline any more, it handles that internally as it has a built-in glyph cache, and neither 1-bit (bitmap) nor 8-bits (FT2 like alpha-channel or palette index, called color map on the image above) visuals supported just 32 bit ones. Originally I wanted to support all VGA modes and X11 visuals, black & white, 16-color, 256-color etc, but then I realized nobody cares, everybody is using true-color framebuffers for quite some time now.)

Cheers,
bzt