Windows NT 4.0 source code leak
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 
 

592 lines
14 KiB

/*----------------------------------------------------------------------------
* *
* CHARATTR.C *
* *
* Copyright (C) Microsoft Corporation 1989-1995 *
* All Rights reserved. *
* *
*---------------------------------------------------------------------------*/
#include "stdafx.h"
#include "cfontmap.h"
#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
#define SIZE_FONT_TABLE 41
#define FNT_TABLE_INCREMENT 11
enum {
iModernFont = 1,
iRomanFont,
iSwissFont,
iScriptFont,
iDecorativeFont,
};
typedef struct{
PSTR szFntName;
int iFntFamily;
} FT, *QFT;
/*
* This is the list of font names which can be forced via the
* OPT_FORCEFONT option in the .HPJ file. 13-Oct-1993 [ralphw] Added the
* names with mixed-case.
*/
static FT ftTab[] = {
"Arial", iSwissFont,
"ATHENS", iDecorativeFont,
"Bookman", iRomanFont,
"Courier New", iModernFont,
"COURIER", iModernFont,
"GENEVA", iSwissFont,
"HELV", iSwissFont,
"HELVETICA", iSwissFont,
"LONDON", iDecorativeFont,
"MODERN", iModernFont,
"MONACO", iModernFont,
"ROMAN", iRomanFont,
"Times New Roman", iRomanFont,
"TIMES", iRomanFont,
"TMS RMN", iRomanFont
};
#define wFTabEntryMac 14
static QIFNTENT qInpFntTab;
static int iInpFntTabEntCount;
static RGBTRIPLE* qInpColTab;
static int iInpColTabEntCount;
static QOFNTENT qFntTab; // Font Table to be outputted to file
static int cFntTableEntries; // Current max No. of entries in table
static int cFntTabCur; // Current count of font entries (MUST be 16-bits)
static BYTE aTmpCharSets[MAX_CHARSETS];
typedef struct{
char szFntName[MAX3_FONTNAME];
} FNTNAME, *QFNTNAME;
static PSTR pFntName;
/*-----------------------------------------------------------------------------
* VProcFontTableInfo()
*
* Description:
* This function stores the font information and forms a unique list of
* font names used in the help file.
*
* Arguments:
* 1. pointer to the font table information obtained from RTF reader.
*
* Returns:
* NOTHING
*-----------------------------------------------------------------------------*/
void STDCALL VProcFontTableInfo(FNTBL* qfnttbl)
{
QIFNTENT qinpfte;
int iT;
PFTE4 qfte;
iInpFntTabEntCount = qfnttbl->cfte;
if (qInpFntTab)
lcFree(qInpFntTab);
qInpFntTab = (QIFNTENT) lcCalloc(
(iInpFntTabEntCount * sizeof(IFNTENT)));
ASSERT(qInpFntTab != NULL);
// Default font name
// iT = GetFontNameId((PSTR) GetStringResource(IDS_DEF_FONT));
// Don't get default font name, since we won't know the charset
for (iT = 0, qinpfte = qInpFntTab, qfte = (PFTE4) &(qfnttbl->rgfte[0]);
iT < qfnttbl->cfte; iT++, qfte++, qinpfte++) {
qinpfte->wIdFntName = GetFontNameId(qfte->szName);
qinpfte->bFntType = (char) IMapFontType(qfte->tokType);
qinpfte->iFntId = qfte->fid;
#ifdef _DEBUG
int cbCharSets = lcSize(paCharSets);
#endif
if (lcSize(paCharSets) <= qinpfte->wIdFntName - 1)
paCharSets = (PBYTE) lcReAlloc(paCharSets, qinpfte->wIdFntName + 1);
#ifdef _DEBUG
// Need these because VC can't display most structure pointers
BYTE bCharSet = qfte->charset;
PSTR pszFontName = qfte->szName;
int idFontName = qinpfte->wIdFntName - 1;
int idFontId = qinpfte->iFntId;
#endif
paCharSets[qinpfte->wIdFntName - 1] = qfte->charset;
}
}
/*-----------------------------------------------------------------------------
* GetFontNameId( szName, qiId )
*
* Description:
* This function stores the font name into the font table and returns
* the font id with which the font will be referred in the help file then on.
*
* Arguments:
* 1. font name.
* 2. pointer to the font id.
*
* Returns:
* NOTHING
*-----------------------------------------------------------------------------*/
int STDCALL GetFontNameId(PSTR pszName)
{
if (!options.pszForceFont) { // if force font option is OFF?
if (!ptblFontNames)
ptblFontNames = new CTable;
SzTrimSz(pszName);
UINT pos;
if ((pos = ptblFontNames->IsStringInTable(pszName)) <= 0) {
if (lstrlen(pszName) > MAX4_FONTNAME - 1) {
// error already reported
return 0; // use default font
}
pos = ptblFontNames->AddString(pszName);
}
return pos;
}
else {
return 0;
}
}
/*-----------------------------------------------------------------------------
* IGetFmtNo()
*
* Description:
*
* Arguments:
*
* Returns:
* NOTHING
*-----------------------------------------------------------------------------*/
int STDCALL IGetFmtNo(CF* pcf)
{
static int iT, iT2;
static QOFNTENT qfte = NULL, qfte2 = NULL;
if (qFntTab == NULL || (cFntTabCur >= cFntTableEntries))
qFntTab = (QOFNTENT) QResizeTable(qFntTab,
cFntTabCur, (int*) &cFntTableEntries,
sizeof(OFNTENT), SIZE_FONT_TABLE, FNT_TABLE_INCREMENT);
ASSERT(qFntTab != NULL);
if (qfte2 && qfte2->fAttr == pcf->fAttr &&
qfte2->wIdFntName == (WORD) (pcf->wIdFntName -1) &&
qfte2->bSize == pcf->bSize &&
qfte2->bFntType == pcf->bFntType &&
memcmp(&qfte2->bForeCol, &pcf->bForeCol, sizeof(RGBTRIPLE)) == 0 &&
memcmp(&qfte2->bBackCol, &pcf->bBackCol, sizeof(RGBTRIPLE)) == 0)
return iT2;
else if (qfte && qfte->fAttr == pcf->fAttr &&
qfte->wIdFntName == (WORD) (pcf->wIdFntName -1) &&
qfte->bSize == pcf->bSize &&
qfte->bFntType == pcf->bFntType &&
memcmp(&qfte->bForeCol, &pcf->bForeCol, sizeof(RGBTRIPLE)) == 0 &&
memcmp(&qfte->bBackCol, &pcf->bBackCol, sizeof(RGBTRIPLE)) == 0)
return iT;
iT2 = iT;
qfte2 = qfte;
// find the match
for (iT = 0, qfte = qFntTab; iT < cFntTabCur; iT++, qfte++) {
if ( qfte->fAttr == pcf->fAttr &&
qfte->wIdFntName == (WORD) (pcf->wIdFntName -1) &&
qfte->bSize == pcf->bSize &&
qfte->bFntType == pcf->bFntType &&
memcmp(&qfte->bForeCol, &pcf->bForeCol, sizeof(RGBTRIPLE)) == 0 &&
memcmp(&qfte->bBackCol, &pcf->bBackCol, sizeof(RGBTRIPLE)) == 0)
return iT;
}
// Match not found, Make an entry
qfte->fAttr = pcf->fAttr;
qfte->bSize = pcf->bSize;
qfte->bFntType = pcf->bFntType;
qfte->wIdFntName = (WORD) (pcf->wIdFntName - 1);
qfte->bForeCol = pcf->bForeCol;
qfte->bBackCol = pcf->bBackCol;
// Increment the count
cFntTabCur++;
return cFntTabCur - 1;
}
/*-----------------------------------------------------------------------------
* IGetFontSize( iInpSize )
*
* Description: Remap the font size, if we should.
*
* Arguments:
*
* Returns:
* NOTHING
*-----------------------------------------------------------------------------*/
int STDCALL IGetFontSize(int iInpSize)
{
int i;
FONTRANGE *pfr;
for (i = 0, pfr = options.rgFontRange;
i < options.iFontRangeMac;
i++, pfr++) {
if (iInpSize >= pfr->halfptInMin && iInpSize <= pfr->halfptInMost) {
return pfr->halfptOut;
break;
}
}
return iInpSize;
}
/***************************************************************************
FUNCTION: FProcFontId
PURPOSE: Convert a font-id into the internally-used number
PARAMETERS:
IdFontInUse
qcf
RETURNS:
COMMENTS:
MODIFICATION DATES:
26-Feb-1994 [ralphw]
***************************************************************************/
BOOL STDCALL FProcFontId(int IdFontInUse, CF* pcf, BOOL fSeenPtSize)
{
QIFNTENT qinpfte, qinpfteMac;
if (fSeenPtSize && !g_pFirst)
return FALSE;
if (options.pszForceFont) {
pcf->bFntType = cfDefault.bFntType;
pcf->wIdFntName = cfDefault.wIdFntName;
return TRUE;
}
if (fSeenPtSize) {
ASSERT(ptblFontNames);
char szFont[MAX4_FONTNAME + 1];
strcpy(szFont, ptblFontNames->GetPointer(pcf->wIdFntName));
int size = pcf->bSize;
int charset = paCharSets[pcf->wIdFntName - 1];
#ifdef _DEBUG
CStr cszOrgFont(szFont);
int orgSize = size;
int orgCharset = charset;
#endif
if (ReplaceFont(szFont, &size, &charset)) {
pcf->wIdFntName = GetFontNameId(szFont);
pcf->bSize = (BYTE) size;
paCharSets[pcf->wIdFntName - 1] = (BYTE) charset;
#ifdef _DEBUG
// Because VC 4 can't see structure pointers
int id = pcf->wIdFntName - 1;
#endif
if (pcf->wIdFntName > (int) idHighestUsedFont)
idHighestUsedFont = pcf->wIdFntName;
}
return TRUE;
}
qinpfteMac = qInpFntTab + iInpFntTabEntCount;
for (qinpfte = qInpFntTab; qinpfte < qinpfteMac; qinpfte++) {
if (qinpfte->iFntId == IdFontInUse)
break;
}
if (qinpfte < qinpfteMac) {
pcf->bFntType = qinpfte->bFntType;
pcf->wIdFntName = qinpfte->wIdFntName;
if (pcf->wIdFntName > (int) idHighestUsedFont)
idHighestUsedFont = pcf->wIdFntName;
return TRUE;
}
return FALSE;
}
/*-----------------------------------------------------------------------------
* IMapFontType()
*
* Description:
*
* Arguments:
*
* Returns:
* NOTHING
*-----------------------------------------------------------------------------*/
int STDCALL IMapFontType(int iTok)
{
int iFntType = 0;
switch(iTok) {
case tokFmodern:
iFntType = iModernFont;
break;
case tokFroman:
iFntType = iRomanFont;
break;
case tokFscript:
iFntType = iScriptFont;
break;
case tokFdecor:
iFntType = iDecorativeFont;
break;
default:
case tokFswiss:
iFntType = iSwissFont;
break;
}
return(iFntType);
}
void STDCALL VProcColTableInfo(CTBL* qColTab)
{
iInpColTabEntCount = qColTab->ccte;
if (qInpColTab)
lcFree(qInpColTab);
qInpColTab = (RGBTRIPLE*) lcCalloc((iInpColTabEntCount * sizeof(CTE)));
ASSERT(qInpColTab);
if (qInpColTab)
memmove(qInpColTab, qColTab->rgcte, (sizeof(CTE) *
iInpColTabEntCount));
}
/*-----------------------------------------------------------------------------
* VUpdateColor()
*
* Description:
* Sets the given rgb value according to the index into the
* color table. If the index exceeds the bounds of the color
* table (which will happen frequently if the color table has
* has not been initialized yet), it does nothing.
*
* Arguments:
*
* Returns:
* NOTHING
*-----------------------------------------------------------------------------*/
void STDCALL VUpdateColor(RGBTRIPLE* qrgb, int iIdx)
{
if (iIdx < iInpColTabEntCount)
memcpy(qrgb, qInpColTab + iIdx, sizeof(RGBTRIPLE));
}
/***************************************************************************
FUNCTION: VOutFontTable
PURPOSE:
PARAMETERS:
void
RETURNS:
COMMENTS:
We saved all font names specified in \fonttbl -- however, this
typically specifies far more font names then are actually used.
Normally, the fonts that are actually used appear at the first
of this list, and unused ones last. We keep track of the highest
used index into our list of fonts, and only write out the ones
up to that point.
MODIFICATION DATES:
26-Feb-1994 [ralphw]
***************************************************************************/
void VOutFontTable(void)
{
int iTemp;
ASSERT(ptblFontNames);
if (!ptblFontNames)
return;
LcbWriteIntAsShort(fmsg.hfFont, idHighestUsedFont);
LcbWriteIntAsShort(fmsg.hfFont, cFntTabCur);
iTemp = sizeof(INT16) * 4;
LcbWriteIntAsShort(fmsg.hfFont, iTemp);
// Write the offset to the font names
iTemp += idHighestUsedFont * MAX4_FONTNAME;
LcbWriteIntAsShort(fmsg.hfFont, iTemp);
if (!options.pszForceFont) {
for (UINT pos = 1; pos <= (UINT) idHighestUsedFont; pos++) {
char szBuf[MAX4_FONTNAME];
memset(szBuf, 0, sizeof(szBuf));
ptblFontNames->GetString(szBuf, pos);
LcbWriteHf(fmsg.hfFont, szBuf, MAX4_FONTNAME);
}
}
LcbWriteHf(fmsg.hfFont, qFntTab, sizeof(OFNTENT) * cFntTabCur);
}
/*-----------------------------------------------------------------------------
* SetForcedFont()
*
* Description: Check that the font name specified is one we know about.
* If it isn't, force font to our default.
*
* Arguments: pszFont - font name. if unrecognized, a default font
* name is copied to this buffer
*
* Returns: NOTHING
*-----------------------------------------------------------------------------*/
void STDCALL SetForcedFont(PSTR pszFont)
{
QFT qft;
int i;
for (i = 0, qft = ftTab; i < wFTabEntryMac; qft++, i++) {
if (!_stricmp(qft->szFntName, pszFont)) {
cfDefault.bFntType = (BYTE) (qft->iFntFamily);
cfDefault.wIdFntName = 0;
return;
}
}
VReportError(HCERR_UNKNOWN_DEF_FONT, &errHpj, pszFont);
GetStringResource(IDS_DEF_FONT, pszFont);
cfDefault.bFntType = (BYTE) iSwissFont;
cfDefault.wIdFntName = 0;
}
/***************************************************************************
FUNCTION: GetCharset
PURPOSE: Retrieve the charset for the specified font
PARAMETERS:
idx font index (internal number, not the RTF number)
RETURNS: charset for the specified font
COMMENTS: For version 3 help files, the charset will either be
SYMBOL_CHARSET or ANSI_CHARSET. Only version 4 help files
will use other charsets.
MODIFICATION DATES:
***************************************************************************/
BYTE STDCALL GetCharset(int idx)
{
char szBuf[MAX4_FONTNAME + 1];
if (idx == -1)
return ANSI_CHARSET; // REVIEW: valid for DBCS?
else
return(ANSI_CHARSET);
// BUGBUG: The following code is now totally useless... 21-Aug-1994 [ralphw]
ASSERT(idx <= idHighestUsedFont && idx >= 0);
ASSERT(ptblFontNames); // have we encounterd any fonts?
// And in case we make it past the above asserts...
if (idx > idHighestUsedFont || !ptblFontNames)
return ANSI_CHARSET;
idx = ((idx + 1) * 2); // because charset values are every other table entry
ptblFontNames->GetString(szBuf, idx);
return (BYTE) atoi(szBuf);
#ifdef DEADCODE
// For version 3 help files, we get the charset based on the font facename
ptblFontNames->GetString(szBuf, idx - 1);
if (stricmp("Symbol", szBuf) == 0 || stricmp("WingDings", szBuf) == 0)
return SYMBOL_CHARSET;
else {
if (defCharSet)
return defCharSet;
HDC hdc = GetDC(NULL);
// Get the system's current charset
if (hdc) {
TEXTMETRIC tm;
GetTextMetrics(hdc, &tm);
BYTE bCharSet = tm.tmCharSet;
ReleaseDC(NULL, hdc);
return bCharSet;
}
else {
return ANSI_CHARSET;
}
}
#endif
}
/***************************************************************************
FUNCTION: GetFirstFont
PURPOSE: Get the first font defined
PARAMETERS:
void
RETURNS:
COMMENTS:
Called when we were handed an invalide default font number.
MODIFICATION DATES:
07-Jan-1995 [ralphw]
***************************************************************************/
int STDCALL GetFirstFont(void)
{
return qInpFntTab->iFntId;
}