bool RenderSVGTransformableContainer::calculateLocalTransform()
{
    SVGStyledTransformableElement* element = static_cast<SVGStyledTransformableElement*>(node());

    // If we're either the renderer for a <use> element, or for any <g> element inside the shadow
    // tree, that was created during the use/symbol/svg expansion in SVGUseElement. These containers
    // need to respect the translations induced by their corresponding use elements x/y attributes.
    SVGUseElement* useElement = 0;
    if (element->hasTagName(SVGNames::useTag))
        useElement = static_cast<SVGUseElement*>(element);
    else if (element->isInShadowTree() && element->hasTagName(SVGNames::gTag)) {
        SVGElement* correspondingElement = element->correspondingElement();
        if (correspondingElement && correspondingElement->hasTagName(SVGNames::useTag))
            useElement = static_cast<SVGUseElement*>(correspondingElement);
    }

    if (useElement) {
        SVGLengthContext lengthContext(useElement);
        FloatSize translation(useElement->x().value(lengthContext), useElement->y().value(lengthContext));
        if (translation != m_lastTranslation)
            m_needsTransformUpdate = true;
        m_lastTranslation = translation;
    }

    m_didTransformToRootUpdate = m_needsTransformUpdate || SVGRenderSupport::transformToRootChanged(parent());
    if (!m_needsTransformUpdate)
        return false;

    m_localTransform = element->animatedLocalTransform();
    m_localTransform.translate(m_lastTranslation.width(), m_lastTranslation.height());
    m_needsTransformUpdate = false;
    return true;
}
Esempio n. 2
0
bool RenderSVGTransformableContainer::calculateLocalTransform()
{
    SVGStyledTransformableElement* element = static_cast<SVGStyledTransformableElement*>(node());

    bool needsUpdate = m_needsTransformUpdate;
    if (needsUpdate) {
        m_localTransform = element->animatedLocalTransform();
        m_needsTransformUpdate = false;
    }

    if (!element->hasTagName(SVGNames::gTag) || !static_cast<SVGGElement*>(element)->isShadowTreeContainerElement())
        return needsUpdate;

    FloatSize translation = static_cast<SVGShadowTreeContainerElement*>(element)->containerTranslation();
    if (translation.width() == 0 && translation.height() == 0)
        return needsUpdate;

    // FIXME: Could optimize this case for use to avoid refetching the animatedLocalTransform() here, if only the containerTranslation() changed.
    if (!needsUpdate)
        m_localTransform = element->animatedLocalTransform();

    m_localTransform.translate(translation.width(), translation.height());
    return true;
}