上面已经介绍到第二人生里是使用FreeType来显示字体的,因此需要使用一个类来封装这些操作,这类就叫做LLFont。在这个类里基本的任务,就是:
1)初始化FreeType的库。
2)打开字体文件。
3)设置字体每点或者每个像素的大小。
4)加载一个字符的笔画,并生成位图。
5)把位图数据生成RAW图片的格式。
6)最后变成纹理贴图让OpenGL输出。
在类LLFontManager里就已经调用函数FT_Init_FreeType来实始化FreeType库了,调用函数FT_Done_FreeType来删除FreeType库。
#001 class LLFont
#002 {
#003 public:
#004
LLFont(LLImageRaw *imagep = NULL);
#005
virtual ~LLFont();
#006
#007
// is_fallback should be true for fallback fonts that aren't used to render directly (Unicode backup, primarily)
下面函数实现打开字体文件,主要调用FT_New_Face函数来打开字体文件,然后调用函数FT_Set_Char_Size来设置字体点或像素大小。同时也创建LLImageRaw对象。
#008
virtual BOOL loadFace(const std::string& filename,
#009
const F32 point_size,
#010
const F32 vert_dpi,
#011
const F32 horz_dpi,
#012
const S32 components,
#013
BOOL is_fallback);
下面函数设置字体列表。
#014
void setFallbackFont(LLFontList *fontp) { mFallbackFontp = fontp; }
#015
#016
void setCharToGlyphMap(llwchar wch, U32 glyph_index) const;
下面函数设置字体生成的图片对象。
#017
void setRawImage( LLImageRaw *imagep );
#018
下面函数获取字体属性。
#019
// Global font metrics - in units of pixels
#020
virtual F32 getLineHeight() const;
#021
virtual F32 getAscenderHeight() const;
#022
virtual F32 getDescenderHeight() const;
#023
#024
#025 // For a lowercase "g":
#026 //
#027 //
------------------------------
#028 //
^ ^
#029 //
| |
#030 //
xxx x |Ascender
#031 //
x x | |
#032 //
--------- xxxx-------------- Baseline
#033 //
^ x | |
#034 // | descender
x | |
#035 //
v xxxx v |LineHeight
#036 // -----------------------
|
#037 //
v
#038 //
------------------------------
#039
#040
enum
#041
{
#042
FIRST_CHAR = 32,
#043
NUM_CHARS = 127 - 32,
#044
LAST_CHAR_BASIC = 127,
#045
#046
// Need full 8-bit ascii range for spanish
#047
NUM_CHARS_FULL = 255 - 32,
#048
LAST_CHAR_FULL = 255
#049
};
#050
#051
const LLFontGlyphInfo &getMetrics(const llwchar wc) const;
#052
F32 getXAdvance(const llwchar wc) const;
#053
F32 getXKerning(const llwchar char_left, const llwchar char_right) const; // Get the kerning between the two characters
#054 protected:
#055
virtual BOOL hasGlyph(const llwchar wch) const; // Has a glyph for this character
下面函数添加一个字符到字体文件。
#056
virtual BOOL addChar(const llwchar wch); // Add a new character to the font if necessary
#057
virtual BOOL addGlyph(const llwchar wch, const U32 glyph_index); // Add a new glyph to the existing font
下面函数从一个字符生成RAW格式的位图对象。
#058
virtual BOOL addGlyphFromFont(LLFont *fontp, const llwchar wch, const U32 glyph_index); // Add a glyph from this font to the other (returns the glyph_index, 0 if
#059 not found)
#060
#061
virtual LLFontGlyphInfo* getGlyphInfo(const llwchar wch) const;
#062
#063
void insertGlyphInfo(llwchar wch, LLFontGlyphInfo* gi) const;
下面函数获取字体的位图。
#064
void renderGlyph(const U32 glyph_index);
#065
#066
void resetBitmap(); // Reset bitmap to contain only the null glyph
#067 protected:
#068
std::string mName;
#069
F32 mAscender;
#070
F32 mDescender;
#071
F32 mLineHeight;
#072
#073
S32 mNumComponents;
#074
S32 mBitmapWidth;
#075
S32 mBitmapHeight;
#076
S32 mMaxCharWidth;
#077
S32 mMaxCharHeight;
#078
S32 mCurrentOffsetX;
#079
S32 mCurrentOffsetY;
#080
#081
LLFT_Face mFTFace;
#082
#083
BOOL mIsFallback;
#084
LLFontList *mFallbackFontp; // A list of fallback fonts to look for glyphs in (for Unicode chars)
#085
#086
typedef std::map<llwchar, LLFontGlyphInfo*> char_glyph_info_map_t;
#087
mutable char_glyph_info_map_t mCharGlyphInfoMap; // Information about glyph location in bitmap
#088
#089
BOOL mValid;
#090
void setSubImageLuminanceAlpha(const U32 x,
#091
const U32 y,
#092
const U32 width,
#093
const U32 height,
#094
const U8 *data,
#095
S32 stride = 0);
#096
#097 private:
#098
LLPointer<LLImageRaw> mRawImagep; // Bitmaps of glyphs are stored here.
#099 };
尽管点阵字体在时间和空间性能上都有较佳的表现,但是由于缺乏灵活性,无法改变字体的大小和风格,除了在一些嵌入式设备中仍然在使用外,大多数系统都使用矢量字体了。矢量字体不像点阵字体那样直接记录字符的字模数据,而是记录字体描述信息,其中最重要的两部分是outline和hint。