diff -r f345bda72bc4 -r 43e37759235e Symbian3/Examples/guid-6013a680-57f9-415b-8851-c4fa63356636/fonts_8c_source.html --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/Symbian3/Examples/guid-6013a680-57f9-415b-8851-c4fa63356636/fonts_8c_source.html Tue Mar 30 16:16:55 2010 +0100 @@ -0,0 +1,1034 @@ + + + + +TB9.2 Example Applications: examples/PIPS/antiword/src/fonts.c Source File + + + + + +

examples/PIPS/antiword/src/fonts.c

00001 /*
+00002  * fonts.c
+00003  * Copyright (C) 1998-2004 A.J. van Os; Released under GNU GPL
+00004  *
+00005  * Description:
+00006  * Functions to deal with fonts (generic)
+00007  */
+00008 
+00009 #include <ctype.h>
+00010 #include <string.h>
+00011 #include "antiword.h"
+00012 
+00013 /* Maximum line length in the font file */
+00014 #define FONT_LINE_LENGTH        81
+00015 
+00016 /* Pitch */
+00017 #define PITCH_UNKNOWN           0
+00018 #define PITCH_FIXED             1
+00019 #define PITCH_VARIABLE          2
+00020 
+00021 /* Font Family */
+00022 #define FAMILY_UNKNOWN          0
+00023 #define FAMILY_ROMAN            1
+00024 #define FAMILY_SWISS            2
+00025 #define FAMILY_MODERN           3
+00026 #define FAMILY_SCRIPT           4
+00027 #define FAMILY_DECORATIVE       5
+00028 
+00029 /* Font Translation Table */
+00030 static size_t           tFontTableRecords = 0;
+00031 static font_table_type  *pFontTable = NULL;
+00032 
+00033 /*
+00034  * Find the given font in the font table
+00035  *
+00036  * returns the index into the FontTable, -1 if not found
+00037  */
+00038 int
+00039 iGetFontByNumber(UCHAR ucWordFontNumber, USHORT usFontStyle)
+00040 {
+00041         int     iIndex;
+00042 
+00043         for (iIndex = 0; iIndex < (int)tFontTableRecords; iIndex++) {
+00044                 if (ucWordFontNumber == pFontTable[iIndex].ucWordFontNumber &&
+00045                     usFontStyle == pFontTable[iIndex].usFontStyle &&
+00046                     pFontTable[iIndex].szOurFontname[0] != '\0') {
+00047                         return iIndex;
+00048                 }
+00049         }
+00050         DBG_DEC(ucWordFontNumber);
+00051         DBG_HEX(usFontStyle);
+00052         return -1;
+00053 } /* end of iGetFontByNumber */
+00054 
+00055 /*
+00056  * szGetOurFontname - Get our font name
+00057  *
+00058  * return our font name from the given index, NULL if not found
+00059  */
+00060 const char *
+00061 szGetOurFontname(int iIndex)
+00062 {
+00063         if (iIndex < 0 || iIndex >= (int)tFontTableRecords) {
+00064                 return NULL;
+00065         }
+00066         return pFontTable[iIndex].szOurFontname;
+00067 } /* end of szGetOurFontname */
+00068 
+00069 /*
+00070  * Find the given font in the font table
+00071  *
+00072  * returns the Word font number, -1 if not found
+00073  */
+00074 int
+00075 iFontname2Fontnumber(const char *szOurFontname, USHORT usFontStyle)
+00076 {
+00077         int     iIndex;
+00078 
+00079         for (iIndex = 0; iIndex < (int)tFontTableRecords; iIndex++) {
+00080                 if (pFontTable[iIndex].usFontStyle == usFontStyle &&
+00081                     STREQ(pFontTable[iIndex].szOurFontname, szOurFontname)) {
+00082                         return (int)pFontTable[iIndex].ucWordFontNumber;
+00083                 }
+00084         }
+00085         return -1;
+00086 } /* end of iFontname2Fontnumber */
+00087 
+00088 /*
+00089  * szGetDefaultFont - get the default font that matches the parameters
+00090  */
+00091 static const char *
+00092 szGetDefaultFont(UCHAR ucFFN, int iEmphasis)
+00093 {
+00094         UCHAR   ucPrq, ucFf;
+00095 
+00096         fail(iEmphasis < 0 || iEmphasis > 3);
+00097 
+00098         ucPrq = ucFFN & 0x03;
+00099         ucFf = (ucFFN & 0x70) >> 4;
+00100         NO_DBG_DEC(ucPrq);
+00101         NO_DBG_DEC(ucFf);
+00102         if (ucPrq == PITCH_FIXED) {
+00103                 /* Set to the default monospaced font */
+00104                 switch (iEmphasis) {
+00105                 case 1: return FONT_MONOSPACED_BOLD;
+00106                 case 2: return FONT_MONOSPACED_ITALIC;
+00107                 case 3: return FONT_MONOSPACED_BOLDITALIC;
+00108                 default: return FONT_MONOSPACED_PLAIN;
+00109                 }
+00110         } else if (ucFf == FAMILY_ROMAN) {
+00111                 /* Set to the default serif font */
+00112                 switch (iEmphasis) {
+00113                 case 1: return FONT_SERIF_BOLD;
+00114                 case 2: return FONT_SERIF_ITALIC;
+00115                 case 3: return FONT_SERIF_BOLDITALIC;
+00116                 default: return FONT_SERIF_PLAIN;
+00117                 }
+00118         } else if (ucFf == FAMILY_SWISS) {
+00119                 /* Set to the default sans serif font */
+00120                 switch (iEmphasis) {
+00121                 case 1: return FONT_SANS_SERIF_BOLD;
+00122                 case 2: return FONT_SANS_SERIF_ITALIC;
+00123                 case 3: return FONT_SANS_SERIF_BOLDITALIC;
+00124                 default: return FONT_SANS_SERIF_PLAIN;
+00125                 }
+00126         } else {
+00127                 /* Set to the default default font */
+00128                 switch (iEmphasis) {
+00129                 case 1: return FONT_SERIF_BOLD;
+00130                 case 2: return FONT_SERIF_ITALIC;
+00131                 case 3: return FONT_SERIF_BOLDITALIC;
+00132                 default: return FONT_SERIF_PLAIN;
+00133                 }
+00134         }
+00135 } /* end of szGetDefaultFont */
+00136 
+00137 /*
+00138  * See if the fontname from the Word file matches the fontname from the
+00139  * font translation file.
+00140  * If iBytesPerChar is one than aucWord is in ISO-8859-x (Word 2/6/7),
+00141  * if iBytesPerChar is two than aucWord is in Unicode (Word 8/9/10).
+00142  */
+00143 static BOOL
+00144 bFontEqual(const UCHAR *aucWord, const char *szTable, int iBytesPerChar)
+00145 {
+00146         const UCHAR     *pucTmp;
+00147         const char      *pcTmp;
+00148 
+00149         fail(aucWord == NULL || szTable == NULL);
+00150         fail(iBytesPerChar != 1 && iBytesPerChar != 2);
+00151 
+00152         for (pucTmp = aucWord, pcTmp = szTable;
+00153              *pucTmp != 0;
+00154              pucTmp += iBytesPerChar, pcTmp++) {
+00155                 if (ulToUpper((ULONG)*pucTmp) !=
+00156                     ulToUpper((ULONG)(UCHAR)*pcTmp)) {
+00157                         return FALSE;
+00158                 }
+00159         }
+00160         return *pcTmp == '\0';
+00161 } /* end of bFontEqual */
+00162 
+00163 /*
+00164  * vFontname2Table - add fontnames to the font table
+00165  */
+00166 static void
+00167 vFontname2Table(const UCHAR *aucFont, const UCHAR *aucAltFont,
+00168         int iBytesPerChar, int iEmphasis, UCHAR ucFFN,
+00169         const char *szWordFont, const char *szOurFont,
+00170         font_table_type *pFontTableRecord)
+00171 {
+00172         BOOL    bMatchFound;
+00173 
+00174         fail(aucFont == NULL || aucFont[0] == 0);
+00175         fail(aucAltFont != NULL && aucAltFont[0] == 0);
+00176         fail(iBytesPerChar != 1 && iBytesPerChar != 2);
+00177         fail(iEmphasis < 0 || iEmphasis > 3);
+00178         fail(szWordFont == NULL || szWordFont[0] == '\0');
+00179         fail(szOurFont == NULL || szOurFont[0] == '\0');
+00180         fail(pFontTableRecord == NULL);
+00181 
+00182         bMatchFound = bFontEqual(aucFont, szWordFont, iBytesPerChar);
+00183 
+00184         if (!bMatchFound && aucAltFont != NULL) {
+00185                 bMatchFound = bFontEqual(aucAltFont, szWordFont, iBytesPerChar);
+00186         }
+00187 
+00188         if (!bMatchFound &&
+00189             pFontTableRecord->szWordFontname[0] == '\0' &&
+00190             szWordFont[0] == '*' &&
+00191             szWordFont[1] == '\0') {
+00192                 /*
+00193                  * szWordFont contains a "*", so szOurFont will contain the
+00194                  * "default default" font. See if we can do better than that.
+00195                  */
+00196                 szOurFont = szGetDefaultFont(ucFFN, iEmphasis);
+00197                 bMatchFound = TRUE;
+00198         }
+00199 
+00200         if (bMatchFound) {
+00201                 switch (iBytesPerChar) {
+00202                 case 1:
+00203                         (void)strncpy(pFontTableRecord->szWordFontname,
+00204                                 (const char *)aucFont,
+00205                                 sizeof(pFontTableRecord->szWordFontname) - 1);
+00206                         break;
+00207                 case 2:
+00208                         (void)unincpy(pFontTableRecord->szWordFontname,
+00209                                 aucFont,
+00210                                 sizeof(pFontTableRecord->szWordFontname) - 1);
+00211                         break;
+00212                 default:
+00213                         DBG_FIXME();
+00214                         pFontTableRecord->szWordFontname[0] = '\0';
+00215                         break;
+00216                 }
+00217                 pFontTableRecord->szWordFontname[
+00218                         sizeof(pFontTableRecord->szWordFontname) - 1] = '\0';
+00219                 (void)strncpy(pFontTableRecord->szOurFontname, szOurFont,
+00220                         sizeof(pFontTableRecord->szOurFontname) - 1);
+00221                 pFontTableRecord->szOurFontname[
+00222                         sizeof(pFontTableRecord->szOurFontname) - 1] = '\0';
+00223                 NO_DBG_MSG(pFontTableRecord->szWordFontname);
+00224                 NO_DBG_MSG(pFontTableRecord->szOurFontname);
+00225                 pFontTableRecord->ucFFN = ucFFN;
+00226                 pFontTableRecord->ucEmphasis = (UCHAR)iEmphasis;
+00227         }
+00228 } /* end of vFontname2Table */
+00229 
+00230 /*
+00231  * vCreateFontTable - Create and initialize the internal font table
+00232  */
+00233 static void
+00234 vCreateFontTable(void)
+00235 {
+00236         font_table_type *pTmp;
+00237         int     iNbr;
+00238 
+00239         if (tFontTableRecords == 0) {
+00240                 pFontTable = xfree(pFontTable);
+00241                 return;
+00242         }
+00243 
+00244         /* Create the font table */
+00245         pFontTable = xcalloc(tFontTableRecords, sizeof(*pFontTable));
+00246 
+00247         /* Initialize the font table */
+00248         for (iNbr = 0, pTmp = pFontTable;
+00249              pTmp < pFontTable + tFontTableRecords;
+00250              iNbr++, pTmp++) {
+00251                 pTmp->ucWordFontNumber = (UCHAR)(iNbr / 4);
+00252                 switch (iNbr % 4) {
+00253                 case 0:
+00254                         pTmp->usFontStyle = FONT_REGULAR;
+00255                         break;
+00256                 case 1:
+00257                         pTmp->usFontStyle = FONT_BOLD;
+00258                         break;
+00259                 case 2:
+00260                         pTmp->usFontStyle = FONT_ITALIC;
+00261                         break;
+00262                 case 3:
+00263                         pTmp->usFontStyle = FONT_BOLD|FONT_ITALIC;
+00264                         break;
+00265                 default:
+00266                         DBG_DEC(iNbr);
+00267                         break;
+00268                 }
+00269         }
+00270 } /* end of vCreateFontTable */
+00271 
+00272 /*
+00273  * vMinimizeFontTable - make the font table as small as possible
+00274  */
+00275 static void
+00276 vMinimizeFontTable(void)
+00277 {
+00278         font_block_type         tFontNext;
+00279         const style_block_type  *pStyle;
+00280         const font_block_type   *pFont;
+00281         font_table_type         *pTmp;
+00282         int     iUnUsed;
+00283         BOOL    bMustAddTableFont;
+00284 
+00285         NO_DBG_MSG("vMinimizeFontTable");
+00286 
+00287         if (tFontTableRecords == 0) {
+00288                 pFontTable = xfree(pFontTable);
+00289                 return;
+00290         }
+00291 
+00292         /* See if we must add a font for our tables */
+00293         bMustAddTableFont = TRUE;
+00294 
+00295 #if 0
+00296         DBG_MSG("Before");
+00297         DBG_DEC(tFontTableRecords);
+00298         for (pTmp = pFontTable;
+00299              pTmp < pFontTable + tFontTableRecords;
+00300              pTmp++) {
+00301                 DBG_DEC(pTmp->ucWordFontNumber);
+00302                 DBG_HEX(pTmp->usFontStyle);
+00303                 DBG_MSG(pTmp->szWordFontname);
+00304                 DBG_MSG(pTmp->szOurFontname);
+00305         }
+00306 #endif /* DEBUG */
+00307 
+00308         /* See which fonts/styles we really need */
+00309 
+00310         /* Default font/style is by definition in use */
+00311         pFontTable[0].ucInUse = 1;
+00312 
+00313         /* Make InUse 1 for all the fonts/styles that WILL be used */
+00314         pFont = NULL;
+00315         while((pFont = pGetNextFontInfoListItem(pFont)) != NULL) {
+00316                 pTmp = pFontTable + 4 * (int)pFont->ucFontNumber;
+00317                 if (bIsBold(pFont->usFontStyle)) {
+00318                         pTmp++;
+00319                 }
+00320                 if (bIsItalic(pFont->usFontStyle)) {
+00321                         pTmp += 2;
+00322                 }
+00323                 if (pTmp >= pFontTable + tFontTableRecords) {
+00324                         continue;
+00325                 }
+00326                 if (STREQ(pTmp->szOurFontname, TABLE_FONT)) {
+00327                         /* The table font is already present */
+00328                         bMustAddTableFont = FALSE;
+00329                 }
+00330                 pTmp->ucInUse = 1;
+00331         }
+00332 
+00333         /* Make InUse 1 for all the fonts/styles that MIGHT be used */
+00334         pStyle = NULL;
+00335         while((pStyle = pGetNextStyleInfoListItem(pStyle)) != NULL) {
+00336                 vFillFontFromStylesheet(pStyle->usIstdNext, &tFontNext);
+00337                 vCorrectFontValues(&tFontNext);
+00338                 pTmp = pFontTable + 4 * (int)tFontNext.ucFontNumber;
+00339                 if (bIsBold(tFontNext.usFontStyle)) {
+00340                         pTmp++;
+00341                 }
+00342                 if (bIsItalic(tFontNext.usFontStyle)) {
+00343                         pTmp += 2;
+00344                 }
+00345                 if (pTmp >= pFontTable + tFontTableRecords) {
+00346                         continue;
+00347                 }
+00348                 if (STREQ(pTmp->szOurFontname, TABLE_FONT)) {
+00349                         /* The table font is already present */
+00350                         bMustAddTableFont = FALSE;
+00351                 }
+00352                 pTmp->ucInUse = 1;
+00353         }
+00354 
+00355         /* Remove the unused font entries from the font table */
+00356         iUnUsed = 0;
+00357         for (pTmp = pFontTable;
+00358              pTmp < pFontTable + tFontTableRecords;
+00359              pTmp++) {
+00360                 if (pTmp->ucInUse == 0) {
+00361                         iUnUsed++;
+00362                         continue;
+00363                 }
+00364                 if (iUnUsed > 0) {
+00365                         fail(pTmp - iUnUsed <= pFontTable);
+00366                         *(pTmp - iUnUsed) = *pTmp;
+00367                 }
+00368         }
+00369         fail(iUnUsed < 0);
+00370         fail(tFontTableRecords <= (size_t)iUnUsed);
+00371         tFontTableRecords -= (size_t)iUnUsed;
+00372 
+00373         if (bMustAddTableFont) {
+00374                 pTmp = pFontTable + tFontTableRecords;
+00375                 fail(pTmp <= pFontTable);
+00376                 pTmp->ucWordFontNumber = (pTmp - 1)->ucWordFontNumber + 1;
+00377                 pTmp->usFontStyle = FONT_REGULAR;
+00378                 pTmp->ucInUse = 1;
+00379                 strcpy(pTmp->szWordFontname, "Extra Table Font");
+00380                 strcpy(pTmp->szOurFontname, TABLE_FONT);
+00381                 tFontTableRecords++;
+00382                 iUnUsed--;
+00383         }
+00384         if (iUnUsed > 0) {
+00385                 /* Resize the font table */
+00386                 pFontTable = xrealloc(pFontTable,
+00387                                 tFontTableRecords * sizeof(*pFontTable));
+00388         }
+00389 #if defined(DEBUG)
+00390         DBG_MSG("After");
+00391         DBG_DEC(tFontTableRecords);
+00392         for (pTmp = pFontTable;
+00393              pTmp < pFontTable + tFontTableRecords;
+00394              pTmp++) {
+00395                 DBG_DEC(pTmp->ucWordFontNumber);
+00396                 DBG_HEX(pTmp->usFontStyle);
+00397                 DBG_MSG(pTmp->szWordFontname);
+00398                 DBG_MSG(pTmp->szOurFontname);
+00399         }
+00400 #endif /* DEBUG */
+00401 } /* end of vMinimizeFontTable */
+00402 
+00403 /*
+00404  * bReadFontFile - read and check a line from the font translation file
+00405  *
+00406  * returns TRUE when a correct line has been read, otherwise FALSE
+00407  */
+00408 static BOOL
+00409 bReadFontFile(FILE *pFontTableFile, char *szWordFont,
+00410         int *piItalic, int *piBold, char *szOurFont, int *piSpecial)
+00411 {
+00412         char    *pcTmp;
+00413         int     iFields;
+00414         char    szLine[FONT_LINE_LENGTH];
+00415 
+00416         fail(szWordFont == NULL || szOurFont == NULL);
+00417         fail(piItalic == NULL || piBold == NULL || piSpecial == NULL);
+00418 
+00419         while (fgets(szLine, (int)sizeof(szLine), pFontTableFile) != NULL) {
+00420                 if (szLine[0] == '#' ||
+00421                     szLine[0] == '\n' ||
+00422                     szLine[0] == '\r') {
+00423                         continue;
+00424                 }
+00425                 iFields = sscanf(szLine, "%[^,],%d,%d,%1s%[^,],%d",
+00426                         szWordFont, piItalic, piBold,
+00427                         &szOurFont[0], &szOurFont[1], piSpecial);
+00428                 if (iFields != 6) {
+00429                         pcTmp = strchr(szLine, '\r');
+00430                         if (pcTmp != NULL) {
+00431                                 *pcTmp = '\0';
+00432                         }
+00433                         pcTmp = strchr(szLine, '\n');
+00434                         if (pcTmp != NULL) {
+00435                                 *pcTmp = '\0';
+00436                         }
+00437                         DBG_DEC(iFields);
+00438                         werr(0, "Syntax error in: '%s'", szLine);
+00439                         continue;
+00440                 }
+00441                 if (strlen(szWordFont) >=
+00442                                 sizeof(pFontTable[0].szWordFontname)) {
+00443                         werr(0, "Word fontname too long: '%s'", szWordFont);
+00444                         continue;
+00445                 }
+00446                 if (strlen(szOurFont) >=
+00447                                 sizeof(pFontTable[0].szOurFontname)) {
+00448                         werr(0, "Local fontname too long: '%s'", szOurFont);
+00449                         continue;
+00450                 }
+00451                 /* The current line passed all the tests */
+00452                 return TRUE;
+00453         }
+00454         return FALSE;
+00455 } /* end of bReadFontFile */
+00456 
+00457 /*
+00458  * vCreate0FontTable - create a font table from Word for DOS
+00459  */
+00460 void
+00461 vCreate0FontTable(void)
+00462 {
+00463         FILE    *pFontTableFile;
+00464         font_table_type *pTmp;
+00465         UCHAR   *aucFont;
+00466         int     iBold, iItalic, iSpecial, iEmphasis, iFtc;
+00467         UCHAR   ucPrq, ucFf, ucFFN;
+00468         char    szWordFont[FONT_LINE_LENGTH], szOurFont[FONT_LINE_LENGTH];
+00469 
+00470         tFontTableRecords = 0;
+00471         pFontTable = xfree(pFontTable);
+00472 
+00473         pFontTableFile = pOpenFontTableFile();
+00474         if (pFontTableFile == NULL) {
+00475                 /* No translation table file, no translation table */
+00476                 return;
+00477         }
+00478 
+00479         /* Get the maximum number of entries in the font table */
+00480         tFontTableRecords = 64;
+00481         tFontTableRecords *= 4; /* Plain, Bold, Italic and Bold/italic */
+00482         tFontTableRecords++;    /* One extra for the table-font */
+00483         vCreateFontTable();
+00484 
+00485         /* Read the font translation file */
+00486         iItalic = 0;
+00487         iBold = 0;
+00488         iSpecial = 0;
+00489         while (bReadFontFile(pFontTableFile, szWordFont,
+00490                         &iItalic, &iBold, szOurFont, &iSpecial)) {
+00491                 iEmphasis = 0;
+00492                 if (iBold != 0) {
+00493                         iEmphasis++;
+00494                 }
+00495                 if (iItalic != 0) {
+00496                         iEmphasis += 2;
+00497                 }
+00498                 for (iFtc = 0, pTmp = pFontTable + iEmphasis;
+00499                      pTmp < pFontTable + tFontTableRecords;
+00500                      iFtc++, pTmp += 4) {
+00501                         if (iFtc >= 16 && iFtc <= 55) {
+00502                                 ucPrq = PITCH_VARIABLE;
+00503                                 ucFf = FAMILY_ROMAN;
+00504                                 aucFont = (UCHAR *)"Times";
+00505                         } else {
+00506                                 ucPrq = PITCH_FIXED;
+00507                                 ucFf = FAMILY_MODERN;
+00508                                 aucFont = (UCHAR *)"Courier";
+00509                         }
+00510                         ucFFN = (ucFf << 4) | ucPrq;
+00511                         vFontname2Table(aucFont, NULL, 1, iEmphasis,
+00512                                         ucFFN, szWordFont, szOurFont, pTmp);
+00513                 }
+00514         }
+00515         (void)fclose(pFontTableFile);
+00516         vMinimizeFontTable();
+00517 } /* end of vCreate0FontTable */
+00518 
+00519 /*
+00520  * vCreate2FontTable - create a font table from WinWord 1/2
+00521  */
+00522 void
+00523 vCreate2FontTable(FILE *pFile, int iWordVersion, const UCHAR *aucHeader)
+00524 {
+00525         FILE    *pFontTableFile;
+00526         font_table_type *pTmp;
+00527         UCHAR   *aucFont;
+00528         UCHAR   *aucBuffer;
+00529         ULONG   ulBeginFontInfo;
+00530         size_t  tFontInfoLen;
+00531         int     iPos, iOff, iRecLen;
+00532         int     iBold, iItalic, iSpecial, iEmphasis;
+00533         UCHAR   ucFFN;
+00534         char    szWordFont[FONT_LINE_LENGTH], szOurFont[FONT_LINE_LENGTH];
+00535 
+00536         fail(pFile == NULL || aucHeader == NULL);
+00537         fail(iWordVersion != 1 && iWordVersion != 2);
+00538 
+00539         tFontTableRecords = 0;
+00540         pFontTable = xfree(pFontTable);
+00541 
+00542         pFontTableFile = pOpenFontTableFile();
+00543         if (pFontTableFile == NULL) {
+00544                 /* No translation table file, no translation table */
+00545                 return;
+00546         }
+00547 
+00548         ulBeginFontInfo = ulGetLong(0xb2, aucHeader); /* fcSttbfffn */
+00549         DBG_HEX(ulBeginFontInfo);
+00550         tFontInfoLen = (size_t)usGetWord(0xb6, aucHeader); /* cbSttbfffn */
+00551         DBG_DEC(tFontInfoLen);
+00552 
+00553         if (ulBeginFontInfo > (ULONG)LONG_MAX || tFontInfoLen == 0) {
+00554                 /* Don't ask me why this is needed */
+00555                 DBG_HEX_C(tFontInfoLen != 0, ulBeginFontInfo);
+00556                 (void)fclose(pFontTableFile);
+00557                 return;
+00558         }
+00559 
+00560         aucBuffer = xmalloc(tFontInfoLen);
+00561         if (!bReadBytes(aucBuffer, tFontInfoLen, ulBeginFontInfo, pFile)) {
+00562                 aucBuffer = xfree(aucBuffer);
+00563                 (void)fclose(pFontTableFile);
+00564                 return;
+00565         }
+00566         NO_DBG_PRINT_BLOCK(aucBuffer, tFontInfoLen);
+00567         DBG_DEC(usGetWord(0, aucBuffer));
+00568 
+00569         /* Compute the maximum number of entries in the font table */
+00570         if (iWordVersion == 1) {
+00571                 fail(tFontInfoLen < 2);
+00572                 /* WinWord 1 has three implicit fonts */
+00573                 tFontTableRecords = 3;
+00574                 iOff = 2;
+00575         } else {
+00576                 fail(tFontInfoLen < 6);
+00577                 /* WinWord 2 and up have no implicit fonts */
+00578                 tFontTableRecords = 0;
+00579                 iOff = 3;
+00580         }
+00581         iPos = 2;
+00582         while (iPos + iOff < (int)tFontInfoLen) {
+00583                 iRecLen = (int)ucGetByte(iPos, aucBuffer);
+00584                 NO_DBG_DEC(iRecLen);
+00585                 NO_DBG_MSG(aucBuffer + iPos + iOff);
+00586                 iPos += iRecLen + 1;
+00587                 tFontTableRecords++;
+00588         }
+00589         tFontTableRecords *= 4; /* Plain, Bold, Italic and Bold/Italic */
+00590         tFontTableRecords++;    /* One extra for the table-font */
+00591         vCreateFontTable();
+00592 
+00593         /* Add the tree implicit fonts (in four variations) */
+00594         if (iWordVersion == 1) {
+00595                 fail(tFontTableRecords < 13);
+00596                 vFontname2Table((UCHAR *)"Tms Rmn", NULL, 1, 0,
+00597                         (UCHAR)((FAMILY_ROMAN << 4) | PITCH_VARIABLE),
+00598                         "*", "Times-Roman", pFontTable + 0);
+00599                 vFontname2Table((UCHAR *)"Tms Rmn", NULL, 1, 1,
+00600                         (UCHAR)((FAMILY_ROMAN << 4) | PITCH_VARIABLE),
+00601                         "*", "Times-Bold", pFontTable + 1);
+00602                 vFontname2Table((UCHAR *)"Tms Rmn", NULL, 1, 2,
+00603                         (UCHAR)((FAMILY_ROMAN << 4) | PITCH_VARIABLE),
+00604                         "*", "Times-Italic", pFontTable + 2);
+00605                 vFontname2Table((UCHAR *)"Tms Rmn", NULL, 1, 3,
+00606                         (UCHAR)((FAMILY_ROMAN << 4) | PITCH_VARIABLE),
+00607                         "*", "Times-BoldItalic", pFontTable + 3);
+00608                 vFontname2Table((UCHAR *)"Symbol", NULL, 1, 0,
+00609                         (UCHAR)((FAMILY_ROMAN << 4) | PITCH_VARIABLE),
+00610                         "*", "Times-Roman", pFontTable + 4);
+00611                 vFontname2Table((UCHAR *)"Symbol", NULL, 1, 1,
+00612                         (UCHAR)((FAMILY_ROMAN << 4) | PITCH_VARIABLE),
+00613                         "*", "Times-Bold", pFontTable + 5);
+00614                 vFontname2Table((UCHAR *)"Symbol", NULL, 1, 2,
+00615                         (UCHAR)((FAMILY_ROMAN << 4) | PITCH_VARIABLE),
+00616                         "*", "Times-Italic", pFontTable + 6);
+00617                 vFontname2Table((UCHAR *)"Symbol", NULL, 1, 3,
+00618                         (UCHAR)((FAMILY_ROMAN << 4) | PITCH_VARIABLE),
+00619                         "*", "Times-BoldItalic", pFontTable + 7);
+00620                 vFontname2Table((UCHAR *)"Helv", NULL, 1, 0,
+00621                         (UCHAR)((FAMILY_SWISS << 4) | PITCH_VARIABLE),
+00622                         "*", "Helvetica", pFontTable + 8);
+00623                 vFontname2Table((UCHAR *)"Helv", NULL, 1, 1,
+00624                         (UCHAR)((FAMILY_SWISS << 4) | PITCH_VARIABLE),
+00625                         "*", "Helvetica-Bold", pFontTable + 9);
+00626                 vFontname2Table((UCHAR *)"Helv", NULL, 1, 2,
+00627                         (UCHAR)((FAMILY_SWISS << 4) | PITCH_VARIABLE),
+00628                         "*", "Helvetica-Oblique", pFontTable + 10);
+00629                 vFontname2Table((UCHAR *)"Helv", NULL, 1, 3,
+00630                         (UCHAR)((FAMILY_SWISS << 4) | PITCH_VARIABLE),
+00631                         "*", "Helvetica-BoldOblique", pFontTable + 11);
+00632         }
+00633 
+00634         /* Read the font translation file */
+00635         iItalic = 0;
+00636         iBold = 0;
+00637         iSpecial = 0;
+00638         while (bReadFontFile(pFontTableFile, szWordFont,
+00639                         &iItalic, &iBold, szOurFont, &iSpecial)) {
+00640                 iEmphasis = 0;
+00641                 if (iBold != 0) {
+00642                         iEmphasis++;
+00643                 }
+00644                 if (iItalic != 0) {
+00645                         iEmphasis += 2;
+00646                 }
+00647                 pTmp = pFontTable + iEmphasis;
+00648                 iPos = 2;
+00649                 while (iPos + iOff < (int)tFontInfoLen) {
+00650                         iRecLen = (int)ucGetByte(iPos, aucBuffer);
+00651                         ucFFN = ucGetByte(iPos + 1, aucBuffer);
+00652                         aucFont = aucBuffer + iPos + iOff;
+00653                         vFontname2Table(aucFont, NULL, 1, iEmphasis,
+00654                                         ucFFN, szWordFont, szOurFont, pTmp);
+00655                         pTmp += 4;
+00656                         iPos += iRecLen + 1;
+00657                 }
+00658         }
+00659         (void)fclose(pFontTableFile);
+00660         aucBuffer = xfree(aucBuffer);
+00661         vMinimizeFontTable();
+00662 } /* end of vCreate2FontTable */
+00663 
+00664 /*
+00665  * vCreate6FontTable - create a font table from Word 6/7
+00666  */
+00667 void
+00668 vCreate6FontTable(FILE *pFile, ULONG ulStartBlock,
+00669         const ULONG *aulBBD, size_t tBBDLen,
+00670         const UCHAR *aucHeader)
+00671 {
+00672         FILE    *pFontTableFile;
+00673         font_table_type *pTmp;
+00674         UCHAR   *aucFont, *aucAltFont;
+00675         UCHAR   *aucBuffer;
+00676         ULONG   ulBeginFontInfo;
+00677         size_t  tFontInfoLen;
+00678         int     iPos, iRecLen, iOffsetAltName;
+00679         int     iBold, iItalic, iSpecial, iEmphasis;
+00680         UCHAR   ucFFN;
+00681         char    szWordFont[FONT_LINE_LENGTH], szOurFont[FONT_LINE_LENGTH];
+00682 
+00683         fail(pFile == NULL || aucHeader == NULL);
+00684         fail(ulStartBlock > MAX_BLOCKNUMBER && ulStartBlock != END_OF_CHAIN);
+00685         fail(aulBBD == NULL);
+00686 
+00687         tFontTableRecords = 0;
+00688         pFontTable = xfree(pFontTable);
+00689 
+00690         pFontTableFile = pOpenFontTableFile();
+00691         if (pFontTableFile == NULL) {
+00692                 /* No translation table file, no translation table */
+00693                 return;
+00694         }
+00695 
+00696         ulBeginFontInfo = ulGetLong(0xd0, aucHeader); /* fcSttbfffn */
+00697         DBG_HEX(ulBeginFontInfo);
+00698         tFontInfoLen = (size_t)ulGetLong(0xd4, aucHeader); /* lcbSttbfffn */
+00699         DBG_DEC(tFontInfoLen);
+00700         fail(tFontInfoLen < 9);
+00701 
+00702         aucBuffer = xmalloc(tFontInfoLen);
+00703         if (!bReadBuffer(pFile, ulStartBlock,
+00704                         aulBBD, tBBDLen, BIG_BLOCK_SIZE,
+00705                         aucBuffer, ulBeginFontInfo, tFontInfoLen)) {
+00706                 aucBuffer = xfree(aucBuffer);
+00707                 (void)fclose(pFontTableFile);
+00708                 return;
+00709         }
+00710         DBG_DEC(usGetWord(0, aucBuffer));
+00711 
+00712         /* Compute the maximum number of entries in the font table */
+00713         tFontTableRecords = 0;
+00714         iPos = 2;
+00715         while (iPos + 6 < (int)tFontInfoLen) {
+00716                 iRecLen = (int)ucGetByte(iPos, aucBuffer);
+00717                 NO_DBG_DEC(iRecLen);
+00718                 iOffsetAltName = (int)ucGetByte(iPos + 5, aucBuffer);
+00719                 NO_DBG_MSG(aucBuffer + iPos + 6);
+00720                 NO_DBG_MSG_C(iOffsetAltName > 0,
+00721                                 aucBuffer + iPos + 6 + iOffsetAltName);
+00722                 iPos += iRecLen + 1;
+00723                 tFontTableRecords++;
+00724         }
+00725         tFontTableRecords *= 4; /* Plain, Bold, Italic and Bold/italic */
+00726         tFontTableRecords++;    /* One extra for the table-font */
+00727         vCreateFontTable();
+00728 
+00729         /* Read the font translation file */
+00730         iItalic = 0;
+00731         iBold = 0;
+00732         iSpecial = 0;
+00733         while (bReadFontFile(pFontTableFile, szWordFont,
+00734                         &iItalic, &iBold, szOurFont, &iSpecial)) {
+00735                 iEmphasis = 0;
+00736                 if (iBold != 0) {
+00737                         iEmphasis++;
+00738                 }
+00739                 if (iItalic != 0) {
+00740                         iEmphasis += 2;
+00741                 }
+00742                 pTmp = pFontTable + iEmphasis;
+00743                 iPos = 2;
+00744                 while (iPos + 6 < (int)tFontInfoLen) {
+00745                         iRecLen = (int)ucGetByte(iPos, aucBuffer);
+00746                         ucFFN = ucGetByte(iPos + 1, aucBuffer);
+00747                         aucFont = aucBuffer + iPos + 6;
+00748                         iOffsetAltName = (int)ucGetByte(iPos + 5, aucBuffer);
+00749                         if (iOffsetAltName <= 0) {
+00750                                 aucAltFont = NULL;
+00751                         } else {
+00752                                 aucAltFont = aucFont + iOffsetAltName;
+00753                                 NO_DBG_MSG(aucFont);
+00754                                 NO_DBG_MSG(aucAltFont);
+00755                         }
+00756                         vFontname2Table(aucFont, aucAltFont, 1, iEmphasis,
+00757                                         ucFFN, szWordFont, szOurFont, pTmp);
+00758                         pTmp += 4;
+00759                         iPos += iRecLen + 1;
+00760                 }
+00761         }
+00762         (void)fclose(pFontTableFile);
+00763         aucBuffer = xfree(aucBuffer);
+00764         vMinimizeFontTable();
+00765 } /* end of vCreate6FontTable */
+00766 
+00767 /*
+00768  * vCreate8FontTable - create a font table from Word 8/9/10
+00769  */
+00770 void
+00771 vCreate8FontTable(FILE *pFile, const pps_info_type *pPPS,
+00772         const ULONG *aulBBD, size_t tBBDLen,
+00773         const ULONG *aulSBD, size_t tSBDLen,
+00774         const UCHAR *aucHeader)
+00775 {
+00776         FILE    *pFontTableFile;
+00777         font_table_type *pTmp;
+00778         const ULONG     *aulBlockDepot;
+00779         UCHAR   *aucFont, *aucAltFont;
+00780         UCHAR   *aucBuffer;
+00781         ULONG   ulBeginFontInfo;
+00782         size_t  tFontInfoLen, tBlockDepotLen, tBlockSize;
+00783         int     iPos, iRecLen, iOffsetAltName;
+00784         int     iBold, iItalic, iSpecial, iEmphasis;
+00785         UCHAR   ucFFN;
+00786         char    szWordFont[FONT_LINE_LENGTH], szOurFont[FONT_LINE_LENGTH];
+00787 
+00788         fail(pFile == NULL || pPPS == NULL || aucHeader == NULL);
+00789         fail(aulBBD == NULL || aulSBD == NULL);
+00790 
+00791         tFontTableRecords = 0;
+00792         pFontTable = xfree(pFontTable);
+00793 
+00794         pFontTableFile = pOpenFontTableFile();
+00795         if (pFontTableFile == NULL) {
+00796                 /* No translation table file, no translation table */
+00797                 return;
+00798         }
+00799 
+00800         ulBeginFontInfo = ulGetLong(0x112, aucHeader); /* fcSttbfffn */
+00801         DBG_HEX(ulBeginFontInfo);
+00802         tFontInfoLen = (size_t)ulGetLong(0x116, aucHeader); /* lcbSttbfffn */
+00803         DBG_DEC(tFontInfoLen);
+00804         fail(tFontInfoLen < 46);
+00805 
+00806         DBG_DEC(pPPS->tTable.ulSB);
+00807         DBG_HEX(pPPS->tTable.ulSize);
+00808         if (pPPS->tTable.ulSize == 0) {
+00809                 DBG_MSG("No fontname table");
+00810                 (void)fclose(pFontTableFile);
+00811                 return;
+00812         }
+00813 
+00814         if (pPPS->tTable.ulSize < MIN_SIZE_FOR_BBD_USE) {
+00815                 /* Use the Small Block Depot */
+00816                 aulBlockDepot = aulSBD;
+00817                 tBlockDepotLen = tSBDLen;
+00818                 tBlockSize = SMALL_BLOCK_SIZE;
+00819         } else {
+00820                 /* Use the Big Block Depot */
+00821                 aulBlockDepot = aulBBD;
+00822                 tBlockDepotLen = tBBDLen;
+00823                 tBlockSize = BIG_BLOCK_SIZE;
+00824         }
+00825         aucBuffer = xmalloc(tFontInfoLen);
+00826         if (!bReadBuffer(pFile, pPPS->tTable.ulSB,
+00827                         aulBlockDepot, tBlockDepotLen, tBlockSize,
+00828                         aucBuffer, ulBeginFontInfo, tFontInfoLen)) {
+00829                 aucBuffer = xfree(aucBuffer);
+00830                 (void)fclose(pFontTableFile);
+00831                 return;
+00832         }
+00833         NO_DBG_PRINT_BLOCK(aucBuffer, tFontInfoLen);
+00834 
+00835         /* Get the maximum number of entries in the font table */
+00836         tFontTableRecords = (size_t)usGetWord(0, aucBuffer);
+00837         tFontTableRecords *= 4; /* Plain, Bold, Italic and Bold/italic */
+00838         tFontTableRecords++;    /* One extra for the table-font */
+00839         vCreateFontTable();
+00840 
+00841         /* Read the font translation file */
+00842         iItalic = 0;
+00843         iBold = 0;
+00844         iSpecial = 0;
+00845         while (bReadFontFile(pFontTableFile, szWordFont,
+00846                         &iItalic, &iBold, szOurFont, &iSpecial)) {
+00847                 iEmphasis = 0;
+00848                 if (iBold != 0) {
+00849                         iEmphasis++;
+00850                 }
+00851                 if (iItalic != 0) {
+00852                         iEmphasis += 2;
+00853                 }
+00854                 pTmp = pFontTable + iEmphasis;
+00855                 iPos = 4;
+00856                 while (iPos + 40 < (int)tFontInfoLen) {
+00857                         iRecLen = (int)ucGetByte(iPos, aucBuffer);
+00858                         ucFFN = ucGetByte(iPos + 1, aucBuffer);
+00859                         aucFont = aucBuffer + iPos + 40;
+00860                         iOffsetAltName = (int)unilen(aucFont);
+00861                         if (iPos + 40 + iOffsetAltName + 4 >= iRecLen) {
+00862                                 aucAltFont = NULL;
+00863                         } else {
+00864                                 aucAltFont = aucFont + iOffsetAltName + 2;
+00865                                 NO_DBG_UNICODE(aucFont);
+00866                                 NO_DBG_UNICODE(aucAltFont);
+00867                         }
+00868                         vFontname2Table(aucFont, aucAltFont, 2, iEmphasis,
+00869                                         ucFFN, szWordFont, szOurFont, pTmp);
+00870                         pTmp += 4;
+00871                         iPos += iRecLen + 1;
+00872                 }
+00873         }
+00874         (void)fclose(pFontTableFile);
+00875         aucBuffer = xfree(aucBuffer);
+00876         vMinimizeFontTable();
+00877 } /* end of vCreate8FontTable */
+00878 
+00879 /*
+00880  * Destroy the internal font table by freeing its memory
+00881  */
+00882 void
+00883 vDestroyFontTable(void)
+00884 {
+00885         DBG_MSG("vDestroyFontTable");
+00886 
+00887         tFontTableRecords = 0;
+00888         pFontTable = xfree(pFontTable);
+00889 } /* end of vDestroyFontTable */
+00890 
+00891 /*
+00892  * pGetNextFontTableRecord
+00893  *
+00894  * returns the next record in the table or NULL if there is no next record
+00895  */
+00896 const font_table_type *
+00897 pGetNextFontTableRecord(const font_table_type *pRecordCurr)
+00898 {
+00899         size_t  tIndexCurr;
+00900 
+00901         if (pRecordCurr == NULL) {
+00902                 /* No current record, so start with the first one */
+00903                 return &pFontTable[0];
+00904         }
+00905 
+00906         if (pRecordCurr < pFontTable ||
+00907             pRecordCurr >= pFontTable + tFontTableRecords) {
+00908                 /* Not a pointer in the array */
+00909                 DBG_HEX(pRecordCurr);
+00910                 DBG_HEX(pFontTable);
+00911                 return NULL;
+00912         }
+00913 
+00914         tIndexCurr = (size_t)(pRecordCurr - pFontTable);
+00915         if (tIndexCurr + 1 < tFontTableRecords) {
+00916                 /* There is a next record, so return it */
+00917                 return &pFontTable[tIndexCurr + 1];
+00918         }
+00919         /* There is no next record */
+00920         return NULL;
+00921 } /* end of pGetNextFontTableRecord */
+00922 
+00923 /*
+00924  * tGetFontTableLength
+00925  *
+00926  * returns the number of records in the internal font table
+00927  */
+00928 size_t
+00929 tGetFontTableLength(void)
+00930 {
+00931         return tFontTableRecords;
+00932 } /* end of tGetFontTableLength */
+00933 
+00934 #if !defined(__riscos)
+00935 /*
+00936  * vCorrect4PDF - only include PDF default fonts
+00937  */
+00938 static void
+00939 vCorrect4PDF(void)
+00940 {
+00941         font_table_type *pTmp;
+00942         const char      *szOurFont;
+00943 
+00944         for (pTmp = pFontTable; pTmp < pFontTable + tFontTableRecords; pTmp++) {
+00945                 if (STRCEQ(pTmp->szOurFontname, FONT_MONOSPACED_PLAIN) ||
+00946                     STRCEQ(pTmp->szOurFontname, FONT_MONOSPACED_BOLD) ||
+00947                     STRCEQ(pTmp->szOurFontname, FONT_MONOSPACED_ITALIC) ||
+00948                     STRCEQ(pTmp->szOurFontname, FONT_MONOSPACED_BOLDITALIC) ||
+00949                     STRCEQ(pTmp->szOurFontname, FONT_SERIF_PLAIN) ||
+00950                     STRCEQ(pTmp->szOurFontname, FONT_SERIF_BOLD) ||
+00951                     STRCEQ(pTmp->szOurFontname, FONT_SERIF_ITALIC) ||
+00952                     STRCEQ(pTmp->szOurFontname, FONT_SERIF_BOLDITALIC) ||
+00953                     STRCEQ(pTmp->szOurFontname, FONT_SANS_SERIF_PLAIN) ||
+00954                     STRCEQ(pTmp->szOurFontname, FONT_SANS_SERIF_BOLD) ||
+00955                     STRCEQ(pTmp->szOurFontname, FONT_SANS_SERIF_ITALIC) ||
+00956                     STRCEQ(pTmp->szOurFontname, FONT_SANS_SERIF_BOLDITALIC)) {
+00957                         /* Already a default font */
+00958                         continue;
+00959                 }
+00960                 szOurFont =
+00961                         szGetDefaultFont(pTmp->ucFFN, (int)pTmp->ucEmphasis);
+00962                 (void)strncpy(pTmp->szOurFontname, szOurFont,
+00963                         sizeof(pTmp->szOurFontname) - 1);
+00964                 pTmp->szOurFontname[sizeof(pTmp->szOurFontname) - 1] = '\0';
+00965         }
+00966 } /* end of vCorrect4PDF */
+00967 
+00968 /*
+00969  * vCorrect4CyrPS - only include monospaced fonts
+00970  */
+00971 static void
+00972 vCorrect4CyrPS(void)
+00973 {
+00974         font_table_type *pTmp;
+00975         const char      *szOurFont;
+00976         UCHAR   ucFFN;
+00977 
+00978         ucFFN = (FAMILY_UNKNOWN << 4) | PITCH_FIXED;
+00979         for (pTmp = pFontTable; pTmp < pFontTable + tFontTableRecords; pTmp++) {
+00980                 szOurFont = szGetDefaultFont(ucFFN, (int)pTmp->ucEmphasis);
+00981                 (void)strncpy(pTmp->szOurFontname, szOurFont,
+00982                         sizeof(pTmp->szOurFontname) - 1);
+00983                 pTmp->szOurFontname[sizeof(pTmp->szOurFontname) - 1] = '\0';
+00984         }
+00985 } /* end of vCorrect4CyrPS */
+00986 #endif /* __riscos */
+00987 
+00988 /*
+00989  * vCorrectFontTable - correct the font table in special cases
+00990  */
+00991 void
+00992 vCorrectFontTable(conversion_type eConversionType, encoding_type eEncoding)
+00993 {
+00994 #if !defined(__riscos)
+00995         if (eConversionType == conversion_pdf) {
+00996                 vCorrect4PDF();
+00997         }
+00998         if (eConversionType == conversion_ps &&
+00999             eEncoding == encoding_cyrillic) {
+01000                 vCorrect4CyrPS();
+01001         }
+01002 #endif /* __riscos */
+01003 } /* end of vCorrectFontTable */
+01004 
+01005 /*
+01006  * lComputeSpaceWidth - compute the width of a space character
+01007  *
+01008  * Returns the space width in millipoints
+01009  */
+01010 long
+01011 lComputeSpaceWidth(drawfile_fontref tFontRef, USHORT usFontSize)
+01012 {
+01013         char    szSpace[] = " ";
+01014 
+01015         fail(usFontSize < MIN_FONT_SIZE || usFontSize > MAX_FONT_SIZE);
+01016 
+01017         return lComputeStringWidth(szSpace, 1, tFontRef, usFontSize);
+01018 } /* end of lComputeSpaceWidth */
+
+
Generated by  + +doxygen 1.6.2
+ +