📄 ftifi.c
字号:
/* *//* OS/2 Font Driver using the FreeType library *//* *//* Copyright (C) 1997, 1998 Michal Necasek <mike@mendelu.cz> *//* Copyright (C) 1997, 1998 David Turner <turner@email.ENST.Fr> *//* Copyright (C) 1997, 1998 International Business Machines *//* *//* Version: 0.9.90 (Beta) *//* *//* This source is to be compiled with IBM VisualAge C++ 3.0 or possibly *//* Watcom C/C++ 10.0 or higher (Wactom doesn't quite work yet). *//* Other compilers may actually work too but don't forget this is NOT a *//* normal DLL but rather a subsystem DLL. That means it shouldn't use *//* the usual C library as it has to run without runtime environment. *//* VisualAge provides a special subsystem version of the run-time library. *//* All this is of course very compiler-dependent. See makefiles for *//* discussion of switches used. *//* *//* Implemantation Notes: *//* *//* Note #1: As a consequence of this being a subsystem librarary, I had to *//* slightly modify the FreeType source, namely ttmemory.c and ttfile.c. *//* FreeType/2 now allocates several chunks of memory and uses them as a *//* heap. Note that memory allocation should use TTAlloc(), possibly *//* directly SSAllocMem(). malloc() is unusable here and it doesn't work *//* at all (runtime library isn't even initialized). See ttmemory.c for *//* more info. *//* In ttfile.c I had to change all fopen(), fseek()... calls *//* to OS/2 API calls (DosOpen, DosSetFilePtr...) because without proper *//* runtime environment a subsystem DLL cannot use std C library calls. *//* *//* Note #2: On exit of each function reading from font file the API *//* TT_Flush_Stream() must be called. This is because file handles opened *//* by this DLL actually belong to the calling process. As a consequence *//* a) it's easy to run out of file handles, which results in really *//* very nasty behavior and/or crashes. This could be solved by *//* increased file handles limit, but cannot because *//* b) it is impossible to close files open by another process and *//* therefore the fonts cannot be properly uninstalled (you can't *//* delete them while the're open by other process) *//* The only solution I found is very simple - just close the file before *//* exiting a DLL function. This ensures files are not left open across *//* processes and other problems. *//* *//* Note #3: The whole business with linked lists is aimed at lowering *//* memory consumption drastically. If you install 50 TT fonts, OS/2 *//* opens all of them at startup. Even if you never use them, they take *//* up at least over 1 Meg memory. With certain fonts the consumption can *//* easily go over several MB. We limit such waste of memory by only *//* actually keeping open several typefaces most recently used. Their *//* number can be set via entry in OS2.INI. *//* *//* For Intelligent Font Interface (IFI) specification please see IFI32.TXT */#ifndef __IBMC__ #ifndef __WATCOMC__ #error "This source requires IBM VisualAge C++ or Watcom C/C++" #endif#endif/* Defining the following uses UCONV.DLL instead of the built-in *//* translation tables. This code should work on any Warp 4 and *//* Warp 3 w/ FixPak 35(?) and above *//* Note: this should be defined before FTIFI.H is #included */#undef USE_UCONV#define INCL_WINSHELLDATA /* for accessing OS2.INI */#define INCL_DOSMISC#define INCL_DOSNLS#define INCL_DOSPROCESS#define INCL_GRE_DCS#define INCL_GRE_DEVSUPPORT#define INCL_DDIMISC#define INCL_IFI#include <os2.h>#include <pmddi.h> /* SSAllocmem(), SSFreemem() and more */#ifdef USE_UCONV /* uconv.h isn't always available */#include <uconv.h>#endif /* USE_UCONV */#include <string.h>#include <stdlib.h> /* min and max macros */#define _syscall _System /* the IFI headers don't compile without it */#include "32pmifi.h" /* IFI header */#include "freetype.h" /* FreeType header */#include "ftxkern.h" /* kerning extension */#include "ftxwidth.h" /* glyph width extension */#include "ftifi.h" /* xlate table *//* For the sake of Netscape's text rendering bugs ! */#define NETSCAPE_FIX/* Create 'fake' Roman face for Times New Roman (to mimic PMATM's *//* behaviour */#define FAKE_TNR/* (indirectly) exported functions */LONG _System ConvertFontFile(PSZ pszSrc, PSZ pszDestDir, PSZ pszNewName);HFF _System LoadFontFile(PSZ pszFileName);LONG _System UnloadFontFile(HFF hff);LONG _System QueryFaces(HFF hff, PIFIMETRICS pifiMetrics, ULONG cMetricLen, ULONG cFountCount, ULONG cStart);HFC _System OpenFontContext(HFF hff, ULONG ulFont);LONG _System SetFontContext(HFC hfc, PCONTEXTINFO pci);LONG _System CloseFontContext(HFC hfc);LONG _System QueryFaceAttr(HFC hfc, ULONG iQuery, PBYTE pBuffer, ULONG cb, PGLYPH pagi, GLYPH giStart);LONG _System QueryCharAttr(HFC hfc, PCHARATTR pCharAttr, PBITMAPMETRICS pbmm);LONG _System QueryFullFaces(HFF hff, PVOID pBuff, PULONG buflen, PULONG cFontCount, ULONG cStart);FDDISPATCH fdisp = { /* Font driver dispatch table */ LoadFontFile, QueryFaces, UnloadFontFile, OpenFontContext, SetFontContext, CloseFontContext, QueryFaceAttr, QueryCharAttr, NULL, /* this one is no more used, only the spec fails to mention it */ ConvertFontFile, QueryFullFaces};/****************************************************************************//* the single exported entry point; this way is faster than exporting every *//* single function and a bit more flexible *//* */#pragma export (fdhdr, "FONT_DRIVER_DISPATCH_TABLE", 1)FDHEADER fdhdr ={ /* Font driver Header */ sizeof(FDHEADER), "OS/2 FONT DRIVER", /* do not change */ "TrueType (Using FreeType Engine)", /* description up to 40 chars */ IFI_VERSION20, /* version */ 0, /* reserved */ &fdisp};/****************************************************************************//* some debug macros and functions. the debug version logs system requests *//* to the file C:\FTIFI.LOG *//* */#ifdef DEBUG HFILE LogHandle = NULLHANDLE; ULONG Written = 0; char log[2048] = ""; char buf[2048] = "";char* itoa10( int i, char* buffer ) { char* ptr = buffer; char* rptr = buffer; char digit; if (i == 0) { buffer[0] = '0'; buffer[1] = 0; return buffer; } if (i < 0) { *ptr = '-'; ptr++; rptr++; i = -i; } while (i != 0) { *ptr = (char) (i % 10 + '0'); ptr++; i /= 10; } *ptr = 0; ptr--; while (ptr > rptr) { digit = *ptr; *ptr = *rptr; *rptr = digit; ptr--; rptr++; } return buffer;} #define COPY(s) strcpy(log, s) #define CAT(s) strcat(log, s) #define CATI(v) strcat(log, itoa10( (int)v, buf )) #define WRITE DosWrite(LogHandle, log, strlen(log), &Written) #define ERET1(label) { COPY("Error at "); \ CATI(__LINE__); \ CAT("\r\n"); \ WRITE; \ goto label; \ } #define ERRRET(e) { COPY("Error at "); \ CATI(__LINE__); \ CAT("\r\n"); \ WRITE; \ return(e); \ }#else #define COPY(s) #define CAT(s) #define CATI(v) #define WRITE #define ERET1(label) goto label; #define ERRRET(e) return(e);#endif /* DEBUG *//****************************************************************************//* *//* 'engine' : *//* *//* The FreeType engine instance. Although this is a DLL, it isn't *//* supposed to be shared by apps, as it is only called by the OS/2 GRE. *//* This means that there is no need to bother with reentrancy/thread *//* safety, which aren't supported by FreeType 1.0 anyway. *//* */TT_Engine engine;/****************************************************************************//* *//* TList and TListElement : *//* *//* simple structures used to implement a doubly linked list. Lists are *//* used to implement the HFF object lists, as well as the font size and *//* outline caches. *//* */typedef struct _TListElement TListElement, *PListElement;struct _TListElement{ PListElement next; /* next element in list - NULL if tail */ PListElement prev; /* previous element in list - NULL if head */ long key; /* value used for searches */ void* data; /* pointer to the listed/cached object */};typedef struct _TList TList, *PList;struct _TList{ PListElement head; /* first element in list - NULL if empty */ PListElement tail; /* last element in list - NULL if empty */ int count; /* number of elements in list */};static PListElement free_elements = 0;#if 0/****************************************************************************//* *//* TGlyph_Image : *//* *//* structure used to store a glyph's attributes, i.e. outlines and metrics *//* Note that we do not cache bitmaps ourselves for the moment. *//* */typedef struct _TGlyph_Image TGlyph_Image, *PGlyph_Image;struct _TGlyph_Image{ PListElement element; /* list element for this glyph image */ TT_Glyph_Metrics metrics; TT_Outline outline;};#endif/****************************************************************************//* *//* TFontFace : *//* *//* a structure related to an open font face. It contains data for each of *//* possibly several faces in a .TTC file. */typedef struct _TFontFace TFontFace, *PFontFace;struct _TFontFace{ TT_Face face; /* handle to actual FreeType face object */ TT_Glyph glyph; /* handle to FreeType glyph container */ TT_CharMap charMap; /* handle to FreeType character map */ TT_Kerning directory; /* kerning directory */ USHORT *widths; /* glyph width cache for large fonts */ USHORT *kernIndices; /* reverse translation cache for kerning */ LONG em_size; /* points per em square */ ULONG flags; /* various FC_* flags (like FC_FLAG_FIXED)*/#if 0 /* not now */ TList sizes; /* list of live child font sizes */#endif LONG charMode; /* character translation mode : */ /* 0 = Unicode to UGL */ /* 1 = Symbol (no translation) */ /* 2 = Unicode w/o translation */};/****************************************************************************//* *//* TFontFile : *//* *//* a structure related to an open font file handle. All TFontFiles are *//* kept in a simple linked list. There can be several faces in one font. *//* Face(s) information is stored in a variable-length array of TFontFaces. *//* A single TFontFile structure exactly corresponds to one HFF. */typedef struct _TFontFile TFontFile, *PFontFile;struct _TFontFile{ PListElement element; /* list element for this font face */ HFF hff; /* HFF handle used from outside */ CHAR filename[260]; /* font file name */ LONG ref_count; /* number of times this font file is open */ ULONG flags; /* various FL_* flags */ ULONG numFaces; /* number of faces in a file (normally 1) */ TFontFace *faces; /* array of FontFace structures */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -