这一篇博客用于分析Text的内容的更新机制,并分析text mesh pro。
首先我们分析Text的文字是如何渲染出来的。
PupulateWithErrors方法会根据字符串生成顶点数据。其实Text会根据所给定的字符串生成相关的图集,然后对图集进行采样就可以渲染出文字了。由于TextGenerator没有开源,我们从unity UI优化文档上可以找到相关步骤。
protected override void OnPopulateMesh(VertexHelper toFill)
{
if (font == null)
return;
// We don't care if we the font Texture changes while we are doing our Update.
// The end result of cachedTextGenerator will be valid for this instance.
// Otherwise we can get issues like Case 619238.
m_DisableFontTextureRebuiltCallback = true;
Vector2 extents = rectTransform.rect.size;
var settings = GetGenerationSettings(extents);
cachedTextGenerator.PopulateWithErrors(text, settings, gameObject);
// Apply the offset to the vertices
IList<UIVertex> verts = cachedTextGenerator.verts;
float unitsPerPixel = 1 / pixelsPerUnit;
int vertCount = verts.Count;
// We have no verts to process just return (case 1037923)
if (vertCount <= 0)
{
toFill.Clear();
return;
}
Vector2 roundingOffset = new Vector2(verts[0].position.x, verts[0].position.y) * unitsPerPixel;
roundingOffset = PixelAdjustPoint(roundingOffset) - roundingOffset;
toFill.Clear();
if (roundingOffset != Vector2.zero)
{
for (int i = 0; i < vertCount; ++i)
{
int tempVertsIndex = i & 3;
m_TempVerts[tempVertsIndex] = verts[i];
m_TempVerts[tempVertsIndex].position *= unitsPerPixel;
m_TempVerts[tempVertsIndex].position.x += roundingOffset.x;
m_TempVerts[tempVertsIndex].position.y += roundingOffset.y;
if (tempVertsIndex == 3)
toFill.AddUIVertexQuad(m_TempVerts);
}
}
else
{
for (int i = 0; i < vertCount; ++i)
{
int tempVertsIndex = i & 3;
m_TempVerts[tempVertsIndex] = verts[i];
m_TempVerts[tempVertsIndex].position *= unitsPerPixel;
if (tempVertsIndex == 3)
toFill.AddUIVertexQuad(m_TempVerts);
}
}
m_DisableFontTextureRebuiltCal
Unity内置的Text组件可以很方便地用于在UI中显示栅格化的文本字形。但是,在使用Text时有很多大家不了解却又经常遇到的与性能相关的因素。当想UI添加文本时,要始终记得——文本字形是作为独立的面片(quad)进行渲染的,每个字符都是一个面片。这些面片通常都含有大量的空白区域围绕着字形,空白区域的大小取决于字形的形状,在放置文本时很容易就会无意中破坏其他UI元素的批处理。
UI文本的网格重建是个重点问题。当Text组件发生变化时,必须重新计算用于显示实际文本的多边形。当Text组件或它的任意级别的父节点被禁用或启用时,也需要进行重新计算。
在含有大量文字标签的UI上,这一行为可能导致问题,例如排行榜页面和统计数据页面。因为在Unity中,最常见的显示和隐藏UI的方法是启用/禁用含有UI的GameObject,含有大量文本组件的UI通常在显示时会导致帧率降低。
那么Text时如何生成图集的?
当全部可现实字符集很大或者在运行时期不确定时,可以用动态字体来显示文本。在Unity的实现中,这些字体在运行时根据Text组件中出现的字符构建一个字形图集(glyph atlas)。
被加载的每个不同的Font对象会维护它自己的纹理集,即使它与其他字体属于同一个字体族。例如,在一个文本控件中使用Arial字体,并且将字体样式(Font Style)设置为粗体(Bold),在另一个文本控件中使用Arial Bold字体&#