1 /* 2 * Copyright (C) 2004, 2005, 2007 Nikolas Zimmermann <zimmermann (at) kde.org> 3 * Copyright (C) 2004, 2005, 2006 Rob Buis <buis (at) kde.org> 4 * Copyright (C) 2005 Oliver Hunt <oliver (at) nerget.com> 5 * 6 * This library is free software; you can redistribute it and/or 7 * modify it under the terms of the GNU Library General Public 8 * License as published by the Free Software Foundation; either 9 * version 2 of the License, or (at your option) any later version. 10 * 11 * This library is distributed in the hope that it will be useful, 12 * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 14 * Library General Public License for more details. 15 * 16 * You should have received a copy of the GNU Library General Public License 17 * along with this library; see the file COPYING.LIB. If not, write to 18 * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, 19 * Boston, MA 02110-1301, USA. 20 */ 21 22 #include "config.h" 23 24 #include "core/svg/SVGFELightElement.h" 25 26 #include "core/SVGNames.h" 27 #include "core/dom/ElementTraversal.h" 28 #include "core/rendering/RenderObject.h" 29 #include "core/rendering/svg/RenderSVGResource.h" 30 #include "core/svg/SVGFEDiffuseLightingElement.h" 31 #include "core/svg/SVGFESpecularLightingElement.h" 32 33 namespace blink { 34 35 SVGFELightElement::SVGFELightElement(const QualifiedName& tagName, Document& document) 36 : SVGElement(tagName, document) 37 , m_azimuth(SVGAnimatedNumber::create(this, SVGNames::azimuthAttr, SVGNumber::create())) 38 , m_elevation(SVGAnimatedNumber::create(this, SVGNames::elevationAttr, SVGNumber::create())) 39 , m_x(SVGAnimatedNumber::create(this, SVGNames::xAttr, SVGNumber::create())) 40 , m_y(SVGAnimatedNumber::create(this, SVGNames::yAttr, SVGNumber::create())) 41 , m_z(SVGAnimatedNumber::create(this, SVGNames::zAttr, SVGNumber::create())) 42 , m_pointsAtX(SVGAnimatedNumber::create(this, SVGNames::pointsAtXAttr, SVGNumber::create())) 43 , m_pointsAtY(SVGAnimatedNumber::create(this, SVGNames::pointsAtYAttr, SVGNumber::create())) 44 , m_pointsAtZ(SVGAnimatedNumber::create(this, SVGNames::pointsAtZAttr, SVGNumber::create())) 45 , m_specularExponent(SVGAnimatedNumber::create(this, SVGNames::specularExponentAttr, SVGNumber::create(1))) 46 , m_limitingConeAngle(SVGAnimatedNumber::create(this, SVGNames::limitingConeAngleAttr, SVGNumber::create())) 47 { 48 addToPropertyMap(m_azimuth); 49 addToPropertyMap(m_elevation); 50 addToPropertyMap(m_x); 51 addToPropertyMap(m_y); 52 addToPropertyMap(m_z); 53 addToPropertyMap(m_pointsAtX); 54 addToPropertyMap(m_pointsAtY); 55 addToPropertyMap(m_pointsAtZ); 56 addToPropertyMap(m_specularExponent); 57 addToPropertyMap(m_limitingConeAngle); 58 } 59 60 SVGFELightElement* SVGFELightElement::findLightElement(const SVGElement& svgElement) 61 { 62 return Traversal<SVGFELightElement>::firstChild(svgElement); 63 } 64 65 FloatPoint3D SVGFELightElement::position() const 66 { 67 return FloatPoint3D(x()->currentValue()->value(), y()->currentValue()->value(), z()->currentValue()->value()); 68 } 69 70 FloatPoint3D SVGFELightElement::pointsAt() const 71 { 72 return FloatPoint3D(pointsAtX()->currentValue()->value(), pointsAtY()->currentValue()->value(), pointsAtZ()->currentValue()->value()); 73 } 74 75 bool SVGFELightElement::isSupportedAttribute(const QualifiedName& attrName) 76 { 77 DEFINE_STATIC_LOCAL(HashSet<QualifiedName>, supportedAttributes, ()); 78 if (supportedAttributes.isEmpty()) { 79 supportedAttributes.add(SVGNames::azimuthAttr); 80 supportedAttributes.add(SVGNames::elevationAttr); 81 supportedAttributes.add(SVGNames::xAttr); 82 supportedAttributes.add(SVGNames::yAttr); 83 supportedAttributes.add(SVGNames::zAttr); 84 supportedAttributes.add(SVGNames::pointsAtXAttr); 85 supportedAttributes.add(SVGNames::pointsAtYAttr); 86 supportedAttributes.add(SVGNames::pointsAtZAttr); 87 supportedAttributes.add(SVGNames::specularExponentAttr); 88 supportedAttributes.add(SVGNames::limitingConeAngleAttr); 89 } 90 return supportedAttributes.contains<SVGAttributeHashTranslator>(attrName); 91 } 92 93 void SVGFELightElement::parseAttribute(const QualifiedName& name, const AtomicString& value) 94 { 95 if (!isSupportedAttribute(name)) { 96 SVGElement::parseAttribute(name, value); 97 return; 98 } 99 100 SVGParsingError parseError = NoError; 101 102 if (name == SVGNames::azimuthAttr) 103 m_azimuth->setBaseValueAsString(value, parseError); 104 else if (name == SVGNames::elevationAttr) 105 m_elevation->setBaseValueAsString(value, parseError); 106 else if (name == SVGNames::xAttr) 107 m_x->setBaseValueAsString(value, parseError); 108 else if (name == SVGNames::yAttr) 109 m_y->setBaseValueAsString(value, parseError); 110 else if (name == SVGNames::zAttr) 111 m_z->setBaseValueAsString(value, parseError); 112 else if (name == SVGNames::pointsAtXAttr) 113 m_pointsAtX->setBaseValueAsString(value, parseError); 114 else if (name == SVGNames::pointsAtYAttr) 115 m_pointsAtY->setBaseValueAsString(value, parseError); 116 else if (name == SVGNames::pointsAtZAttr) 117 m_pointsAtZ->setBaseValueAsString(value, parseError); 118 else if (name == SVGNames::specularExponentAttr) 119 m_specularExponent->setBaseValueAsString(value, parseError); 120 else if (name == SVGNames::limitingConeAngleAttr) 121 m_limitingConeAngle->setBaseValueAsString(value, parseError); 122 else 123 ASSERT_NOT_REACHED(); 124 125 reportAttributeParsingError(parseError, name, value); 126 } 127 128 void SVGFELightElement::svgAttributeChanged(const QualifiedName& attrName) 129 { 130 if (!isSupportedAttribute(attrName)) { 131 SVGElement::svgAttributeChanged(attrName); 132 return; 133 } 134 135 SVGElement::InvalidationGuard invalidationGuard(this); 136 137 if (attrName == SVGNames::azimuthAttr 138 || attrName == SVGNames::elevationAttr 139 || attrName == SVGNames::xAttr 140 || attrName == SVGNames::yAttr 141 || attrName == SVGNames::zAttr 142 || attrName == SVGNames::pointsAtXAttr 143 || attrName == SVGNames::pointsAtYAttr 144 || attrName == SVGNames::pointsAtZAttr 145 || attrName == SVGNames::specularExponentAttr 146 || attrName == SVGNames::limitingConeAngleAttr) { 147 ContainerNode* parent = parentNode(); 148 if (!parent) 149 return; 150 151 RenderObject* renderer = parent->renderer(); 152 if (!renderer || !renderer->isSVGResourceFilterPrimitive()) 153 return; 154 155 if (isSVGFEDiffuseLightingElement(*parent)) { 156 toSVGFEDiffuseLightingElement(*parent).lightElementAttributeChanged(this, attrName); 157 return; 158 } 159 if (isSVGFESpecularLightingElement(*parent)) { 160 toSVGFESpecularLightingElement(*parent).lightElementAttributeChanged(this, attrName); 161 return; 162 } 163 } 164 165 ASSERT_NOT_REACHED(); 166 } 167 168 void SVGFELightElement::childrenChanged(const ChildrenChange& change) 169 { 170 SVGElement::childrenChanged(change); 171 172 if (!change.byParser) { 173 if (ContainerNode* parent = parentNode()) { 174 RenderObject* renderer = parent->renderer(); 175 if (renderer && renderer->isSVGResourceFilterPrimitive()) 176 RenderSVGResource::markForLayoutAndParentResourceInvalidation(renderer); 177 } 178 } 179 } 180 181 } 182