//private CanvasRenderer m_canvasRenderer; //private List<UIVertex> m_uiVertices; protected override void Awake() { //base.Awake(); m_manager = GetComponentInParent <InlineGraphicManager>(); }
protected override void OnEnable() { base.OnEnable(); this.m_manager = base.GetComponentInParent <InlineGraphicManager>(); if ((this.m_manager != null) && (this.m_manager.spriteAsset != null)) { this.texture = this.m_manager.spriteAsset.spriteSheet; } }
//private CanvasRenderer m_canvasRenderer; //private List<UIVertex> m_uiVertices; protected override void OnEnable() { base.OnEnable(); m_manager = GetComponentInParent<InlineGraphicManager>(); //m_canvasRenderer = GetComponent<CanvasRenderer>(); if (m_manager != null && m_manager.spriteAsset != null) texture = m_manager.spriteAsset.spriteSheet; }
//private CanvasRenderer m_canvasRenderer; //private List<UIVertex> m_uiVertices; protected override void OnEnable() { base.OnEnable(); m_manager = GetComponentInParent <InlineGraphicManager>(); //m_canvasRenderer = GetComponent<CanvasRenderer>(); if (m_manager != null && m_manager.spriteAsset != null) { texture = m_manager.spriteAsset.spriteSheet; } }
// Function to identify and validate the rich tag. Returns the position of the > if the tag was valid. bool ValidateHtmlTag(int[] chars, int startIndex, out int endIndex) { Array.Clear(m_htmlTag, 0, m_htmlTag.Length); int tagCharCount = 0; int tagHashCode = 0; TagAttribute attribute_1 = new TagAttribute(); TagAttribute attribute_2 = new TagAttribute(); byte attributeFlag = 0; TagUnits tagUnits = TagUnits.Pixels; int numSequenceStart = 0; int numSequenceEnd = 0; int numSequenceDecimalPos = 0; int numSequenceUnitPos = 0; endIndex = startIndex; bool isValidHtmlTag = false; bool hasNumericalValue = false; for (int i = startIndex; i < chars.Length && chars[i] != 0 && tagCharCount < m_htmlTag.Length && chars[i] != 60; i++) { if (chars[i] == 62) // ASCII Code of End HTML tag '>' { isValidHtmlTag = true; endIndex = i; m_htmlTag[tagCharCount] = (char)0; if (numSequenceEnd == 0) numSequenceEnd = tagCharCount - 1; break; } m_htmlTag[tagCharCount] = (char)chars[i]; tagCharCount += 1; // Compute HashCode for 1st attribute if (attributeFlag == 1) { if (chars[i] != 34) // Exclude quotes from the HashCode. { if (attribute_1.startIndex == 0) attribute_1.startIndex = tagCharCount - 1; attribute_1.hashCode = (attribute_1.hashCode << 5) - attribute_1.hashCode + chars[i]; attribute_1.length += 1; } else if (attribute_1.startIndex != 0) attributeFlag = 2; } // Compute HashCode for 2st attribute if (attributeFlag == 3) { if (chars[i] != 34) // Exclude quotes from the HashCode. { if (attribute_2.startIndex == 0) attribute_2.startIndex = tagCharCount - 1; attribute_2.hashCode = (attribute_2.hashCode << 5) - attribute_2.hashCode + chars[i]; attribute_2.length += 1; } else if (attribute_2.startIndex != 0) attributeFlag = 0; } // Extract numerical value and unit type (px, em, %) if (chars[i] == 61) // '=' { numSequenceStart = tagCharCount; attributeFlag += 1; } else if (chars[i] == 46) // '.' numSequenceDecimalPos = tagCharCount - 1; else if (numSequenceStart != 00 && !hasNumericalValue && char.IsDigit((char)chars[i])) hasNumericalValue = true; else if (numSequenceStart != 0 && numSequenceUnitPos == 0 && (chars[i] == 112 || chars[i] == 101 || chars[i] == 37)) { numSequenceEnd = tagCharCount - 2; numSequenceUnitPos = tagCharCount - 1; if (chars[i] == 101) tagUnits = TagUnits.FontUnits; else if (chars[i] == 37) tagUnits = TagUnits.Percentage; } // Compute HashCode for the <tag> if (numSequenceStart == 0) tagHashCode = (tagHashCode << 3) - tagHashCode + chars[i]; } if (!isValidHtmlTag) { return false; } //Debug.Log("Tag is [" + m_htmlTag.ArrayToString() + "]. Tag HashCode: " + tagHashCode + " Attribute HashCode: " + attribute_1.hashCode); // Special handling of the NoParsing tag if (tag_NoParsing && tagHashCode != 53822163) return false; else if (tagHashCode == 53822163) { tag_NoParsing = false; return true; } // Color <#FF00FF> if (m_htmlTag[0] == 35 && tagCharCount == 7) // if Tag begins with # and contains 7 characters. { m_htmlColor = HexCharsToColor(m_htmlTag, tagCharCount); m_colorStack[m_colorStackIndex] = m_htmlColor; m_colorStackIndex += 1; return true; } // Color <#FF00FF00> with alpha else if (m_htmlTag[0] == 35 && tagCharCount == 9) // if Tag begins with # and contains 9 characters. { m_htmlColor = HexCharsToColor(m_htmlTag, tagCharCount); m_colorStack[m_colorStackIndex] = m_htmlColor; m_colorStackIndex += 1; return true; } else { float value = 0; switch (tagHashCode) { case 98: // <b> m_style |= FontStyles.Bold; return true; case 427: // </b> if ((m_fontStyle & FontStyles.Bold) != FontStyles.Bold) m_style &= ~FontStyles.Bold; return true; case 105: // <i> m_style |= FontStyles.Italic; return true; case 434: // </i> m_style &= ~FontStyles.Italic; return true; case 115: // <s> m_style |= FontStyles.Strikethrough; return true; case 444: // </s> if ((m_fontStyle & FontStyles.Strikethrough) != FontStyles.Strikethrough) m_style &= ~FontStyles.Strikethrough; return true; case 117: // <u> m_style |= FontStyles.Underline; return true; case 446: // </u> if ((m_fontStyle & FontStyles.Underline) != FontStyles.Underline) m_style &= ~FontStyles.Underline; return true; case 6552: // <sub> m_currentFontSize *= m_fontAsset.fontInfo.SubSize > 0 ? m_fontAsset.fontInfo.SubSize : 1; // Subscript characters are half size. m_fontScale = m_currentFontSize / m_fontAsset.fontInfo.PointSize; m_baselineOffset = m_fontAsset.fontInfo.SubscriptOffset * m_fontScale; m_style |= FontStyles.Subscript; //m_isRecalculateScaleRequired = true; return true; case 22673: // </sub> m_currentFontSize /= m_fontAsset.fontInfo.SubSize > 0 ? m_fontAsset.fontInfo.SubSize : 1; //m_fontSize / m_fontAsset.FontInfo.PointSize * .1f; m_baselineOffset = 0; m_fontScale = m_currentFontSize / m_fontAsset.fontInfo.PointSize; m_style &= ~FontStyles.Subscript; //m_isRecalculateScaleRequired = true; return true; case 6566: // <sup> m_currentFontSize *= m_fontAsset.fontInfo.SubSize > 0 ? m_fontAsset.fontInfo.SubSize : 1; m_fontScale = m_currentFontSize / m_fontAsset.fontInfo.PointSize; m_baselineOffset = m_fontAsset.fontInfo.SuperscriptOffset * m_fontScale; m_style |= FontStyles.Superscript; //m_isRecalculateScaleRequired = true; return true; case 22687: // </sup> m_currentFontSize /= m_fontAsset.fontInfo.SubSize > 0 ? m_fontAsset.fontInfo.SubSize : 1; //m_fontSize / m_fontAsset.FontInfo.PointSize * .1f; m_baselineOffset = 0; m_fontScale = m_currentFontSize / m_fontAsset.fontInfo.PointSize; m_style &= ~FontStyles.Superscript; //m_isRecalculateScaleRequired = true; return true; case 6380: // <pos=000.00px> <pos=0em> <pos=50%> value = ConvertToFloat(m_htmlTag, numSequenceStart, numSequenceEnd, numSequenceDecimalPos); if (value == -9999 || value == 0) return false; switch (tagUnits) { case TagUnits.Pixels: m_xAdvance = value; //m_isIgnoringAlignment = true; return true; case TagUnits.FontUnits: m_xAdvance = value * m_fontScale * m_fontAsset.fontInfo.TabWidth / m_fontAsset.TabSize; //m_isIgnoringAlignment = true; return true; case TagUnits.Percentage: m_xAdvance = m_marginWidth * value / 100; //m_isIgnoringAlignment = true; return true; } return false; case 22501: // </pos> m_isIgnoringAlignment = false; return true; case 16034505: // <voffset> value = ConvertToFloat(m_htmlTag, numSequenceStart, numSequenceEnd, numSequenceDecimalPos); if (value == -9999 || value == 0) return false; switch (tagUnits) { case TagUnits.Pixels: m_baselineOffset = value; return true; case TagUnits.FontUnits: m_baselineOffset = value * m_fontScale * m_fontAsset.fontInfo.Ascender; return true; case TagUnits.Percentage: //m_baselineOffset = m_marginHeight * val / 100; return false; } return false; case 54741026: // </voffset> m_baselineOffset = 0; return true; case 43991: // <page> // This tag only works when Overflow - Page mode is used. if (m_overflowMode == TextOverflowModes.Page) { m_xAdvance = 0 + tag_LineIndent + tag_Indent; //m_textInfo.lineInfo[m_lineNumber].marginLeft = m_xAdvance; m_lineOffset = 0; m_pageNumber += 1; m_isNewPage = true; } return true; case 43969: // <nobr> m_isNonBreakingSpace = true; return true; case 156816: // </nobr> m_isNonBreakingSpace = false; return true; case 45545: // <size=> value = ConvertToFloat(m_htmlTag, numSequenceStart, numSequenceEnd, numSequenceDecimalPos); if (value == -9999 || value == 0) return false; switch (tagUnits) { case TagUnits.Pixels: if (m_htmlTag[5] == 43) // <size=+00> { m_currentFontSize = m_fontSize + value; m_isRecalculateScaleRequired = true; return true; } else if (m_htmlTag[5] == 45) // <size=-00> { m_currentFontSize = m_fontSize + value; m_isRecalculateScaleRequired = true; return true; } else // <size=00.0> { m_currentFontSize = value; m_isRecalculateScaleRequired = true; return true; } case TagUnits.FontUnits: m_currentFontSize *= value; m_isRecalculateScaleRequired = true; return true; case TagUnits.Percentage: m_currentFontSize = m_fontSize * value / 100; m_isRecalculateScaleRequired = true; return true; } return false; case 158392: // </size> m_currentFontSize = m_fontSize; m_isRecalculateScaleRequired = true; //m_fontScale = m_fontSize / m_fontAsset.fontInfo.PointSize * .1f; return true; case 41311: // <font=xx> //Debug.Log("Font name: \"" + new string(m_htmlTag, attribute_1.startIndex, attribute_1.length) + "\" HashCode: " + attribute_1.hashCode + " Material Name: \"" + new string(m_htmlTag, attribute_2.startIndex, attribute_2.length) + "\" Hashcode: " + attribute_2.hashCode); int fontHashCode = attribute_1.hashCode; int materialHashCode = attribute_2.hashCode; TextMeshProFont tempFont; Material tempMaterial; // HANDLE NEW FONT ASSET if (m_fontAsset_Dict.TryGetValue(fontHashCode, out tempFont)) { if (tempFont != m_currentFontAsset) { //Debug.Log("Assigning Font Asset: " + tempFont.name); m_currentFontAsset = m_fontAsset_Dict[fontHashCode]; m_isRecalculateScaleRequired = true; } } else { // Load new font asset tempFont = Resources.Load("Fonts & Materials/" + new string(m_htmlTag, attribute_1.startIndex, attribute_1.length), typeof(TextMeshProFont)) as TextMeshProFont; if (tempFont != null) { //Debug.Log("Loading and Assigning Font Asset: " + tempFont.name); m_fontAsset_Dict.Add(fontHashCode, tempFont); m_currentFontAsset = tempFont; m_isRecalculateScaleRequired = true; } else return false; } // HANDLE NEW MATERIAL if (materialHashCode == 0) { if (!m_fontMaterial_Dict.TryGetValue(m_currentFontAsset.materialHashCode, out tempMaterial)) m_fontMaterial_Dict.Add(m_currentFontAsset.materialHashCode, m_currentFontAsset.material); if (m_currentMaterial != m_currentFontAsset.material) { //Debug.Log("Assigning Default Font Asset Material: " + m_currentFontAsset.material.name); m_currentMaterial = m_currentFontAsset.material; } } else if (m_fontMaterial_Dict.TryGetValue(materialHashCode, out tempMaterial)) { if (tempMaterial != m_currentMaterial) { //Debug.Log("Assigning Material: " + tempMaterial.name); m_currentMaterial = tempMaterial; } } else { // Load new material tempMaterial = Resources.Load("Fonts & Materials/" + new string(m_htmlTag, attribute_2.startIndex, attribute_2.length), typeof(Material)) as Material; if (tempMaterial != null) { //Debug.Log("Loading and Assigning Material: " + tempMaterial.name); m_fontMaterial_Dict.Add(materialHashCode, tempMaterial); m_currentMaterial = tempMaterial; } else return false; } return true; case 320078: // <space=000.00> value = ConvertToFloat(m_htmlTag, numSequenceStart, numSequenceEnd, numSequenceDecimalPos); if (value == -9999 || value == 0) return false; switch (tagUnits) { case TagUnits.Pixels: m_xAdvance += value; return true; case TagUnits.FontUnits: m_xAdvance += value * m_fontScale * m_fontAsset.fontInfo.TabWidth / m_fontAsset.TabSize; return true; case TagUnits.Percentage: // Not applicable return false; } return false; case 276254: // <alpha=#FF> m_htmlColor.a = (byte)(HexToInt(m_htmlTag[7]) * 16 + HexToInt(m_htmlTag[8])); return true; case 1750458: // <a name=" "> return true; case 426: // </a> return true; case 43066: // <link="name"> if (m_isParsingText) { tag_LinkInfo.hashCode = attribute_1.hashCode; tag_LinkInfo.firstCharacterIndex = m_characterCount; //Debug.Log("Link begin at Character # " + m_characterCount); } return true; case 155913: // </link> if (m_isParsingText) { tag_LinkInfo.lastCharacterIndex = m_characterCount - 1; tag_LinkInfo.characterCount = m_characterCount - tag_LinkInfo.firstCharacterIndex; m_textInfo.linkInfo.Add(tag_LinkInfo); m_textInfo.linkCount += 1; //Debug.Log("*** LinkInfo Element Added ***\nHashCode: " + tag_LinkInfo.hashCode + " First Index: " + tag_LinkInfo.firstCharacterIndex + " Last Index: " + tag_LinkInfo.lastCharacterIndex + " Link Count: " + m_textInfo.linkCount); } return true; case 275917: // <align=> switch (attribute_1.hashCode) { case 3317767: // <align=left> m_lineJustification = TextAlignmentOptions.Left; return true; case 108511772: // <align=right> m_lineJustification = TextAlignmentOptions.Right; return true; case -1364013995: // <align=center> m_lineJustification = TextAlignmentOptions.Center; return true; case 1838536479: // <align=justified> m_lineJustification = TextAlignmentOptions.Justified; return true; } return false; case 1065846: // </align> m_lineJustification = m_textAlignment; return true; case 327550: // <width=xx> value = ConvertToFloat(m_htmlTag, numSequenceStart, numSequenceEnd, numSequenceDecimalPos); if (value == -9999 || value == 0) return false; switch (tagUnits) { case TagUnits.Pixels: m_width = value; break; case TagUnits.FontUnits: return false; //break; case TagUnits.Percentage: m_width = m_marginWidth * value / 100; break; } return true; case 1117479: // </width> m_width = -1; return true; case 322689: // <style="name"> TMP_Style style = TMP_StyleSheet.Instance.GetStyle(attribute_1.hashCode); if (style == null) return false; m_styleStack[m_styleStackIndex] = style.hashCode; m_styleStackIndex += 1; //// Parse Style Macro for (int i = 0; i < style.styleOpeningTagArray.Length; i++) { if (style.styleOpeningTagArray[i] == 60) ValidateHtmlTag(style.styleOpeningTagArray, i + 1, out i); } return true; case 1112618: // </style> style = TMP_StyleSheet.Instance.GetStyle(attribute_1.hashCode); if (style == null) { // Get style from the Style Stack m_styleStackIndex = m_styleStackIndex > 0 ? m_styleStackIndex - 1 : 0; style = TMP_StyleSheet.Instance.GetStyle(m_styleStack[m_styleStackIndex]); } if (style == null) return false; //// Parse Style Macro for (int i = 0; i < style.styleClosingTagArray.Length; i++) { if (style.styleClosingTagArray[i] == 60) ValidateHtmlTag(style.styleClosingTagArray, i + 1, out i); } return true; case 281955: // <color=#FF00FF> or <color=#FF00FF00> // <color=#FF00FF> if (m_htmlTag[6] == 35 && tagCharCount == 13) { m_htmlColor = HexCharsToColor(m_htmlTag, tagCharCount); m_colorStack[m_colorStackIndex] = m_htmlColor; m_colorStackIndex += 1; return true; } // <color=#FF00FF00> else if (m_htmlTag[6] == 35 && tagCharCount == 15) { m_htmlColor = HexCharsToColor(m_htmlTag, tagCharCount); m_colorStack[m_colorStackIndex] = m_htmlColor; m_colorStackIndex += 1; return true; } // <color=name> switch (attribute_1.hashCode) { case 112785: // <color=red> m_htmlColor = Color.red; m_colorStack[m_colorStackIndex] = m_htmlColor; m_colorStackIndex += 1; return true; case 3027034: // <color=blue> m_htmlColor = Color.blue; m_colorStack[m_colorStackIndex] = m_htmlColor; m_colorStackIndex += 1; return true; case 93818879: // <color=black> m_htmlColor = Color.black; m_colorStack[m_colorStackIndex] = m_htmlColor; m_colorStackIndex += 1; return true; case 98619139: // <color=green> m_htmlColor = Color.green; m_colorStack[m_colorStackIndex] = m_htmlColor; m_colorStackIndex += 1; return true; case 113101865: // <color=white> m_htmlColor = Color.white; m_colorStack[m_colorStackIndex] = m_htmlColor; m_colorStackIndex += 1; return true; case -1008851410: // <color=orange> m_htmlColor = new Color32(255, 128, 0, 255); m_colorStack[m_colorStackIndex] = m_htmlColor; m_colorStackIndex += 1; return true; case -976943172: // <color=purple> m_htmlColor = new Color32(160, 32, 240, 255); m_colorStack[m_colorStackIndex] = m_htmlColor; m_colorStackIndex += 1; return true; case -734239628: // <color=yellow> m_htmlColor = Color.yellow; m_colorStack[m_colorStackIndex] = m_htmlColor; m_colorStackIndex += 1; return true; } return false; case 1983971: // <cspace=xx.x> value = ConvertToFloat(m_htmlTag, numSequenceStart, numSequenceEnd, numSequenceDecimalPos); if (value == -9999 || value == 0) return false; switch (tagUnits) { case TagUnits.Pixels: m_cSpacing = value; break; case TagUnits.FontUnits: m_cSpacing = value; m_cSpacing *= m_fontScale * m_fontAsset.fontInfo.TabWidth / m_fontAsset.TabSize; break; case TagUnits.Percentage: return false; } return true; case 7513474: // </cspace> m_cSpacing = 0; return true; case 2152041: // <mspace=xx.x> value = ConvertToFloat(m_htmlTag, numSequenceStart, numSequenceEnd, numSequenceDecimalPos); if (value == -9999 || value == 0) return false; switch (tagUnits) { case TagUnits.Pixels: m_monoSpacing = value; break; case TagUnits.FontUnits: m_monoSpacing = value; m_monoSpacing *= m_fontScale * m_fontAsset.fontInfo.TabWidth / m_fontAsset.TabSize; break; case TagUnits.Percentage: return false; } return true; case 7681544: // </mspace> m_monoSpacing = 0; return true; case 280416: // <class="name"> return false; case 1071884: // </color> m_colorStackIndex -= 1; if (m_colorStackIndex <= 0) { m_htmlColor = m_fontColor32; m_colorStackIndex = 0; } else { m_htmlColor = m_colorStack[m_colorStackIndex - 1]; } return true; case 2068980: // <indent=10px> <indent=10em> <indent=50%> value = ConvertToFloat(m_htmlTag, numSequenceStart, numSequenceEnd, numSequenceDecimalPos); if (value == -9999 || value == 0) return false; switch (tagUnits) { case TagUnits.Pixels: tag_Indent = value; break; case TagUnits.FontUnits: tag_Indent *= m_fontScale * m_fontAsset.fontInfo.TabWidth / m_fontAsset.TabSize; break; case TagUnits.Percentage: tag_Indent = m_marginWidth * tag_Indent / 100; break; } m_xAdvance = tag_Indent; return true; case 7598483: // </indent> tag_Indent = 0; return true; case 1109386397: // <line-indent> value = ConvertToFloat(m_htmlTag, numSequenceStart, numSequenceEnd, numSequenceDecimalPos); if (value == -9999 || value == 0) return false; switch (tagUnits) { case TagUnits.Pixels: tag_LineIndent = value; break; case TagUnits.FontUnits: tag_LineIndent = value; tag_LineIndent *= m_fontScale * m_fontAsset.fontInfo.TabWidth / m_fontAsset.TabSize; break; case TagUnits.Percentage: tag_LineIndent = m_marginWidth * tag_LineIndent / 100; break; } m_xAdvance += tag_LineIndent; return true; case -445537194: // </line-indent> tag_LineIndent = 0; return true; case 2246877: // <sprite=x> if (m_inlineGraphics == null) m_inlineGraphics = GetComponent<InlineGraphicManager>() ?? gameObject.AddComponent<InlineGraphicManager>(); if (char.IsDigit(m_htmlTag[7])) { int index = (int)ConvertToFloat(m_htmlTag, numSequenceStart, numSequenceEnd, numSequenceDecimalPos); m_spriteIndex = m_inlineGraphics.GetSpriteIndexByIndex(index); if (m_spriteIndex == -1) return false; } else { // Get sprite index by looking it up by name. m_spriteIndex = m_inlineGraphics.GetSpriteIndexByHashCode(attribute_1.hashCode); if (m_spriteIndex == -1) return false; //Debug.Log("Sprite name is: \"" + new string(m_htmlTag, attribute_1.startIndex, attribute_1.length) + "\" with HashCode: " + attribute_1.hashCode); } m_isSprite = true; return true; case 13526026: // <allcaps> m_style |= FontStyles.UpperCase; return true; case 52232547: // </allcaps> m_style &= ~FontStyles.UpperCase; return true; case 766244328: // <smallcaps> m_style |= FontStyles.SmallCaps; return true; case -1632103439: // </smallcaps> m_style &= ~FontStyles.SmallCaps; m_isRecalculateScaleRequired = true; return true; case 2109854: // <margin=00.0> <margin=00em> <margin=50%> value = ConvertToFloat(m_htmlTag, numSequenceStart, numSequenceEnd, numSequenceDecimalPos); // px if (value == -9999 || value == 0) return false; m_marginLeft = value; switch (tagUnits) { case TagUnits.Pixels: // Default behavior break; case TagUnits.FontUnits: m_marginLeft *= m_fontScale * m_fontAsset.fontInfo.TabWidth / m_fontAsset.TabSize; break; case TagUnits.Percentage: m_marginLeft = (m_marginWidth - (m_width != -1 ? m_width : 0)) * m_marginLeft / 100; break; } m_marginLeft = m_marginLeft >= 0 ? m_marginLeft : 0; m_marginRight = m_marginLeft; return true; case 7639357: // </margin> m_marginLeft = 0; m_marginRight = 0; return true; case 1100728678: // <margin-left=xx.x> value = ConvertToFloat(m_htmlTag, numSequenceStart, numSequenceEnd, numSequenceDecimalPos); // px if (value == -9999 || value == 0) return false; m_marginLeft = value; switch (tagUnits) { case TagUnits.Pixels: // Default behavior break; case TagUnits.FontUnits: m_marginLeft *= m_fontScale * m_fontAsset.fontInfo.TabWidth / m_fontAsset.TabSize; break; case TagUnits.Percentage: m_marginLeft = (m_marginWidth - (m_width != -1 ? m_width : 0)) * m_marginLeft / 100; break; } m_marginLeft = m_marginLeft >= 0 ? m_marginLeft : 0; return true; case -884817987: // <margin-right=xx.x> value = ConvertToFloat(m_htmlTag, numSequenceStart, numSequenceEnd, numSequenceDecimalPos); // px if (value == -9999 || value == 0) return false; m_marginRight = value; switch (tagUnits) { case TagUnits.Pixels: // Default behavior break; case TagUnits.FontUnits: m_marginRight *= m_fontScale * m_fontAsset.fontInfo.TabWidth / m_fontAsset.TabSize; break; case TagUnits.Percentage: m_marginRight = (m_marginWidth - (m_width != -1 ? m_width : 0)) * m_marginRight / 100; break; } m_marginRight = m_marginRight >= 0 ? m_marginRight : 0; return true; case 1109349752: // <line-height=xx.x> value = ConvertToFloat(m_htmlTag, numSequenceStart, numSequenceEnd, numSequenceDecimalPos); if (value == -9999 || value == 0) return false; m_lineHeight = value; switch (tagUnits) { case TagUnits.Pixels: m_lineHeight /= m_fontScale; break; case TagUnits.FontUnits: m_lineHeight *= m_fontAsset.fontInfo.LineHeight; break; case TagUnits.Percentage: m_lineHeight = m_fontAsset.fontInfo.LineHeight * m_lineHeight / 100; break; } return true; case -445573839: // </line-height> m_lineHeight = 0; return true; case 15115642: // <noparse> tag_NoParsing = true; return true; } } return false; }
// This function parses through the Char[] to determine how many characters will be visible. It then makes sure the arrays are large enough for all those characters. int SetArraySizes(int[] chars) { //Debug.Log("Set Array Size called."); int visibleCount = 0; int totalCount = 0; int tagEnd = 0; int spriteCount = 0; m_isUsingBold = false; m_isParsingText = false; m_isSprite = false; m_fontIndex = 0; m_VisibleCharacters.Clear(); //Array.Clear(m_meshAllocCount, 0, 17); for (int i = 0; chars[i] != 0; i++) { int c = chars[i]; if (m_isRichText && c == 60) // if Char '<' { // Check if Tag is Valid if (ValidateHtmlTag(chars, i + 1, out tagEnd)) { i = tagEnd; if ((m_style & FontStyles.Underline) == FontStyles.Underline) visibleCount += 3; if ((m_style & FontStyles.Bold) == FontStyles.Bold) m_isUsingBold = true; if (m_isSprite) { spriteCount += 1; totalCount += 1; m_VisibleCharacters.Add((char)(57344 + m_spriteIndex)); m_isSprite = false; } continue; } } if (c != 9 && c != 10 && c != 13 && c != 32 && c != 160) { visibleCount += 1; // Track how many characters per mesh //m_meshAllocCount[m_fontIndex] += 1; } m_VisibleCharacters.Add((char)c); totalCount += 1; } // Allocated secondary vertex buffers for InlineGraphic Component if present. if (spriteCount > 0) { if (m_inlineGraphics == null) m_inlineGraphics = GetComponent<InlineGraphicManager>() ?? gameObject.AddComponent<InlineGraphicManager>(); m_inlineGraphics.AllocatedVertexBuffers(spriteCount); } else if (m_inlineGraphics != null) m_inlineGraphics.ClearUIVertex(); m_spriteCount = spriteCount; if (m_textInfo.characterInfo == null || totalCount > m_textInfo.characterInfo.Length) { m_textInfo.characterInfo = new TMP_CharacterInfo[totalCount > 1024 ? totalCount + 256 : Mathf.NextPowerOfTwo(totalCount)]; } // Make sure our Mesh Buffer Allocations can hold these new Quads. if (m_textInfo.meshInfo.vertices == null) m_textInfo.meshInfo = new TMP_MeshInfo(m_mesh, visibleCount); if (visibleCount * 4 > m_textInfo.meshInfo.vertices.Length) { // If this is the first allocation, we allocated exactly the number of Quads we need. Otherwise, we allocated more since this text object is dynamic. if (m_isFirstAllocation) { SetMeshArrays(visibleCount); m_isFirstAllocation = false; } else { SetMeshArrays(visibleCount > 1024 ? visibleCount + 256 : Mathf.NextPowerOfTwo(visibleCount)); } } /* // Make sure our Mesh Array has enough capacity for the different fonts if (m_textInfo.meshInfo.meshArrays == null) m_textInfo.meshInfo.meshArrays = new UIVertex[17][]; for (int i = 0; i < 17; i++ ) { if (m_textInfo.meshInfo.meshArrays[i] == null || m_textInfo.meshInfo.meshArrays[i].Length < m_meshAllocCount[i]) { int arraySize = m_meshAllocCount[i] * 4; m_textInfo.meshInfo.meshArrays[i] = new UIVertex[arraySize > 1024 ? arraySize + 256 : Mathf.NextPowerOfTwo(arraySize)]; } if (i > 0 && m_meshAllocCount[i] > 0) { if (subObjects[i] == null) { subObjects[i] = new GameObject("Font #" + i, typeof(CanvasRenderer)); RectTransform rectTransform = subObjects[i].AddComponent<RectTransform>(); rectTransform.SetParent(m_rectTransform); rectTransform.localPosition = Vector3.zero; rectTransform.sizeDelta = Vector2.zero; rectTransform.anchorMin = Vector2.zero; rectTransform.anchorMax = Vector2.one; } } } */ return totalCount; }
//private CanvasRenderer m_canvasRenderer; //private List<UIVertex> m_uiVertices; protected override void Awake() { //base.Awake(); m_manager = GetComponentInParent<InlineGraphicManager>(); }
/// <summary> /// Function to identify and validate the rich tag. Returns the position of the > if the tag was valid. /// </summary> /// <param name="chars"></param> /// <param name="startIndex"></param> /// <param name="endIndex"></param> /// <returns></returns> protected bool ValidateHtmlTag(int[] chars, int startIndex, out int endIndex) { Array.Clear(m_htmlTag, 0, m_htmlTag.Length); int tagCharCount = 0; //int tagHashCode = 0; byte attributeFlag = 0; TagUnits tagUnits = TagUnits.Pixels; TagType tagType = TagType.None; int attributeIndex = 0; m_xmlAttribute[attributeIndex].nameHashCode = 0; m_xmlAttribute[attributeIndex].valueHashCode = 0; m_xmlAttribute[attributeIndex].valueStartIndex = 0; m_xmlAttribute[attributeIndex].valueLength = 0; m_xmlAttribute[attributeIndex].valueDecimalIndex = 0; endIndex = startIndex; bool isValidHtmlTag = false; for (int i = startIndex; i < chars.Length && chars[i] != 0 && tagCharCount < m_htmlTag.Length && chars[i] != 60; i++) { if (chars[i] == 62) // ASCII Code of End HTML tag '>' { isValidHtmlTag = true; endIndex = i; m_htmlTag[tagCharCount] = (char)0; break; } m_htmlTag[tagCharCount] = (char)chars[i]; tagCharCount += 1; if (attributeFlag == 1) { if (m_xmlAttribute[attributeIndex].valueStartIndex == 0) { // Check for attribute type if (chars[i] == 43 || chars[i] == 45 || char.IsDigit((char)chars[i])) { tagType = TagType.NumericalValue; m_xmlAttribute[attributeIndex].valueStartIndex = tagCharCount - 1; m_xmlAttribute[attributeIndex].valueLength += 1; } else if (chars[i] == 35) { tagType = TagType.ColorValue; m_xmlAttribute[attributeIndex].valueStartIndex = tagCharCount - 1; m_xmlAttribute[attributeIndex].valueLength += 1; } else if (chars[i] != 34) { tagType = TagType.StringValue; m_xmlAttribute[attributeIndex].valueStartIndex = tagCharCount - 1; m_xmlAttribute[attributeIndex].valueHashCode = (m_xmlAttribute[attributeIndex].valueHashCode << 5) + m_xmlAttribute[attributeIndex].valueHashCode ^ chars[i]; m_xmlAttribute[attributeIndex].valueLength += 1; } } else { if (tagType == TagType.NumericalValue) { if (chars[i] == 46) // '.' Decimal Point Index m_xmlAttribute[attributeIndex].valueDecimalIndex = tagCharCount - 1; // Check for termination of numerical value. if (chars[i] == 112 || chars[i] == 101 || chars[i] == 37 || chars[i] == 32) { attributeFlag = 2; tagType = TagType.None; attributeIndex += 1; m_xmlAttribute[attributeIndex].nameHashCode = 0; m_xmlAttribute[attributeIndex].valueHashCode = 0; m_xmlAttribute[attributeIndex].valueStartIndex = 0; m_xmlAttribute[attributeIndex].valueLength = 0; m_xmlAttribute[attributeIndex].valueDecimalIndex = 0; if (chars[i] == 101) tagUnits = TagUnits.FontUnits; else if (chars[i] == 37) tagUnits = TagUnits.Percentage; } else if (attributeFlag != 2) { m_xmlAttribute[attributeIndex].valueLength += 1; } } else if (tagType == TagType.ColorValue) { if (chars[i] != 32) { m_xmlAttribute[attributeIndex].valueLength += 1; } else { attributeFlag = 2; tagType = TagType.None; attributeIndex += 1; m_xmlAttribute[attributeIndex].nameHashCode = 0; m_xmlAttribute[attributeIndex].valueHashCode = 0; m_xmlAttribute[attributeIndex].valueStartIndex = 0; m_xmlAttribute[attributeIndex].valueLength = 0; m_xmlAttribute[attributeIndex].valueDecimalIndex = 0; } } else if (tagType == TagType.StringValue) { // Compute HashCode value for the named tag. if (chars[i] != 34) { m_xmlAttribute[attributeIndex].valueHashCode = (m_xmlAttribute[attributeIndex].valueHashCode << 5) + m_xmlAttribute[attributeIndex].valueHashCode ^ chars[i]; m_xmlAttribute[attributeIndex].valueLength += 1; } else { attributeFlag = 2; tagType = TagType.None; attributeIndex += 1; m_xmlAttribute[attributeIndex].nameHashCode = 0; m_xmlAttribute[attributeIndex].valueHashCode = 0; m_xmlAttribute[attributeIndex].valueStartIndex = 0; m_xmlAttribute[attributeIndex].valueLength = 0; m_xmlAttribute[attributeIndex].valueDecimalIndex = 0; } } } } if (chars[i] == 61) // '=' attributeFlag = 1; // Compute HashCode for the name of the attribute if (attributeFlag == 0) m_xmlAttribute[attributeIndex].nameHashCode = (m_xmlAttribute[attributeIndex].nameHashCode << 3) - m_xmlAttribute[attributeIndex].nameHashCode + chars[i]; if (attributeFlag == 2 && chars[i] == 32) attributeFlag = 0; } if (!isValidHtmlTag) { return false; } //Debug.Log("Tag is [" + m_htmlTag.ArrayToString() + "]. Tag HashCode: " + m_xmlAttribute[0].nameHashCode + " Tag Value HashCode: " + m_xmlAttribute[0].valueHashCode + " Attribute 1 HashCode: " + m_xmlAttribute[1].nameHashCode + " Value HashCode: " + m_xmlAttribute[1].valueHashCode); //for (int i = 0; i < attributeIndex + 1; i++) // Debug.Log("Tag [" + i + "] with HashCode: " + m_xmlAttribute[i].nameHashCode + " has value of [" + new string(m_htmlTag, m_xmlAttribute[i].valueStartIndex, m_xmlAttribute[i].valueLength) + "] Numerical Value: " + ConvertToFloat(m_htmlTag, m_xmlAttribute[i].valueStartIndex, m_xmlAttribute[i].valueLength, m_xmlAttribute[i].valueDecimalIndex)); // Special handling of the NoParsing tag if (tag_NoParsing && m_xmlAttribute[0].nameHashCode != 53822163) return false; else if (m_xmlAttribute[0].nameHashCode == 53822163) { tag_NoParsing = false; return true; } // Color <#FF00FF> if (m_htmlTag[0] == 35 && tagCharCount == 7) // if Tag begins with # and contains 7 characters. { m_htmlColor = HexCharsToColor(m_htmlTag, tagCharCount); m_colorStack.Add(m_htmlColor); return true; } // Color <#FF00FF00> with alpha else if (m_htmlTag[0] == 35 && tagCharCount == 9) // if Tag begins with # and contains 9 characters. { m_htmlColor = HexCharsToColor(m_htmlTag, tagCharCount); m_colorStack.Add(m_htmlColor); return true; } else { float value = 0; switch (m_xmlAttribute[0].nameHashCode) { case 98: // <b> m_style |= FontStyles.Bold; return true; case 427: // </b> if ((m_fontStyle & FontStyles.Bold) != FontStyles.Bold) m_style &= ~FontStyles.Bold; return true; case 105: // <i> m_style |= FontStyles.Italic; return true; case 434: // </i> m_style &= ~FontStyles.Italic; return true; case 115: // <s> m_style |= FontStyles.Strikethrough; return true; case 444: // </s> if ((m_fontStyle & FontStyles.Strikethrough) != FontStyles.Strikethrough) m_style &= ~FontStyles.Strikethrough; return true; case 117: // <u> m_style |= FontStyles.Underline; return true; case 446: // </u> if ((m_fontStyle & FontStyles.Underline) != FontStyles.Underline) m_style &= ~FontStyles.Underline; return true; case 6552: // <sub> float fontSize = m_currentFontSize; // Use of temporary variable as to not modify the current font size. fontSize *= m_currentFontAsset.fontInfo.SubSize > 0 ? m_currentFontAsset.fontInfo.SubSize : 1; // Subscript characters are half size. m_fontScale = (fontSize / m_currentFontAsset.fontInfo.PointSize * m_currentFontAsset.fontInfo.Scale * (m_isOrthographic ? 1 : 0.1f)); m_baselineOffset = m_currentFontAsset.fontInfo.SubscriptOffset * m_fontScale; m_style |= FontStyles.Subscript; return true; case 22673: // </sub> m_baselineOffset = 0; m_fontScale = (m_currentFontSize / m_currentFontAsset.fontInfo.PointSize * m_currentFontAsset.fontInfo.Scale * (m_isOrthographic ? 1 : 0.1f)); m_style &= ~FontStyles.Subscript; return true; case 6566: // <sup> fontSize = m_currentFontSize; // Use of temporary variable as to not modify the current font size. fontSize *= m_currentFontAsset.fontInfo.SubSize > 0 ? m_currentFontAsset.fontInfo.SubSize : 1; m_fontScale = (fontSize / m_currentFontAsset.fontInfo.PointSize * m_currentFontAsset.fontInfo.Scale * (m_isOrthographic ? 1 : 0.1f)); m_baselineOffset = m_currentFontAsset.fontInfo.SuperscriptOffset * m_fontScale; m_style |= FontStyles.Superscript; return true; case 22687: // </sup> m_baselineOffset = 0; m_fontScale = (m_currentFontSize / m_currentFontAsset.fontInfo.PointSize * m_currentFontAsset.fontInfo.Scale * (m_isOrthographic ? 1 : 0.1f)); m_style &= ~FontStyles.Superscript; return true; case 6380: // <pos=000.00px> <pos=0em> <pos=50%> value = ConvertToFloat(m_htmlTag, m_xmlAttribute[0].valueStartIndex, m_xmlAttribute[0].valueLength, m_xmlAttribute[0].valueDecimalIndex); if (value == -9999 || value == 0) return false; switch (tagUnits) { case TagUnits.Pixels: m_xAdvance = value; //m_isIgnoringAlignment = true; return true; case TagUnits.FontUnits: m_xAdvance = value * m_fontScale * m_fontAsset.fontInfo.TabWidth / m_fontAsset.tabSize; //m_isIgnoringAlignment = true; return true; case TagUnits.Percentage: m_xAdvance = m_marginWidth * value / 100; //m_isIgnoringAlignment = true; return true; } return false; case 22501: // </pos> m_isIgnoringAlignment = false; return true; case 16034505: // <voffset> value = ConvertToFloat(m_htmlTag, m_xmlAttribute[0].valueStartIndex, m_xmlAttribute[0].valueLength, m_xmlAttribute[0].valueDecimalIndex); if (value == -9999 || value == 0) return false; switch (tagUnits) { case TagUnits.Pixels: m_baselineOffset = value; return true; case TagUnits.FontUnits: m_baselineOffset = value * m_fontScale * m_fontAsset.fontInfo.Ascender; return true; case TagUnits.Percentage: //m_baselineOffset = m_marginHeight * val / 100; return false; } return false; case 54741026: // </voffset> m_baselineOffset = 0; return true; case 43991: // <page> // This tag only works when Overflow - Page mode is used. if (m_overflowMode == TextOverflowModes.Page) { m_xAdvance = 0 + tag_LineIndent + tag_Indent; //m_textInfo.lineInfo[m_lineNumber].marginLeft = m_xAdvance; m_lineOffset = 0; m_pageNumber += 1; m_isNewPage = true; } return true; case 43969: // <nobr> m_isNonBreakingSpace = true; return true; case 156816: // </nobr> m_isNonBreakingSpace = false; return true; case 45545: // <size=> value = ConvertToFloat(m_htmlTag, m_xmlAttribute[0].valueStartIndex, m_xmlAttribute[0].valueLength, m_xmlAttribute[0].valueDecimalIndex); if (value == -9999 || value == 0) return false; switch (tagUnits) { case TagUnits.Pixels: if (m_htmlTag[5] == 43) // <size=+00> { m_currentFontSize = m_fontSize + value; m_sizeStack.Add(m_currentFontSize); m_fontScale = (m_currentFontSize / m_currentFontAsset.fontInfo.PointSize * m_currentFontAsset.fontInfo.Scale * (m_isOrthographic ? 1 : 0.1f)); return true; } else if (m_htmlTag[5] == 45) // <size=-00> { m_currentFontSize = m_fontSize + value; m_sizeStack.Add(m_currentFontSize); m_fontScale = (m_currentFontSize / m_currentFontAsset.fontInfo.PointSize * m_currentFontAsset.fontInfo.Scale * (m_isOrthographic ? 1 : 0.1f)); return true; } else // <size=00.0> { m_currentFontSize = value; m_sizeStack.Add(m_currentFontSize); m_fontScale = (m_currentFontSize / m_currentFontAsset.fontInfo.PointSize * m_currentFontAsset.fontInfo.Scale * (m_isOrthographic ? 1 : 0.1f)); return true; } case TagUnits.FontUnits: m_currentFontSize = m_fontSize * value; m_sizeStack.Add(m_currentFontSize); m_fontScale = (m_currentFontSize / m_currentFontAsset.fontInfo.PointSize * m_currentFontAsset.fontInfo.Scale * (m_isOrthographic ? 1 : 0.1f)); return true; case TagUnits.Percentage: m_currentFontSize = m_fontSize * value / 100; m_sizeStack.Add(m_currentFontSize); m_fontScale = (m_currentFontSize / m_currentFontAsset.fontInfo.PointSize * m_currentFontAsset.fontInfo.Scale * (m_isOrthographic ? 1 : 0.1f)); return true; } return false; case 158392: // </size> m_currentFontSize = m_sizeStack.Remove(); m_fontScale = (m_currentFontSize / m_currentFontAsset.fontInfo.PointSize * m_currentFontAsset.fontInfo.Scale * (m_isOrthographic ? 1 : 0.1f)); return true; case 41311: // <font=xx> //Debug.Log("Font name: \"" + new string(m_htmlTag, attribute_1.startIndex, attribute_1.length) + "\" HashCode: " + attribute_1.hashCode + " Material Name: \"" + new string(m_htmlTag, attribute_2.startIndex, attribute_2.length) + "\" Hashcode: " + attribute_2.hashCode); int fontHashCode = m_xmlAttribute[0].valueHashCode; int materialHashCode = m_xmlAttribute[1].valueHashCode; TMP_FontAsset tempFont; Material tempMaterial; // HANDLE NEW FONT ASSET if (m_fontAsset_Dict.TryGetValue(fontHashCode, out tempFont)) { if (tempFont != m_currentFontAsset) { //Debug.Log("Assigning Font Asset: " + tempFont.name); m_currentFontAsset = m_fontAsset_Dict[fontHashCode]; //m_isRecalculateScaleRequired = true; } } else { // Load new font asset tempFont = Resources.Load("Fonts & Materials/" + new string(m_htmlTag, m_xmlAttribute[0].valueStartIndex, m_xmlAttribute[0].valueLength), typeof(TMP_FontAsset)) as TMP_FontAsset; if (tempFont != null) { //Debug.Log("Loading and Assigning Font Asset: " + tempFont.name); m_fontAsset_Dict.Add(fontHashCode, tempFont); m_currentFontAsset = tempFont; //m_isRecalculateScaleRequired = true; } else return false; } // HANDLE NEW MATERIAL if (materialHashCode == 0) { if (!m_fontMaterial_Dict.TryGetValue(m_currentFontAsset.materialHashCode, out tempMaterial)) m_fontMaterial_Dict.Add(m_currentFontAsset.materialHashCode, m_currentFontAsset.material); if (m_currentMaterial != m_currentFontAsset.material) { //Debug.Log("Assigning Default Font Asset Material: " + m_currentFontAsset.material.name); m_currentMaterial = m_currentFontAsset.material; } } else if (m_fontMaterial_Dict.TryGetValue(materialHashCode, out tempMaterial)) { if (tempMaterial != m_currentMaterial) { //Debug.Log("Assigning Material: " + tempMaterial.name); m_currentMaterial = tempMaterial; } } else { // Load new material tempMaterial = Resources.Load("Fonts & Materials/" + new string(m_htmlTag, m_xmlAttribute[1].valueStartIndex, m_xmlAttribute[1].valueLength), typeof(Material)) as Material; if (tempMaterial != null) { //Debug.Log("Loading and Assigning Material: " + tempMaterial.name); m_fontMaterial_Dict.Add(materialHashCode, tempMaterial); m_currentMaterial = tempMaterial; } else return false; } return true; case 320078: // <space=000.00> value = ConvertToFloat(m_htmlTag, m_xmlAttribute[0].valueStartIndex, m_xmlAttribute[0].valueLength, m_xmlAttribute[0].valueDecimalIndex); if (value == -9999 || value == 0) return false; switch (tagUnits) { case TagUnits.Pixels: m_xAdvance += value; return true; case TagUnits.FontUnits: m_xAdvance += value * m_fontScale * m_fontAsset.fontInfo.TabWidth / m_fontAsset.tabSize; return true; case TagUnits.Percentage: // Not applicable return false; } return false; case 276254: // <alpha=#FF> if (m_xmlAttribute[0].valueLength != 3) return false; m_htmlColor.a = (byte)(HexToInt(m_htmlTag[7]) * 16 + HexToInt(m_htmlTag[8])); return true; case 1750458: // <a name=" "> return true; case 426: // </a> return true; case 43066: // <link="name"> if (m_isParsingText) { tag_LinkInfo.textComponent = this; tag_LinkInfo.hashCode = m_xmlAttribute[0].valueHashCode; tag_LinkInfo.linkTextfirstCharacterIndex = m_characterCount; tag_LinkInfo.linkIdFirstCharacterIndex = startIndex + m_xmlAttribute[0].valueStartIndex; tag_LinkInfo.linkIdLength = m_xmlAttribute[0].valueLength; } return true; case 155913: // </link> if (m_isParsingText) { tag_LinkInfo.linkTextLength = m_characterCount - tag_LinkInfo.linkTextfirstCharacterIndex; int size = m_textInfo.linkInfo.Length; if (m_textInfo.linkCount + 1 > size) TMP_TextInfo.Resize(ref m_textInfo.linkInfo, size + 1); m_textInfo.linkInfo[m_textInfo.linkCount] = tag_LinkInfo; m_textInfo.linkCount += 1; } return true; case 275917: // <align=> switch (m_xmlAttribute[0].valueHashCode) { case 3774683: // <align=left> m_lineJustification = TextAlignmentOptions.Left; return true; case 136703040: // <align=right> m_lineJustification = TextAlignmentOptions.Right; return true; case -458210101: // <align=center> m_lineJustification = TextAlignmentOptions.Center; return true; case -523808257: // <align=justified> m_lineJustification = TextAlignmentOptions.Justified; return true; } return false; case 1065846: // </align> m_lineJustification = m_textAlignment; return true; case 327550: // <width=xx> value = ConvertToFloat(m_htmlTag, m_xmlAttribute[0].valueStartIndex, m_xmlAttribute[0].valueLength, m_xmlAttribute[0].valueDecimalIndex); if (value == -9999 || value == 0) return false; switch (tagUnits) { case TagUnits.Pixels: m_width = value; break; case TagUnits.FontUnits: return false; //break; case TagUnits.Percentage: m_width = m_marginWidth * value / 100; break; } return true; case 1117479: // </width> m_width = -1; return true; case 322689: // <style="name"> TMP_Style style = TMP_StyleSheet.Instance.GetStyle(m_xmlAttribute[0].valueHashCode); if (style == null) return false; m_styleStack.Add(style.hashCode); //// Parse Style Macro for (int i = 0; i < style.styleOpeningTagArray.Length; i++) { if (style.styleOpeningTagArray[i] == 60) ValidateHtmlTag(style.styleOpeningTagArray, i + 1, out i); } return true; case 1112618: // </style> style = TMP_StyleSheet.Instance.GetStyle(m_xmlAttribute[0].valueHashCode); if (style == null) { // Get style from the Style Stack int styleHashCode = m_styleStack.Remove(); style = TMP_StyleSheet.Instance.GetStyle(styleHashCode); } if (style == null) return false; //// Parse Style Macro for (int i = 0; i < style.styleClosingTagArray.Length; i++) { if (style.styleClosingTagArray[i] == 60) ValidateHtmlTag(style.styleClosingTagArray, i + 1, out i); } return true; case 281955: // <color=#FF00FF> or <color=#FF00FF00> // <color=#FF00FF> 3 Hex pairs if (m_htmlTag[6] == 35 && tagCharCount == 13) { m_htmlColor = HexCharsToColor(m_htmlTag, tagCharCount); m_colorStack.Add(m_htmlColor); return true; } // <color=#FF00FF00> 4 Hex pairs else if (m_htmlTag[6] == 35 && tagCharCount == 15) { m_htmlColor = HexCharsToColor(m_htmlTag, tagCharCount); m_colorStack.Add(m_htmlColor); return true; } // <color=name> switch (m_xmlAttribute[0].valueHashCode) { case 125395: // <color=red> m_htmlColor = Color.red; m_colorStack.Add(m_htmlColor); return true; case 3573310: // <color=blue> m_htmlColor = Color.blue; m_colorStack.Add(m_htmlColor); return true; case 117905991: // <color=black> m_htmlColor = Color.black; m_colorStack.Add(m_htmlColor); return true; case 121463835: // <color=green> m_htmlColor = Color.green; m_colorStack.Add(m_htmlColor); return true; case 140357351: // <color=white> m_htmlColor = Color.white; m_colorStack.Add(m_htmlColor); return true; case 26556144: // <color=orange> m_htmlColor = new Color32(255, 128, 0, 255); m_colorStack.Add(m_htmlColor); return true; case -36881330: // <color=purple> m_htmlColor = new Color32(160, 32, 240, 255); m_colorStack.Add(m_htmlColor); return true; case 554054276: // <color=yellow> m_htmlColor = Color.yellow; m_colorStack.Add(m_htmlColor); return true; } return false; case 1983971: // <cspace=xx.x> value = ConvertToFloat(m_htmlTag, m_xmlAttribute[0].valueStartIndex, m_xmlAttribute[0].valueLength, m_xmlAttribute[0].valueDecimalIndex); if (value == -9999 || value == 0) return false; switch (tagUnits) { case TagUnits.Pixels: m_cSpacing = value; break; case TagUnits.FontUnits: m_cSpacing = value; m_cSpacing *= m_fontScale * m_fontAsset.fontInfo.TabWidth / m_fontAsset.tabSize; break; case TagUnits.Percentage: return false; } return true; case 7513474: // </cspace> m_cSpacing = 0; return true; case 2152041: // <mspace=xx.x> value = ConvertToFloat(m_htmlTag, m_xmlAttribute[0].valueStartIndex, m_xmlAttribute[0].valueLength, m_xmlAttribute[0].valueDecimalIndex); if (value == -9999 || value == 0) return false; switch (tagUnits) { case TagUnits.Pixels: m_monoSpacing = value; break; case TagUnits.FontUnits: m_monoSpacing = value; m_monoSpacing *= m_fontScale * m_fontAsset.fontInfo.TabWidth / m_fontAsset.tabSize; break; case TagUnits.Percentage: return false; } return true; case 7681544: // </mspace> m_monoSpacing = 0; return true; case 280416: // <class="name"> return false; case 1071884: // </color> m_htmlColor = m_colorStack.Remove(); return true; case 2068980: // <indent=10px> <indent=10em> <indent=50%> value = ConvertToFloat(m_htmlTag, m_xmlAttribute[0].valueStartIndex, m_xmlAttribute[0].valueLength, m_xmlAttribute[0].valueDecimalIndex); if (value == -9999 || value == 0) return false; switch (tagUnits) { case TagUnits.Pixels: tag_Indent = value; break; case TagUnits.FontUnits: tag_Indent = value; tag_Indent *= m_fontScale * m_fontAsset.fontInfo.TabWidth / m_fontAsset.tabSize; break; case TagUnits.Percentage: tag_Indent = m_marginWidth * value / 100; break; } m_indentStack.Add(tag_Indent); m_xAdvance = tag_Indent; return true; case 7598483: // </indent> tag_Indent = m_indentStack.Remove(); //m_xAdvance = tag_Indent; return true; case 1109386397: // <line-indent> value = ConvertToFloat(m_htmlTag, m_xmlAttribute[0].valueStartIndex, m_xmlAttribute[0].valueLength, m_xmlAttribute[0].valueDecimalIndex); if (value == -9999 || value == 0) return false; switch (tagUnits) { case TagUnits.Pixels: tag_LineIndent = value; break; case TagUnits.FontUnits: tag_LineIndent = value; tag_LineIndent *= m_fontScale * m_fontAsset.fontInfo.TabWidth / m_fontAsset.tabSize; break; case TagUnits.Percentage: tag_LineIndent = m_marginWidth * value / 100; break; } m_xAdvance += tag_LineIndent; return true; case -445537194: // </line-indent> tag_LineIndent = 0; return true; case 2246877: // <sprite=x> if (m_inlineGraphics == null) m_inlineGraphics = GetComponent<InlineGraphicManager>() ?? gameObject.AddComponent<InlineGraphicManager>(); if (char.IsDigit(m_htmlTag[7])) { int index = (int)ConvertToFloat(m_htmlTag, m_xmlAttribute[0].valueStartIndex, m_xmlAttribute[0].valueLength, m_xmlAttribute[0].valueDecimalIndex); m_spriteIndex = m_inlineGraphics.GetSpriteIndexByIndex(index); //Debug.Log(m_xmlAttribute[0].valueStartIndex + " " + m_xmlAttribute[0].valueLength + " " + m_xmlAttribute[1].valueStartIndex + " " + m_xmlAttribute[1].valueLength); if (m_spriteIndex == -1) return false; } else { // Get sprite index by looking it up by name. m_spriteIndex = m_inlineGraphics.GetSpriteIndexByHashCode(m_xmlAttribute[0].valueHashCode); if (m_spriteIndex == -1) return false; //Debug.Log("Sprite name is: \"" + new string(m_htmlTag, attribute_1.startIndex, attribute_1.length) + "\" with HashCode: " + attribute_1.hashCode); } m_spriteColor = s_colorWhite; m_tintSprite = false; // Handle Tint Attribute if (m_xmlAttribute[1].nameHashCode == 45819) m_tintSprite = ConvertToFloat(m_htmlTag, m_xmlAttribute[1].valueStartIndex, m_xmlAttribute[1].valueLength, m_xmlAttribute[1].valueDecimalIndex) != 0; else if (m_xmlAttribute[2].nameHashCode == 45819) m_tintSprite = ConvertToFloat(m_htmlTag, m_xmlAttribute[2].valueStartIndex, m_xmlAttribute[2].valueLength, m_xmlAttribute[2].valueDecimalIndex) != 0; // Handle Color Attribute if (m_xmlAttribute[1].nameHashCode == 281955) m_spriteColor = HexCharsToColor(m_htmlTag, m_xmlAttribute[1].valueStartIndex, m_xmlAttribute[1].valueLength); else if (m_xmlAttribute[2].nameHashCode == 281955) m_spriteColor = HexCharsToColor(m_htmlTag, m_xmlAttribute[2].valueStartIndex, m_xmlAttribute[2].valueLength); m_textElementType = TMP_TextElementType.Sprite; return true; case 730022849: // <lowercase> m_style |= FontStyles.LowerCase; return true; case -1668324918: // </lowercase> m_style &= ~FontStyles.LowerCase; return true; case 13526026: // <allcaps> case 781906058: // <uppercase> m_style |= FontStyles.UpperCase; return true; case 52232547: // </allcaps> case -1616441709: // </uppercase> m_style &= ~FontStyles.UpperCase; return true; case 766244328: // <smallcaps> m_style |= FontStyles.SmallCaps; return true; case -1632103439: // </smallcaps> m_style &= ~FontStyles.SmallCaps; return true; case 2109854: // <margin=00.0> <margin=00em> <margin=50%> value = ConvertToFloat(m_htmlTag, m_xmlAttribute[0].valueStartIndex, m_xmlAttribute[0].valueLength, m_xmlAttribute[0].valueDecimalIndex); // px if (value == -9999 || value == 0) return false; m_marginLeft = value; switch (tagUnits) { case TagUnits.Pixels: // Default behavior break; case TagUnits.FontUnits: m_marginLeft *= m_fontScale * m_fontAsset.fontInfo.TabWidth / m_fontAsset.tabSize; break; case TagUnits.Percentage: m_marginLeft = (m_marginWidth - (m_width != -1 ? m_width : 0)) * m_marginLeft / 100; break; } m_marginLeft = m_marginLeft >= 0 ? m_marginLeft : 0; m_marginRight = m_marginLeft; return true; case 7639357: // </margin> m_marginLeft = 0; m_marginRight = 0; return true; case 1100728678: // <margin-left=xx.x> value = ConvertToFloat(m_htmlTag, m_xmlAttribute[0].valueStartIndex, m_xmlAttribute[0].valueLength, m_xmlAttribute[0].valueDecimalIndex); // px if (value == -9999 || value == 0) return false; m_marginLeft = value; switch (tagUnits) { case TagUnits.Pixels: // Default behavior break; case TagUnits.FontUnits: m_marginLeft *= m_fontScale * m_fontAsset.fontInfo.TabWidth / m_fontAsset.tabSize; break; case TagUnits.Percentage: m_marginLeft = (m_marginWidth - (m_width != -1 ? m_width : 0)) * m_marginLeft / 100; break; } m_marginLeft = m_marginLeft >= 0 ? m_marginLeft : 0; return true; case -884817987: // <margin-right=xx.x> value = ConvertToFloat(m_htmlTag, m_xmlAttribute[0].valueStartIndex, m_xmlAttribute[0].valueLength, m_xmlAttribute[0].valueDecimalIndex); // px if (value == -9999 || value == 0) return false; m_marginRight = value; switch (tagUnits) { case TagUnits.Pixels: // Default behavior break; case TagUnits.FontUnits: m_marginRight *= m_fontScale * m_fontAsset.fontInfo.TabWidth / m_fontAsset.tabSize; break; case TagUnits.Percentage: m_marginRight = (m_marginWidth - (m_width != -1 ? m_width : 0)) * m_marginRight / 100; break; } m_marginRight = m_marginRight >= 0 ? m_marginRight : 0; return true; case 1109349752: // <line-height=xx.x> value = ConvertToFloat(m_htmlTag, m_xmlAttribute[0].valueStartIndex, m_xmlAttribute[0].valueLength, m_xmlAttribute[0].valueDecimalIndex); if (value == -9999 || value == 0) return false; m_lineHeight = value; switch (tagUnits) { case TagUnits.Pixels: //m_lineHeight *= m_isOrthographic ? 1 : 0.1f; break; case TagUnits.FontUnits: m_lineHeight *= m_fontAsset.fontInfo.LineHeight * m_fontScale; break; case TagUnits.Percentage: m_lineHeight = m_fontAsset.fontInfo.LineHeight * m_lineHeight / 100 * m_fontScale; break; } return true; case -445573839: // </line-height> m_lineHeight = 0; return true; case 15115642: // <noparse> tag_NoParsing = true; return true; case 1913798: // <action> // TODO return true; case 7443301: // </action> // TODO return true; } } return false; }