The New Font Format

Handling the new font format is optional for display drivers. A display driver indicates that it is capable of handling the new font format as well as the Windows 3.x font format by setting the C1_BYTE_PACKED or C1_BIT_PACKED bit in dpCaps1 of the GDIINFO structure at enable time.

The NewFontSeg structure defines the new font format and replaces the old FONTINFO structure.


typedef struct _NewFontSeg
{
    WORD  nfVersion;      // version of the font header
    WORD  nfFormat;          // format flags for font
    WORD  nfNumGlyphs;    // number of glyphs in the font
    DWORD nfGlyphOffset;  // offset to array of glyph pointers
    DWORD nfAWTable;      // offset to array of glyph advance widths
    WORD  nfHeight;          // windows font height
    WORD  nfAscent;          // distance from top of font to baseline
    DWORD nfUniqueID;     // unique value that identifies this font
} NewFontSeg;

The new header is simpler than the old FONTINFO structure. Only the information needed to locate the glyph bitmaps and do font caching in the driver is available. All other information is maintained by GDI.

The main differences between the old format and the new format are:

Byte-packed glyphs are stored in rows where each row is padded out to a byte boundary. For example, a glyph that is 1 pixel wide and 10 pixels tall would require 10 bytes [int((1+7)/8)* 10] of storage. Each glyph bitmap is preceded by a header.


typedef struct _SMALLROWGLYPH
{
  SBYTE srgOrgX;  // distance from glyph org to left edge of blackbox
  SBYTE srgOrgY;  // distance from glyph org to top of glyph blackbox
  BYTE  srgWidth; // width of glyph's blackbox
  BYTE  srgHeight; // height of glyph's blackbox
} SMALLROWGLYPH;

typedef struct _LARGEROWGLYPH
{
  SHORT lrgOrgX;  // distance from glyph org to left edge of blackbox
  SHORT lrgOrgY;  // distance from glyph org to top of glyph blackbox
  USHORT  lrgWidth;  // width of glyph's blackbox
  USHORT  lrgHeight; // height of glyph's blackbox
} LARGEROWGLYPH;

Bit-packed glyphs are stored in rows with no padding. For example, the same 1x10 glyph would only require 2 bytes [int((1*10+7)/8)] of storage. Bit-packed format yields the highest memory savings and highest performance provided the display hardware can accept data in this format. Each glyph bitmap is preceded by a header.


typedef struct _SMALLBITGLYPH
{
  SBYTE sbgOrgX; // distance from glyph org to left edge of blackbox
  SBYTE sbgOrgY;  // distance from glyph org to top of glyph blackbox
  BYTE  sbgWidth;  // width of glyph's blackbox
  BYTE  sbgHeight; // height of glyph's blackbox
  BYTE  sbgPixels; // number of bits in glyph (width * height)
} SMALLBITGLYPH;

typedef struct _LARGEBITGLYPH
{
  SHORT lbgOrgX;  // distance from glyph org to left edge of blackbox
  SHORT lbgOrgY;  // distance from glyph org to top of glyph blackbox
  USHORT  lbgWidth;  // width of glyph's blackbox
  USHORT  lbgHeight; // height of glyph's blackbox
  USHORT  lbgPixels; // number of bits in glyph (width * height)
} LARGEROWGLYPH;

See also NewFontSeg, SMALLROWGLYPH, LARGEROWGLYPH, SMALLBITGLYPH, LARGEBITGLYPH