Exemple #1
0
void SVGFontElement::ensureGlyphCache()
{
    if (m_isGlyphCacheValid)
        return;

    KerningPairVector horizontalKerningPairs;
    KerningPairVector verticalKerningPairs;

    SVGMissingGlyphElement* firstMissingGlyphElement = 0;
    Vector<String> ligatures;
    for (SVGElement* element = Traversal<SVGElement>::firstChild(*this); element; element = Traversal<SVGElement>::nextSibling(*element)) {
        if (isSVGGlyphElement(*element)) {
            SVGGlyphElement& glyph = toSVGGlyphElement(*element);
            AtomicString unicode = glyph.fastGetAttribute(SVGNames::unicodeAttr);
            AtomicString glyphId = glyph.getIdAttribute();
            if (glyphId.isEmpty() && unicode.isEmpty())
                continue;

            m_glyphMap.addGlyph(glyphId, unicode, glyph.buildGlyphIdentifier());

            // Register ligatures, if needed, don't mix up with surrogate pairs though!
            if (unicode.length() > 1 && !U16_IS_SURROGATE(unicode[0]))
                ligatures.append(unicode.string());
        } else if (isSVGHKernElement(*element)) {
            toSVGHKernElement(*element).buildHorizontalKerningPair(horizontalKerningPairs);
        } else if (isSVGVKernElement(*element)) {
            toSVGVKernElement(*element).buildVerticalKerningPair(verticalKerningPairs);
        } else if (isSVGMissingGlyphElement(*element) && !firstMissingGlyphElement) {
            firstMissingGlyphElement = toSVGMissingGlyphElement(element);
        }
    }

    // Build the kerning tables.
    buildKerningTable(horizontalKerningPairs, m_horizontalKerningTable);
    buildKerningTable(verticalKerningPairs, m_verticalKerningTable);

    // The glyph-name->glyph-id map won't be needed/used after having built the kerning table(s).
    m_glyphMap.dropNamedGlyphMap();

    // Register each character of each ligature, if needed.
    if (!ligatures.isEmpty())
        registerLigaturesInGlyphCache(ligatures);

    // Register missing-glyph element, if present.
    if (firstMissingGlyphElement) {
        SVGGlyph svgGlyph = SVGGlyphElement::buildGenericGlyphIdentifier(firstMissingGlyphElement);
        m_glyphMap.appendToGlyphTable(svgGlyph);
        m_missingGlyph = svgGlyph.tableEntry;
        ASSERT(m_missingGlyph > 0);
    }

    m_isGlyphCacheValid = true;
}
void SVGFontElement::ensureGlyphCache()
{
    if (m_isGlyphCacheValid)
        return;

    const SVGMissingGlyphElement* firstMissingGlyphElement = nullptr;
    Vector<String> ligatures;
    for (auto& child : childrenOfType<SVGElement>(*this)) {
        if (isSVGGlyphElement(child)) {
            SVGGlyphElement& glyph = toSVGGlyphElement(child);
            AtomicString unicode = glyph.fastGetAttribute(SVGNames::unicodeAttr);
            AtomicString glyphId = glyph.getIdAttribute();
            if (glyphId.isEmpty() && unicode.isEmpty())
                continue;

            m_glyphMap.addGlyph(glyphId, unicode, glyph.buildGlyphIdentifier());

            // Register ligatures, if needed, don't mix up with surrogate pairs though!
            if (unicode.length() > 1 && !U16_IS_SURROGATE(unicode[0]))
                ligatures.append(unicode.string());
        } else if (isSVGHKernElement(child)) {
            SVGHKernElement& hkern = toSVGHKernElement(child);
            hkern.buildHorizontalKerningPair(m_horizontalKerningMap);
        } else if (isSVGVKernElement(child)) {
            SVGVKernElement& vkern = toSVGVKernElement(child);
            vkern.buildVerticalKerningPair(m_verticalKerningMap);
        } else if (isSVGMissingGlyphElement(child) && !firstMissingGlyphElement)
            firstMissingGlyphElement = &toSVGMissingGlyphElement(child);
    }

    // Register each character of each ligature, if needed.
    if (!ligatures.isEmpty())
        registerLigaturesInGlyphCache(ligatures);

    // Register missing-glyph element, if present.
    if (firstMissingGlyphElement) {
        SVGGlyph svgGlyph = SVGGlyphElement::buildGenericGlyphIdentifier(firstMissingGlyphElement);
        m_glyphMap.appendToGlyphTable(svgGlyph);
        m_missingGlyph = svgGlyph.tableEntry;
        ASSERT(m_missingGlyph > 0);
    }

    m_isGlyphCacheValid = true;
}
void SVGFontElement::ensureGlyphCache()
{
    if (m_isGlyphCacheValid)
        return;

    SVGMissingGlyphElement* firstMissingGlyphElement = 0;
    Vector<String> ligatures;
    for (Node* child = firstChild(); child; child = child->nextSibling()) {
        if (child->hasTagName(SVGNames::glyphTag)) {
            SVGGlyphElement* glyph = toSVGGlyphElement(child);
            AtomicString unicode = glyph->fastGetAttribute(SVGNames::unicodeAttr);
            AtomicString glyphId = glyph->getIdAttribute();
            if (glyphId.isEmpty() && unicode.isEmpty())
                continue;

            m_glyphMap.addGlyph(glyphId, unicode, glyph->buildGlyphIdentifier());

            // Register ligatures, if needed, don't mix up with surrogate pairs though!
            if (unicode.length() > 1 && !U16_IS_SURROGATE(unicode[0]))
                ligatures.append(unicode.string());
        } else if (child->hasTagName(SVGNames::hkernTag)) {
            toSVGHKernElement(child)->buildHorizontalKerningPair(m_horizontalKerningPairs);
        } else if (child->hasTagName(SVGNames::vkernTag)) {
            toSVGVKernElement(child)->buildVerticalKerningPair(m_verticalKerningPairs);
        } else if (child->hasTagName(SVGNames::missing_glyphTag) && !firstMissingGlyphElement) {
            firstMissingGlyphElement = toSVGMissingGlyphElement(child);
        }
    }

    // Register each character of each ligature, if needed.
    if (!ligatures.isEmpty())
        registerLigaturesInGlyphCache(ligatures);

    // Register missing-glyph element, if present.
    if (firstMissingGlyphElement) {
        SVGGlyph svgGlyph = SVGGlyphElement::buildGenericGlyphIdentifier(firstMissingGlyphElement);
        m_glyphMap.appendToGlyphTable(svgGlyph);
        m_missingGlyph = svgGlyph.tableEntry;
        ASSERT(m_missingGlyph > 0);
    }

    m_isGlyphCacheValid = true;
}