Re: Downloadable fonts and image replacement

On Apr 27, 2006, at 5:09 AM, Håkon Wium Lie wrote:

> So, something like this:
>
>    .company {
>      font-family: url(fonts/company.svg), url(img/company.svg),
>         url(img/companty.png), url(fonts/goodfish.zip), "Impact",  
> serif;
>    }
>
> (It doesn't quite do what you want it to as the images (svg and png)
> are generic to the whole class.)
>
Yes, and while obviously you could just set it by ID instead, it  
would be kind of irritating that you would have to list the whole  
order-of-preferences each time rather than somehow being able to just  
add the images to each element.  It just doesn't quite seem right to  
have the replacement images as part of the font-family property.   
However, using more than one property, it would be hard to specify  
arbitrary orderings.  It might work to group all the replaced content  
together and have a keyword in the font-family list that specified  
where the replaced content goes, although then wouldn't we also need  
a way to select the content based on the activation of that keyword?   
Something like this might work:

.company {
	font-family: url(fonts/company.svg#companyfont), fallbackimage, url 
(fonts/goodfish.zip), "Impact", serif;
}

#companyname:fallbackimage {
	content: url(img/companyname.svg), url(img/companyname.png), contents;
}

#divisionname:fallbackimage {
	content: url(img/divisionname.svg), url(img/divisionname.png),  
contents;
}

I suppose the way to implement that would be to have the font engine  
activate the fallbackimage psuedo-class if it encounters the  
fallbackimage keyword in the font-family, and then continue down the  
list until it successfully gets a font it can render.  Then, the  
fallbackimage psuedo-class selector is used to activate the  
replacement content (which in this example would have to all fall in  
one position in the font list), which ends with the "contents"  
keyword in case the images all fail, which would then be rendered in  
whatever font was successfully loaded.

This is sort of the inverse of your previous #3 suggestion "Use  
'content' and 'font-family'".  The earlier one limited the webfonts  
to one region of the ordering, this version instead limits the  
replacement content to one position in the ordering.

To make an arbitrary ordering possible, perhaps a pseudo-class that  
selects based on the rank number of the font that has successfully  
been loaded (or the first that failed to load) would work.  In that  
case, no explicit keyword would be necessary since the rank order  
could implicitly set a keyword for each position.  To clarify, in the  
font family property, the list of n fonts could be numbered  
1,2,3,4,5,..n and in the example:

.company {
	font-family: url(fonts/company.svg#companyfont), url(fonts/ 
goodfish.zip), "Impact", serif;
}

If the SVG font url(fonts/company.svg#companyfont) were loaded  
successfully, then the psuedo-class ":font-family-fail(0)" would be  
activated, indicating none of the fonts failed to load.
If the SVG font url(fonts/company.svg#companyfont) failed to load,  
then the psuedo-class ":font-family-fail(1)" would be activated.
If the truetype font url(fonts/goodfish.zip) failed to load, then the  
pseudo-class ":font-family-fail(2)" would be activated.
If the "Impact" font failed to load, then the pseudo-class ":font- 
family-fail(3)" would be activated.
If the generic serif font failed to load, then the pseudo-class  
":font-family-fail(4)" would be activated.


A full example (which specifies the ordering SVG font, SVG image,  
truetype font, PNG image, JPEG image, System font, generic font) for  
two elements in the class company that get different replacement  
content:

.company {
	font-family: url(fonts/company.svg#companyfont), url(fonts/ 
goodfish.zip), "Impact", serif;
}

#companyname:font-family-fail(2) {
	content: url(img/companyname.png), url(img/companyname.jpeg), contents;
}

#companyname:font-family-fail(1) {
	content: url(img/companyname.svg), contents;
}

#divisionname:font-family-fail(2) {
	content: url(img/divisionname.png), url(img/divisionname.jpeg),  
contents;
}

#divisionname:font-family-fail(1) {
	content: url(img/divisionname.svg), contents;
}


This would give authors the ability to specify arbitrary orderings  
between fonts and replacement content.  It also doesn't cause  
confusion by putting things that aren't fonts in the font-family  
property.  However, it does obviously require the addition of a new  
pseudo-class, which is more implementation work than any of the other  
suggestions, although it seems to me to be a cleaner solution than  
multiple keywords would be.  Would having a new pseudo-class for this  
purpose be overly complex, or is the ability to have arbitrary  
orderings important enough to make it worth it?


>> "The purpose of SVG fonts is to allow for delivery of glyph outlines
>> in display-only environments. SVG fonts that accompany Web pages must
>> be supported only in browsing and viewing situations. Graphics
>> editing applications or file translation tools must not attempt to
>> convert SVG fonts into system fonts." (http://www.w3.org/TR/SVG/
>> fonts.html#SVGFontsOverview)
>
> Hmm, this could be troublesome. From discussion with our engineers, it
> seems clear that we want to convert all webfonts to system fonts and
> inject them into the system. This way, the browser's display engine
> only have to relate to one font API. So, an incoming SVG font would be
> converted to a format the system can accept. This would be
> TrueType/OpenType, in most cases. So, if this conversion is
> discouraged, adding support for SVG fonts could require more work than
> we want to do. The restriction only applies to "Graphics editing
> applications or file translation tools" so it may still be possible
> for a browser to convert, as long as the "system fonts" are not
> exposed to other applications. A clarification would be helpful.

At least some system font APIs do not require a font to be  
"installed" in order to use it or allow an application to specify  
that a font should only be installed for use by a particular  
process.  Freetype is happy to load a font from memory or from a file  
specified by an application.  On WinXP, you can call  
AddFontResourceEx with the FR_PRIVATE flag, which should limit access  
to the font.

>
> Has anyone written the SVG-to-TTF converter?
Not that I know of, although I don't see any reason that it would be  
any more complicated to go that way than it is to go TTF-to-SVG.   
Browser support for SVG fonts by relying on the underlying OS is the  
first use case I've heard of that would require an SVG-to-TTF  
converter (since there isn't really a huge library of SVG fonts out  
there that people want to use in their truetype systems).

I had thought that one of the benefits of SVG fonts was that all the  
work in rendering them would be done by the browser's internal SVG  
engine, such that the rendering would be handled the same way on all  
platforms.  I suppose the problem with that is that the layout code  
in most browsers is probably tightly tied to system font engines, and  
doesn't have appropriate hooks with which to support multiple font  
engines simultaneously?


Joshua RANDALL <joshua.randall@francetelecom.com>
Senior Research Specialist
France Telecom R&D, Boston

Received on Thursday, 27 April 2006 18:36:27 UTC