cocos2dx TTF字体渲染流程

2dx支持几种格式的文字,如下:

enum class LabelType {
        TTF,
        BMFONT,
        CHARMAP,
        STRING_TEXTURE
    };

今天看了TTF字体渲染的流程,总结如下:
1、对文本中的每个字符遍历,取得该字符的字符编码(unicode码);
2、通过该编码用取得文字对应的bitmap数据:

void renderCharAt(unsigned char *dest,int posX, int posY, unsigned char* bitmap,long bitmapWidth,long bitmapHeight);    //对该字符的rect区域挨个像素的图设置内容,效率太低了吧,还能优化么?

3、通过这些bitmap数据,生成一个textrue2d对象(2dx纹理对象):

bool FontAtlas::prepareLetterDefinitions(const std::u16string& utf16Text)
{
    if (_fontFreeType == nullptr)
    {
        return false;
    } 

    std::unordered_map<unsigned short, unsigned short> codeMapOfNewChar;
    findNewCharacters(utf16Text, codeMapOfNewChar);
    if (codeMapOfNewChar.empty())
    {
        return false;
    }

    int adjustForDistanceMap = _letterPadding / 2;
    int adjustForExtend = _letterEdgeExtend / 2;
    long bitmapWidth;
    long bitmapHeight;
    Rect tempRect;
    FontLetterDefinition tempDef;

    auto scaleFactor = CC_CONTENT_SCALE_FACTOR();
    auto  pixelFormat = _fontFreeType->getOutlineSize() > 0 ? Texture2D::PixelFormat::AI88 : Texture2D::PixelFormat::A8;

    float startY = _currentPageOrigY;

    for (auto&& it : codeMapOfNewChar)
    {
        ...  //内容略,可以去2dx看源码
    }

    unsigned char *data = nullptr;
    if (pixelFormat == Texture2D::PixelFormat::AI88)
    {
        data = _currentPageData + CacheTextureWidth * (int)startY * 2;
    }
    else
    {
        data = _currentPageData + CacheTextureWidth * (int)startY;
    }
    _atlasTextures[_currentPage]->updateWithData(data, 0, startY, CacheTextureWidth, _currentPageOrigY - startY + _lineHeight);  //在这之前已经生成了一张大的空纹理对象,这个地方就用有效的数据去更新大纹理的内容

    return true;
}

4、以上的步骤已经取得需要渲染的纹理了,2dx采用批量渲染的方式去渲染文字的:

void Label::onDraw(const Mat4& transform, bool transformUpdated)
{
    ...
    for (auto&& batchNode : _batchNodes)
    {
        batchNode->getTextureAtlas()->drawQuads();
    }
}

5、这样渲染的过程和图片等流程一样了,加到渲染队列,选择shader,提交纹理坐标,颜色。

疑问:
1、distance field(_useDistanceField控制开关)对边缘平滑处理是怎么做的??
2、描边是怎么实现的?
3、字体渲染怎么优化drawcall?

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值