| <!doctype html public "-//w3c//dtd html 4.0 transitional//en" |
| "http://www.w3.org/TR/REC-html40/loose.dtd"> |
| <html> |
| <head> |
| <meta http-equiv="Content-Type" |
| content="text/html; charset=iso-8859-1"> |
| <meta name="Author" |
| content="David Turner"> |
| <title>The Design of FreeType 2 - Internal Objects</title> |
| </head> |
| |
| <body text="#000000" |
| bgcolor="#ffffff"> |
| |
| <h1 align=center> |
| The Design of FreeType 2 |
| </h1> |
| |
| <center> |
| <table width="75%"> |
| <tr><td> |
| |
| <table width="100%"> |
| <tr bgcolor="#ccccee"><td> |
| <h1> |
| III. Internal Objects and Classes |
| </h1> |
| </td></tr> |
| </table> |
| |
| <p>Let us have a look now at the <em>internal</em> objects that |
| FreeType 2 uses, i.e., those not directly available to client |
| applications, and see how they fit into the picture.</p> |
| |
| <h2> |
| 1. Memory management |
| </h2> |
| |
| <p>All memory management operations are performed through three specific |
| routines of the base layer, namely: <tt>FT_Alloc()</tt>, |
| <tt>FT_Realloc()</tt>, and <tt>FT_Free()</tt>. Each one of these |
| functions expects a <tt>FT_Memory</tt> handle as its first |
| parameter.</p> |
| |
| <p>The latter is a pointer to a simple object used to describe the |
| current memory pool/manager. It contains a simple table of |
| alloc/realloc/free functions. A memory manager is created at library |
| initialization time by <tt>FT_Init_FreeType()</tt>, calling the function |
| <tt>FT_New_Memory()</tt> provided by the <tt>ftsystem</tt> |
| component.</p> |
| |
| <p>By default, this manager uses the ANSI <tt>malloc()</tt>, |
| <tt>realloc()</tt>, and <tt>free()</tt> functions. However, as |
| <tt>ftsystem</tt> is a replaceable part of the base layer, a specific |
| build of the library could provide a different default memory |
| manager.</p> |
| |
| <p>Even with a default build, client applications are still able to |
| provide their own memory manager by not calling |
| <tt>FT_Init_FreeType()</tt> but follow these simple steps:</p> |
| |
| <ol> |
| <li> |
| <p>Create a new <tt>FT_Memory</tt> object by hand. The definition |
| of <tt>FT_MemoryRec</tt> is located in the public file |
| <tt><freetype/ftsystem.h></tt>.</p> |
| </li> |
| <li> |
| <p>Call <tt>FT_New_Library()</tt> to create a new library instance |
| using your custom memory manager. This new library doesn't yet |
| contain any registered modules.</p> |
| </li> |
| <li> |
| <p>Register the set of default modules by calling the function |
| <tt>FT_Add_Default_Modules()</tt> provided by the <tt>ftinit</tt> |
| component, or manually register your drivers by repeatedly |
| calling <tt>FT_Add_Module()</tt>.</p> |
| </li> |
| </ol> |
| |
| <hr> |
| |
| <h2> |
| 2. Input streams |
| </h2> |
| |
| <p>Font files are always read through <tt>FT_Stream</tt> objects. The |
| definition of <tt>FT_StreamRec</tt> is located in the public file |
| <tt><freetype/ftsystem.h></tt>, which allows client developers to |
| provide their own implementation of streams if they wish so.</p> |
| |
| <p>The function <tt>FT_New_Face()</tt> will always automatically create |
| a new stream object from the C pathname given as its second |
| argument. This is achieved by calling the function |
| <tt>FT_New_Stream()</tt> provided by the <tt>ftsystem</tt> component. |
| As the latter is replaceable, the implementation of streams may vary |
| greatly between platforms.</p> |
| |
| <p>As an example, the default implementation of streams is located in |
| the file <tt>src/base/ftsystem.c</tt> and uses the ANSI |
| <tt>fopen()</tt>, <tt>fseek()</tt>, and <tt>fread()</tt> calls. |
| However, the Unix build of FreeType 2 provides an alternative |
| implementation that uses memory-mapped files, when available on the host |
| platform, resulting in a significant access speed-up.</p> |
| |
| <p>FreeType distinguishes between memory-based and disk-based streams. |
| In the first case, all data is directly accessed in memory (e.g. |
| ROM-based, write-only static data and memory-mapped files), while in the |
| second, portions of the font files are read in chunks called |
| <em>frames</em>, and temporarily buffered similarly through typical |
| seek/read operations.</p> |
| |
| <p>The FreeType stream sub-system also implements extremely efficient |
| algorithms to very quickly load structures from font files while |
| ensuring complete safety in the case of a "broken file".</p> |
| |
| <p>The function <tt>FT_New_Memory_Face()</tt> can be used to directly |
| create/open a <tt>FT_Face</tt> object from data that is readily |
| available in memory (including ROM-based fonts).</p> |
| |
| <p>Finally, in the case where a custom input stream is needed, client |
| applications can use the function <tt>FT_Open_Face()</tt>, which can |
| accept custom input streams. This may be useful in the case of |
| compressed or remote font files, or even embedded font files that need |
| to be extracted from certain documents.</p> |
| |
| <p>Note that each face owns a single stream, which is also destroyed by |
| <tt>FT_Done_Face()</tt>. Generally speaking, it is certainly |
| <em>not</em> a good idea to keep numerous <tt>FT_Face</tt> objects |
| opened.</p> |
| |
| <hr> |
| |
| <h2> |
| 3. Modules |
| </h2> |
| |
| <p>A FreeType 2 module is itself a piece of code. However, the |
| library creates a single <tt>FT_Module</tt> object for each module that |
| is registered when <tt>FT_Add_Module()</tt> is called.</p> |
| |
| <p>The definition of <tt>FT_ModuleRec</tt> is not publicly available to |
| client applications. However, each <em>module type</em> is described by |
| a simple public structure named <tt>FT_Module_Class</tt>, defined in |
| <tt><freetype/ftmodule.h></tt>, and is described later in this |
| document:</p> |
| |
| <p>You need a pointer to an <tt>FT_Module_Class</tt> structure when |
| calling <tt>FT_Add_Module()</tt>, whose declaration is:</p> |
| |
| <font color="blue"><pre> |
| FT_Error FT_Add_Module( FT_Library library, |
| const FT_Module_Class* clazz );</pre> |
| </font> |
| |
| <p>Calling this function will do the following:</p> |
| |
| <ul> |
| <li> |
| <p>It will check whether the library already holds a module object |
| corresponding to the same module name as the one found in |
| <tt>FT_Module_Class</tt>.</p> |
| </li> |
| <li> |
| <p>If this is the case, it will compare the module version number to |
| see whether it is possible to <em>upgrade</em> the module to a new |
| version. If the module class's version number is smaller than the |
| already installed one, the function returns immediately. Similarly, |
| it checks that the version of FreeType 2 that is running is |
| correct compared to the one required by the module.</p> |
| </li> |
| <li> |
| <p>It creates a new <tt>FT_Module</tt> object, using data and flags |
| of the module class to determine its byte size and how to properly |
| initialize it.</p> |
| </li> |
| <li> |
| <p>If a module initializer is present in the module class, it will |
| be called to complete the module object's initialization.</p> |
| </li> |
| <li> |
| <p>The new module is added to the library's list of "registered" |
| modules. In case of an upgrade, the previous module object is |
| simply destroyed.</p> |
| </li> |
| </ul> |
| |
| <p>Note that this function doesn't return an <tt>FT_Module</tt> handle, |
| given that module objects are completely internal to the library (and |
| client applications shouldn't normally mess with them :-)</p> |
| |
| <p>Finally, it is important to understand that FreeType 2 |
| recognizes and manages several kinds of modules. These will be |
| explained in more details later in this document, but we will list for |
| now the following types:</p> |
| |
| <ul> |
| <li> |
| <p><em>Renderer</em> modules are used to convert native glyph images |
| to bitmaps/pixmaps. FreeType 2 comes with two renderer modules |
| by default: one to generate monochrome bitmaps, the other to |
| generate high-quality anti-aliased pixmaps.</p> |
| </li> |
| <li> |
| <p><em>Font driver</em> modules are used to support one or more font |
| formats. Typically, each font driver provides a specific |
| implementation/derivative of <tt>FT_Face</tt>, <tt>FT_Size</tt>, |
| <tt>FT_GlyphSlot</tt>, as well as <tt>FT_CharMap</tt>.</p> |
| </li> |
| <li> |
| <p><em>Helper</em> modules are shared by several font drivers. For |
| example, the <tt>sfnt</tt> module parses and manages tables found in |
| SFNT-based font formats; it is then used by both the TrueType and |
| OpenType font drivers.</p> |
| </li> |
| <li> |
| <p>Finally, the <em>auto-hinter</em> module has a specific place in |
| the library's design, as its role is to process vectorial glyph |
| outlines, independently of their native font format, to produce |
| optimal results at small pixel sizes.</p> |
| </li> |
| </ul> |
| |
| <p>Note that every <tt>FT_Face</tt> object is <em>owned</em> by the |
| corresponding font driver, depending on the original font file's format. |
| This means that all face objects are destroyed when a module is |
| removed/unregistered from a library instance (typically by calling the |
| <tt>FT_Remove_Module()</tt> function).</p> |
| |
| <p><em>Because of this, you should always take care that no |
| <tt>FT_Face</tt> object is opened when you upgrade or remove a module |
| from a library, as this could cause unexpected object deletion!</em></p> |
| |
| <hr> |
| |
| <h2> |
| 4. Libraries |
| </h2> |
| |
| <p>We now come back to our well-known <tt>FT_Library</tt> object. From |
| what have been said before, we already know that a library instance owns |
| at least the following:</p> |
| |
| <ul> |
| <li> |
| <p>A memory manager object (<tt>FT_Memory</tt>), used for all |
| allocation/releases within the instance.</p> |
| </li> |
| <li> |
| <p>A list of <tt>FT_Module</tt> objects, corresponding to the |
| "installed" or "registered" modules of the instance. This list can |
| be changed at any time through <tt>FT_Add_Module()</tt> and |
| <tt>FT_Remove_Module()</tt>.</p> |
| </li> |
| <li> |
| <p>Remember that face objects are owner by font drivers that are |
| themselves modules owned by the library.</p> |
| </li> |
| </ul> |
| |
| <p>There is however another object owned by the library instance that |
| hasn't been described yet: the <em>raster pool</em>.</p> |
| |
| <p>The <em>raster pool</em> is simply a block of memory of fixed size |
| that is used internally as a "scratch area" for various memory-hungry |
| transient operations, avoiding memory allocation. For example, it is |
| used by each renderer when converting a vectorial glyph outline into a |
| bitmap (actually, that's where its name comes from :-).</p> |
| |
| <p>The size of the raster pool is fixed at initialisation time (it |
| defaults to 16kByte) and cannot be changed at run-time (though we could |
| fix this if there is a real need for that).</p> |
| |
| <p>When a transient operation needs more memory than the pool's size, it |
| can decide to either allocate a heap block as an exceptional condition, |
| or sub-divide recursively the task to perform in order to never exceed |
| the pool's threshold.</p> |
| |
| <p>This extremely memory-conservative behaviour is certainly one of the |
| keys to FreeType's performance in certain areas (most importantly in |
| glyph rendering/scanline-conversion).</p> |
| |
| <hr> |
| |
| <h2> |
| 5. Summary |
| </h2> |
| |
| <p>Finally, the following picture illustrates what has been said in this |
| section, as well as the previous, by presenting the complete object |
| graph of FreeType 2's base design:</p> |
| |
| <center> |
| <img alt="to be done"> |
| </center> |
| |
| </td></tr> |
| </table> |
| </center> |
| </body> |
| </html> |