Index: configure.in =================================================================== RCS file: /cvsroot/mozilla/configure.in,v --- configure.in 12 Oct 2004 04:13:29 -0000 1.1335.2.11 +++ configure.in 17 Oct 2004 11:09:46 -0000 @@ -3419,14 +3419,18 @@ dnl ==================================== dnl = Xft dnl ======================================================== MOZ_ARG_ENABLE_BOOL(xft, [ --enable-xft Enable Xft support ], MOZ_ENABLE_XFT=1, MOZ_ENABLE_XFT= ) +if test "$MOZ_ENABLE_XFT" && test "$MOZ_ENABLE_FREETYPE2"; then + AC_MSG_ERROR([Cannot enable XFT and FREETYPE2 at the same time.]) +fi + if test "$MOZ_ENABLE_XFT" then AC_DEFINE(MOZ_ENABLE_XFT) PKG_CHECK_MODULES(MOZ_XFT, xft) if test "$MOZ_ENABLE_GTK2"; then PKG_CHECK_MODULES(_PANGOCHK, pango >= 1.1.0) fi Index: gfx/idl/Makefile.in =================================================================== RCS file: /cvsroot/mozilla/gfx/idl/Makefile.in,v --- gfx/idl/Makefile.in 14 Jan 2004 12:56:38 -0000 1.30 +++ gfx/idl/Makefile.in 17 Oct 2004 11:09:46 -0000 @@ -35,22 +35,27 @@ XPIDLSRCS = \ nsIFontList.idl \ nsIScriptableRegion.idl \ nsIScreen.idl \ nsIScreenManager.idl \ nsIPrintOptions.idl \ nsIPrintSettings.idl \ nsIPrintSettingsService.idl \ - nsIFontCatalogService.idl \ - nsIFreeType2.idl \ nsIPrintSession.idl \ gfxIFormats.idl \ gfxIImageFrame.idl \ gfxtypes.idl \ $(NULL) +ifdef MOZ_ENABLE_FREETYPE2 +XPIDLSRCS += \ + nsIFontCatalogService.idl \ + nsIFreeType2.idl \ + $(NULL) +endif + ifneq (,$(filter mac cocoa,$(MOZ_GFX_TOOLKIT))) XPIDLSRCS += nsIPrintSettingsX.idl \ nsIPrintSessionX.idl \ $(NULL) endif ifeq ($(MOZ_GFX_TOOLKIT),windows) Index: gfx/src/gtk/Makefile.in =================================================================== RCS file: /cvsroot/mozilla/gfx/src/gtk/Makefile.in,v --- gfx/src/gtk/Makefile.in 10 Nov 2003 12:24:51 -0000 1.108 +++ gfx/src/gtk/Makefile.in 17 Oct 2004 11:09:46 -0000 @@ -62,21 +62,26 @@ endif NATIVE_THEME_SUPPORT = 1 CSRCS = nsPrintdGTK.c # Code shared between GTK+, Xlib and Xprint gfx modules X11SHARED_LCPPSRCS = \ nsAntiAliasedGlyph.cpp \ - nsFontFreeType.cpp \ - nsFT2FontNode.cpp \ - nsFT2FontCatalog.cpp \ nsX11AlphaBlend.cpp \ nsXFontAAScaledBitmap.cpp \ nsXFontNormal.cpp \ $(NULL) + +ifdef MOZ_ENABLE_FREETYPE2 +X11SHARED_LCPPSRCS += \ + nsFontFreeType.cpp \ + nsFT2FontNode.cpp \ + nsFT2FontCatalog.cpp \ + $(NULL) +endif CPPSRCS = \ nsDeviceContextGTK.cpp \ nsDeviceContextSpecFactoryG.cpp \ nsDeviceContextSpecG.cpp \ nsDrawingSurfaceGTK.cpp \ nsGfxFactoryGTK.cpp \ @@ -204,21 +209,21 @@ EXTRA_DSO_LDOPTS += \ endif LOCAL_INCLUDES = \ -I../.. \ -I$(srcdir)/. \ -I$(srcdir)/.. \ -I$(srcdir)/../shared \ - -I$(srcdir)/../freetype \ -I$(srcdir)/../x11shared \ $(MOZ_XFT_CFLAGS) \ $(NULL) ifdef MOZ_ENABLE_FREETYPE2 INCLUDES += $(FT2_CFLAGS) +LOCAL_INCLUDES += -I$(srcdir)/../freetype endif ifdef MOZ_ENABLE_XPRINT export:: $(addprefix $(srcdir)/../xprint/,$(XPU_LCSRCS)) $(addprefix $(srcdir)/../x11shared/,$(X11SHARED_LCPPSRCS)) $(INSTALL) $^ . else export:: $(addprefix $(srcdir)/../x11shared/,$(X11SHARED_LCPPSRCS)) Index: gfx/src/gtk/nsFontMetricsGTK.cpp =================================================================== RCS file: /cvsroot/mozilla/gfx/src/gtk/nsFontMetricsGTK.cpp,v --- gfx/src/gtk/nsFontMetricsGTK.cpp 9 Mar 2004 14:14:54 -0000 1.268 +++ gfx/src/gtk/nsFontMetricsGTK.cpp 17 Oct 2004 11:10:00 -0000 @@ -58,16 +58,18 @@ #include "nsPrintfCString.h" #include "nspr.h" #include "nsHashtable.h" #include "nsReadableUtils.h" #include "nsAString.h" #include "nsXPIDLString.h" #include "nsFontDebug.h" +#ifdef MOZ_ENABLE_FREETYPE2 #include "nsFT2FontNode.h" #include "nsFontFreeType.h" +#endif #include "nsXFontNormal.h" #include "nsX11AlphaBlend.h" #include "nsXFontAAScaledBitmap.h" #include "nsUnicharUtils.h" #ifdef ENABLE_X_FONT_BANNING #include #endif /* ENABLE_X_FONT_BANNING */ @@ -98,28 +100,34 @@ static PRLogModuleInfo * FontMetricsGTKL // this factor larger than the height of the display, it's clamped to // that value instead of the requested size. #define FONT_MAX_FONT_SCALE 2 #undef NOISY_FONTS #undef REALLY_NOISY_FONTS +#ifndef MOZ_ENABLE_FREETYPE2 +static PRUint32 gFontDebug = 0 | NS_FONT_DEBUG_FONT_SCAN; +#endif + struct nsFontCharSetMap; struct nsFontFamilyName; struct nsFontPropertyName; struct nsFontStyle; struct nsFontWeight; struct nsFontLangGroup; struct nsFontCharSetInfo { const char* mCharSet; nsFontCharSetConverter Convert; PRUint8 mSpecialUnderline; +#ifdef MOZ_ENABLE_FREETYPE2 PRInt32 mCodeRange1Bits; PRInt32 mCodeRange2Bits; +#endif PRUint16* mCCMap; nsIUnicodeEncoder* mConverter; nsIAtom* mLangGroup; PRBool mInitedSizeInfo; PRInt32 mOutlineScaleMin; PRInt32 mAABitmapScaleMin; double mAABitmapOversize; @@ -216,14 +224,15 @@ static gint DoubleByteConvert(nsFontChar const PRUnichar* aSrcBuf, PRInt32 aSrcLen, char* aDestBuf, PRInt32 aDestLen); static gint ISO10646Convert(nsFontCharSetInfo* aSelf, XFontStruct* aFont, const PRUnichar* aSrcBuf, PRInt32 aSrcLen, char* aDestBuf, PRInt32 aDestLen); static nsFontCharSetInfo Unknown = { nsnull }; static nsFontCharSetInfo Special = { nsnull }; +#ifdef MOZ_ENABLE_FREETYPE2 static nsFontCharSetInfo USASCII = { "us-ascii", SingleByteConvert, 0, TT_OS2_CPR1_LATIN1 | TT_OS2_CPR1_MAC_ROMAN, TT_OS2_CPR2_CA_FRENCH | TT_OS2_CPR2_PORTUGESE | TT_OS2_CPR2_WE_LATIN1 | TT_OS2_CPR2_US }; static nsFontCharSetInfo ISO88591 = { "ISO-8859-1", SingleByteConvert, 0, @@ -421,15 +430,168 @@ static nsFontCharSetInfo Mathematica2 = { "x-mathematica2", SingleByteConvert, 0, TT_OS2_CPR1_SYMBOL, 0}; static nsFontCharSetInfo Mathematica3 = { "x-mathematica3", SingleByteConvert, 0, TT_OS2_CPR1_SYMBOL, 0}; static nsFontCharSetInfo Mathematica4 = { "x-mathematica4", SingleByteConvert, 0, TT_OS2_CPR1_SYMBOL, 0}; static nsFontCharSetInfo Mathematica5 = { "x-mathematica5", SingleByteConvert, 0, TT_OS2_CPR1_SYMBOL, 0}; -#endif +#endif /* MATHML */ + +#else + +static nsFontCharSetInfo USASCII = + { "us-ascii", SingleByteConvert, 0 }; +static nsFontCharSetInfo ISO88591 = + { "ISO-8859-1", SingleByteConvert, 0 }; +static nsFontCharSetInfo ISO88592 = + { "ISO-8859-2", SingleByteConvert, 0 }; +static nsFontCharSetInfo ISO88593 = + { "ISO-8859-3", SingleByteConvert, 0 }; +static nsFontCharSetInfo ISO88594 = + { "ISO-8859-4", SingleByteConvert, 0 }; +static nsFontCharSetInfo ISO88595 = + { "ISO-8859-5", SingleByteConvert, 0 }; +static nsFontCharSetInfo ISO88596 = + { "ISO-8859-6", SingleByteConvert, 0 }; +static nsFontCharSetInfo ISO885968x = + { "x-iso-8859-6-8-x", SingleByteConvert, 0 }; +static nsFontCharSetInfo ISO8859616 = + { "x-iso-8859-6-16", SingleByteConvert, 0 }; +static nsFontCharSetInfo IBM1046 = + { "x-IBM1046", SingleByteConvert, 0 }; +static nsFontCharSetInfo ISO88597 = + { "ISO-8859-7", SingleByteConvert, 0 }; +static nsFontCharSetInfo ISO88598 = + { "ISO-8859-8", SingleByteConvert, 0 }; +// change from +// { "ISO-8859-8", SingleByteConvertReverse, 0, 0, 0 }; +// untill we fix the layout and ensure we only call this with pure RTL text +static nsFontCharSetInfo ISO88599 = + { "ISO-8859-9", SingleByteConvert, 0 }; +// no support for iso-8859-10 (Nordic/Icelandic) currently +// static nsFontCharSetInfo ISO885910 = +// { "ISO-8859-10", SingleByteConvert, 0, +// 0, TT_OS2_CPR2_NORDIC | TT_OS2_CPR2_ICELANDIC }; +// no support for iso-8859-12 (Vietnamese) currently +// static nsFontCharSetInfo ISO885912 = +// { "ISO-8859-12", SingleByteConvert, 0, +// TT_OS2_CPR1_VIETNAMESE, 0 }; +static nsFontCharSetInfo ISO885913 = + { "ISO-8859-13", SingleByteConvert, 0 }; +static nsFontCharSetInfo ISO885915 = + { "ISO-8859-15", SingleByteConvert, 0 }; +static nsFontCharSetInfo JISX0201 = + { "jis_0201", SingleByteConvert, 1 }; +static nsFontCharSetInfo KOI8R = + { "KOI8-R", SingleByteConvert, 0 }; +static nsFontCharSetInfo KOI8U = + { "KOI8-U", SingleByteConvert, 0 }; +static nsFontCharSetInfo TIS6202 = +/* Added to support thai context sensitive shaping if + * CTL extension is is in force */ +#ifdef SUNCTL + { "tis620-2", SingleByteConvert, 0 }; +#else + { "windows-874", SingleByteConvert, 0 }; +#endif /* SUNCTL */ +static nsFontCharSetInfo TIS620 = + { "TIS-620", SingleByteConvert, 0 }; +static nsFontCharSetInfo ISO885911 = + { "ISO-8859-11", SingleByteConvert, 0 }; +static nsFontCharSetInfo Big5 = + { "x-x-big5", DoubleByteConvert, 1 }; +// a kludge to distinguish zh-TW only fonts in Big5 (such as hpbig5-) +// from zh-TW/zh-HK common fonts in Big5 (such as big5-1) +static nsFontCharSetInfo Big5TWHK = + { "x-x-big5", DoubleByteConvert, 1 }; +static nsFontCharSetInfo CNS116431 = + { "x-cns-11643-1", DoubleByteConvert, 1 }; +static nsFontCharSetInfo CNS116432 = + { "x-cns-11643-2", DoubleByteConvert, 1 }; +static nsFontCharSetInfo CNS116433 = + { "x-cns-11643-3", DoubleByteConvert, 1 }; +static nsFontCharSetInfo CNS116434 = + { "x-cns-11643-4", DoubleByteConvert, 1 }; +static nsFontCharSetInfo CNS116435 = + { "x-cns-11643-5", DoubleByteConvert, 1 }; +static nsFontCharSetInfo CNS116436 = + { "x-cns-11643-6", DoubleByteConvert, 1 }; +static nsFontCharSetInfo CNS116437 = + { "x-cns-11643-7", DoubleByteConvert, 1 }; +static nsFontCharSetInfo GB2312 = + { "gb_2312-80", DoubleByteConvert, 1 }; +static nsFontCharSetInfo GB18030_0 = + { "gb18030.2000-0", DoubleByteConvert, 1 }; +static nsFontCharSetInfo GB18030_1 = + { "gb18030.2000-1", DoubleByteConvert, 1 }; +static nsFontCharSetInfo GBK = + { "x-gbk-noascii", DoubleByteConvert, 1 }; +static nsFontCharSetInfo HKSCS = + { "hkscs-1", DoubleByteConvert, 1 }; +static nsFontCharSetInfo JISX0208 = + { "jis_0208-1983", DoubleByteConvert, 1 }; +static nsFontCharSetInfo JISX0212 = + { "jis_0212-1990", DoubleByteConvert, 1 }; +static nsFontCharSetInfo KSC5601 = + { "ks_c_5601-1987", DoubleByteConvert, 1 }; +static nsFontCharSetInfo X11Johab = + { "x-x11johab", DoubleByteConvert, 1 }; +static nsFontCharSetInfo JohabNoAscii = + { "x-johab-noascii", DoubleByteConvert, 1 }; +static nsFontCharSetInfo JamoTTF = + { "x-koreanjamo-0", DoubleByteConvert, 1 }; +static nsFontCharSetInfo TamilTTF = + { "x-tamilttf-0", DoubleByteConvert, 0 }; +static nsFontCharSetInfo CP1250 = + { "windows-1250", SingleByteConvert, 0 }; +static nsFontCharSetInfo CP1251 = + { "windows-1251", SingleByteConvert, 0 }; +static nsFontCharSetInfo CP1252 = + { "windows-1252", SingleByteConvert, 0 }; +static nsFontCharSetInfo CP1253 = + { "windows-1253", SingleByteConvert, 0 }; +static nsFontCharSetInfo CP1257 = + { "windows-1257", SingleByteConvert, 0 }; + +#ifdef SUNCTL +/* Hindi range currently unsupported in FT2 range. Change TT* once we + arrive at a way to identify hindi */ +static nsFontCharSetInfo SunIndic = + { "x-sun-unicode-india-0", DoubleByteConvert, 0 }; +#endif /* SUNCTL */ + +static nsFontCharSetInfo ISO106461 = + { nsnull, ISO10646Convert, 1}; + +static nsFontCharSetInfo AdobeSymbol = + { "Adobe-Symbol-Encoding", SingleByteConvert, 0 }; +static nsFontCharSetInfo AdobeEuro = + { "x-adobe-euro", SingleByteConvert, 0 }; + +#ifdef MOZ_MATHML +static nsFontCharSetInfo CMCMEX = + { "x-t1-cmex", SingleByteConvert, 0}; +static nsFontCharSetInfo CMCMSY = + { "x-t1-cmsy", SingleByteConvert, 0}; +static nsFontCharSetInfo CMCMR = + { "x-t1-cmr", SingleByteConvert, 0}; +static nsFontCharSetInfo CMCMMI = + { "x-t1-cmmi", SingleByteConvert, 0}; +static nsFontCharSetInfo Mathematica1 = + { "x-mathematica1", SingleByteConvert, 0}; +static nsFontCharSetInfo Mathematica2 = + { "x-mathematica2", SingleByteConvert, 0}; +static nsFontCharSetInfo Mathematica3 = + { "x-mathematica3", SingleByteConvert, 0}; +static nsFontCharSetInfo Mathematica4 = + { "x-mathematica4", SingleByteConvert, 0}; +static nsFontCharSetInfo Mathematica5 = + { "x-mathematica5", SingleByteConvert, 0}; +#endif /* MATHML */ +#endif /* FREETYPE2 */ static nsFontLangGroup FLG_WESTERN = { "x-western", nsnull }; static nsFontLangGroup FLG_RUSSIAN = { "x-cyrillic", nsnull }; static nsFontLangGroup FLG_BALTIC = { "x-baltic", nsnull }; static nsFontLangGroup FLG_CE = { "x-central-euro",nsnull }; static nsFontLangGroup FLG_GREEK = { "el", nsnull }; static nsFontLangGroup FLG_TURKISH = { "tr", nsnull }; @@ -817,15 +979,17 @@ FreeNodeArray(nsHashKey* aKey, void* aDa static void FreeGlobals(void) { // XXX complete this gInitialized = 0; +#ifdef MOZ_ENABLE_FREETYPE2 nsFT2FontNode::FreeGlobals(); +#endif #ifdef ENABLE_X_FONT_BANNING if (gFontRejectRegEx) { regfree(gFontRejectRegEx); delete gFontRejectRegEx; gFontRejectRegEx = nsnull; } @@ -1217,19 +1381,21 @@ InitGlobals(nsIDeviceContext *aDevice) FreeGlobals(); return NS_ERROR_INVALID_ARG; } } #endif /* ENABLE_X_FONT_BANNING */ +#ifdef MOZ_ENABLE_FREETYPE2 rv = nsFT2FontNode::InitGlobals(); if (NS_FAILED(rv)) { FreeGlobals(); return NS_ERROR_OUT_OF_MEMORY; } +#endif gInitialized = 1; return NS_OK; } // do the 8 to 16 bit conversion on the stack @@ -1553,23 +1719,23 @@ NS_IMETHODIMP nsFontMetricsGTK::Destroy } void nsFontMetricsGTK::RealizeFont() { float f; f = mDeviceContext->DevUnitsToAppUnits(); +#ifdef MOZ_ENABLE_FREETYPE2 if (mWesternFont->IsFreeTypeFont()) { nsFreeTypeFont *ft = (nsFreeTypeFont *)mWesternFont; if (!ft) return; // now that there are multiple font types (eg: core X fonts // and TrueType fonts) there should be a common set of methods // to get the metrics info from the font object. These methods // probably should be virtual functions defined in nsFontGTK. -#if (defined(MOZ_ENABLE_FREETYPE2)) int lineSpacing = ft->ascent() + ft->descent(); if (lineSpacing > mWesternFont->mSize) { mLeading = nscoord((lineSpacing - mWesternFont->mSize) * f); } else { mLeading = 0; } @@ -1633,16 +1799,16 @@ void nsFontMetricsGTK::RealizeFont() } /* need better way to calculate this */ mStrikeoutOffset = NSToCoordRound(mXHeight / 2.0); mStrikeoutSize = mUnderlineSize; return; -#endif /* (defined(MOZ_ENABLE_FREETYPE2)) */ } +#endif nsXFont *xFont = mWesternFont->GetXFont(); XFontStruct *fontInfo = xFont->GetXFontStruct(); f = mDeviceContext->DevUnitsToAppUnits(); nscoord lineSpacing = nscoord((fontInfo->ascent + fontInfo->descent) * f); mEmHeight = PR_MAX(1, nscoord(mWesternFont->mSize * f)); if (lineSpacing > mEmHeight) { @@ -3251,14 +3417,16 @@ nsFontMetricsGTK::GetAASBBaseFont(nsFont return base_aafont; } nsFontGTK* nsFontMetricsGTK::PickASizeAndLoad(nsFontStretch* aStretch, nsFontCharSetInfo* aCharSet, PRUint32 aChar, const char *aName) { + +#ifdef MOZ_ENABLE_FREETYPE2 if (aStretch->mFreeTypeFaceID) { //FREETYPE_FONT_PRINTF(("mFreeTypeFaceID = 0x%p", aStretch->mFreeTypeFaceID)); nsFreeTypeFont *ftfont = nsFreeTypeFont::NewFont(aStretch->mFreeTypeFaceID, mPixelSize, aName); if (!ftfont) { FREETYPE_FONT_PRINTF(("failed to create font")); @@ -3283,14 +3451,15 @@ nsFontMetricsGTK::PickASizeAndLoad(nsFon return AddToLoadedFontsList(ftfont); } if (IS_SURROGATE(aChar)) { // SURROGATE is only supported by FreeType return nsnull; } +#endif PRBool use_scaled_font = PR_FALSE; PRBool have_nearly_rightsized_bitmap = PR_FALSE; nsFontGTK* base_aafont = nsnull; PRInt32 bitmap_size = NOT_FOUND_FONT_SIZE; PRInt32 scale_size = mPixelSize; @@ -5191,16 +5360,18 @@ GetFontNames(const char* aPattern, PRBoo { #ifdef NS_FONT_DEBUG_CALL_TRACE if (gFontDebug & NS_FONT_DEBUG_CALL_TRACE) { printf("GetFontNames %s\n", aPattern); } #endif +#ifdef MOZ_ENABLE_FREETYPE2 // get FreeType fonts nsFT2FontNode::GetFontNames(aPattern, aNodes); +#endif nsCAutoString previousNodeName; nsHashtable* node_hash; if (aAnyFoundry) { NS_ASSERTION(aPattern[1] == '*', "invalid 'anyFoundry' pattern"); node_hash = gAFRENodes; } @@ -6565,18 +6736,20 @@ GetCharSetMap(const char *aCharSetName) nsFontCharSetMap* charSetMap = (nsFontCharSetMap*) gCharSetMaps->Get(&charSetKey); if (!charSetMap) charSetMap = gNoneCharSetMap; return charSetMap; } +#ifdef MOZ_ENABLE_FREETYPE2 void CharSetNameToCodeRangeBits(const char *aCharset, PRUint32 *aCodeRange1, PRUint32 *aCodeRange2) { nsFontCharSetMap *charSetMap = GetCharSetMap(aCharset); nsFontCharSetInfo* charSetInfo = charSetMap->mInfo; *aCodeRange1 = charSetInfo->mCodeRange1Bits; *aCodeRange2 = charSetInfo->mCodeRange2Bits; } +#endif Index: gfx/src/gtk/nsFontMetricsGTK.h =================================================================== RCS file: /cvsroot/mozilla/gfx/src/gtk/nsFontMetricsGTK.h,v --- gfx/src/gtk/nsFontMetricsGTK.h 5 Feb 2004 01:57:03 -0000 1.60 +++ gfx/src/gtk/nsFontMetricsGTK.h 17 Oct 2004 11:10:04 -0000 @@ -48,15 +48,17 @@ #include "nsIDeviceContext.h" #include "nsCRT.h" #include "nsCOMPtr.h" #include "nsRenderingContextGTK.h" #include "nsICharRepresentable.h" #include "nsCompressedCharMap.h" #include "nsIFontMetricsGTK.h" +#ifdef MOZ_ENABLE_FREETYPE2 #include "nsIFontCatalogService.h" +#endif #include #include #undef FONT_HAS_GLYPH #define FONT_HAS_GLYPH(map, char) IS_REPRESENTABLE(map, char) #define WEIGHT_INDEX(weight) (((weight) / 100) - 1) @@ -88,15 +90,17 @@ struct nsFontStretch nsFontGTK** mSizes; PRUint16 mSizesAlloc; PRUint16 mSizesCount; char* mScalable; PRBool mOutlineScaled; nsVoidArray mScaledFonts; +#ifdef MOZ_ENABLE_FREETYPE2 nsITrueTypeFontCatalogEntry* mFreeTypeFaceID; +#endif }; struct nsFontStyle { NS_DECL_AND_IMPL_ZEROING_OPERATOR_NEW void FillWeightHoles(void); @@ -407,14 +411,16 @@ public: NS_DECL_ISUPPORTS NS_DECL_NSIFONTENUMERATOR }; class nsHashKey; PRBool FreeNode(nsHashKey* aKey, void* aData, void* aClosure); nsFontCharSetInfo *GetCharSetInfo(const char *aCharSetName); +#ifdef MOZ_ENABLE_FREETYPE2 void CharSetNameToCodeRangeBits(const char*, PRUint32*, PRUint32*); +#endif nsFontCharSetMap *GetCharSetMap(const char *aCharSetName); #endif Index: gfx/src/gtk/nsFontMetricsXft.cpp =================================================================== RCS file: /cvsroot/mozilla/gfx/src/gtk/nsFontMetricsXft.cpp,v --- gfx/src/gtk/nsFontMetricsXft.cpp 14 Oct 2004 20:36:14 -0000 1.51.6.2 +++ gfx/src/gtk/nsFontMetricsXft.cpp 17 Oct 2004 11:10:11 -0000 @@ -60,14 +60,15 @@ #include "nsICharsetConverterManager.h" #include "nsICharRepresentable.h" #include "nsIPersistentProperties2.h" #include "nsCompressedCharMap.h" #include "nsNetUtil.h" #include "nsClassHashtable.h" #include "nsAutoBuffer.h" +#include "nsFontConfigUtils.h" #include #include #include #define FORCE_PR_LOG #include "prlog.h" @@ -190,34 +191,14 @@ class nsFontXftInfo { // Unicode, Custom, CustomWide nsXftFontType mFontType; // Truetype cmap to use for direct retrieval of GIDs with FT_Get_Char_Index // for 'narrow' custom fonts. FT_Encoding mFT_Encoding; }; -struct MozXftLangGroup { - const char *mozLangGroup; - FcChar32 character; - const FcChar8 *XftLang; -}; - -static const MozXftLangGroup MozXftLangGroups[] = { - { "x-western", 0x0041, (const FcChar8 *)"en" }, - { "x-central-euro", 0x0100, (const FcChar8 *)"pl" }, - { "x-cyrillic", 0x0411, (const FcChar8 *)"ru" }, - { "x-baltic", 0x0104, (const FcChar8 *)"lv" }, - { "x-devanagari", 0x0905, (const FcChar8 *)"hi" }, - { "x-tamil", 0x0B85, (const FcChar8 *)"ta" }, - { "x-unicode", 0x0000, 0 }, - { "x-user-def", 0x0000, 0 }, -}; - -#define NUM_XFT_LANG_GROUPS (sizeof (MozXftLangGroups) / \ - sizeof (MozXftLangGroups[0])) - struct DrawStringData { nscoord x; nscoord y; const nscoord *spacing; nscoord xOffset; nsRenderingContextGTK *context; XftDraw *draw; @@ -232,29 +213,19 @@ struct BoundingMetricsData { PRBool firstTime; }; #endif /* MOZ_MATHML */ #define AUTO_BUFFER_SIZE 3000 typedef nsAutoBuffer nsAutoFcChar32Buffer; -static int CalculateSlant (PRUint8 aStyle); -static int CalculateWeight (PRUint16 aWeight); -static void AddLangGroup (FcPattern *aPattern, nsIAtom *aLangGroup); -static void AddFFRE (FcPattern *aPattern, nsCString *aFamily, - PRBool aWeak); -static void FFREToFamily (nsACString &aFFREName, nsACString &oFamily); -static int FFRECountHyphens (nsACString &aFFREName); static int CompareFontNames (const void* aArg1, const void* aArg2, void* aClosure); -static PRBool IsASCIIFontName (const nsString& aName); static nsresult EnumFontsXft (nsIAtom* aLangGroup, const char* aGeneric, PRUint32* aCount, PRUnichar*** aResult); -static const MozXftLangGroup* FindFCLangGroup (nsACString &aLangGroup); - static void ConvertCharToUCS4 (const char *aString, PRUint32 aLength, nsAutoFcChar32Buffer &aOutBuffer, PRUint32 *aOutLen); static void ConvertUnicharToUCS4 (const PRUnichar *aString, PRUint32 aLength, nsAutoFcChar32Buffer &aOutBuffer, @@ -1018,21 +989,21 @@ nsFontMetricsXft::SetupFCPattern(void) for (int i=0; i < mFontList.Count(); ++i) { // if this was a generic name, break out of the loop since we // don't want to add it to the pattern yet if (mFontIsGeneric[i]) break;; nsCString *familyName = mFontList.CStringAt(i); - AddFFRE(mPattern, familyName, PR_FALSE); + NS_AddFFRE(mPattern, familyName, PR_FALSE); } // Add the language group. Note that we do this before adding any // generics. That's because the language is more important than // any generic font. - AddLangGroup (mPattern, mLangGroup); + NS_AddLangGroup (mPattern, mLangGroup); // If there's a generic add a pref for the generic if there's one // set. if (mGenericFont && !mFont->systemFont) { nsCString name; name += "font.name."; name += mGenericFont->get(); @@ -1048,31 +1019,31 @@ nsFontMetricsXft::SetupFCPattern(void) if (pref) { nsresult rv; nsXPIDLCString value; rv = pref->GetCharPref(name.get(), getter_Copies(value)); // we ignore prefs that have three hypens since they are X // style prefs. - if (FFRECountHyphens(value) < 3) { + if (NS_FFRECountHyphens(value) < 3) { nsCString tmpstr; tmpstr.Append(value); if (PR_LOG_TEST(gXftFontLoad, PR_LOG_DEBUG)) { printf("\tadding generic font from preferences: %s\n", tmpstr.get()); } - AddFFRE(mPattern, &tmpstr, PR_FALSE); + NS_AddFFRE(mPattern, &tmpstr, PR_FALSE); } } } // Add the generic if there is one. if (mGenericFont && !mFont->systemFont) - AddFFRE(mPattern, mGenericFont, PR_FALSE); + NS_AddFFRE(mPattern, mGenericFont, PR_FALSE); if (PR_LOG_TEST(gXftFontLoad, PR_LOG_DEBUG)) { // generic font if (mGenericFont && !mFont->systemFont) { printf("\tadding generic family: %s\n", mGenericFont->get()); } @@ -1091,31 +1062,31 @@ nsFontMetricsXft::SetupFCPattern(void) default: printf("roman\n"); break; } // weight printf("\tweight: (orig,calc) %d,%d\n", - mFont->weight, CalculateWeight(mFont->weight)); + mFont->weight, NS_CalculateWeight(mFont->weight)); } // add the point size // We've done some round-tripping of floating point numbers so they // might not be quite right. Since Xft rounds down, add a little, // so we don't go from 9.00000 to 8.99999 to 8. FcPatternAddDouble(mPattern, FC_PIXEL_SIZE, mPixelSize + 0.000001); // Add the slant type FcPatternAddInteger(mPattern, FC_SLANT, - CalculateSlant(mFont->style)); + NS_CalculateSlant(mFont->style)); // Add the weight FcPatternAddInteger(mPattern, FC_WEIGHT, - CalculateWeight(mFont->weight)); + NS_CalculateWeight(mFont->weight)); // Set up the default substitutions for this font FcConfigSubstitute(0, mPattern, FcMatchPattern); XftDefaultSubstitute(GDK_DISPLAY(), DefaultScreen(GDK_DISPLAY()), mPattern); } @@ -1270,15 +1241,15 @@ nsFontMetricsXft::SetupMiniFont(void) XftPatternAddBool(mPattern, XFT_RENDER, False); FcPatternAddString(pattern, FC_FAMILY, (FcChar8 *)"monospace"); FcPatternAddInteger(pattern, FC_PIXEL_SIZE, int(0.5 * mPixelSize)); FcPatternAddInteger(pattern, FC_WEIGHT, - CalculateWeight(mFont->weight)); + NS_CalculateWeight(mFont->weight)); FcConfigSubstitute(0, pattern, FcMatchPattern); XftDefaultSubstitute(GDK_DISPLAY(), DefaultScreen(GDK_DISPLAY()), pattern); FcResult res; @@ -1686,15 +1657,15 @@ nsFontMetricsXft::BoundingMetricsCallbac #endif /* MOZ_MATHML */ /* static */ nsresult nsFontMetricsXft::FamilyExists(nsIDeviceContext *aDevice, const nsString &aName) { - if (!IsASCIIFontName(aName)) + if (!NS_IsASCIIFontName(aName)) return NS_ERROR_FAILURE; NS_ConvertUCS2toUTF8 name(aName); FcFontSet *set = nsnull; FcObjectSet *os = nsnull; @@ -1744,15 +1715,15 @@ nsFontMetricsXft::FamilyExists(nsIDevice /* static */ PRBool nsFontMetricsXft::EnumFontCallback(const nsString &aFamily, PRBool aIsGeneric, void *aData) { // make sure it's an ascii name, if not then return and continue // enumerating - if (!IsASCIIFontName(aFamily)) + if (!NS_IsASCIIFontName(aFamily)) return PR_TRUE; nsCAutoString name; name.AssignWithConversion(aFamily.get()); ToLowerCase(name); nsFontMetricsXft *metrics = (nsFontMetricsXft *)aData; metrics->mFontList.AppendCString(name); @@ -1842,15 +1813,15 @@ nsFontEnumeratorXft::GetDefaultFont(cons match_pattern = FcPatternCreate(); if (!match_pattern) return NS_OK; // not fatal, just return an empty default name if (aLangGroup && *aLangGroup) { nsCOMPtr langGroup = do_GetAtom(aLangGroup); - AddLangGroup(match_pattern, langGroup); + NS_AddLangGroup(match_pattern, langGroup); } FcConfigSubstitute(0, match_pattern, FcMatchPattern); FcDefaultSubstitute(match_pattern); FcPattern* result_pattern = FcFontMatch(0, match_pattern, &res); if (result_pattern) { char *family; @@ -2227,182 +2198,22 @@ nsAutoDrawSpecBuffer::Flush() } } // Static functions /* static */ int -CalculateSlant(PRUint8 aStyle) -{ - int fcSlant; - - switch(aStyle) { - case NS_FONT_STYLE_ITALIC: - fcSlant = FC_SLANT_ITALIC; - break; - case NS_FONT_STYLE_OBLIQUE: - fcSlant = FC_SLANT_OBLIQUE; - break; - default: - fcSlant = FC_SLANT_ROMAN; - break; - } - - return fcSlant; -} - -/* static */ -int -CalculateWeight (PRUint16 aWeight) -{ - /* - * weights come in two parts crammed into one - * integer -- the "base" weight is weight / 100, - * the rest of the value is the "offset" from that - * weight -- the number of steps to move to adjust - * the weight in the list of supported font weights, - * this value can be negative or positive. - */ - PRInt32 baseWeight = (aWeight + 50) / 100; - PRInt32 offset = aWeight - baseWeight * 100; - - /* clip weights to range 0 to 9 */ - if (baseWeight < 0) - baseWeight = 0; - if (baseWeight > 9) - baseWeight = 9; - - /* Map from weight value to fcWeights index */ - static int fcWeightLookup[10] = { - 0, 0, 0, 0, 1, 1, 2, 3, 3, 4, - }; - - PRInt32 fcWeight = fcWeightLookup[baseWeight]; - - /* - * adjust by the offset value, make sure we stay inside the - * fcWeights table - */ - fcWeight += offset; - - if (fcWeight < 0) - fcWeight = 0; - if (fcWeight > 4) - fcWeight = 4; - - /* Map to final FC_WEIGHT value */ - static int fcWeights[5] = { - FC_WEIGHT_LIGHT, /* 0 */ - FC_WEIGHT_MEDIUM, /* 1 */ - FC_WEIGHT_DEMIBOLD, /* 2 */ - FC_WEIGHT_BOLD, /* 3 */ - FC_WEIGHT_BLACK, /* 4 */ - }; - - return fcWeights[fcWeight]; - -} - -/* static */ -void -AddLangGroup(FcPattern *aPattern, nsIAtom *aLangGroup) -{ - // Find the FC lang group for this lang group - nsCAutoString cname; - aLangGroup->ToUTF8String(cname); - - // see if the lang group needs to be translated from mozilla's - // internal mapping into fontconfig's - const struct MozXftLangGroup *langGroup; - langGroup = FindFCLangGroup(cname); - - // if there's no lang group, just use the lang group as it was - // passed to us - // - // we're casting away the const here for the strings - should be - // safe. - if (!langGroup) - FcPatternAddString(aPattern, FC_LANG, (FcChar8 *)cname.get()); - else if (langGroup->XftLang) - FcPatternAddString(aPattern, FC_LANG, (FcChar8 *)langGroup->XftLang); -} - -/* static */ -void -AddFFRE(FcPattern *aPattern, nsCString *aFamily, PRBool aWeak) -{ - nsCAutoString family; - FFREToFamily(*aFamily, family); - - FcValue v; - v.type = FcTypeString; - // casting away the const here, should be safe - v.u.s = (FcChar8 *)family.get(); - - if (aWeak) - FcPatternAddWeak(aPattern, FC_FAMILY, v, FcTrue); - else - FcPatternAdd(aPattern, FC_FAMILY, v, FcTrue); -} - -/* static */ -void -FFREToFamily(nsACString &aFFREName, nsACString &oFamily) -{ - if (FFRECountHyphens(aFFREName) == 3) { - PRInt32 familyHyphen = aFFREName.FindChar('-') + 1; - PRInt32 registryHyphen = aFFREName.FindChar('-',familyHyphen); - oFamily.Append(Substring(aFFREName, familyHyphen, - registryHyphen-familyHyphen)); - } - else { - oFamily.Append(aFFREName); - } -} - -/* static */ -int -FFRECountHyphens (nsACString &aFFREName) -{ - int h = 0; - PRInt32 hyphen = 0; - while ((hyphen = aFFREName.FindChar('-', hyphen)) >= 0) { - ++h; - ++hyphen; - } - return h; -} - -/* static */ -int CompareFontNames (const void* aArg1, const void* aArg2, void* aClosure) { const PRUnichar* str1 = *((const PRUnichar**) aArg1); const PRUnichar* str2 = *((const PRUnichar**) aArg2); return nsCRT::strcmp(str1, str2); } -PRBool -IsASCIIFontName(const nsString& aName) -{ - PRUint32 len = aName.Length(); - const PRUnichar* str = aName.get(); - for (PRUint32 i = 0; i < len; i++) { - /* - * X font names are printable ASCII, ignore others (for now) - */ - if ((str[i] < 0x20) || (str[i] > 0x7E)) { - return PR_FALSE; - } - } - - return PR_TRUE; -} - /* static */ nsresult EnumFontsXft(nsIAtom* aLangGroup, const char* aGeneric, PRUint32* aCount, PRUnichar*** aResult) { FcPattern *pat = NULL; FcObjectSet *os = NULL; @@ -2422,15 +2233,15 @@ EnumFontsXft(nsIAtom* aLangGroup, const os = FcObjectSetBuild(FC_FAMILY, FC_FOUNDRY, 0); if (!os) goto end; // take the pattern and add the lang group to it if (aLangGroup) - AddLangGroup(pat, aLangGroup); + NS_AddLangGroup(pat, aLangGroup); // get the font list fs = FcFontList(0, pat, os); if (!fs) goto end; @@ -2530,28 +2341,14 @@ EnumFontsXft(nsIAtom* aLangGroup, const if (fs) FcFontSetDestroy(fs); return rv; } /* static */ -const MozXftLangGroup* -FindFCLangGroup (nsACString &aLangGroup) -{ - for (unsigned int i=0; i < NUM_XFT_LANG_GROUPS; ++i) { - if (aLangGroup.Equals(MozXftLangGroups[i].mozLangGroup, - nsCaseInsensitiveCStringComparator())) { - return &MozXftLangGroups[i]; - } - } - - return nsnull; -} - -/* static */ void ConvertCharToUCS4(const char *aString, PRUint32 aLength, nsAutoFcChar32Buffer &aOutBuffer, PRUint32 *aOutLen) { *aOutLen = 0; FcChar32 *outBuffer; Index: gfx/src/gtk/nsGfxFactoryGTK.cpp =================================================================== RCS file: /cvsroot/mozilla/gfx/src/gtk/nsGfxFactoryGTK.cpp,v --- gfx/src/gtk/nsGfxFactoryGTK.cpp 7 Sep 2003 22:20:38 -0000 1.58 +++ gfx/src/gtk/nsGfxFactoryGTK.cpp 17 Oct 2004 11:10:11 -0000 @@ -67,16 +67,18 @@ #endif #ifdef MOZ_ENABLE_COREXFONTS #include "nsFontMetricsGTK.h" #endif #include "nsFontMetricsUtils.h" #include "nsPrintSession.h" #include "gfxImageFrame.h" +#ifdef MOZ_ENABLE_FREETYPE2 #include "nsFT2FontCatalog.h" #include "nsFreeType.h" +#endif // objects that just require generic constructors NS_GENERIC_FACTORY_CONSTRUCTOR(nsDeviceContextGTK) NS_GENERIC_FACTORY_CONSTRUCTOR(nsRenderingContextGTK) NS_GENERIC_FACTORY_CONSTRUCTOR(nsImageGTK) NS_GENERIC_FACTORY_CONSTRUCTOR(nsBlender) @@ -88,16 +90,16 @@ NS_GENERIC_FACTORY_CONSTRUCTOR(nsScreenM NS_GENERIC_FACTORY_CONSTRUCTOR(nsPrintOptionsGTK) NS_GENERIC_FACTORY_CONSTRUCTOR(nsPrinterEnumeratorGTK) #ifdef NATIVE_THEME_SUPPORT NS_GENERIC_FACTORY_CONSTRUCTOR(nsNativeThemeGTK) #endif NS_GENERIC_FACTORY_CONSTRUCTOR_INIT(nsPrintSession, Init) NS_GENERIC_FACTORY_CONSTRUCTOR(gfxImageFrame) -NS_GENERIC_FACTORY_CONSTRUCTOR(nsFT2FontCatalog) #ifdef MOZ_ENABLE_FREETYPE2 +NS_GENERIC_FACTORY_CONSTRUCTOR(nsFT2FontCatalog) NS_GENERIC_FACTORY_CONSTRUCTOR_INIT(nsFreeType2, Init) #endif // our custom constructors static nsresult nsFontMetricsConstructor(nsISupports *aOuter, REFNSIID aIID, void **aResult) @@ -287,19 +289,19 @@ static const nsModuleComponentInfo compo GFX_IMAGEFRAME_CID, "@mozilla.org/gfx/image/frame;2", gfxImageFrameConstructor, }, { "Print Session", NS_PRINTSESSION_CID, "@mozilla.org/gfx/printsession;1", nsPrintSessionConstructor }, +#ifdef MOZ_ENABLE_FREETYPE2 { "TrueType Font Catalog Service", NS_FONTCATALOGSERVICE_CID, "@mozilla.org/gfx/xfontcatalogservice;1", nsFT2FontCatalogConstructor }, -#ifdef MOZ_ENABLE_FREETYPE2 { "FreeType2 routines", NS_FREETYPE2_CID, NS_FREETYPE2_CONTRACTID, nsFreeType2Constructor }, #endif #ifdef NATIVE_THEME_SUPPORT { "Native Theme Renderer", Index: gfx/src/ps/Makefile.in =================================================================== RCS file: /cvsroot/mozilla/gfx/src/ps/Makefile.in,v --- gfx/src/ps/Makefile.in 11 Mar 2004 22:05:32 -0000 1.50 +++ gfx/src/ps/Makefile.in 17 Oct 2004 11:10:14 -0000 @@ -73,35 +73,46 @@ EXTRA_DSO_LDOPTS = \ -L$(DIST)/lib \ -lgfxshared_s \ $(EXTRA_DSO_LIBS) \ $(MOZ_COMPONENT_LIBS) \ $(MOZ_UNICHARUTIL_LIBS) \ $(NULL) -ifdef MOZ_ENABLE_FREETYPE2 +ifdef MOZ_ENABLE_XFT +EXTRA_DSO_LDOPTS += \ + $(MOZ_XFT_LIBS) \ + $(NULL) +endif + +ifneq (,$(MOZ_ENABLE_FREETYPE2)$(MOZ_ENABLE_XFT)) CPPSRCS += \ nsCidMap.cpp \ nsType1.cpp \ nsType8.cpp \ $(NULL) endif include $(topsrcdir)/config/rules.mk -ifdef MOZ_ENABLE_FREETYPE2 -INCLUDES += $(FT2_CFLAGS) -endif - CFLAGS += $(TK_CFLAGS) CXXFLAGS += $(TK_CFLAGS) LOCAL_INCLUDES = \ -I../.. \ -I$(srcdir)/.. \ $(NULL) +ifdef MOZ_ENABLE_XFT +INCLUDES += $(MOZ_XFT_CFLAGS) +LOCAL_INCLUDES += -I$(srcdir)/../shared +else +ifdef MOZ_ENABLE_FREETYPE2 +INCLUDES += $(FT2_CFLAGS) +endif +endif + libs:: $(INSTALL) $(EXPORT_RESOURCE) $(DIST)/bin/res install:: $(SYSINSTALL) $(IFLAGS1) $(EXPORT_RESOURCE) $(DESTDIR)$(mozappdir)/res Index: gfx/src/ps/nsDeviceContextPS.cpp =================================================================== RCS file: /cvsroot/mozilla/gfx/src/ps/nsDeviceContextPS.cpp,v --- gfx/src/ps/nsDeviceContextPS.cpp 20 Feb 2004 17:29:31 -0000 1.65 +++ gfx/src/ps/nsDeviceContextPS.cpp 17 Oct 2004 11:10:14 -0000 @@ -209,24 +209,35 @@ nsDeviceContextPS::InitDeviceContextPS(n mParentDeviceContext = aParentContext; mPSFontGeneratorList = new nsHashtable(); NS_ENSURE_TRUE(mPSFontGeneratorList, NS_ERROR_OUT_OF_MEMORY); nsresult rv; nsCOMPtr pref(do_GetService(NS_PREF_CONTRACTID, &rv)); +#ifdef MOZ_ENABLE_XFT + if (NS_SUCCEEDED(rv)) { + rv = pref->GetBoolPref("font.FreeType2.printing", &mFTPEnable); + if (NS_FAILED(rv)) + mFTPEnable = PR_FALSE; + } +#else + mFTPEnable = PR_FALSE; +#ifdef MOZ_ENABLE_FREETYPE2 if (NS_SUCCEEDED(rv)) { rv = pref->GetBoolPref("font.FreeType2.enable", &mFTPEnable); if (NS_FAILED(rv)) mFTPEnable = PR_FALSE; if (mFTPEnable) { rv = pref->GetBoolPref("font.FreeType2.printing", &mFTPEnable); if (NS_FAILED(rv)) mFTPEnable = PR_FALSE; } } +#endif +#endif // the user's locale nsCOMPtr langService; langService = do_GetService(NS_LANGUAGEATOMSERVICE_CONTRACTID); if (langService) { langService->GetLocaleLanguageGroup(&gUsersLocale); } @@ -431,15 +442,15 @@ GeneratePSFontCallback(nsHashKey *aKey, */ NS_IMETHODIMP nsDeviceContextPS::EndDocument(void) { PR_LOG(nsDeviceContextPSLM, PR_LOG_DEBUG, ("nsDeviceContextPS::EndDocument()\n")); NS_ENSURE_TRUE(mPSObj != nsnull, NS_ERROR_NULL_POINTER); -#ifdef MOZ_ENABLE_FREETYPE2 +#if defined(MOZ_ENABLE_FREETYPE2) || defined(MOZ_ENABLE_XFT) // Before output Type8 font, check whether printer support CID font if (mFTPEnable && mPSFontGeneratorList) if (mPSFontGeneratorList->Count() > 0) mPSObj->add_cid_check(); #endif /* Core of TrueType printing: Index: gfx/src/ps/nsFontMetricsPS.cpp =================================================================== RCS file: /cvsroot/mozilla/gfx/src/ps/nsFontMetricsPS.cpp,v --- gfx/src/ps/nsFontMetricsPS.cpp 5 Feb 2004 01:57:05 -0000 1.42 +++ gfx/src/ps/nsFontMetricsPS.cpp 17 Oct 2004 11:10:16 -0000 @@ -17,14 +17,17 @@ * The Initial Developer of the Original Code is * Netscape Communications Corporation. * Portions created by the Initial Developer are Copyright (C) 1998 * the Initial Developer. All Rights Reserved. * * Contributor(s): * Roland Mainz + * Ervin Yan + * Christopher Blizzard + * Jungshik Shin * * * Alternatively, the contents of this file may be used under the terms of * either the GNU General Public License Version 2 or later (the "GPL"), or * the GNU Lesser General Public License Version 2.1 or later (the "LGPL"), * in which case the provisions of the GPL or the LGPL are applicable instead * of those above. If you wish to allow use of your version of this file only @@ -43,30 +46,39 @@ #include "nsRenderingContextPS.h" #include "nsIServiceManager.h" #include "nsGfxCIID.h" #include "nsIPref.h" #include "nsVoidArray.h" #include "nsReadableUtils.h" -#ifdef MOZ_ENABLE_FREETYPE2 +#if defined(MOZ_ENABLE_FREETYPE2) || defined(MOZ_ENABLE_XFT) #include "nsType8.h" #endif #include "prlog.h" #include "nsArray.h" extern nsIAtom *gUsersLocale; #define NS_IS_BOLD(weight) ((weight) > 400 ? 1 : 0) +#ifdef MOZ_ENABLE_XFT + +#include "nsFontConfigUtils.h" + +static nsFontPS* CreateFontPS(nsXftEntry*, const nsFont&, + nsFontMetricsPS*); + +#else #ifdef MOZ_ENABLE_FREETYPE2 static nsFontPS* CreateFontPS(nsITrueTypeFontCatalogEntry*, const nsFont&, nsFontMetricsPS*); static NS_DEFINE_CID(kFCSCID, NS_FONTCATALOGSERVICE_CID); #endif +#endif #ifdef PR_LOGGING static PRLogModuleInfo *gFontMetricsPSM = PR_NewLogModule("FontMetricsPS"); #endif /** --------------------------------------------------- * See documentation in nsFontMetricsPS.h @@ -89,19 +101,28 @@ nsFontMetricsPS :: ~nsFontMetricsPS() if (mFontsPS) { int i; for (i=0; iCount(); i++) { fontps *fontPS = (fontps *)mFontsPS->ElementAt(i); if (!fontPS) continue; - NS_IF_RELEASE(fontPS->entry); if (fontPS->fontps) delete fontPS->fontps; +#ifdef MOZ_ENABLE_XFT + if (fontPS->entry) + delete fontPS->entry; + if (fontPS->charset) + FcCharSetDestroy(fontPS->charset); +#else +#ifdef MOZ_ENABLE_FREETYPE2 + NS_IF_RELEASE(fontPS->entry); if (fontPS->ccmap) FreeCCMap(fontPS->ccmap); +#endif +#endif delete fontPS; } delete mFontsPS; } if (mFontsAlreadyLoaded) { delete mFontsAlreadyLoaded; @@ -123,14 +144,15 @@ NS_IMPL_ISUPPORTS1(nsFontMetricsPS, nsIF NS_IMETHODIMP nsFontMetricsPS :: Init(const nsFont& aFont, nsIAtom* aLangGroup, nsIDeviceContext *aContext) { mLangGroup = aLangGroup; mFont = new nsFont(aFont); + //don't addref this to avoid circular refs mDeviceContext = (nsDeviceContextPS *)aContext; mFontsPS = new nsVoidArray(); NS_ENSURE_TRUE(mFontsPS, NS_ERROR_OUT_OF_MEMORY); mFontsAlreadyLoaded = new nsHashtable(); NS_ENSURE_TRUE(mFontsAlreadyLoaded, NS_ERROR_OUT_OF_MEMORY); @@ -158,15 +180,15 @@ nsFontMetricsPS :: Destroy() void nsFontMetricsPS::RealizeFont() { if (mFont && mDeviceContext) { float dev2app; dev2app = mDeviceContext->DevUnitsToAppUnits(); fontps *font = (fontps*)mFontsPS->ElementAt(0); -#ifdef MOZ_ENABLE_FREETYPE2 +#if defined(MOZ_ENABLE_FREETYPE2) || defined(MOZ_ENABLE_XFT) NS_ASSERTION(font && font->entry, "no font available"); if (font && !font->fontps && font->entry) font->fontps = CreateFontPS(font->entry, *mFont, this); #endif NS_ASSERTION(font && font->fontps, "no font available"); if (font && font->fontps) font->fontps->RealizeFont(this, dev2app); @@ -464,19 +486,23 @@ nsFontPS::FindFont(char aChar, const nsF // nsFontPS nsFontPS* nsFontPS::FindFont(PRUnichar aChar, const nsFont& aFont, nsFontMetricsPS* aFontMetrics) { nsFontPS* fontPS; -#ifdef MOZ_ENABLE_FREETYPE2 +#if defined(MOZ_ENABLE_FREETYPE2) || defined(MOZ_ENABLE_XFT) nsDeviceContextPS* dc = aFontMetrics->GetDeviceContext(); NS_ENSURE_TRUE(dc, nsnull); if (dc->mFTPEnable) { +#ifdef MOZ_ENABLE_XFT + fontPS = nsFontPSXft::FindFont(aChar, aFont, aFontMetrics); +#else fontPS = nsFontPSFreeType::FindFont(aChar, aFont, aFontMetrics); +#endif if (fontPS) return fontPS; } #endif /* Find in afm font */ if (aFontMetrics->GetFontsPS()->Count() > 0) { @@ -484,17 +510,23 @@ nsFontPS::FindFont(PRUnichar aChar, cons NS_ENSURE_TRUE(fps, nsnull); fontPS = fps->fontps; } else { fontPS = nsFontPSAFM::FindFont(aFont, aFontMetrics); fontps *fps = new fontps; NS_ENSURE_TRUE(fps, nsnull); - fps->entry = nsnull; fps->fontps = fontPS; +#if defined(MOZ_ENABLE_XFT) || defined(MOZ_ENABLE_FREETYPE2) + fps->entry = nsnull; +#ifdef MOZ_ENABLE_XFT + fps->charset = nsnull; +#else fps->ccmap = nsnull; +#endif +#endif aFontMetrics->GetFontsPS()->AppendElement(fps); } return fontPS; } nsFontPS::nsFontPS(const nsFont& aFont, nsFontMetricsPS* aFontMetrics) { @@ -544,162 +576,926 @@ nsFontPSAFM::FindFont(const nsFont& aFon } nsFontPSAFM::nsFontPSAFM(const nsFont& aFont, nsAFMObject* aAFMInfo, PRInt16 fontIndex, nsFontMetricsPS* aFontMetrics) : nsFontPS(aFont, aFontMetrics), mAFMInfo(aAFMInfo), mFontIndex(fontIndex) { if (!(mFont && mAFMInfo)) return; - mFamilyName.AssignWithConversion((char*)mAFMInfo->mPSFontInfo->mFamilyName); + AppendASCIItoUTF16(mAFMInfo->mPSFontInfo->mFamilyName, mFamilyName); } nsFontPSAFM::~nsFontPSAFM() { if (mAFMInfo) { delete mAFMInfo; mAFMInfo = nsnull; } } nscoord nsFontPSAFM::GetWidth(const char* aString, PRUint32 aLength) { - nscoord width = 0; - if (mAFMInfo) { - mAFMInfo->GetStringWidth(aString, width, aLength); - } - return width; + nscoord width = 0; + if (mAFMInfo) { + mAFMInfo->GetStringWidth(aString, width, aLength); + } + return width; +} + +nscoord +nsFontPSAFM::GetWidth(const PRUnichar* aString, PRUint32 aLength) +{ + nscoord width = 0; + if (mAFMInfo) { + mAFMInfo->GetStringWidth(aString, width, aLength); + } + return width; +} + +nscoord +nsFontPSAFM::DrawString(nsRenderingContextPS* aContext, + nscoord aX, nscoord aY, + const char* aString, PRUint32 aLength) +{ + NS_ENSURE_TRUE(aContext, 0); + nsPostScriptObj* psObj = aContext->GetPostScriptObj(); + NS_ENSURE_TRUE(psObj, 0); + + psObj->moveto(aX, aY); + psObj->show(aString, aLength, ""); + return GetWidth(aString, aLength); +} + +nscoord +nsFontPSAFM::DrawString(nsRenderingContextPS* aContext, + nscoord aX, nscoord aY, + const PRUnichar* aString, PRUint32 aLength) +{ + NS_ENSURE_TRUE(aContext, 0); + nsPostScriptObj* psObj = aContext->GetPostScriptObj(); + NS_ENSURE_TRUE(psObj, 0); + + psObj->moveto(aX, aY); + psObj->show(aString, aLength, "", 0); + return GetWidth(aString, aLength); +} + +nsresult +nsFontPSAFM::RealizeFont(nsFontMetricsPS* aFontMetrics, float dev2app) +{ + NS_ENSURE_ARG_POINTER(aFontMetrics); + + float fontSize; + float offset; + + nscoord onePixel = NSToCoordRound(1 * dev2app); + + // convert the font size which is in twips to points + fontSize = mFont->size / TWIPS_PER_POINT_FLOAT; + + offset = NSFloatPointsToTwips(fontSize * mAFMInfo->mPSFontInfo->mXHeight) / 1000.0f; + nscoord xHeight = NSToCoordRound(offset); + aFontMetrics->SetXHeight(xHeight); + aFontMetrics->SetSuperscriptOffset(xHeight); + aFontMetrics->SetSubscriptOffset(xHeight); + aFontMetrics->SetStrikeout((nscoord)(xHeight / 2), onePixel); + + offset = NSFloatPointsToTwips(fontSize * mAFMInfo->mPSFontInfo->mUnderlinePosition) / 1000.0f; + aFontMetrics->SetUnderline(NSToCoordRound(offset), onePixel); + + nscoord size = NSToCoordRound(fontSize * dev2app); + aFontMetrics->SetHeight(size); + aFontMetrics->SetEmHeight(size); + aFontMetrics->SetMaxAdvance(size); + aFontMetrics->SetMaxHeight(size); + + offset = NSFloatPointsToTwips(fontSize * mAFMInfo->mPSFontInfo->mAscender) / 1000.0f; + nscoord ascent = NSToCoordRound(offset); + aFontMetrics->SetAscent(ascent); + aFontMetrics->SetEmAscent(ascent); + aFontMetrics->SetMaxAscent(ascent); + + offset = NSFloatPointsToTwips(fontSize * mAFMInfo->mPSFontInfo->mDescender) / 1000.0f; + nscoord descent = -(NSToCoordRound(offset)); + aFontMetrics->SetDescent(descent); + aFontMetrics->SetEmDescent(descent); + aFontMetrics->SetMaxDescent(descent); + + aFontMetrics->SetLeading(0); + + nscoord spaceWidth = GetWidth(" ", 1); + aFontMetrics->SetSpaceWidth(spaceWidth); + + nscoord aveCharWidth = GetWidth("x", 1); + aFontMetrics->SetAveCharWidth(aveCharWidth); + + return NS_OK; +} + +nsresult +nsFontPSAFM::SetupFont(nsRenderingContextPS* aContext) +{ + NS_ENSURE_TRUE(aContext && mFontMetrics, 0); + nsPostScriptObj* psObj = aContext->GetPostScriptObj(); + NS_ENSURE_TRUE(psObj, 0); + + nscoord fontHeight = 0; + mFontMetrics->GetHeight(fontHeight); + + psObj->setscriptfont(mFontIndex, mFamilyName, + fontHeight, mFont->style, mFont->variant, + mFont->weight, mFont->decorations); + return NS_OK; +} + +#ifdef MOZ_MATHML +nsresult +nsFontPSAFM::GetBoundingMetrics(const char* aString, + PRUint32 aLength, + nsBoundingMetrics& aBoundingMetrics) +{ + return NS_ERROR_NOT_IMPLEMENTED; +} + +nsresult +nsFontPSAFM::GetBoundingMetrics(const PRUnichar* aString, + PRUint32 aLength, + nsBoundingMetrics& aBoundingMetrics) +{ + return NS_ERROR_NOT_IMPLEMENTED; +} +#endif + +#if defined(MOZ_ENABLE_FREETYPE2) || defined(MOZ_ENABLE_XFT) + +#define WIDEN_8_TO_16_BUF_SIZE 1024 + +#ifdef MOZ_ENABLE_XFT + +nsXftEntry::nsXftEntry(FcPattern *aFontPattern) +{ + mFace = nsnull; + mFaceIndex = 0; + + char *fcResult; + + if (FcPatternGetString(aFontPattern, FC_FILE, 0, (FcChar8 **) &fcResult) + == FcResultMatch) + mFontFileName = fcResult; + + if (FcPatternGetString(aFontPattern, FC_FAMILY, 0, (FcChar8 **) &fcResult) + == FcResultMatch) + mFamilyName = fcResult; + + if (FcPatternGetString(aFontPattern, FC_STYLE, 0, (FcChar8 **) &fcResult) + == FcResultMatch) + mStyleName = fcResult; +} + + +static nsFontPS* +CreateFontPS(nsXftEntry *aEntry, const nsFont& aFont, + nsFontMetricsPS* aFontMetrics) +{ + nsresult rv; + nsDeviceContextPS* dc = aFontMetrics->GetDeviceContext(); + NS_ENSURE_TRUE(dc, nsnull); + + nsCAutoString fileName(aEntry->mFontFileName); + nsCAutoString familyName(aEntry->mFamilyName); + nsCAutoString styleName(aEntry->mStyleName); + ToLowerCase(familyName); + ToLowerCase(styleName); + + nsCAutoString fontName; + fontName.Append(familyName); + fontName.Append("-"); + fontName.Append(styleName); + nsCStringKey key(fontName); + + nsHashtable *psFGList = dc->GetPSFontGeneratorList(); + NS_ENSURE_TRUE(psFGList, nsnull); + + nsPSFontGenerator* psFontGen = (nsPSFontGenerator*) psFGList->Get(&key); + if (!psFontGen) { + psFontGen = new nsXftType8Generator; + NS_ENSURE_TRUE(psFontGen, nsnull); + rv = ((nsXftType8Generator*)psFontGen)->Init(aEntry); + if (NS_FAILED(rv)) { + delete psFontGen; + return nsnull; + } + psFGList->Put(&key, (void *) psFontGen); + } + nsFontPSXft* font = new nsFontPSXft(aFont, aFontMetrics); + NS_ENSURE_TRUE(font, nsnull); + rv = font->Init(aEntry, psFontGen); + if (NS_FAILED(rv)) { + delete font; + return nsnull; + } + return font; +} + +/* static */ +PRBool +nsFontPSXft::CSSFontEnumCallback(const nsString& aFamily, PRBool aIsGeneric, + void* aFpi) +{ + fontPSInfo *fpi = (fontPSInfo *)aFpi; + + // make sure it's an ascii name, if not then return and continue + // enumerating + if (!NS_IsASCIIFontName(aFamily)) + return PR_TRUE; + + NS_LossyConvertUTF16toASCII name(aFamily); + ToLowerCase(name); + fpi->mFontList.AppendCString(name); + fpi->mFontIsGeneric.AppendElement((void *)aIsGeneric); + if (aIsGeneric) { + fpi->mGenericFont = + fpi->mFontList.CStringAt(fpi->mFontList.Count() - 1); + return PR_FALSE; // stop processing + } + + return PR_TRUE; // keep processing +} + +nsFontPS* +nsFontPSXft::FindFont(PRUnichar aChar, const nsFont& aFont, + nsFontMetricsPS* aFontMetrics) +{ + PRBool inited = PR_FALSE; + nsCOMPtr langGroup; + fontPSInfo fpi; + fpi.fontps = aFontMetrics->GetFontsPS(); + int i = 0; + + while (1) { + // + // see if it is already in the list of fonts + // + for (; iCount(); i++) { + fontps *fi = (fontps *)fpi.fontps->ElementAt(i); + if (!fi->entry || !fi->charset) { + NS_ASSERTION(fi->entry, "invalid entry"); + NS_ASSERTION(fi->charset, "invalid charset"); + continue; + } + if (FcCharSetHasChar(fi->charset, aChar)) { + if (!fi->fontps) { +#ifdef PR_LOGGING + if (PR_LOG_TEST(gFontMetricsPSM, PR_LOG_DEBUG)) { + PR_LogPrint("CreateFontPS %s/%s\n", + fi->entry->mFamilyName.get(), fi->entry->mStyleName.get()); + } +#endif + fi->fontps = CreateFontPS(fi->entry, aFont, aFontMetrics); + } + if (fi->fontps) + return fi->fontps; + } + } + + // if already get all matched fonts and not found suitable + // then return nsnull + if (fpi.fontps->Count() > 0) + return nsnull; + + // + // it is not already in the list of fonts + // so add more fonts to the list + // + if (inited) + return nsnull; + + inited = PR_TRUE; + + fpi.nsfont = &aFont; + fpi.alreadyLoaded = aFontMetrics->GetFontsAlreadyLoadedList(); + fpi.mGenericFont = nsnull; + + aFontMetrics->GetLangGroup(getter_AddRefs(langGroup)); + if (!langGroup) + langGroup = NS_NewAtom("x-western"); + + // enumerate over the font names passed in + aFont.EnumerateFamilies(nsFontPSXft::CSSFontEnumCallback, &fpi); + + nsCOMPtr prefService; + prefService = do_GetService(NS_PREF_CONTRACTID); + if (!prefService) + return nsnull; + + nsXPIDLCString value; + nsCAutoString aDefaultFont; + + // Set up the default font name if it's not set + if (!fpi.mGenericFont) { + prefService->CopyCharPref("font.default", getter_Copies(value)); + + if (value.get()) + aDefaultFont = value.get(); + else + aDefaultFont = "serif"; + + fpi.mGenericFont = &aDefaultFont; + } + + // If pattern is null, set up the base bits of it so we can + // match. If we need to match later we don't have to set it up + // again. + FcPattern *pattern = nsnull; + + pattern = FcPatternCreate(); + if (!pattern) + return nsnull; + + // XXX need to add user defined family + + // Add CSS names - walk the list of fonts, adding the generic as + // the last font + for (int i=0; i < fpi.mFontList.Count(); ++i) { + // if this was a generic name, break out of the loop since we + // don't want to add it to the pattern yet + if (fpi.mFontIsGeneric[i]) + break;; + + nsCString *familyName = fpi.mFontList.CStringAt(i); + NS_AddFFRE(pattern, familyName, PR_FALSE); + } + + // Add the language group. Note that we do this before adding any + // generics. That's because the language is more important than + // any generic font. + NS_AddLangGroup(pattern, langGroup); + + // If there's a generic add a pref for the generic if there's one + // set. + if (fpi.mGenericFont && !aFont.systemFont) { + nsCAutoString name("font.name."); + name += fpi.mGenericFont->get(); + name += "."; + + nsAutoString langGroupStr; + langGroup->ToString(langGroupStr); + + LossyAppendUTF16toASCII(langGroupStr, name); + + nsCOMPtr pref; + pref = do_GetService(NS_PREF_CONTRACTID); + if (pref) { + nsresult rv; + nsXPIDLCString value; + rv = pref->GetCharPref(name.get(), getter_Copies(value)); + + // we ignore prefs that have three hypens since they are X + // style prefs. + if (NS_FFRECountHyphens(value) < 3) { + nsCAutoString tmpstr(value); + + if (PR_LOG_TEST(gFontMetricsPSM, PR_LOG_DEBUG)) { + printf("\tadding generic font from preferences: %s\n", + tmpstr.get()); + } + + NS_AddFFRE(pattern, &tmpstr, PR_FALSE); + } + } + } + + // Add the generic if there is one. + if (fpi.mGenericFont && !aFont.systemFont) + NS_AddFFRE(pattern, fpi.mGenericFont, PR_FALSE); + + // Add the slant type + FcPatternAddInteger(pattern, FC_SLANT, NS_CalculateSlant(aFont.style)); + + // Add the weight + FcPatternAddInteger(pattern, FC_WEIGHT, NS_CalculateWeight(aFont.weight)); + + // Set up the default substitutions for this font + FcConfigSubstitute(0, pattern, FcMatchPattern); + FcDefaultSubstitute(pattern); + + FcResult result; + FcFontSet *set = FcFontSort(0, pattern, FcTrue, 0, &result); + if (!set) { + return nsnull; + } + + // Create a list of new font objects based on the fonts returned + // as part of the query + for (int i=0; i < set->nfont; ++i) { + FcBool fc_outline; + FcChar8 *fc_family; + FcChar8 *fc_style; + FcCharSet *fc_charset; + + // skip if the fonts is not outline font files. + result = FcPatternGetBool (set->fonts[i], FC_OUTLINE, 0, &fc_outline); + if (!fc_outline) + continue; + + result = FcPatternGetString (set->fonts[i], FC_FAMILY, 0, &fc_family); + if (result != FcResultMatch || fc_family == nsnull) + continue; + + result = FcPatternGetString (set->fonts[i], FC_STYLE, 0, &fc_style); + if (result != FcResultMatch || fc_style == nsnull) + continue; + + result = FcPatternGetCharSet(set->fonts[i], FC_CHARSET, 0, &fc_charset); + if (result != FcResultMatch || fc_charset == nsnull) + continue; + + nsXftEntry *xftEntry = new nsXftEntry(set->fonts[i]); + if (!xftEntry) + continue; + + fontps *fps = new fontps; + fps->entry = xftEntry; + fps->charset = fc_charset; + fps->fontps = nsnull; + fpi.fontps->AppendElement(fps); + } + + // we're done with the set now + FcFontSetDestroy(set); + + FcPatternDestroy(pattern); + } + + return nsnull; +} + +/*FT_CALLBACK_DEF*/ +FT_Error +nsXftFaceRequester(FTC_FaceID face_id, FT_Library lib, + FT_Pointer request_data, FT_Face* aFace) +{ + nsXftEntry *faceID = (nsXftEntry *)face_id; + + FT_Error fterror = FT_New_Face(lib, faceID->mFontFileName.get(), + faceID->mFaceIndex, aFace); + if (fterror) + *aFace = nsnull; + return 0; +} + +nsFontPSXft::nsFontPSXft(const nsFont& aFont, + nsFontMetricsPS* aFontMetrics) + :nsFontPS(aFont, aFontMetrics) +{ +} + +nsresult +nsFontPSXft::Init(nsXftEntry* aEntry, + nsPSFontGenerator* aPSFontGen) +{ + NS_ENSURE_TRUE(aEntry && aPSFontGen, NS_ERROR_FAILURE); + mEntry = aEntry; + mPSFontGenerator = aPSFontGen; + + float app2dev; + nsIDeviceContext* dc = mFontMetrics->GetDeviceContext(); + NS_ENSURE_TRUE(dc, NS_ERROR_NULL_POINTER); + app2dev = dc->AppUnitsToDevUnits(); + + mPixelSize = NSToIntRound(app2dev * mFont->size); + + mImageDesc.font.face_id = (void*)mEntry; + mImageDesc.font.pix_width = mPixelSize; + mImageDesc.font.pix_height = mPixelSize; + mImageDesc.image_type = 0; + + FT_Error fterror; + fterror = FT_Init_FreeType(&mFreeTypeLibrary); + if (fterror) { + NS_ASSERTION(!fterror, "failed to initialize FreeType library"); + mFreeTypeLibrary = nsnull; + return NS_ERROR_FAILURE; + } + fterror = FTC_Manager_New(mFreeTypeLibrary, 0, 0, 0, nsXftFaceRequester, + NULL, &mFTCacheManager); + NS_ASSERTION(!fterror, "failed to create FreeType Cache manager"); + if (fterror) + return NS_ERROR_FAILURE; + + fterror = FTC_Image_Cache_New(mFTCacheManager, &mImageCache); + NS_ASSERTION(!fterror, "failed to create FreeType image cache"); + if (fterror) + return NS_ERROR_FAILURE; + + return NS_OK; +} + +nsFontPSXft::~nsFontPSXft() +{ + FTC_Manager_Done(mFTCacheManager); + + if (FT_Done_FreeType(mFreeTypeLibrary)) + return; + + mEntry = nsnull; +} + +FT_Face +nsFontPSXft::getFTFace() +{ + FT_Error error; + FT_Face face = mEntry->mFace; + + if (face) + return (face); + + error = FTC_Manager_Lookup_Size(mFTCacheManager, &mImageDesc.font, + &face, nsnull); + NS_ASSERTION(error == 0, "failed to get face/size"); + if (error) + return nsnull; + + mEntry->mFace = face; + return face; +} + +nscoord +nsFontPSXft::GetWidth(const char* aString, PRUint32 aLength) +{ + PRUnichar unichars[WIDEN_8_TO_16_BUF_SIZE]; + PRUint32 len, width = 0; + while ( aLength > 0 ) { + len = PR_MIN(aLength, WIDEN_8_TO_16_BUF_SIZE); + for (PRUint32 i=0; i < len; i++) { + unichars[i] = PRUnichar(PRUint8(aString[i])); + } + width += GetWidth(unichars, len); + aString += len; + aLength -= len; + } + return width; +} + + +nscoord +nsFontPSXft::GetWidth(const PRUnichar* aString, PRUint32 aLength) +{ + FT_UInt glyph_index; + FT_Glyph glyph; + double origin_x = 0; + + // get the face/size from the FreeType cache + FT_Face face = getFTFace(); + NS_ASSERTION(face, "failed to get face/size"); + if (!face) + return 0; + + for (PRUint32 i=0; isize->metrics.x_ppem/2 + 2); + continue; + } + origin_x += glyph->advance.x; + } + + NS_ENSURE_TRUE(mFontMetrics, 0); + + nsDeviceContextPS* dc = mFontMetrics->GetDeviceContext(); + NS_ENSURE_TRUE(dc, 0); + + float dev2app; + dev2app = dc->DevUnitsToAppUnits(); + origin_x *= dev2app; + origin_x /= FT_REG_TO_16_16(1); + + return NSToCoordRound((nscoord)origin_x); +} + +nscoord +nsFontPSXft::DrawString(nsRenderingContextPS* aContext, + nscoord aX, nscoord aY, + const char* aString, PRUint32 aLength) +{ + NS_ENSURE_TRUE(aContext, 0); + nsPostScriptObj* psObj = aContext->GetPostScriptObj(); + NS_ENSURE_TRUE(psObj, 0); + nscoord width = 0; + + psObj->moveto(aX, aY); + + PRUnichar unichars[WIDEN_8_TO_16_BUF_SIZE]; + PRUint32 len; + + while ( aLength > 0 ) { + len = PR_MIN(aLength, WIDEN_8_TO_16_BUF_SIZE); + for (PRUint32 i=0; i < len; i++) { + unichars[i] = PRUnichar(PRUint8(aString[i])); + } + psObj->show(unichars, len, "", 1); + mPSFontGenerator->AddToSubset(unichars, len); + width += GetWidth(unichars, len); + aString += len; + aLength -= len; + } + return width; +} + +nscoord +nsFontPSXft::DrawString(nsRenderingContextPS* aContext, + nscoord aX, nscoord aY, + const PRUnichar* aString, PRUint32 aLength) +{ + NS_ENSURE_TRUE(aContext, 0); + nsPostScriptObj* psObj = aContext->GetPostScriptObj(); + NS_ENSURE_TRUE(psObj, 0); + + psObj->moveto(aX, aY); + psObj->show(aString, aLength, "", 1); + + mPSFontGenerator->AddToSubset(aString, aLength); + return GetWidth(aString, aLength); +} + +int +nsFontPSXft::ascent() +{ + FT_Face face = getFTFace(); + NS_ASSERTION(face, "failed to get face/size"); + NS_ENSURE_TRUE(face, 0); + return FT_DESIGN_UNITS_TO_PIXELS(face->ascender, face->size->metrics.y_scale); +} + +int +nsFontPSXft::descent() +{ + FT_Face face = getFTFace(); + NS_ASSERTION(face, "failed to get face/size"); + NS_ENSURE_TRUE(face, 0); + return FT_DESIGN_UNITS_TO_PIXELS(-face->descender, face->size->metrics.y_scale); +} + +int +nsFontPSXft::max_ascent() +{ + FT_Face face = getFTFace(); + NS_ASSERTION(face, "failed to get face/size"); + NS_ENSURE_TRUE(face, 0); + TT_OS2 *tt_os2 = (TT_OS2 *) FT_Get_Sfnt_Table(face, ft_sfnt_os2); + NS_ASSERTION(tt_os2, "unable to get OS2 table"); + if (tt_os2) + return FT_DESIGN_UNITS_TO_PIXELS(tt_os2->sTypoAscender, + face->size->metrics.y_scale); + else + return FT_DESIGN_UNITS_TO_PIXELS(face->bbox.yMax, + face->size->metrics.y_scale); +} + +int +nsFontPSXft::max_descent() +{ + FT_Face face = getFTFace(); + NS_ASSERTION(face, "failed to get face/size"); + NS_ENSURE_TRUE(face, 0); + TT_OS2 *tt_os2 = (TT_OS2 *) FT_Get_Sfnt_Table(face, ft_sfnt_os2); + NS_ASSERTION(tt_os2, "unable to get OS2 table"); + if (tt_os2) + return FT_DESIGN_UNITS_TO_PIXELS(-tt_os2->sTypoDescender, + face->size->metrics.y_scale); + else + return FT_DESIGN_UNITS_TO_PIXELS(-face->bbox.yMin, + face->size->metrics.y_scale); +} + +int +nsFontPSXft::max_width() +{ + FT_Face face = getFTFace(); + NS_ASSERTION(face, "failed to get face/size"); + NS_ENSURE_TRUE(face, 0); + return FT_DESIGN_UNITS_TO_PIXELS(face->max_advance_width, + face->size->metrics.x_scale); +} + +PRBool +nsFontPSXft::getXHeight(unsigned long &aVal) +{ + FT_Face face = getFTFace(); + NS_ASSERTION(face, "failed to get face/size"); + if (!face || !aVal) + return PR_FALSE; + aVal = FT_DESIGN_UNITS_TO_PIXELS(face->height, face->size->metrics.y_scale); + + return PR_TRUE; +} + +PRBool +nsFontPSXft::underlinePosition(long &aVal) +{ + FT_Face face = getFTFace(); + NS_ASSERTION(face, "failed to get face/size"); + if (!face) + return PR_FALSE; + aVal = FT_DESIGN_UNITS_TO_PIXELS(-face->underline_position, + face->size->metrics.y_scale); + return PR_TRUE; } -nscoord -nsFontPSAFM::GetWidth(const PRUnichar* aString, PRUint32 aLength) +PRBool +nsFontPSXft::underline_thickness(unsigned long &aVal) { - nscoord width = 0; - if (mAFMInfo) { - mAFMInfo->GetStringWidth(aString, width, aLength); - } - return width; + FT_Face face = getFTFace(); + NS_ASSERTION(face, "failed to get face/size"); + if (!face) + return PR_FALSE; + aVal = FT_DESIGN_UNITS_TO_PIXELS(face->underline_thickness, + face->size->metrics.x_scale); + return PR_TRUE; } -nscoord -nsFontPSAFM::DrawString(nsRenderingContextPS* aContext, - nscoord aX, nscoord aY, - const char* aString, PRUint32 aLength) +PRBool +nsFontPSXft::superscript_y(long &aVal) { - NS_ENSURE_TRUE(aContext, 0); - nsPostScriptObj* psObj = aContext->GetPostScriptObj(); - NS_ENSURE_TRUE(psObj, 0); + aVal = 0; + FT_Face face = getFTFace(); + NS_ASSERTION(face, "failed to get face/size"); + if (!face) + return PR_FALSE; - psObj->moveto(aX, aY); - psObj->show(aString, aLength, ""); - return GetWidth(aString, aLength); + TT_OS2 *tt_os2 = (TT_OS2 *) FT_Get_Sfnt_Table(face, ft_sfnt_os2); + NS_ASSERTION(tt_os2, "unable to get OS2 table"); + if (!tt_os2) + return PR_FALSE; + + aVal = FT_DESIGN_UNITS_TO_PIXELS(tt_os2->ySuperscriptYOffset, + face->size->metrics.y_scale); + return PR_TRUE; } -nscoord -nsFontPSAFM::DrawString(nsRenderingContextPS* aContext, - nscoord aX, nscoord aY, - const PRUnichar* aString, PRUint32 aLength) +PRBool +nsFontPSXft::subscript_y(long &aVal) { - NS_ENSURE_TRUE(aContext, 0); - nsPostScriptObj* psObj = aContext->GetPostScriptObj(); - NS_ENSURE_TRUE(psObj, 0); + aVal = 0; + FT_Face face = getFTFace(); + NS_ASSERTION(face, "failed to get face/size"); + if (!face) + return PR_FALSE; - psObj->moveto(aX, aY); - psObj->show(aString, aLength, "", 0); - return GetWidth(aString, aLength); + TT_OS2 *tt_os2 = (TT_OS2 *) FT_Get_Sfnt_Table(face, ft_sfnt_os2); + NS_ASSERTION(tt_os2, "unable to get OS2 table"); + if (!tt_os2) + return PR_FALSE; + + aVal = FT_DESIGN_UNITS_TO_PIXELS(tt_os2->ySubscriptYOffset, + face->size->metrics.y_scale); + + // some fonts have the sign wrong. it should be always positive. + aVal = (aVal < 0) ? -aVal : aVal; + return PR_TRUE; } nsresult -nsFontPSAFM::RealizeFont(nsFontMetricsPS* aFontMetrics, float dev2app) +nsFontPSXft::RealizeFont(nsFontMetricsPS* aFontMetrics, float dev2app) { - NS_ENSURE_ARG_POINTER(aFontMetrics); - - float fontSize; - float offset; + + nscoord leading, emHeight, emAscent, emDescent; + nscoord maxHeight, maxAscent, maxDescent, maxAdvance; + nscoord xHeight, spaceWidth, aveCharWidth; + nscoord underlineOffset, underlineSize, superscriptOffset, subscriptOffset; + nscoord strikeoutOffset, strikeoutSize; - nscoord onePixel = NSToCoordRound(1 * dev2app); + int lineSpacing = ascent() + descent(); + if (lineSpacing > mPixelSize) { + leading = nscoord((lineSpacing - mPixelSize) * dev2app); + } + else { + leading = 0; + } + emHeight = PR_MAX(1, nscoord(mPixelSize * dev2app)); + emAscent = nscoord(ascent() * mPixelSize * dev2app / lineSpacing); + emDescent = emHeight - emAscent; - // convert the font size which is in twips to points - fontSize = mFont->size / TWIPS_PER_POINT_FLOAT; + maxHeight = nscoord((max_ascent() + max_descent()) * dev2app); + maxAscent = nscoord(max_ascent() * dev2app) ; + maxDescent = nscoord(max_descent() * dev2app); + maxAdvance = nscoord(max_width() * dev2app); - offset = NSFloatPointsToTwips(fontSize * mAFMInfo->mPSFontInfo->mXHeight) / 1000.0f; - nscoord xHeight = NSToCoordRound(offset); - aFontMetrics->SetXHeight(xHeight); - aFontMetrics->SetSuperscriptOffset(xHeight); - aFontMetrics->SetSubscriptOffset(xHeight); - aFontMetrics->SetStrikeout((nscoord)(xHeight / 2), onePixel); + // 56% of ascent, best guess for non-true type + xHeight = NSToCoordRound((float)ascent()* dev2app * 0.56f); - offset = NSFloatPointsToTwips(fontSize * mAFMInfo->mPSFontInfo->mUnderlinePosition) / 1000.0f; - aFontMetrics->SetUnderline(NSToCoordRound(offset), onePixel); + PRUnichar space = (PRUnichar)' '; + spaceWidth = NSToCoordRound(GetWidth(&space, 1)); + PRUnichar averageX = (PRUnichar)'x'; + aveCharWidth = NSToCoordRound(GetWidth(&averageX, 1)); + + unsigned long pr = 0; + if (getXHeight(pr)) { + xHeight = (nscoord(pr * dev2app)); + } - nscoord size = NSToCoordRound(fontSize * dev2app); - aFontMetrics->SetHeight(size); - aFontMetrics->SetEmHeight(size); - aFontMetrics->SetMaxAdvance(size); - aFontMetrics->SetMaxHeight(size); + float height; + long val; + + height = ascent() + descent(); + underlineOffset = -NSToIntRound( + PR_MAX (1, floor (0.1 * height + 0.5)) * dev2app); - offset = NSFloatPointsToTwips(fontSize * mAFMInfo->mPSFontInfo->mAscender) / 1000.0f; - nscoord ascent = NSToCoordRound(offset); - aFontMetrics->SetAscent(ascent); - aFontMetrics->SetEmAscent(ascent); - aFontMetrics->SetMaxAscent(ascent); + if (underline_thickness(pr)) { + /* this will only be provided from adobe .afm fonts */ + underlineSize = nscoord(PR_MAX(dev2app, NSToIntRound(pr * dev2app))); + } + else { + height = ascent() + descent(); + underlineSize = NSToIntRound( + PR_MAX(1, floor (0.05 * height + 0.5)) * dev2app); + } - offset = NSFloatPointsToTwips(fontSize * mAFMInfo->mPSFontInfo->mDescender) / 1000.0f; - nscoord descent = -(NSToCoordRound(offset)); - aFontMetrics->SetDescent(descent); - aFontMetrics->SetEmDescent(descent); - aFontMetrics->SetMaxDescent(descent); + if (superscript_y(val)) { + superscriptOffset = nscoord(PR_MAX(dev2app, NSToIntRound(val * dev2app))); + } + else { + superscriptOffset = xHeight; + } - aFontMetrics->SetLeading(0); + if (subscript_y(val)) { + subscriptOffset = nscoord(PR_MAX(dev2app, NSToIntRound(val * dev2app))); + } + else { + subscriptOffset = xHeight; + } - nscoord spaceWidth = GetWidth(" ", 1); + /* need better way to calculate this */ + strikeoutOffset = NSToCoordRound(xHeight / 2.0); + strikeoutSize = underlineSize; + + // TODO: leading never used, does it equal to "Height"? + aFontMetrics->SetHeight(emHeight); + aFontMetrics->SetEmHeight(emHeight); + aFontMetrics->SetEmAscent(emAscent); + aFontMetrics->SetEmDescent(emDescent); + aFontMetrics->SetMaxHeight(maxHeight); + aFontMetrics->SetMaxAscent(maxAscent); + aFontMetrics->SetMaxDescent(maxDescent); + aFontMetrics->SetMaxAdvance(maxAdvance); + aFontMetrics->SetXHeight(xHeight); aFontMetrics->SetSpaceWidth(spaceWidth); - - nscoord aveCharWidth = GetWidth("x", 1); aFontMetrics->SetAveCharWidth(aveCharWidth); + aFontMetrics->SetUnderline(underlineOffset, underlineSize); + aFontMetrics->SetSuperscriptOffset(superscriptOffset); + aFontMetrics->SetSubscriptOffset(subscriptOffset); + aFontMetrics->SetStrikeout(strikeoutOffset, strikeoutSize); return NS_OK; } nsresult -nsFontPSAFM::SetupFont(nsRenderingContextPS* aContext) +nsFontPSXft::SetupFont(nsRenderingContextPS* aContext) { - NS_ENSURE_TRUE(aContext && mFontMetrics, 0); + NS_ENSURE_TRUE(aContext, NS_ERROR_FAILURE); nsPostScriptObj* psObj = aContext->GetPostScriptObj(); - NS_ENSURE_TRUE(psObj, 0); + NS_ENSURE_TRUE(psObj, NS_ERROR_FAILURE); nscoord fontHeight = 0; mFontMetrics->GetHeight(fontHeight); - psObj->setscriptfont(mFontIndex, mFamilyName, - fontHeight, mFont->style, mFont->variant, - mFont->weight, mFont->decorations); + nsCString fontName; + int wmode = 0; + FT_Face face = getFTFace(); + NS_ENSURE_TRUE(face, NS_ERROR_NULL_POINTER); + char *cidFontName = FT2ToType8CidFontName(face, wmode); + NS_ENSURE_TRUE(cidFontName, NS_ERROR_FAILURE); + fontName.Assign(cidFontName); + psObj->setfont(fontName, fontHeight); + PR_Free(cidFontName); + return NS_OK; } #ifdef MOZ_MATHML nsresult -nsFontPSAFM::GetBoundingMetrics(const char* aString, - PRUint32 aLength, - nsBoundingMetrics& aBoundingMetrics) +nsFontPSXft::GetBoundingMetrics(const char* aString, + PRUint32 aLength, + nsBoundingMetrics& aBoundingMetrics) { return NS_ERROR_NOT_IMPLEMENTED; } nsresult -nsFontPSAFM::GetBoundingMetrics(const PRUnichar* aString, - PRUint32 aLength, - nsBoundingMetrics& aBoundingMetrics) +nsFontPSXft::GetBoundingMetrics(const PRUnichar* aString, + PRUint32 aLength, + nsBoundingMetrics& aBoundingMetrics) { return NS_ERROR_NOT_IMPLEMENTED; } -#endif - -#ifdef MOZ_ENABLE_FREETYPE2 +#endif //MOZ_MATHML -#define WIDEN_8_TO_16_BUF_SIZE 1024 +#else PRBool nsFontPSFreeType::CSSFontEnumCallback(const nsString& aFamily, PRBool aGeneric, void* aFpi) { fontPSInfo* fpi = (fontPSInfo*)aFpi; nsCAutoString familyname; @@ -709,15 +1505,15 @@ nsFontPSFreeType::CSSFontEnumCallback(co return PR_TRUE; // keep trying } nsXPIDLCString value; nsresult rv; nsCOMPtr pref(do_GetService(NS_PREF_CONTRACTID, &rv)); NS_ENSURE_SUCCESS(rv, PR_TRUE); // keep trying nsCAutoString name("font.name."); - name.AppendWithConversion(aFamily.get()); + LossyAppendUTF16toASCII(aFamily, name); name.Append(char('.')); name.Append(fpi->lang); pref->CopyCharPref(name.get(), getter_Copies(value)); if (!value.get()) return PR_TRUE; // keep trying // strip down to just the family name PRInt32 startFamily = value.FindChar('-') + 1; @@ -730,15 +1526,15 @@ nsFontPSFreeType::CSSFontEnumCallback(co else // FFRE familyname.Append(Substring(value, startFamily, endFamily - startFamily)); } PR_LOG(gFontMetricsPSM, PR_LOG_DEBUG, ("generic font \"%s\" -> \"%s\"\n", name.get(), familyname.get())); } else - familyname.AppendWithConversion(aFamily); + LossyAppendUTF16toASCII(aFamily, familyname); AddFontEntries(familyname, fpi->lang, fpi->weight, nsIFontCatalogService::kFCWidthAny, fpi->slant, nsIFontCatalogService::kFCSpacingAny, fpi); return PR_TRUE; } @@ -1556,14 +2352,15 @@ nsFontPSFreeType::GetBoundingMetrics(con nsBoundingMetrics& aBoundingMetrics) { return NS_ERROR_NOT_IMPLEMENTED; } #endif //MOZ_MATHML #endif //MOZ_ENABLE_FREETYPE2 +#endif //MOZ_ENABLE_XFT // Implementation of nsPSFontGenerator nsPSFontGenerator::nsPSFontGenerator() { } nsPSFontGenerator::~nsPSFontGenerator() @@ -1589,15 +2386,77 @@ void nsPSFontGenerator::AddToSubset(cons for (PRUint32 i=0; i < aLength; i++) { unichar = (PRUnichar)((unsigned char)aString[i]); if (mSubset.FindChar(unichar) == -1 ) mSubset.Append(unichar); } } +#ifdef MOZ_ENABLE_XFT +nsXftType8Generator::nsXftType8Generator() +{ +} + +nsresult +nsXftType8Generator::Init(nsXftEntry* aEntry) +{ + NS_ENSURE_TRUE(aEntry, NS_ERROR_FAILURE); + mEntry = aEntry; + + FT_Error error = FT_Init_FreeType(&mFreeTypeLibrary); + NS_ASSERTION(!error, "failed to initialize FreeType library"); + if (error) { + mFreeTypeLibrary = nsnull; + return NS_ERROR_FAILURE; + } + error = FTC_Manager_New(mFreeTypeLibrary, 0, 0, 0, nsXftFaceRequester, + NULL, &mFTCacheManager); + NS_ASSERTION(!error, "failed to create FreeType Cache manager"); + if (error) + return NS_ERROR_FAILURE; + + return NS_OK; +} + +nsXftType8Generator::~nsXftType8Generator() +{ + FTC_Manager_Done(mFTCacheManager); + + if (FT_Done_FreeType(mFreeTypeLibrary)) + return; + + mEntry = nsnull; +} + +void nsXftType8Generator::GeneratePSFont(FILE* aFile) +{ + FT_Error error; + FT_Face face = mEntry->mFace; + + if (face == nsnull) { + mImageDesc.font.face_id = (void*)mEntry; + mImageDesc.font.pix_width = 16; + mImageDesc.font.pix_height = 16; + mImageDesc.image_type = 0; + error = FTC_Manager_Lookup_Size(mFTCacheManager, &mImageDesc.font, + &face, nsnull); + if (error) + return; + } + + if (face == nsnull) + return; + + int wmode = 0; + if (!mSubset.IsEmpty()) + FT2SubsetToType8(face, mSubset.get(), mSubset.Length(), wmode, aFile); +} + +#else #ifdef MOZ_ENABLE_FREETYPE2 + nsFT2Type8Generator::nsFT2Type8Generator() { } nsresult nsFT2Type8Generator::Init(nsITrueTypeFontCatalogEntry* aEntry) { @@ -1635,9 +2494,10 @@ void nsFT2Type8Generator::GeneratePSFont if (NS_FAILED(rv)) return; int wmode = 0; if (!mSubset.IsEmpty()) FT2SubsetToType8(face, mSubset.get(), mSubset.Length(), wmode, aFile); } -#endif //MOZ_ENABLE_FREETYPE2 +#endif //MOZ_ENABLE_FREETYPE2 +#endif //MOZ_ENABLE_XFT Index: gfx/src/ps/nsFontMetricsPS.h =================================================================== RCS file: /cvsroot/mozilla/gfx/src/ps/nsFontMetricsPS.h,v --- gfx/src/ps/nsFontMetricsPS.h 22 Apr 2003 16:25:09 -0000 1.24 +++ gfx/src/ps/nsFontMetricsPS.h 17 Oct 2004 11:10:19 -0000 @@ -47,15 +47,28 @@ #include "nsIAtom.h" #include "nsUnitConversion.h" #include "nsIDeviceContext.h" #include "nsCOMPtr.h" #include "nsCRT.h" #include "nsCompressedCharMap.h" #include "nsPostScriptObj.h" +#ifdef MOZ_ENABLE_XFT +#include +#include FT_FREETYPE_H +#include FT_GLYPH_H +#include FT_CACHE_H +#include FT_CACHE_IMAGE_H +#include FT_OUTLINE_H +#include FT_OUTLINE_H +#include FT_TRUETYPE_TABLES_H +#else +#ifdef MOZ_ENABLE_FREETYPE2 #include "nsIFontCatalogService.h" +#endif +#endif #include "nsVoidArray.h" #include "nsHashtable.h" class nsPSFontGenerator; class nsDeviceContextPS; class nsRenderingContextPS; class nsFontPS; @@ -247,24 +260,121 @@ public: #endif nsAFMObject* mAFMInfo; PRInt16 mFontIndex; nsString mFamilyName; }; + +#ifdef MOZ_ENABLE_XFT + +#include + +class nsXftEntry +{ +public: + nsXftEntry(FcPattern *aFontPattern); + ~nsXftEntry() {}; + + FT_Face mFace; + int mFaceIndex; + nsCString mFontFileName; + nsCString mFamilyName; + nsCString mStyleName; + +protected: + nsXftEntry() {}; +}; + +struct fontps { + nsXftEntry *entry; + nsFontPS *fontps; + FcCharSet *charset; +}; + +struct fontPSInfo { + nsVoidArray *fontps; + const nsFont* nsfont; + nsCAutoString lang; + nsHashtable *alreadyLoaded; + nsCStringArray mFontList; + nsAutoVoidArray mFontIsGeneric; + nsCString *mGenericFont; +}; + +class nsFontPSXft : public nsFontPS +{ +public: + static nsFontPS* FindFont(PRUnichar aChar, const nsFont& aFont, + nsFontMetricsPS* aFontMetrics); + nsresult Init(nsXftEntry* aEntry, + nsPSFontGenerator* aPSFontGen); + static PRBool CSSFontEnumCallback(const nsString& aFamily, PRBool aGeneric, + void* aFpi); + + nsFontPSXft(const nsFont& aFont, nsFontMetricsPS* aFontMetrics); + virtual ~nsFontPSXft(); + NS_DECL_AND_IMPL_ZEROING_OPERATOR_NEW + + nscoord GetWidth(const char* aString, PRUint32 aLength); + nscoord GetWidth(const PRUnichar* aString, PRUint32 aLength); + nscoord DrawString(nsRenderingContextPS* aContext, + nscoord aX, nscoord aY, + const char* aString, PRUint32 aLength); + nscoord DrawString(nsRenderingContextPS* aContext, + nscoord aX, nscoord aY, + const PRUnichar* aString, PRUint32 aLength); + nsresult RealizeFont(nsFontMetricsPS* aFontMetrics, float dev2app); + nsresult SetupFont(nsRenderingContextPS* aContext); + +#ifdef MOZ_MATHML + nsresult + GetBoundingMetrics(const char* aString, + PRUint32 aLength, + nsBoundingMetrics& aBoundingMetrics); + nsresult + GetBoundingMetrics(const PRUnichar* aString, + PRUint32 aLength, + nsBoundingMetrics& aBoundingMetrics); +#endif + + nsXftEntry *mEntry; + FT_Face getFTFace(); + +protected: + PRUint16 mPixelSize; + FTC_Image_Desc mImageDesc; + FT_Library mFreeTypeLibrary; + FTC_Manager mFTCacheManager; + FTC_Image_Cache mImageCache; + + int ascent(); + int descent(); + PRBool getXHeight(unsigned long &aVal); + int max_ascent(); + int max_descent(); + int max_width(); + PRBool superscript_y(long &aVal); + PRBool subscript_y(long &aVal); + PRBool underlinePosition(long &aVal); + PRBool underline_thickness(unsigned long &aVal); + nsPSFontGenerator* mPSFontGenerator; +}; + +#else + +#ifdef MOZ_ENABLE_FREETYPE2 +#include "nsIFreeType2.h" + typedef struct { nsITrueTypeFontCatalogEntry *entry; nsFontPS *fontps; unsigned short *ccmap; } fontps; -#ifdef MOZ_ENABLE_FREETYPE2 - -#include "nsIFreeType2.h" - typedef struct { nsVoidArray *fontps; const nsFont* nsfont; nsCAutoString lang; nsHashtable *alreadyLoaded; PRUint16 slant; PRUint16 weight; @@ -334,38 +444,61 @@ protected: PRBool superscript_y(long &aVal); PRBool subscript_y(long &aVal); PRBool underlinePosition(long &aVal); PRBool underline_thickness(unsigned long &aVal); nsPSFontGenerator* mPSFontGenerator; }; -#endif +#else // !FREETYPE2 && !XFT +typedef struct { + nsFontPS *fontps; +} fontps; +#endif // MOZ_ENABLE_FREETYPE2 +#endif // MOZ_ENABLE_XFT class nsPSFontGenerator { public: nsPSFontGenerator(); virtual ~nsPSFontGenerator(); virtual void GeneratePSFont(FILE* aFile); void AddToSubset(const PRUnichar* aString, PRUint32 aLength); void AddToSubset(const char* aString, PRUint32 aLength); protected: nsString mSubset; }; + +#ifdef MOZ_ENABLE_XFT + +class nsXftType8Generator : public nsPSFontGenerator { +public: + nsXftType8Generator(); + ~nsXftType8Generator(); + nsresult Init(nsXftEntry* aFce); + void GeneratePSFont(FILE* aFile); + +protected: + nsXftEntry *mEntry; + FTC_Image_Desc mImageDesc; + FT_Library mFreeTypeLibrary; + FTC_Manager mFTCacheManager; +}; +#else #ifdef MOZ_ENABLE_FREETYPE2 class nsFT2Type8Generator : public nsPSFontGenerator { public: nsFT2Type8Generator(); ~nsFT2Type8Generator(); nsresult Init(nsITrueTypeFontCatalogEntry* aFce); void GeneratePSFont(FILE* aFile); protected: nsCOMPtr mEntry; nsCOMPtr mFt2; FTC_Image_Desc mImageDesc; }; -#endif +#endif // MOZ_ENABLE_FREETYPE2 +#endif // MOZ_ENABLE_XFT #endif Index: gfx/src/ps/nsType1.cpp =================================================================== RCS file: /cvsroot/mozilla/gfx/src/ps/nsType1.cpp,v --- gfx/src/ps/nsType1.cpp 11 Dec 2002 06:24:47 -0000 1.1 +++ gfx/src/ps/nsType1.cpp 17 Oct 2004 11:10:19 -0000 @@ -67,15 +67,17 @@ #include "nsType1.h" static const PRUint16 type1_encryption_c1 = TYPE1_ENCRYPTION_C1; static const PRUint16 type1_encryption_c2 = TYPE1_ENCRYPTION_C2; typedef struct { +#ifndef MOZ_ENABLE_XFT nsIFreeType2 *ft2; +#endif FT_Face face; int elm_cnt; int len; double cur_x; double cur_y; unsigned char *buf; int wmode; @@ -177,25 +179,32 @@ sideWidthAndBearing(FT_Vector *aEndPt, F { int aw = 0; int ah = 0; FT_UShort upm = aFti->face->units_per_EM; FT_GlyphSlot slot; FT_Glyph glyph; FT_BBox bbox; - nsresult rv; slot = aFti->face->glyph; - rv = aFti->ft2->GetGlyph(slot, &glyph); +#ifdef MOZ_ENABLE_XFT + FT_Error error = FT_Get_Glyph(slot, &glyph); + if (error) { + NS_ERROR("sideWidthAndBearing failed to get glyph"); + return PR_FALSE; + } + FT_Glyph_Get_CBox(glyph, ft_glyph_bbox_unscaled, &bbox); +#else + nsresult rv = aFti->ft2->GetGlyph(slot, &glyph); if (NS_FAILED(rv)) { NS_ERROR("sideWidthAndBearing failed to get glyph"); return PR_FALSE; } aFti->ft2->GlyphGetCBox(glyph, ft_glyph_bbox_unscaled, &bbox); - +#endif if (aFti->wmode == 0) aw = toCS(upm, slot->metrics.horiAdvance); else aw = -toCS(upm, slot->metrics.vertAdvance); if (aEndPt->y == 0) { @@ -367,52 +376,73 @@ static FT_Outline_Funcs ft_outline_funcs conicto, cubicto, 0, 0 }; FT_Error +#ifdef MOZ_ENABLE_XFT +FT2GlyphToType1CharString(FT_Face aFace, PRUint32 aGlyphID, + int aWmode, int aLenIV, unsigned char *aBuf) +#else FT2GlyphToType1CharString(nsIFreeType2 *aFt2, FT_Face aFace, PRUint32 aGlyphID, int aWmode, int aLenIV, unsigned char *aBuf) +#endif { int j; FT_Int32 flags = FT_LOAD_NO_BITMAP | FT_LOAD_NO_SCALE | FT_LOAD_NO_HINTING; FT_GlyphSlot slot; unsigned char *start = aBuf; FT2PT1_info fti; - nsresult rv; - rv = aFt2->LoadGlyph(aFace, aGlyphID, flags); +#ifdef MOZ_ENABLE_XFT + FT_Error error = FT_Load_Glyph(aFace, aGlyphID, flags); + if (error) { + NS_ERROR("failed to load aGlyphID"); + return error; + } +#else + nsresult rv = aFt2->LoadGlyph(aFace, aGlyphID, flags); if (NS_FAILED(rv)) { NS_ERROR("failed to load aGlyphID"); return 1; } +#endif slot = aFace->glyph; if (slot->format != ft_glyph_format_outline) { NS_ERROR("aGlyphID is not an outline glyph"); return 1; } +#ifndef MOZ_ENABLE_XFT fti.ft2 = aFt2; +#endif fti.face = aFace; fti.buf = aBuf; fti.elm_cnt = 0; fti.len = 0; fti.wmode = aWmode; /* add space for "random" bytes */ for (j=0; j< aLenIV; j++) { fti.len += ecsi(&fti.buf, 0); } +#ifdef MOZ_ENABLE_XFT + if (FT_Outline_Decompose(&slot->outline, &ft_outline_funcs, &fti)) { + NS_ERROR("error decomposing aGlyphID"); + return 1; + } +#else rv = aFt2->OutlineDecompose(&slot->outline, &ft_outline_funcs, &fti); if (NS_FAILED(rv)) { NS_ERROR("error decomposing aGlyphID"); return 1; } +#endif if (fti.elm_cnt) { fti.len += csc(&fti.buf, T1_CLOSEPATH); fti.len += csc(&fti.buf, T1_ENDCHAR); } else { FT_Vector end_pt; Index: gfx/src/ps/nsType1.h =================================================================== RCS file: /cvsroot/mozilla/gfx/src/ps/nsType1.h,v --- gfx/src/ps/nsType1.h 16 Jan 2003 05:04:23 -0000 1.2 +++ gfx/src/ps/nsType1.h 17 Oct 2004 11:10:19 -0000 @@ -50,15 +50,23 @@ // #ifndef TYPE1_H #define TYPE1_H #include #include "nspr.h" +#ifdef MOZ_ENABLE_XFT +#include "nsISupports.h" +#include +#include FT_FREETYPE_H +#include FT_GLYPH_H +#include FT_OUTLINE_H +#else #include "nsIFreeType2.h" +#endif /* to/from Character Space */ inline int toCS(double upm, double x) { return (int)((x*1000.0)/upm); } @@ -91,12 +99,16 @@ fromCS(double upm, double x) /* the 2 byte (escaped) Postscript Type 1 commands */ #define T1_ESC_SBW 7 /* 0x07 */ #define TYPE1_ENCRYPTION_KEY 4330 #define TYPE1_ENCRYPTION_C1 52845 #define TYPE1_ENCRYPTION_C2 22719 +#ifdef MOZ_ENABLE_XFT +FT_Error FT2GlyphToType1CharString(FT_Face aFace, +#else /* MOZ_ENABLE_FREETYPE2 */ FT_Error FT2GlyphToType1CharString(nsIFreeType2 *aFt2, FT_Face aFace, +#endif PRUint32 aGlyphID, int aWmode, int aLenIV, unsigned char *aBuf); #endif /* TYPE1_H */ Index: gfx/src/ps/nsType8.cpp =================================================================== RCS file: /cvsroot/mozilla/gfx/src/ps/nsType8.cpp,v --- gfx/src/ps/nsType8.cpp 17 Jan 2003 23:28:42 -0000 1.5 +++ gfx/src/ps/nsType8.cpp 17 Oct 2004 11:10:22 -0000 @@ -49,29 +49,35 @@ #include #include #include "nsCidMap.h" #include "nsType1.h" #include "nsType8.h" +#ifndef MOZ_ENABLE_XFT #include "nsIFreeType2.h" +#endif #include "nsIServiceManager.h" #include "nsISignatureVerifier.h" #include "plbase64.h" #include "nsCRT.h" #define DEFAULT_CMAP_SIZE 10240 #define HEXASCII_LINE_LEN 64 static void hex_out(unsigned char *buf, PRUint32 n, FILE *f, PRUint32 *pos); static void flatten_name(char *aToName); +#ifdef MOZ_ENABLE_XFT +static int FT2SubsetToCidKeyedType1(FT_Face aFace, +#else static int FT2SubsetToCidKeyedType1(nsIFreeType2 *aFt2, FT_Face aFace, +#endif const PRUnichar *aCharIDs, int aLen, const char *aFontName, const char *aRegistry, const char *aEncoding, int aSupplement, int aWmode, int aLenIV, FILE *aFile); void @@ -315,20 +321,22 @@ FT2SubsetToType8(FT_Face aFace, const PR char *encoding = NULL; int supplement, lenIV; PRUint32 CIDs_buf[5000]; PRUint32 *CIDs = CIDs_buf; int cmap_type = 0; PRBool status = PR_FALSE; +#ifndef MOZ_ENABLE_XFT nsresult rv; nsCOMPtr ft2 = do_GetService(NS_FREETYPE2_CONTRACTID, &rv); if (NS_FAILED(rv)) { NS_ERROR("Failed to get nsIFreeType2 service"); goto done; } +#endif if ((aNumChars+1) > sizeof(CIDs_buf)/sizeof(CIDs_buf[0])) CIDs = (PRUint32 *)PR_Malloc((aNumChars+1)*sizeof(CIDs_buf[0])); if (!CIDs) { NS_ERROR("Failed to alloc space for CIDs"); goto done; } @@ -364,15 +372,19 @@ FT2SubsetToType8(FT_Face aFace, const PR WriteCmapHeader(cmapname, registry, encoding, supplement, cmap_type, aWmode, aFile); WriteCodeSpaceRangeMapUCS2(aFile); WriteCidCharMap(aCharIDs, CIDs, aNumChars, aFile); WriteCmapFooter(aFile); /* output the Type 8 CID font */ +#ifdef MOZ_ENABLE_XFT + FT2SubsetToCidKeyedType1(aFace, aCharIDs, aNumChars, fontname, +#else FT2SubsetToCidKeyedType1(ft2, aFace, aCharIDs, aNumChars, fontname, +#endif registry, encoding, supplement, aWmode, lenIV, aFile); fprintf(aFile, "\n"); /* compose the cmap and font */ fprintf(aFile, "/%s\n", cidfontname); fprintf(aFile, " /%s /CMap findresource\n", cmapname); @@ -388,15 +400,19 @@ done: PR_FREEIF(cidfontname); if (CIDs != CIDs_buf) PR_Free(CIDs); return status; } static PRBool +#ifdef MOZ_ENABLE_XFT +FT2SubsetToCidKeyedType1(FT_Face aFace, +#else FT2SubsetToCidKeyedType1(nsIFreeType2 *aFt2, FT_Face aFace, +#endif const PRUnichar *aCharIDs, int aLen, const char *aFontName, const char *aRegistry, const char *aEncoding, int aSupplement, int aWmode, int aLenIV, FILE *aFile) { int i, charstrings_len, data_offset; unsigned int charstring_len; @@ -441,24 +457,34 @@ FT2SubsetToCidKeyedType1(nsIFreeType2 *a toCS(upm, aFace->bbox.yMin), toCS(upm, aFace->bbox.xMax), toCS(upm, aFace->bbox.yMax)); fprintf(aFile, "\n"); /* measure the notdef glyph length */ +#ifdef MOZ_ENABLE_XFT + cmapinfo[0] = FT2GlyphToType1CharString(aFace, 0, aWmode, aLenIV, NULL); +#else cmapinfo[0] = FT2GlyphToType1CharString(aFt2, aFace, 0, aWmode, aLenIV, NULL); +#endif num_charstrings = 1; charstrings_len = cmapinfo[0]; /* get charstring lengths */ max_charstring = cmapinfo[0]; for (i=0; iGetCharIndex(aFace, aCharIDs[i], &glyphID); cmapinfo[i+1] = FT2GlyphToType1CharString(aFt2, aFace, glyphID, aWmode, aLenIV, NULL); +#endif charstrings_len += cmapinfo[i+1]; if (cmapinfo[i+1]) num_charstrings++; if (cmapinfo[i+1] > max_charstring) max_charstring = cmapinfo[i+1]; } cmapinfo[i+1] = 0; @@ -550,23 +576,34 @@ FT2SubsetToCidKeyedType1(nsIFreeType2 *a data_offset += cmapinfo[i]; } // // output the charStrings // // output the notdef glyph +#ifdef MOZ_ENABLE_XFT + charstring_len = FT2GlyphToType1CharString(aFace, 0, aWmode, aLenIV, + charstring); +#else charstring_len = FT2GlyphToType1CharString(aFt2, aFace, 0, aWmode, aLenIV, charstring); +#endif hex_out(charstring, charstring_len, aFile, &line_pos); /* output the charstrings for the glyphs */ for (i=0; iGetCharIndex(aFace, aCharIDs[i], &glyphID); charstring_len = FT2GlyphToType1CharString(aFt2, aFace, glyphID, aWmode, aLenIV, charstring); +#endif NS_ASSERTION(charstring_len==cmapinfo[i+1], "glyph data changed"); hex_out(charstring, charstring_len, aFile, &line_pos); } // add one byte padding so the interperter can always do 2 byte reads charstring[0] = 0; hex_out(charstring, 1, aFile, &line_pos); Index: gfx/src/ps/nsType8.h =================================================================== RCS file: /cvsroot/mozilla/gfx/src/ps/nsType8.h,v --- gfx/src/ps/nsType8.h 16 Jan 2003 05:04:24 -0000 1.2 +++ gfx/src/ps/nsType8.h 17 Oct 2004 11:10:22 -0000 @@ -39,15 +39,32 @@ * ***** END LICENSE BLOCK ***** */ #ifndef TYPE8_H #define TYPE8_H #include #include "nspr.h" +#ifdef MOZ_ENABLE_XFT +#include +#include FT_FREETYPE_H +#include FT_GLYPH_H +#include FT_CACHE_H +#include FT_CACHE_IMAGE_H +#include FT_OUTLINE_H +// macros to handle FreeType2 26.6 numbers (26 bit number with 6 bit fraction) +#define FT_REG_TO_16_16(x) ((x)<<16) +#ifndef FT_MulFix +#define FT_MulFix(v, s) (((v)*(s))>>16) +#endif +#define FT_ROUND(x) (((x) + 32) & ~63) // 63 = 2^6 - 1 +#define FT_TRUNC(x) ((x) >> 6) +#define FT_DESIGN_UNITS_TO_PIXELS(v, s) FT_TRUNC(FT_ROUND(FT_MulFix((v) , (s)))) +#else /* MOZ_ENABLE_FREETYPE2 */ #include "nsIFreeType2.h" +#endif /* MOZ_ENABLE_XFT */ void AddCIDCheckCode(FILE *aFile); PRBool FT2SubsetToType8(FT_Face aFace, const PRUnichar *aCharIDs, PRUint32 aNumChars, int aWmode, FILE *aFile); char* FT2ToType8CidFontName(FT_Face aFace, int aWmode); Index: gfx/src/x11shared/nsFontDebug.h =================================================================== RCS file: /cvsroot/mozilla/gfx/src/x11shared/nsFontDebug.h,v --- gfx/src/x11shared/nsFontDebug.h 17 Sep 2002 06:15:04 -0000 1.1 +++ gfx/src/x11shared/nsFontDebug.h 17 Oct 2004 11:10:22 -0000 @@ -93,11 +93,13 @@ fflush(stdout); \ } \ PR_END_MACRO #define FREETYPE_FONT_PRINTF(x) \ DEBUG_PRINTF_MACRO(x, NS_FONT_DEBUG_FREETYPE_FONT) +#ifdef MOZ_ENABLE_FREETYPE2 extern PRUint32 gFontDebug; +#endif #endif Index: gfx/src/xlib/nsFontMetricsXlib.cpp =================================================================== RCS file: /cvsroot/mozilla/gfx/src/xlib/nsFontMetricsXlib.cpp,v --- gfx/src/xlib/nsFontMetricsXlib.cpp 9 Mar 2004 14:14:55 -0000 1.165 +++ gfx/src/xlib/nsFontMetricsXlib.cpp 17 Oct 2004 11:10:49 -0000 @@ -60,18 +60,18 @@ #include "nsCOMPtr.h" #include "nsPrintfCString.h" #include "nspr.h" #include "nsHashtable.h" #include "nsReadableUtils.h" #include "nsAString.h" #include "nsXPIDLString.h" -#ifdef USE_FREETYPE +#ifdef MOZ_ENABLE_FREETYPE2 #include "nsFT2FontCatalog.h" #include "nsFreeType.h" -#endif /* USE_FREETYPE */ +#endif /* MOZ_ENABLE_FREETYPE2 */ #ifdef USE_X11SHARED_CODE #include "nsXFontNormal.h" #endif /* USE_X11SHARED_CODE */ #ifdef USE_AASB #include "nsX11AlphaBlend.h" #include "nsXFontAAScaledBitmap.h" #endif /* USE_AASB */ @@ -109,17 +109,17 @@ static PRLogModuleInfo *FontMetricsXlibL #define FONT_MAX_FONT_SCALE 2 #undef NOISY_FONTS #undef REALLY_NOISY_FONTS /* Local prototypes */ static PRBool FreeNode(nsHashKey* aKey, void* aData, void* aClosure); -#ifdef USE_FREETYPE +#ifdef MOZ_ENABLE_FREETYPE2 static void CharSetNameToCodeRangeBits(const char*, PRUint32*, PRUint32*); -#endif /* USE_FREETYPE */ +#endif /* MOZ_ENABLE_FREETYPE2 */ static const nsFontCharSetMapXlib *GetCharSetMap(nsFontMetricsXlibContext *aFmctx, const char *aCharSetName); // the font catalog is so expensive to generate // always tell the user what is happening static PRUint32 gFontDebug = 0 | NS_FONT_DEBUG_FONT_SCAN; struct nsFontCharSetMapXlib; @@ -211,19 +211,19 @@ public: double mBitmapUndersize; #ifdef USE_AASB PRInt32 mAntiAliasMinimum; #endif /* USE_AASB */ PRInt32 mEmbeddedBitmapMaximumHeight; -#ifdef USE_FREETYPE +#ifdef MOZ_ENABLE_FREETYPE2 PRBool mEnableFreeType2; PRBool mFreeType2Autohinted; PRBool mFreeType2Unhinted; -#endif /* USE_FREETYPE */ +#endif /* MOZ_ENABLE_FREETYPE2 */ #ifdef USE_AASB PRUint8 mAATTDarkTextMinValue; double mAATTDarkTextGain; #endif /* USE_AASB */ #ifdef ENABLE_X_FONT_BANNING regex_t *mFontRejectRegEx, @@ -232,16 +232,18 @@ public: }; struct nsFontCharSetInfoXlib { const char* mCharSet; nsFontCharSetConverterXlib Convert; PRUint8 mSpecialUnderline; +#ifdef MOZ_ENABLE_FREETYPE2 PRInt32 mCodeRange1Bits; PRInt32 mCodeRange2Bits; +#endif PRUint16* mCCMap; nsIUnicodeEncoder* mConverter; nsIAtom* mLangGroup; PRBool mInitedSizeInfo; PRInt32 mOutlineScaleMin; PRInt32 mBitmapScaleMin; double mBitmapOversize; @@ -281,14 +283,15 @@ static int DoubleByteConvert(nsFontCharS const PRUnichar* aSrcBuf, PRInt32 aSrcLen, char* aDestBuf, PRInt32 aDestLen); static int ISO10646Convert(nsFontCharSetInfoXlib* aSelf, XFontStruct* aFont, const PRUnichar* aSrcBuf, PRInt32 aSrcLen, char* aDestBuf, PRInt32 aDestLen); static nsFontCharSetInfoXlib Unknown = { nsnull }; static nsFontCharSetInfoXlib Special = { nsnull }; +#ifdef MOZ_ENABLE_FREETYPE2 static nsFontCharSetInfoXlib USASCII = { "us-ascii", SingleByteConvert, 0, TT_OS2_CPR1_LATIN1 | TT_OS2_CPR1_MAC_ROMAN, TT_OS2_CPR2_CA_FRENCH | TT_OS2_CPR2_PORTUGESE | TT_OS2_CPR2_WE_LATIN1 | TT_OS2_CPR2_US }; static nsFontCharSetInfoXlib ISO88591 = { "ISO-8859-1", SingleByteConvert, 0, @@ -486,15 +489,168 @@ static nsFontCharSetInfoXlib Mathematica { "x-mathematica2", SingleByteConvert, 0, TT_OS2_CPR1_SYMBOL, 0}; static nsFontCharSetInfoXlib Mathematica3 = { "x-mathematica3", SingleByteConvert, 0, TT_OS2_CPR1_SYMBOL, 0}; static nsFontCharSetInfoXlib Mathematica4 = { "x-mathematica4", SingleByteConvert, 0, TT_OS2_CPR1_SYMBOL, 0}; static nsFontCharSetInfoXlib Mathematica5 = { "x-mathematica5", SingleByteConvert, 0, TT_OS2_CPR1_SYMBOL, 0}; -#endif /* MOZ_MATHML */ +#endif /* MATHML */ + +#else + +static nsFontCharSetInfoXlib USASCII = + { "us-ascii", SingleByteConvert, 0 }; +static nsFontCharSetInfoXlib ISO88591 = + { "ISO-8859-1", SingleByteConvert, 0 }; +static nsFontCharSetInfoXlib ISO88592 = + { "ISO-8859-2", SingleByteConvert, 0 }; +static nsFontCharSetInfoXlib ISO88593 = + { "ISO-8859-3", SingleByteConvert, 0 }; +static nsFontCharSetInfoXlib ISO88594 = + { "ISO-8859-4", SingleByteConvert, 0 }; +static nsFontCharSetInfoXlib ISO88595 = + { "ISO-8859-5", SingleByteConvert, 0 }; +static nsFontCharSetInfoXlib ISO88596 = + { "ISO-8859-6", SingleByteConvert, 0 }; +static nsFontCharSetInfoXlib ISO885968x = + { "x-iso-8859-6-8-x", SingleByteConvert, 0 }; +static nsFontCharSetInfoXlib ISO8859616 = + { "x-iso-8859-6-16", SingleByteConvert, 0 }; +static nsFontCharSetInfoXlib IBM1046 = + { "x-IBM1046", SingleByteConvert, 0 }; +static nsFontCharSetInfoXlib ISO88597 = + { "ISO-8859-7", SingleByteConvert, 0 }; +static nsFontCharSetInfoXlib ISO88598 = + { "ISO-8859-8", SingleByteConvert, 0 }; +// change from +// { "ISO-8859-8", SingleByteConvertReverse, 0, 0, 0 }; +// untill we fix the layout and ensure we only call this with pure RTL text +static nsFontCharSetInfoXlib ISO88599 = + { "ISO-8859-9", SingleByteConvert, 0 }; +// no support for iso-8859-10 (Nordic/Icelandic) currently +// static nsFontCharSetInfoXlib ISO885910 = +// { "ISO-8859-10", SingleByteConvert, 0, +// 0, TT_OS2_CPR2_NORDIC | TT_OS2_CPR2_ICELANDIC }; +// no support for iso-8859-12 (Vietnamese) currently +// static nsFontCharSetInfoXlib ISO885912 = +// { "ISO-8859-12", SingleByteConvert, 0, +// TT_OS2_CPR1_VIETNAMESE, 0 }; +static nsFontCharSetInfoXlib ISO885913 = + { "ISO-8859-13", SingleByteConvert, 0 }; +static nsFontCharSetInfoXlib ISO885915 = + { "ISO-8859-15", SingleByteConvert, 0 }; +static nsFontCharSetInfoXlib JISX0201 = + { "jis_0201", SingleByteConvert, 1 }; +static nsFontCharSetInfoXlib KOI8R = + { "KOI8-R", SingleByteConvert, 0 }; +static nsFontCharSetInfoXlib KOI8U = + { "KOI8-U", SingleByteConvert, 0 }; +static nsFontCharSetInfoXlib TIS6202 = +/* Added to support thai context sensitive shaping if + * CTL extension is is in force */ +#ifdef SUNCTL + { "tis620-2", SingleByteConvert, 0 }; +#else + { "windows-874", SingleByteConvert, 0 }; +#endif /* SUNCTL */ +static nsFontCharSetInfoXlib TIS620 = + { "TIS-620", SingleByteConvert, 0 }; +static nsFontCharSetInfoXlib ISO885911 = + { "ISO-8859-11", SingleByteConvert, 0 }; +static nsFontCharSetInfoXlib Big5 = + { "x-x-big5", DoubleByteConvert, 1 }; +// a kludge to distinguish zh-TW only fonts in Big5 (such as hpbig5-) +// from zh-TW/zh-HK common fonts in Big5 (such as big5-1) +static nsFontCharSetInfoXlib Big5TWHK = + { "x-x-big5", DoubleByteConvert, 1 }; +static nsFontCharSetInfoXlib CNS116431 = + { "x-cns-11643-1", DoubleByteConvert, 1 }; +static nsFontCharSetInfoXlib CNS116432 = + { "x-cns-11643-2", DoubleByteConvert, 1 }; +static nsFontCharSetInfoXlib CNS116433 = + { "x-cns-11643-3", DoubleByteConvert, 1 }; +static nsFontCharSetInfoXlib CNS116434 = + { "x-cns-11643-4", DoubleByteConvert, 1 }; +static nsFontCharSetInfoXlib CNS116435 = + { "x-cns-11643-5", DoubleByteConvert, 1 }; +static nsFontCharSetInfoXlib CNS116436 = + { "x-cns-11643-6", DoubleByteConvert, 1 }; +static nsFontCharSetInfoXlib CNS116437 = + { "x-cns-11643-7", DoubleByteConvert, 1 }; +static nsFontCharSetInfoXlib GB2312 = + { "gb_2312-80", DoubleByteConvert, 1 }; +static nsFontCharSetInfoXlib GB18030_0 = + { "gb18030.2000-0", DoubleByteConvert, 1 }; +static nsFontCharSetInfoXlib GB18030_1 = + { "gb18030.2000-1", DoubleByteConvert, 1 }; +static nsFontCharSetInfoXlib GBK = + { "x-gbk-noascii", DoubleByteConvert, 1 }; +static nsFontCharSetInfoXlib HKSCS = + { "hkscs-1", DoubleByteConvert, 1 }; +static nsFontCharSetInfoXlib JISX0208 = + { "jis_0208-1983", DoubleByteConvert, 1 }; +static nsFontCharSetInfoXlib JISX0212 = + { "jis_0212-1990", DoubleByteConvert, 1 }; +static nsFontCharSetInfoXlib KSC5601 = + { "ks_c_5601-1987", DoubleByteConvert, 1 }; +static nsFontCharSetInfoXlib X11Johab = + { "x-x11johab", DoubleByteConvert, 1 }; +static nsFontCharSetInfoXlib JohabNoAscii = + { "x-johab-noascii", DoubleByteConvert, 1 }; +static nsFontCharSetInfoXlib JamoTTF = + { "x-koreanjamo-0", DoubleByteConvert, 1 }; +static nsFontCharSetInfoXlib TamilTTF = + { "x-tamilttf-0", DoubleByteConvert, 0 }; +static nsFontCharSetInfoXlib CP1250 = + { "windows-1250", SingleByteConvert, 0 }; +static nsFontCharSetInfoXlib CP1251 = + { "windows-1251", SingleByteConvert, 0 }; +static nsFontCharSetInfoXlib CP1252 = + { "windows-1252", SingleByteConvert, 0 }; +static nsFontCharSetInfoXlib CP1253 = + { "windows-1253", SingleByteConvert, 0 }; +static nsFontCharSetInfoXlib CP1257 = + { "windows-1257", SingleByteConvert, 0 }; + +#ifdef SUNCTL +/* Hindi range currently unsupported in FT2 range. Change TT* once we + arrive at a way to identify hindi */ +static nsFontCharSetInfoXlib SunIndic = + { "x-sun-unicode-india-0", DoubleByteConvert, 0 }; +#endif /* SUNCTL */ + +static nsFontCharSetInfoXlib ISO106461 = + { nsnull, ISO10646Convert, 1}; + +static nsFontCharSetInfoXlib AdobeSymbol = + { "Adobe-Symbol-Encoding", SingleByteConvert, 0 }; +static nsFontCharSetInfoXlib AdobeEuro = + { "x-adobe-euro", SingleByteConvert, 0 }; + +#ifdef MOZ_MATHML +static nsFontCharSetInfoXlib CMCMEX = + { "x-t1-cmex", SingleByteConvert, 0}; +static nsFontCharSetInfoXlib CMCMSY = + { "x-t1-cmsy", SingleByteConvert, 0}; +static nsFontCharSetInfoXlib CMCMR = + { "x-t1-cmr", SingleByteConvert, 0}; +static nsFontCharSetInfoXlib CMCMMI = + { "x-t1-cmmi", SingleByteConvert, 0}; +static nsFontCharSetInfoXlib Mathematica1 = + { "x-mathematica1", SingleByteConvert, 0}; +static nsFontCharSetInfoXlib Mathematica2 = + { "x-mathematica2", SingleByteConvert, 0}; +static nsFontCharSetInfoXlib Mathematica3 = + { "x-mathematica3", SingleByteConvert, 0}; +static nsFontCharSetInfoXlib Mathematica4 = + { "x-mathematica4", SingleByteConvert, 0}; +static nsFontCharSetInfoXlib Mathematica5 = + { "x-mathematica5", SingleByteConvert, 0}; +#endif /* MATHML */ +#endif /* FREETYPE2 */ static nsFontLangGroupXlib FLG_WESTERN = { "x-western", nsnull }; static nsFontLangGroupXlib FLG_BALTIC = { "x-baltic", nsnull }; static nsFontLangGroupXlib FLG_CE = { "x-central-euro",nsnull }; static nsFontLangGroupXlib FLG_RUSSIAN = { "x-cyrillic", nsnull }; static nsFontLangGroupXlib FLG_GREEK = { "el", nsnull }; static nsFontLangGroupXlib FLG_TURKISH = { "tr", nsnull }; @@ -1044,17 +1200,17 @@ FreeNodeArray(nsHashKey* aKey, void* aDa /* This is only required for the main display */ static nsFontMetricsXlibContext *global_fmctx = nsnull; nsFontMetricsXlibContext::~nsFontMetricsXlibContext() { PR_LOG(FontMetricsXlibLM, PR_LOG_DEBUG, ("# nsFontMetricsXlibContext destroy()\n")); -#ifdef USE_FREETYPE +#ifdef MOZ_ENABLE_FREETYPE2 nsFreeTypeFreeGlobals(); -#endif /* USE_FREETYPE */ +#endif /* MOZ_ENABLE_FREETYPE2 */ #ifdef ENABLE_X_FONT_BANNING if (mFontRejectRegEx) { regfree(mFontRejectRegEx); delete mFontRejectRegEx; } @@ -1176,19 +1332,19 @@ nsFontMetricsXlibContext::Init(nsIDevice mBitmapUndersize = 0.8; #ifdef USE_AASB mAntiAliasMinimum = 8; #endif /* USE_AASB */ mEmbeddedBitmapMaximumHeight = 1000000; -#ifdef USE_FREETYPE +#ifdef MOZ_ENABLE_FREETYPE2 mEnableFreeType2 = PR_TRUE; mFreeType2Autohinted = PR_FALSE; mFreeType2Unhinted = PR_TRUE; -#endif /* USE_FREETYPE */ +#endif /* MOZ_ENABLE_FREETYPE2 */ #ifdef USE_AASB mAATTDarkTextMinValue = 64; mAATTDarkTextGain = 0.8; #endif /* USE_AASB */ #ifdef ENABLE_X_FONT_BANNING mFontRejectRegEx = nsnull; @@ -1364,15 +1520,15 @@ nsFontMetricsXlibContext::Init(nsIDevice #ifdef USE_XPRINT } #endif /* USE_XPRINT */ if (NS_SUCCEEDED(rv)) { mForceOutlineScaledFonts = force_outline_scaled_fonts; } -#ifdef USE_FREETYPE +#ifdef MOZ_ENABLE_FREETYPE2 PRBool enable_freetype2 = PR_TRUE; rv = mPref->GetBoolPref("font.FreeType2.enable", &enable_freetype2); if (NS_SUCCEEDED(rv)) { mEnableFreeType2 = enable_freetype2; FREETYPE_FONT_PRINTF(("mEnableFreeType2 = %d", mEnableFreeType2)); } @@ -1385,15 +1541,15 @@ nsFontMetricsXlibContext::Init(nsIDevice PRBool freetype2_unhinted = PR_TRUE; rv = mPref->GetBoolPref("font.FreeType2.unhinted", &freetype2_unhinted); if (NS_SUCCEEDED(rv)) { mFreeType2Unhinted = freetype2_unhinted; FREETYPE_FONT_PRINTF(("mFreeType2Unhinted = %d", mFreeType2Unhinted)); } -#endif /* USE_FREETYPE */ +#endif /* MOZ_ENABLE_FREETYPE2 */ #ifdef USE_AASB PRInt32 antialias_minimum = 8; rv = mPref->GetIntPref("font.antialias.min", &antialias_minimum); if (NS_SUCCEEDED(rv)) { mAntiAliasMinimum = antialias_minimum; FREETYPE_FONT_PRINTF(("mAntiAliasMinimum = %d", mAntiAliasMinimum)); @@ -1581,20 +1737,20 @@ nsFontMetricsXlibContext::Init(nsIDevice mFontAcceptRegEx = nsnull; return NS_ERROR_INVALID_ARG; } } #endif /* ENABLE_X_FONT_BANNING */ -#ifdef USE_FREETYPE +#ifdef MOZ_ENABLE_FREETYPE2 rv = nsFreeTypeInitGlobals(); if (NS_FAILED(rv)) { return NS_ERROR_OUT_OF_MEMORY; } -#endif /* USE_FREETYPE */ +#endif /* MOZ_ENABLE_FREETYPE2 */ return NS_OK; } #ifdef USE_X11SHARED_CODE #error not implemented yet #else @@ -1912,15 +2068,15 @@ NS_IMETHODIMP nsFontMetricsXlib::Destro } void nsFontMetricsXlib::RealizeFont() { float f; f = mDeviceContext->DevUnitsToAppUnits(); -#ifdef USE_FREETYPE +#ifdef MOZ_ENABLE_FREETYPE2 if (mWesternFont->IsFreeTypeFont()) { nsFreeTypeFont *ft = (nsFreeTypeFont *)mWesternFont; if (!ft) return; // now that there are multiple font types (eg: core X fonts // and TrueType fonts) there should be a common set of methods // to get the metrics info from the font object. These methods @@ -1995,15 +2151,15 @@ void nsFontMetricsXlib::RealizeFont() /* need better way to calculate this */ mStrikeoutOffset = NSToCoordRound(mXHeight / 2.0); mStrikeoutSize = mUnderlineSize; return; #endif /* MOZ_ENABLE_FREETYPE2 */ } -#endif /* USE_FREETYPE */ +#endif /* MOZ_ENABLE_FREETYPE2 */ nsXFont *xFont = mWesternFont->GetXFont(); XFontStruct *fontInfo = xFont->GetXFontStruct(); f = mDeviceContext->DevUnitsToAppUnits(); nscoord lineSpacing = nscoord((fontInfo->ascent + fontInfo->descent) * f); mEmHeight = PR_MAX(1, nscoord(mWesternFont->mSize * f)); if (lineSpacing > mEmHeight) { @@ -3006,21 +3162,21 @@ nsFontXlib::GetXFont(void) PRBool nsFontXlib::GetXFontIs10646(void) { return ((PRBool) (mCharSetInfo == mFontMetricsContext->mISO106461)); } -#ifdef USE_FREETYPE +#ifdef MOZ_ENABLE_FREETYPE2 PRBool nsFontXlib::IsFreeTypeFont(void) { return PR_FALSE; } -#endif /* USE_FREETYPE */ +#endif /* MOZ_ENABLE_FREETYPE2 */ MOZ_DECL_CTOR_COUNTER(nsFontXlib) nsFontXlib::nsFontXlib() { MOZ_COUNT_CTOR(nsFontXlib); } @@ -3650,15 +3806,15 @@ nsFontMetricsXlib::GetAASBBaseFont(nsFon } #endif /* USE_AASB */ nsFontXlib* nsFontMetricsXlib::PickASizeAndLoad(nsFontStretchXlib* aStretch, nsFontCharSetInfoXlib* aCharSet, PRUnichar aChar, const char *aName) { -#ifdef USE_FREETYPE +#ifdef MOZ_ENABLE_FREETYPE2 if (aStretch->mFreeTypeFaceID) { //FREETYPE_FONT_PRINTF(("mFreeTypeFaceID = 0x%p", aStretch->mFreeTypeFaceID)); nsFreeTypeFont *ftfont = nsFreeTypeFont::NewFont(aStretch->mFreeTypeFaceID, mPixelSize, aName); if (!ftfont) { FREETYPE_FONT_PRINTF(("failed to create font")); @@ -3678,15 +3834,15 @@ nsFontMetricsXlib::PickASizeAndLoad(nsFo SetCharsetLangGroup(mFontMetricsContext, aCharSet); ftfont->mSize = mPixelSize; ftfont->LoadFont(); ftfont->mCharSetInfo = mFontMetricsContext->mISO106461; //FREETYPE_FONT_PRINTF(("add the ftfont")); return AddToLoadedFontsList(ftfont); } -#endif /* USE_FREETYPE */ +#endif /* MOZ_ENABLE_FREETYPE2 */ PRBool use_scaled_font = PR_FALSE; PRBool have_nearly_rightsized_bitmap = PR_FALSE; #ifdef USE_AASB nsFontXlib *base_aafont = nsnull; #endif /* USE_AASB */ @@ -4494,18 +4650,18 @@ GetFontNames(nsFontMetricsXlibContext *a #ifdef NS_FONT_DEBUG_CALL_TRACE if (gFontDebug & NS_FONT_DEBUG_CALL_TRACE) { printf("GetFontNames %s\n", aPattern); } #endif -#ifdef USE_FREETYPE +#ifdef MOZ_ENABLE_FREETYPE2 // get FreeType fonts nsFT2FontCatalog::GetFontNames(aFmctx, aPattern, aNodes); -#endif /* USE_FREETYPE */ +#endif /* MOZ_ENABLE_FREETYPE2 */ nsCAutoString previousNodeName; nsHashtable* node_hash; if (aAnyFoundry) { NS_ASSERTION(aPattern[1] == '*', "invalid 'anyFoundry' pattern"); node_hash = &aFmctx->mAFRENodes; } @@ -5892,20 +6048,20 @@ const nsFontCharSetMapXlib *GetCharSetMa nsCStringKey charSetKey(aCharSetName); const nsFontCharSetMapXlib* charSetMap = (const nsFontCharSetMapXlib *) aFmctx->mCharSetMaps.Get(&charSetKey); if (!charSetMap) charSetMap = aFmctx->mNoneCharSetMap; return charSetMap; } -#ifdef USE_FREETYPE +#ifdef MOZ_ENABLE_FREETYPE2 static void CharSetNameToCodeRangeBits(const char *aCharset, PRUint32 *aCodeRange1, PRUint32 *aCodeRange2) { nsFontCharSetMapXlib *charSetMap = GetCharSetMap(aFmctx, aCharset); nsFontCharSetInfoXlib *charSetInfo = charSetMap->mInfo; *aCodeRange1 = charSetInfo->mCodeRange1Bits; *aCodeRange2 = charSetInfo->mCodeRange2Bits; } -#endif /* USE_FREETYPE */ +#endif /* MOZ_ENABLE_FREETYPE2 */ Index: gfx/src/xlib/nsFontMetricsXlib.h =================================================================== RCS file: /cvsroot/mozilla/gfx/src/xlib/nsFontMetricsXlib.h,v --- gfx/src/xlib/nsFontMetricsXlib.h 5 Feb 2004 01:57:06 -0000 1.37 +++ gfx/src/xlib/nsFontMetricsXlib.h 17 Oct 2004 11:10:49 -0000 @@ -52,15 +52,15 @@ #include "nsCRT.h" #include "nsCOMPtr.h" #include "nsRenderingContextXlib.h" #include "nsICharRepresentable.h" #include "nsCompressedCharMap.h" /* Undefine some CPP symbols which wrap not-yet-implemented code */ -#undef USE_FREETYPE +#undef MOZ_ENABLE_FREETYPE2 #undef USE_AASB #undef USE_X11SHARED_CODE #ifdef USE_X11SHARED_CODE /* XXX: I wish I would use the code in gfx/src/x11shared/ - unfortunately * it is full of GDK/GTK+ dependices which makes it impossible to use it * yet... ;-( @@ -183,34 +183,34 @@ struct nsFontCharSetXlib; struct nsFontFamilyXlib; struct nsFontNodeXlib; struct nsFontStretchXlib; struct nsFontWeightXlib; class nsFontXlibUserDefined; class nsFontMetricsXlib; -#ifdef USE_FREETYPE +#ifdef MOZ_ENABLE_FREETYPE2 class nsFreeTypeFace; -#endif /* USE_FREETYPE */ +#endif /* MOZ_ENABLE_FREETYPE2 */ struct nsFontStretchXlib { NS_DECL_AND_IMPL_ZEROING_OPERATOR_NEW void SortSizes(void); nsFontXlib **mSizes; PRUint16 mSizesAlloc; PRUint16 mSizesCount; char* mScalable; PRBool mOutlineScaled; nsVoidArray mScaledFonts; -#ifdef USE_FREETYPE +#ifdef MOZ_ENABLE_FREETYPE2 nsFreeTypeFace *mFreeTypeFaceID; -#endif /* USE_FREETYPE */ +#endif /* MOZ_ENABLE_FREETYPE2 */ }; struct nsFontStyleXlib { NS_DECL_AND_IMPL_ZEROING_OPERATOR_NEW void FillWeightHoles(void); @@ -285,17 +285,17 @@ public: inline int SupportsChar(PRUnichar aChar) { return mCCMap && CCMAP_HAS_CHAR(mCCMap, aChar); }; virtual XFontStruct *GetXFontStruct(void); virtual nsXFont *GetXFont(void); virtual PRBool GetXFontIs10646(void); -#ifdef USE_FREETYPE +#ifdef MOZ_ENABLE_FREETYPE2 virtual PRBool IsFreeTypeFont(void); -#endif /* USE_FREETYPE */ +#endif /* MOZ_ENABLE_FREETYPE2 */ virtual int GetWidth(const PRUnichar* aString, PRUint32 aLength) = 0; virtual int DrawString(nsRenderingContextXlib *aContext, nsIDrawingSurfaceXlib *aSurface, nscoord aX, nscoord aY, const PRUnichar* aString, PRUint32 aLength) = 0; #ifdef MOZ_MATHML // bounding metrics for a string @@ -472,15 +472,15 @@ public: class nsHashKey; /* XXX: We can't include gfx/src/x11shared/nsFreeType.h because it relies on * GDK/GTK+ includes which are not available in Xlib builds (fix is to remove * the GDK/GTK+ dependicy from the code in gfx/src/x11shared/ ...) */ -#ifndef USE_FREETYPE +#ifndef MOZ_ENABLE_FREETYPE2 /* * Defines for the TrueType codepage bits. * Used as a hint for the languages supported in a TrueType font. */ /* * ulCodePageRange1 @@ -521,11 +521,11 @@ class nsHashKey; #define TT_OS2_CPR2_CYRILLIC (0x02000000)/*IBM Cyrillic; primarily Russian*/ #define TT_OS2_CPR2_LATIN2 (0x04000000) /* Latin 2 */ #define TT_OS2_CPR2_BALTIC (0x08000000) /* MS-DOS Baltic */ #define TT_OS2_CPR2_GREEK_437G (0x10000000) /* Greek; former 437 G */ #define TT_OS2_CPR2_ARABIC_708 (0x20000000) /* Arabic; ASMO 708 */ #define TT_OS2_CPR2_WE_LATIN1 (0x40000000) /* WE/Latin 1 */ #define TT_OS2_CPR2_US (0x80000000) /* US */ -#endif /* !USE_FREETYPE */ +#endif /* !MOZ_ENABLE_FREETYPE2 */ #endif /* !nsFontMetricsXlib_h__ */ Index: gfx/src/shared/Makefile.in =================================================================== RCS file: /cvsroot/mozilla/gfx/src/shared/Makefile.in,v --- gfx/src/shared/Makefile.in 12 Mar 2003 04:57:15 -0000 1.5 +++ gfx/src/shared/Makefile.in 17 Oct 2004 11:10:49 -0000 @@ -50,10 +50,15 @@ CPPSRCS = \ ifneq (,$(filter mac cocoa,$(MOZ_WIDGET_TOOLKIT))) CPPSRCS += nsNativeTheme.cpp endif LOCAL_INCLUDES = -I$(srcdir)/.. \ $(NULL) + +ifdef MOZ_ENABLE_XFT +CPPSRCS += nsFontConfigUtils.cpp +LOCAL_INCLUDES += $(MOZ_XFT_CFLAGS) +endif include $(topsrcdir)/config/rules.mk Index: gfx/src/shared/nsFontConfigUtils.cpp =================================================================== RCS file: gfx/src/shared/nsFontConfigUtils.cpp --- /dev/null 1 Jan 1970 00:00:00 -0000 +++ gfx/src/shared/nsFontConfigUtils.cpp 17 Oct 2004 11:10:50 -0000 @@ -0,0 +1,227 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* ***** BEGIN LICENSE BLOCK ***** + * Version: MPL 1.1/GPL 2.0/LGPL 2.1 + * + * The contents of this file are subject to the Mozilla Public License Version + * 1.1 (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * http://www.mozilla.org/MPL/ + * + * Software distributed under the License is distributed on an "AS IS" basis, + * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License + * for the specific language governing rights and limitations under the + * License. + * + * The Original Code is mozilla.org code. + * + * The Initial Developer of the Original Code is Christopher Blizzard + * . Portions created by the Initial Developer + * are Copyright (C) 2002 the Initial Developer. All Rights Reserved. + * + * Contributor(s): + * + * Alternatively, the contents of this file may be used under the terms of + * either of the GNU General Public License Version 2 or later (the "GPL"), + * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"), + * in which case the provisions of the GPL or the LGPL are applicable instead + * of those above. If you wish to allow use of your version of this file only + * under the terms of either the GPL or the LGPL, and not to allow others to + * use your version of this file under the terms of the MPL, indicate your + * decision by deleting the provisions above and replace them with the notice + * and other provisions required by the GPL or the LGPL. If you do not delete + * the provisions above, a recipient may use your version of this file under + * the terms of any one of the MPL, the GPL or the LGPL. + * + * ***** END LICENSE BLOCK ***** */ + +#include "nsFontConfigUtils.h" + +struct MozXftLangGroup { + const char *mozLangGroup; + FcChar32 character; + const FcChar8 *XftLang; +}; + +const MozXftLangGroup MozXftLangGroups[] = { + { "x-western", 0x0041, (const FcChar8 *)"en" }, + { "x-central-euro", 0x0100, (const FcChar8 *)"pl" }, + { "x-cyrillic", 0x0411, (const FcChar8 *)"ru" }, + { "x-baltic", 0x0104, (const FcChar8 *)"lv" }, + { "x-devanagari", 0x0905, (const FcChar8 *)"hi" }, + { "x-tamil", 0x0B85, (const FcChar8 *)"ta" }, + { "x-unicode", 0x0000, 0 }, + { "x-user-def", 0x0000, 0 }, +}; + +#define NUM_XFT_LANG_GROUPS (sizeof (MozXftLangGroups) / \ + sizeof (MozXftLangGroups[0])) + +static +void FFREToFamily(nsACString &aFFREName, nsACString &oFamily); + +static +const MozXftLangGroup* +FindFCLangGroup (nsACString &aLangGroup) +{ + for (unsigned int i=0; i < NUM_XFT_LANG_GROUPS; ++i) { + if (aLangGroup.Equals(MozXftLangGroups[i].mozLangGroup, + nsCaseInsensitiveCStringComparator())) { + return &MozXftLangGroups[i]; + } + } + + return nsnull; +} + +int +NS_CalculateSlant(PRUint8 aStyle) +{ + int fcSlant; + + switch(aStyle) { + case NS_FONT_STYLE_ITALIC: + fcSlant = FC_SLANT_ITALIC; + break; + case NS_FONT_STYLE_OBLIQUE: + fcSlant = FC_SLANT_OBLIQUE; + break; + default: + fcSlant = FC_SLANT_ROMAN; + break; + } + + return fcSlant; +} + +int +NS_CalculateWeight (PRUint16 aWeight) +{ + /* + * weights come in two parts crammed into one + * integer -- the "base" weight is weight / 100, + * the rest of the value is the "offset" from that + * weight -- the number of steps to move to adjust + * the weight in the list of supported font weights, + * this value can be negative or positive. + */ + PRInt32 baseWeight = (aWeight + 50) / 100; + PRInt32 offset = aWeight - baseWeight * 100; + + /* clip weights to range 0 to 9 */ + if (baseWeight < 0) + baseWeight = 0; + if (baseWeight > 9) + baseWeight = 9; + + /* Map from weight value to fcWeights index */ + static int fcWeightLookup[10] = { + 0, 0, 0, 0, 1, 1, 2, 3, 3, 4, + }; + + PRInt32 fcWeight = fcWeightLookup[baseWeight]; + + /* + * adjust by the offset value, make sure we stay inside the + * fcWeights table + */ + fcWeight += offset; + if (fcWeight < 0) + fcWeight = 0; + if (fcWeight > 4) + fcWeight = 4; + + /* Map to final FC_WEIGHT value */ + static int fcWeights[5] = { + FC_WEIGHT_LIGHT, /* 0 */ + FC_WEIGHT_MEDIUM, /* 1 */ + FC_WEIGHT_DEMIBOLD, /* 2 */ + FC_WEIGHT_BOLD, /* 3 */ + FC_WEIGHT_BLACK, /* 4 */ + }; + + return fcWeights[fcWeight]; +} + +void +NS_AddLangGroup(FcPattern *aPattern, nsIAtom *aLangGroup) +{ + // Find the FC lang group for this lang group + nsCAutoString cname; + aLangGroup->ToUTF8String(cname); + + // see if the lang group needs to be translated from mozilla's + // internal mapping into fontconfig's + const struct MozXftLangGroup *langGroup; + langGroup = FindFCLangGroup(cname); + + // if there's no lang group, just use the lang group as it was + // passed to us + // + // we're casting away the const here for the strings - should be + // safe. + if (!langGroup) + FcPatternAddString(aPattern, FC_LANG, (FcChar8 *)cname.get()); + else if (langGroup->XftLang) + FcPatternAddString(aPattern, FC_LANG, (FcChar8 *)langGroup->XftLang); +} + +void +NS_AddFFRE(FcPattern *aPattern, nsCString *aFamily, PRBool aWeak) +{ + nsCAutoString family; + FFREToFamily(*aFamily, family); + + FcValue v; + v.type = FcTypeString; + // casting away the const here, should be safe + v.u.s = (FcChar8 *)family.get(); + + if (aWeak) + FcPatternAddWeak(aPattern, FC_FAMILY, v, FcTrue); + else + FcPatternAdd(aPattern, FC_FAMILY, v, FcTrue); +} + +/* static */ +void +FFREToFamily(nsACString &aFFREName, nsACString &oFamily) +{ + if (NS_FFRECountHyphens(aFFREName) == 3) { + PRInt32 familyHyphen = aFFREName.FindChar('-') + 1; + PRInt32 registryHyphen = aFFREName.FindChar('-',familyHyphen); + oFamily.Append(Substring(aFFREName, familyHyphen, + registryHyphen-familyHyphen)); + } + else { + oFamily.Append(aFFREName); + } +} + +int +NS_FFRECountHyphens (nsACString &aFFREName) +{ + int h = 0; + PRInt32 hyphen = 0; + while ((hyphen = aFFREName.FindChar('-', hyphen)) >= 0) { + ++h; + ++hyphen; + } + return h; +} + +PRBool +NS_IsASCIIFontName(const nsString& aName) +{ + PRUint32 len = aName.Length(); + const PRUnichar* str = aName.get(); + for (PRUint32 i = 0; i < len; i++) { + /* + * X font names are printable ASCII, ignore others (for now) + */ + if ((str[i] < 0x20) || (str[i] > 0x7E)) { + return PR_FALSE; + } + } + + return PR_TRUE; +} Index: gfx/src/shared/nsFontConfigUtils.h =================================================================== RCS file: gfx/src/shared/nsFontConfigUtils.h --- /dev/null 1 Jan 1970 00:00:00 -0000 +++ gfx/src/shared/nsFontConfigUtils.h 17 Oct 2004 11:10:50 -0000 @@ -0,0 +1,55 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* ***** BEGIN LICENSE BLOCK ***** + * Version: MPL 1.1/GPL 2.0/LGPL 2.1 + * + * The contents of this file are subject to the Mozilla Public License Version + * 1.1 (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * http://www.mozilla.org/MPL/ + * + * Software distributed under the License is distributed on an "AS IS" basis, + * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License + * for the specific language governing rights and limitations under the + * License. + * + * The Original Code is mozilla.org code. + * + * The Initial Developer of the Original Code is Christopher Blizzard + * . Portions created by the Initial Developer + * are Copyright (C) 2002 the Initial Developer. All Rights Reserved. + * + * Contributor(s): + * + * Alternatively, the contents of this file may be used under the terms of + * either of the GNU General Public License Version 2 or later (the "GPL"), + * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"), + * in which case the provisions of the GPL or the LGPL are applicable instead + * of those above. If you wish to allow use of your version of this file only + * under the terms of either the GPL or the LGPL, and not to allow others to + * use your version of this file under the terms of the MPL, indicate your + * decision by deleting the provisions above and replace them with the notice + * and other provisions required by the GPL or the LGPL. If you do not delete + * the provisions above, a recipient may use your version of this file under + * the terms of any one of the MPL, the GPL or the LGPL. + * + * ***** END LICENSE BLOCK ***** */ + +#ifndef nsFontConfigUtils_h__ +#define nsFontConfigUtils_h__ + +#include "nspr.h" +#include "nsString.h" +#include "nsIAtom.h" +#include "nsFont.h" + +#include + +extern int NS_CalculateSlant (PRUint8 aStyle); +extern int NS_CalculateWeight (PRUint16 aWeight); +extern void NS_AddLangGroup (FcPattern *aPattern, nsIAtom *aLangGroup); +extern void NS_AddFFRE (FcPattern *aPattern, nsCString *aFamily, + PRBool aWeak); +extern int NS_FFRECountHyphens (nsACString &aFFREName); +extern PRBool NS_IsASCIIFontName (const nsString& aName); +#endif +