• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2004, 2005 Nikolas Zimmermann <zimmermann@kde.org>
3  * Copyright (C) 2004, 2005, 2006, 2007 Rob Buis <buis@kde.org>
4  * Copyright (C) Research In Motion Limited 2010-2011. All rights reserved.
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 #if ENABLE(SVG)
25 #include "SVGPaint.h"
26 
27 #include "SVGException.h"
28 #include "SVGURIReference.h"
29 #include <wtf/text/StringConcatenate.h>
30 
31 namespace WebCore {
32 
colorTypeForPaintType(const SVGPaint::SVGPaintType & paintType)33 static inline SVGColor::SVGColorType colorTypeForPaintType(const SVGPaint::SVGPaintType& paintType)
34 {
35     switch (paintType) {
36     case SVGPaint::SVG_PAINTTYPE_NONE:
37     case SVGPaint::SVG_PAINTTYPE_UNKNOWN:
38     case SVGPaint::SVG_PAINTTYPE_URI:
39     case SVGPaint::SVG_PAINTTYPE_URI_NONE:
40         return SVGColor::SVG_COLORTYPE_UNKNOWN;
41     case SVGPaint::SVG_PAINTTYPE_URI_RGBCOLOR:
42     case SVGPaint::SVG_PAINTTYPE_RGBCOLOR:
43         return SVGColor::SVG_COLORTYPE_RGBCOLOR;
44     case SVGPaint::SVG_PAINTTYPE_URI_RGBCOLOR_ICCCOLOR:
45     case SVGPaint::SVG_PAINTTYPE_RGBCOLOR_ICCCOLOR:
46         return SVGColor::SVG_COLORTYPE_RGBCOLOR_ICCCOLOR;
47     case SVGPaint::SVG_PAINTTYPE_URI_CURRENTCOLOR:
48     case SVGPaint::SVG_PAINTTYPE_CURRENTCOLOR:
49         return SVGColor::SVG_COLORTYPE_CURRENTCOLOR;
50     }
51 
52     ASSERT_NOT_REACHED();
53     return SVGColor::SVG_COLORTYPE_UNKNOWN;
54 }
55 
SVGPaint(const SVGPaintType & paintType,String uri)56 SVGPaint::SVGPaint(const SVGPaintType& paintType, String uri)
57     : SVGColor(colorTypeForPaintType(paintType))
58     , m_paintType(paintType)
59     , m_uri(uri)
60 {
61 }
62 
setUri(const String & uri)63 void SVGPaint::setUri(const String& uri)
64 {
65     // Spec: Sets the paintType to SVG_PAINTTYPE_URI_NONE and sets uri to the specified value.
66     m_uri = uri;
67     m_paintType = SVG_PAINTTYPE_URI_NONE;
68     setColor(Color());
69     setColorType(colorTypeForPaintType(m_paintType));
70     // FIXME: A follow up patch will call valueChanged() here.
71 }
72 
defaultFill()73 SVGPaint* SVGPaint::defaultFill()
74 {
75     static SVGPaint* staticDefaultFill = createColor(Color::black).releaseRef();
76     return staticDefaultFill;
77 }
78 
defaultStroke()79 SVGPaint* SVGPaint::defaultStroke()
80 {
81     static SVGPaint* staticDefaultStroke = createNone().releaseRef();
82     return staticDefaultStroke;
83 }
84 
setPaint(unsigned short paintType,const String & uri,const String & rgbColor,const String & iccColor,ExceptionCode & ec)85 void SVGPaint::setPaint(unsigned short paintType, const String& uri, const String& rgbColor, const String& iccColor, ExceptionCode& ec)
86 {
87     if ((paintType > SVG_PAINTTYPE_RGBCOLOR_ICCCOLOR && paintType < SVG_PAINTTYPE_NONE) || paintType > SVG_PAINTTYPE_URI) {
88         ec = SVGException::SVG_WRONG_TYPE_ERR;
89         return;
90     }
91 
92     bool requiresURI = false;
93 
94     SVGPaintType type = static_cast<SVGPaintType>(paintType);
95     switch (type) {
96     case SVG_PAINTTYPE_UNKNOWN:
97         // Spec: It is invalid to attempt to define a new value of this type or to attempt to switch an existing value to this type.
98         ec = SVGException::SVG_INVALID_VALUE_ERR;
99         return;
100     case SVG_PAINTTYPE_RGBCOLOR:
101     case SVG_PAINTTYPE_RGBCOLOR_ICCCOLOR:
102     case SVG_PAINTTYPE_NONE:
103     case SVG_PAINTTYPE_CURRENTCOLOR:
104         break;
105     case SVG_PAINTTYPE_URI_NONE:
106     case SVG_PAINTTYPE_URI_CURRENTCOLOR:
107     case SVG_PAINTTYPE_URI_RGBCOLOR:
108     case SVG_PAINTTYPE_URI_RGBCOLOR_ICCCOLOR:
109     case SVG_PAINTTYPE_URI:
110         requiresURI = true;
111         break;
112     };
113 
114     // Spec: If paintType requires a URI, then uri must be non-null; otherwise, uri must be null.
115     if (requiresURI && uri.isEmpty()) {
116         ec = SVGException::SVG_INVALID_VALUE_ERR;
117         return;
118     }
119 
120     SVGColor::SVGColorType colorType = colorTypeForPaintType(type);
121     if (colorType == SVGColor::SVG_COLORTYPE_UNKNOWN) {
122         // The standard setColor() code path used in the else branch
123         // raises an exception when attempting to switch to an unknown color type.
124         // Here we explicitely want to reset to Color() and an unknown type, so force it.
125         setColorType(colorType);
126         setColor(Color());
127     } else {
128         setColor(colorType, rgbColor, iccColor, ec);
129         if (ec)
130             return;
131     }
132 
133     m_paintType = type;
134     m_uri = requiresURI ? uri : String();
135     // FIXME: A follow up patch will call valueChanged() here.
136 }
137 
cssText() const138 String SVGPaint::cssText() const
139 {
140     switch (m_paintType) {
141     case SVG_PAINTTYPE_UNKNOWN:
142     case SVG_PAINTTYPE_RGBCOLOR:
143     case SVG_PAINTTYPE_RGBCOLOR_ICCCOLOR:
144     case SVG_PAINTTYPE_CURRENTCOLOR:
145         return SVGColor::cssText();
146     case SVG_PAINTTYPE_NONE:
147         return "none";
148     case SVG_PAINTTYPE_URI_NONE:
149         return makeString(m_uri, " none");
150     case SVG_PAINTTYPE_URI_CURRENTCOLOR:
151     case SVG_PAINTTYPE_URI_RGBCOLOR:
152     case SVG_PAINTTYPE_URI_RGBCOLOR_ICCCOLOR: {
153         String color = SVGColor::cssText();
154         if (color.isEmpty())
155             return m_uri;
156         return makeString(m_uri, ' ', color);
157     }
158     case SVG_PAINTTYPE_URI:
159         return m_uri;
160     };
161 
162     ASSERT_NOT_REACHED();
163     return String();
164 }
165 
matchesTargetURI(const String & referenceId)166 bool SVGPaint::matchesTargetURI(const String& referenceId)
167 {
168     switch (m_paintType) {
169     case SVG_PAINTTYPE_UNKNOWN:
170     case SVG_PAINTTYPE_RGBCOLOR:
171     case SVG_PAINTTYPE_RGBCOLOR_ICCCOLOR:
172     case SVG_PAINTTYPE_CURRENTCOLOR:
173     case SVG_PAINTTYPE_NONE:
174         return false;
175     case SVG_PAINTTYPE_URI_NONE:
176     case SVG_PAINTTYPE_URI_CURRENTCOLOR:
177     case SVG_PAINTTYPE_URI_RGBCOLOR:
178     case SVG_PAINTTYPE_URI_RGBCOLOR_ICCCOLOR:
179     case SVG_PAINTTYPE_URI:
180         return referenceId == SVGURIReference::getTarget(m_uri);
181     }
182 
183     ASSERT_NOT_REACHED();
184     return false;
185 }
186 
187 }
188 
189 #endif // ENABLE(SVG)
190