前面已经介绍了显示人物名称的基本框架,但是使用OpenGL显示这个名称出来是需要很复杂的步骤。由于OpenGL是图形引擎显示,也就是说所有字符的显示都是基于图形来显示,而图形的显示,就需要获取字体的图片,即是获取字体的字模。由于不能使用Windows的标准GDI来显示,那么就需要实现GDI所做的所有功能,比如从字体里读取每个字符的轮廓,然后生成合适大小的位图,再把这幅位图当作纹理贴到3D的平面上去,这样才可以在OpenGL显示字符串出来。在第二人生里的代码流程如下:
1、LLFontGL::addChar() 添加一个字符纹理图片
2、mImageGLp->bind() 绑定纹理图片。
3、LLImageGL::bindTextureInternal() 真正绑定纹理图片,在这个函数里调用glBindTexture函数来绑定纹理。
4、LLFontGL::render() 这个函数显示所有字符串。
仔细地分析一下这个函数,看看怎么样显示字符串的,如下:
#001S32 LLFontGL::render(const LLWString &wstr,
#002 const S32 begin_offset,
#003 const F32 x, const F32 y,
#004 const LLColor4 &color,
#005 const HAlign halign, const VAlign valign,
#006 U8 style,
#007 const S32 max_chars, S32 max_pixels,
#008 F32* right_x,
#009 BOOL use_embedded,
#010 BOOL use_ellipses) const
#011{
#012 LLGLEnable texture_2d(GL_TEXTURE_2D);
#013
下面绑定纹理图片。
#089
#090 // Bind the font texture
#091
#092 mImageGLp->bind(0);
#093
#094 glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); // Not guaranteed to be set correctly
#095
下面开始循环地显示字符串。
#160
#161 for (i = begin_offset; i < begin_offset + length; i++)
#162 {
#163 llwchar wch = wstr[i];
#164
#165 // Handle embedded characters first, if they're enabled.
#166 // Embedded characters are a hack for notecards
#167 const embedded_data_t* ext_data = use_embedded ? getEmbeddedCharData(wch) : NULL;
#168 if (ext_data)
#169 {
……
#224 // Bind the font texture
#225 mImageGLp->bind();
#226 }
#227 else
#228 {
#229 if (!hasGlyph(wch))
#230 {
#231 (const_cast<LLFontGL*>(this))->addChar(wch);
#232 }
#233
#234 const LLFontGlyphInfo* fgi= getGlyphInfo(wch);
#235 if (!fgi)
#236 {
#237 llerrs << "Missing Glyph Info" << llendl;
#238 break;
#239 }
#240 if ((start_x + scaled_max_pixels) < (cur_x + fgi->mXBearing + fgi->mWidth))
#241 {
#242 // Not enough room for this character.
#243 break;
#244 }
#245
#246 // Draw the text at the appropriate location
#247 //Specify vertices and texture coordinates
#248 LLRectf uv_rect((fgi->mXBitmapOffset - PAD_AMT) * inv_width,
#249 (fgi->mYBitmapOffset + fgi->mHeight + PAD_AMT) * inv_height,
#250 (fgi->mXBitmapOffset + fgi->mWidth + PAD_AMT) * inv_width,
#251 (fgi->mYBitmapOffset - PAD_AMT) * inv_height);
#252 LLRectf screen_rect(cur_render_x + (F32)fgi->mXBearing - PAD_AMT,
#253 cur_render_y + (F32)fgi->mYBearing + PAD_AMT,
#254 cur_render_x + (F32)fgi->mXBearing + (F32)fgi-
#255>mWidth + PAD_AMT,
#256 cur_render_y + (F32)fgi->mYBearing - (F32)fgi-
#257>mHeight - PAD_AMT);
#258
这里设置每个字符的纹理坐标以及顶点坐标。
#259 drawGlyph(screen_rect, uv_rect, color, style, drop_shadow_strength);
#260
#261 chars_drawn++;
#262 cur_x += fgi->mXAdvance;
#263 cur_y += fgi->mYAdvance;
#264
#265 llwchar next_char = wstr[i+1];
#266 if (next_char && (next_char < LAST_CHARACTER))
#267 {
#268 // Kern this puppy.
#269 if (!hasGlyph(next_char))
#270 {
#271 (const_cast<LLFontGL*>(this))->addChar(next_char);
#272 }
#273 cur_x += getXKerning(wch, next_char);
#274 }
#275
#276 // Round after kerning.
#277 // Must do this to cur_x, not just to cur_render_x, otherwise you
#278 // will squish sub-pixel kerned characters too close together.
#279 // For example, "CCCCC" looks bad.
#280 cur_x = (F32)llfloor(cur_x + 0.5f);
#281 //cur_y = (F32)llfloor(cur_y + 0.5f);
#282
#283 cur_render_x = cur_x;
#284 cur_render_y = cur_y;
#285 }
#286 }
#287
……
#320 glPopMatrix();
#321 }
#322
#323 glPopMatrix();
#324
#325 return chars_drawn;
#326}
#327
蔡军生 <chsdate w:st="on" isrocdate="False" islunardate="False" day="24" month="1" year="2008">2008/01/25</chsdate> QQ:9073204 深圳
分享到:
相关推荐
网上收集的第二人生源码分析资料,感谢原创作者的无私支持!原作者就是CSDN的资深。。。
winscp二次开发,源码分析和详细讲解。 winscp二次开发,源码分析和详细讲解。 winscp二次开发,源码分析和详细讲解。 winscp二次开发,源码分析和详细讲解。 winscp二次开发,源码分析和详细讲解。 winscp二次开发...
武侠2源码分析,分析的很透彻,希望对你的学习有所帮助
图解U-Boot:第二阶段源码分析(清晰)
网络上收集的quake3源码分析资料,感谢原创作者的无私奉献。第二人生和传奇的代码分析CSDN上就有,一并感谢各位资深的贡献!
Docker源码分析 (容器技术系列).zip
VC++滚动字体源码-从文件读取文字到对话框 滚动显示,使用了二级缓存消除了字体刷新的闪烁问题
Linux常见驱动源码分析(kernel hacker修炼之道)--李万鹏 李万鹏 IBM Linux Technology Center kernel team 驱动资料清单内容如下: Linux设备模型(中)之上层容器.pdf Linux设备模型(上)之底层模型.pdf Linux...
算法设计与分析(第二版)程序源码 贪心法 分治法 分支限界法 适用于老师或者学生
Spring源代码解析(二):ioc容器在Web容器中的启动 Spring源代码分析(三):Spring JDBC Spring源代码解析(四):Spring MVC Spring源代码解析(五):Spring AOP获取Proxy Spring源代码解析(六):Spring声明式事务处理...
Cordova-Android源码分析系列二(.docx#资源达人分享计划#
Spring5 源码分析(第 2 版) ,知名老师心得,值得一读
Kettle体系结构与源码分析,详细剖析Kettle的架构与源码,对Kettle的二次开发起关键指导作用
zookeeper源码分析(一)工作原理概述 zookeeper源码分析(二)FastLeader选举算法 Zookeeper源码分析之Paxos算法之旅
Netty权威指南 第二版 源码
matlab智能算法30个案例分析第二版源代码,便于学习过程中实践。
unity棋牌游戏源码,二十一点纸牌游戏源码Blackjack Pro Unity精品小游戏源码 , Unity完整项目源码 是Unitypackage包 , 新建空项目直接导入到项目里面就可以运行了,无需其他操作。 适合二次开发和学习使用,都是经典...
APUE UNIX环境高级编程 第二版 源码
Redis 的源码分析第二部分 By SinSay