[cairo] On the behaviour of cairo_scaled_font_create with regards to font options

Behdad Esfahbod behdad at behdad.org
Thu Oct 11 18:39:11 PDT 2007

On Mon, 2007-07-09 at 19:14 +0200, David Turner wrote:
> Hi Behdad,

Hi David,

Picking up this again...

> > Hi David,
> > 
> > I'm trying to get back to reviewing your cairo-ft rewrite, so we need to
> > resolve this issue first.
> > 
> I don't think this is a blocker at all, since my patch implements both behaviours,
> depending wether you use the old unsafe APIs, or the new safe ones. It should be
> pretty trivial to change it to be consistent in one direction or the other.

Good to know.  Thanks.

> > >From my understanding the reason for the skewed pattern is that
> > cairo_font_face_t is built for a fontconfig pattern and the pattern is
> > never touched anymore during scaled_font creation.  So, to have the
> > fontconfig configuration stuff work properly, one needs to know all the
> > font options before creating font_face_t.
> > 
> > What you suggest (to override pattern options with font-options during
> > scaled font creation) works, except that some fontconfig configurations
> > won't work anymore.
> > 
> either fontconfig is broken by design, or Cairo is not using it properly. I believe the latter.

One or the other, sure. :)

> from what I understand, there are two kinds of "patterns" in FontConfig, and both
> are implemented through a FcPattern object:
> - a "query" pattern describes what the user would like to use as a font. It may not
>   contain much (for example, a simple family name and a size) and is sent to fontconfig's
>   matching engine.


> - the engine uses it to produce a "match" pattern, which should correspond to the user wishes
>   expressed in the query, as well as the configuration rules embedded in the system and
>   user-specific fontconfig config files. these patterns always provide things like a file
>   pathname for the corresponding font file, a face index within this file, some
>   additionnal flags, etc... and can be used to open a font file with FreeType or other
>   font engines and render their content properly.

Small correction: 'the engine uses it to produce a "match" pattern' is
not accurate, and that's exactly where the problem comes from.  Pango
uses FcFontSort() that returns a list of "match" patterns.

> due to the way fontconfig works, there can be enormous differences between what
> is asked in a query-pattern, and what is retrieved in the corresponding match-pattern.
> the fontconfig configuration language is pretty complex and expressive and can do all sort of
> weird tricks. for example, it is possible to write configuration rules that would always
> invert a user's preferences with regards to a given rendering parameter. I.e. something
> along the lines of:
> - if the query-pattern asks for anti-aliased rendering, return a monochrome rendering match-pattern
> - if the query-pattern asks for monochrome rendering, return an anti-aliased rendering match-pattern
> this is just to show that the configuration language is very complex.


> Now, if we consider that the patterns passed to the scaled font creation functions are
> "match-patterns" *only*,

Note that there's no pattern passed to the scaled font creation
functions, but font face creation functions.  The problem is exactly
right there, that cairo_font_options_t is passed in at scaled font
creation time, but fontconfig pattern at font face creation time.

>  then it is natural to consider that the cairo_font_options_t we used on
> them describe specific rendering over-rides that the user want to be applied to the resulting font.
> Note that by default, a fresh new font options objects only contains fields with a value of "default",
> which means always use the setting from the original pattern and/or target surface.
> On the other hand, if we consider that the patterns passed to the scaled font creation functions
> are "query-pattern", then we might want to enable all the really stupid things, which means something
> along the lines of:
> - copying the original query-pattern into a new one
> - if needed, modify the new query-pattern according to the cairo_font_options_t fields !
> - re-run a fontconfig query to create a match-pattern (this is sloooooow)
> - use the latter to do the rendering...

This is what I like it to look like, but unfortunately we don't have
such luxuries as query-pattern to match-pattern mapping is one-to-many.

> In comparison, the current scheme is:
> - if the scaled font was created from a FcPattern, ignore all fields of a cairo_font_options_t,
>   only use the settings in the pattern, if any
> - if the scaled font was not created from a FcPattern, apply the cairo_font_options_t fields

Right.  Because font options should be applied before FcFontSort().  The
belong into query pattern, not match pattern.

> which is a blatant lack of abstraction, confusing and a pain to deal with if you want to write portable code
> with Cairo, since you need to "remember" somewhere if a given scaled font was created with Cairo or not
> (and if it is, you need a way to access the corresponding pattern to alter its fields if needed).


> I would thus suggest to implement both "correct" schemes in Cairo. I personally think that using
> query-patterns as input to scaled-font creation is stupid, but there is no reason that we should prevent
> people to shoot themselves in the foot if they really want to. Just make the query/match choice explicit
> when creating the scaled font from the pattern, in order to greatly optimize the first case.

So, hopefully I've made it clear by now that Pango's use case fits in
none of those cases.  Pango does FcFontSort(), then create a cairo font
face and then scaled font for each returned match pattern.

> > Given the way fontconfig works (that you can totally choose different
> > fonts based on anything (size, etc...)), I don't see how this can be
> > fixed without regression.
> >
> I hope my proposal would work. If not, I'd be happy to know exactly why.

I hope you come up with a proposal that works too.  It's too much pain
currently :).

> And thanks a lot for looking at this patch. I greatly appreciate it.

Sorry that it slipped again.  I'll try to get it in for 1.6.



> Regards,
> - David Turner
> - The FreeType Project  (www.freetype.org)
> > 
> > > Thanks in advance,
> > > 
> > > - David Turner
> > > - The FreeType Project  (www.freetype.org)
> > -- 
> > behdad
> > http://behdad.org/
> > 
> > "Those who would give up Essential Liberty to purchase a little
> >  Temporary Safety, deserve neither Liberty nor Safety."
> >         -- Benjamin Franklin, 1759
> > 
> > 
> > 

"Those who would give up Essential Liberty to purchase a little
 Temporary Safety, deserve neither Liberty nor Safety."
        -- Benjamin Franklin, 1759

More information about the cairo mailing list