389a2d80a1adf9cf8776ff2c007b039fe0d8e886
[WebKit-https.git] / WebCore / khtml / css / css_valueimpl.h
1 /*
2  * This file is part of the DOM implementation for KDE.
3  *
4  * (C) 1999-2003 Lars Knoll (knoll@kde.org)
5  * Copyright (C) 2004 Apple Computer, Inc.
6  *
7  * This library is free software; you can redistribute it and/or
8  * modify it under the terms of the GNU Library General Public
9  * License as published by the Free Software Foundation; either
10  * version 2 of the License, or (at your option) any later version.
11  *
12  * This library is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
15  * Library General Public License for more details.
16  *
17  * You should have received a copy of the GNU Library General Public License
18  * along with this library; see the file COPYING.LIB.  If not, write to
19  * the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
20  * Boston, MA 02111-1307, USA.
21  */
22
23 #ifndef _CSS_css_valueimpl_h_
24 #define _CSS_css_valueimpl_h_
25
26 #include "dom/css_value.h"
27 #include "css/css_base.h"
28 #include "misc/loader_client.h"
29 #include <qvaluelist.h>
30
31 namespace khtml {
32     class RenderStyle;
33     class CachedImage;
34     class DocLoader;
35 }
36
37 namespace DOM {
38
39 class CSSMutableStyleDeclarationImpl;
40 class CounterImpl;
41
42 class CSSStyleDeclarationImpl : public StyleBaseImpl
43 {
44 public:
45     virtual bool isStyleDeclaration();
46
47     CSSRuleImpl *parentRule() const;
48
49     virtual DOMString cssText() const = 0;
50     virtual void setCssText(const DOMString &, int &exceptionCode) = 0;
51
52     virtual unsigned long length() const = 0;
53     virtual DOMString item(unsigned long index) const = 0;
54
55     virtual CSSValueImpl *getPropertyCSSValue(int propertyID) const = 0;
56     virtual DOMString getPropertyValue(int propertyID) const = 0;
57     virtual bool getPropertyPriority(int propertyID) const = 0;
58
59     virtual void setProperty(int propertyId, const DOMString &value, bool important, int &exceptionCode) = 0;
60     virtual DOMString removeProperty(int propertyID, int &exceptionCode) = 0;
61
62     virtual CSSMutableStyleDeclarationImpl *copy() const = 0;
63     virtual CSSMutableStyleDeclarationImpl *makeMutable() = 0;
64  
65     void diff(CSSMutableStyleDeclarationImpl *) const;
66
67     CSSMutableStyleDeclarationImpl *copyPropertiesInSet(const int *set, unsigned length) const;
68
69 protected:
70     CSSStyleDeclarationImpl(CSSRuleImpl *parentRule = 0);
71
72
73 private:
74     CSSStyleDeclarationImpl(const CSSStyleDeclarationImpl &);
75     CSSStyleDeclarationImpl& operator=(const CSSStyleDeclarationImpl &);
76 };
77
78 class CSSValueImpl : public StyleBaseImpl
79 {
80 public:
81     virtual unsigned short cssValueType() const = 0;
82     virtual DOMString cssText() const = 0;
83
84     virtual bool isValue() { return true; }
85     virtual bool isFontValue() { return false; }
86 };
87
88 class CSSInheritedValueImpl : public CSSValueImpl
89 {
90 public:
91     virtual unsigned short cssValueType() const;
92     virtual DOMString cssText() const;
93 };
94
95 class CSSInitialValueImpl : public CSSValueImpl
96 {
97 public:
98     virtual unsigned short cssValueType() const;
99     virtual DOMString cssText() const;
100 };
101
102 class CSSValueListImpl : public CSSValueImpl
103 {
104 public:
105     CSSValueListImpl();
106
107     virtual ~CSSValueListImpl();
108
109     unsigned long length() const { return m_values.count(); }
110     CSSValueImpl *item ( unsigned long index ) { return m_values.at(index); }
111
112     virtual bool isValueList() { return true; }
113
114     virtual unsigned short cssValueType() const;
115
116     void append(CSSValueImpl *val);
117     virtual DOMString cssText() const;
118
119 protected:
120     QPtrList<CSSValueImpl> m_values;
121 };
122
123
124 class Counter;
125 class RGBColor;
126 class Rect;
127 class DashboardRegionImpl;
128
129 class CSSPrimitiveValueImpl : public CSSValueImpl
130 {
131 public:
132     CSSPrimitiveValueImpl();
133     CSSPrimitiveValueImpl(int ident);
134     CSSPrimitiveValueImpl(double num, CSSPrimitiveValue::UnitTypes type);
135     CSSPrimitiveValueImpl(const DOMString &str, CSSPrimitiveValue::UnitTypes type);
136     CSSPrimitiveValueImpl(const Counter &c);
137     CSSPrimitiveValueImpl(RectImpl *r);
138     CSSPrimitiveValueImpl(DashboardRegionImpl *r);
139     CSSPrimitiveValueImpl(QRgb color);
140
141     virtual ~CSSPrimitiveValueImpl();
142
143     void cleanup();
144
145     unsigned short primitiveType() const {
146             return m_type;
147     }
148
149     /*
150      * computes a length in pixels out of the given CSSValue. Need the RenderStyle to get
151      * the fontinfo in case val is defined in em or ex.
152      *
153      * The metrics have to be a bit different for screen and printer output.
154      * For screen output we assume 1 inch == 72 px, for printer we assume 300 dpi
155      *
156      * this is screen/printer dependent, so we probably need a config option for this,
157      * and some tool to calibrate.
158      */
159     int computeLength( khtml::RenderStyle *style, QPaintDeviceMetrics *devMetrics );
160     int computeLength( khtml::RenderStyle *style, QPaintDeviceMetrics *devMetrics, double multiplier );
161     double computeLengthFloat( khtml::RenderStyle *style, QPaintDeviceMetrics *devMetrics,
162                                bool applyZoomFactor = true );
163
164     // use with care!!!
165     void setPrimitiveType(unsigned short type) { m_type = type; }
166     void setFloatValue ( unsigned short unitType, double floatValue, int &exceptioncode );
167     double getFloatValue ( unsigned short/* unitType */) const {
168         return m_value.num;
169     }
170
171     void setStringValue ( unsigned short stringType, const DOM::DOMString &stringValue, int &exceptioncode );
172     DOM::DOMString getStringValue() const;
173     
174     CounterImpl *getCounterValue () const {
175         return ( m_type != CSSPrimitiveValue::CSS_COUNTER ? 0 : m_value.counter );
176     }
177
178     RectImpl *getRectValue () const {
179         return ( m_type != CSSPrimitiveValue::CSS_RECT ? 0 : m_value.rect );
180     }
181
182     QRgb getRGBColorValue () const {
183         return ( m_type != CSSPrimitiveValue::CSS_RGBCOLOR ? 0 : m_value.rgbcolor );
184     }
185
186 #if APPLE_CHANGES
187     DashboardRegionImpl *getDashboardRegionValue () const {
188         return ( m_type != CSSPrimitiveValue::CSS_DASHBOARD_REGION ? 0 : m_value.region );
189     }
190 #endif
191
192     virtual bool isPrimitiveValue() const { return true; }
193     virtual unsigned short cssValueType() const;
194
195     int getIdent();
196
197     virtual bool parseString( const DOMString &string, bool = false);
198     virtual DOMString cssText() const;
199
200     virtual bool isQuirkValue() { return false; }
201
202 protected:
203     int m_type;
204     union {
205         int ident;
206         double num;
207         DOMStringImpl *string;
208         CounterImpl *counter;
209         RectImpl *rect;
210         QRgb rgbcolor;
211         DashboardRegionImpl *region;
212     } m_value;
213 };
214
215 // This value is used to handle quirky margins in reflow roots (body, td, and th) like WinIE.
216 // The basic idea is that a stylesheet can use the value __qem (for quirky em) instead of em
217 // in a stylesheet.  When the quirky value is used, if you're in quirks mode, the margin will
218 // collapse away inside a table cell.
219 class CSSQuirkPrimitiveValueImpl : public CSSPrimitiveValueImpl
220 {
221 public:
222     CSSQuirkPrimitiveValueImpl(double num, CSSPrimitiveValue::UnitTypes type)
223       :CSSPrimitiveValueImpl(num, type) {}
224
225     virtual bool isQuirkValue() { return true; }
226 };
227
228 class CounterImpl : public khtml::Shared<CounterImpl> {
229 public:
230     DOMString identifier() const { return m_identifier; }
231     DOMString listStyle() const { return m_listStyle; }
232     DOMString separator() const { return m_separator; }
233
234     DOMString m_identifier;
235     DOMString m_listStyle;
236     DOMString m_separator;
237 };
238
239 class RectImpl : public khtml::Shared<RectImpl> {
240 public:
241     RectImpl();
242     virtual ~RectImpl();
243
244     CSSPrimitiveValueImpl *top() { return m_top; }
245     CSSPrimitiveValueImpl *right() { return m_right; }
246     CSSPrimitiveValueImpl *bottom() { return m_bottom; }
247     CSSPrimitiveValueImpl *left() { return m_left; }
248
249     void setTop( CSSPrimitiveValueImpl *top );
250     void setRight( CSSPrimitiveValueImpl *right );
251     void setBottom( CSSPrimitiveValueImpl *bottom );
252     void setLeft( CSSPrimitiveValueImpl *left );
253 protected:
254     CSSPrimitiveValueImpl *m_top;
255     CSSPrimitiveValueImpl *m_right;
256     CSSPrimitiveValueImpl *m_bottom;
257     CSSPrimitiveValueImpl *m_left;
258 };
259
260 #if APPLE_CHANGES
261
262 class DashboardRegionImpl : public RectImpl {
263 public:
264     DashboardRegionImpl() : m_next(0), m_isCircle(0), m_isRectangle(0) { }
265     ~DashboardRegionImpl() {
266         if (m_next)
267             m_next->deref();
268     }
269
270     void setNext (DashboardRegionImpl *next)
271     {
272         if (next) next->ref();
273         if (m_next) m_next->deref();
274         m_next = next;
275     }
276     
277 public:
278     DashboardRegionImpl *m_next;
279     QString m_label;
280     QString m_geometryType;
281     unsigned int m_isCircle:1;
282     unsigned int m_isRectangle:1;
283 };
284
285 #endif
286
287 class CSSImageValueImpl : public CSSPrimitiveValueImpl, public khtml::CachedObjectClient
288 {
289 public:
290     CSSImageValueImpl();
291     CSSImageValueImpl(const DOMString &url, StyleBaseImpl *style);
292     virtual ~CSSImageValueImpl();
293
294     khtml::CachedImage *image(khtml::DocLoader* loader);
295
296 protected:
297     khtml::CachedImage* m_image;
298     bool m_accessedImage;
299 };
300
301 class FontFamilyValueImpl : public CSSPrimitiveValueImpl
302 {
303 public:
304     FontFamilyValueImpl( const QString &string);
305     const QString &fontName() const { return parsedFontName; }
306     int genericFamilyType() const { return _genericFamilyType; }
307
308     virtual DOMString cssText() const;
309
310     QString parsedFontName;
311 private:
312     int _genericFamilyType;
313 };
314
315 class FontValueImpl : public CSSValueImpl
316 {
317 public:
318     FontValueImpl();
319     virtual ~FontValueImpl();
320
321     virtual unsigned short cssValueType() const { return CSSValue::CSS_CUSTOM; }
322     
323     virtual DOMString cssText() const;
324     
325     virtual bool isFontValue() { return true; }
326
327     CSSPrimitiveValueImpl *style;
328     CSSPrimitiveValueImpl *variant;
329     CSSPrimitiveValueImpl *weight;
330     CSSPrimitiveValueImpl *size;
331     CSSPrimitiveValueImpl *lineHeight;
332     CSSValueListImpl *family;
333 };
334
335 // Used for text-shadow and box-shadow
336 class ShadowValueImpl : public CSSValueImpl
337 {
338 public:
339     ShadowValueImpl(CSSPrimitiveValueImpl* _x, CSSPrimitiveValueImpl* _y,
340                     CSSPrimitiveValueImpl* _blur, CSSPrimitiveValueImpl* _color);
341     virtual ~ShadowValueImpl();
342
343     virtual unsigned short cssValueType() const { return CSSValue::CSS_CUSTOM; }
344
345     virtual DOMString cssText() const;
346
347     CSSPrimitiveValueImpl* x;
348     CSSPrimitiveValueImpl* y;
349     CSSPrimitiveValueImpl* blur;
350     CSSPrimitiveValueImpl* color;
351 };
352
353 // Used by box-flex-group-transition
354 class FlexGroupTransitionValueImpl : public CSSValueImpl
355 {
356 public:
357     FlexGroupTransitionValueImpl();
358     FlexGroupTransitionValueImpl(unsigned int _group1, 
359                                  unsigned int _group2,
360                                  CSSPrimitiveValueImpl* _length);
361     virtual ~FlexGroupTransitionValueImpl();
362     
363     virtual unsigned short cssValueType() const { return CSSValue::CSS_CUSTOM; }
364     
365     virtual DOMString cssText() const;
366     
367     bool isAuto() const { return autoValue; }
368
369     bool autoValue;
370     unsigned int group1;
371     unsigned int group2;
372     CSSPrimitiveValueImpl* length;
373 };
374
375 // ------------------------------------------------------------------------------
376
377 // another helper class
378 class CSSProperty
379 {
380 public:
381     CSSProperty() : m_id(-1), m_bImportant(false), m_value(0)
382     {
383     }
384     CSSProperty(int propID, CSSValueImpl *value, bool important = false)
385         : m_id(propID), m_bImportant(important), m_value(value)
386     {
387         if (value) value->ref();
388     }
389     CSSProperty(const CSSProperty& o)
390     {
391         m_id = o.m_id;
392         m_bImportant = o.m_bImportant;
393         m_value = o.m_value;
394         if (m_value) m_value->ref();
395     }
396     CSSProperty &operator=(const CSSProperty& o)
397     {
398         if (o.m_value) o.m_value->ref();
399         if (m_value) m_value->deref();
400         m_id = o.m_id;
401         m_bImportant = o.m_bImportant;
402         m_value = o.m_value;
403         return *this;
404     }
405     ~CSSProperty() {
406         if(m_value) m_value->deref();
407     }
408
409     void setValue(CSSValueImpl *val) {
410         if (val) val->ref();
411         if (m_value) m_value->deref();
412         m_value = val;
413     }
414
415     int id() const { return m_id; }
416     bool isImportant() const { return m_bImportant; }
417     CSSValueImpl *value() const { return m_value; }
418     
419     DOMString cssText() const;
420
421     // make sure the following fits in 4 bytes.
422     int  m_id;
423     bool m_bImportant;
424
425     friend bool operator==(const CSSProperty &, const CSSProperty &);
426
427 protected:
428     CSSValueImpl *m_value;
429 };
430
431 class CSSMutableStyleDeclarationImpl : public CSSStyleDeclarationImpl
432 {
433 public:
434     CSSMutableStyleDeclarationImpl();
435     CSSMutableStyleDeclarationImpl(CSSRuleImpl *parentRule);
436     CSSMutableStyleDeclarationImpl(CSSRuleImpl *parentRule, const QValueList<CSSProperty> &);
437     CSSMutableStyleDeclarationImpl(CSSRuleImpl *parentRule, const CSSProperty * const *, int numProperties);
438     virtual ~CSSMutableStyleDeclarationImpl();
439
440     CSSMutableStyleDeclarationImpl &operator=(const CSSMutableStyleDeclarationImpl &);
441
442     void setNode(NodeImpl *node) { m_node = node; }
443
444     virtual DOMString cssText() const;
445     virtual void setCssText(const DOMString &, int &exceptionCode);
446
447     virtual unsigned long length() const;
448     virtual DOMString item(unsigned long index) const;
449
450     virtual CSSValueImpl *getPropertyCSSValue(int propertyID) const;
451     virtual DOMString getPropertyValue(int propertyID) const;
452     virtual bool getPropertyPriority(int propertyID) const;
453
454     virtual void setProperty(int propertyId, const DOMString &value, bool important, int &exceptionCode);
455     virtual DOMString removeProperty(int propertyID, int &exceptionCode);
456
457     virtual CSSMutableStyleDeclarationImpl *copy() const;
458     virtual CSSMutableStyleDeclarationImpl *makeMutable();
459
460     QValueListConstIterator<CSSProperty> valuesIterator() const { return m_values.begin(); }
461
462     bool setProperty(int propertyID, int value, bool important = false, bool notifyChanged = true);
463     bool setProperty(int propertyID, const DOMString &value, bool important, bool notifyChanged, int &exceptionCode);
464     bool setProperty(int propertyId, const DOMString &value, bool important = false, bool notifyChanged = true)
465         { int exceptionCode; return setProperty(propertyId, value, important, notifyChanged, exceptionCode); }
466
467     DOMString removeProperty(int propertyID, bool notifyChanged, int &exceptionCode);
468     DOMString removeProperty(int propertyID, bool notifyChanged = true)
469         { int exceptionCode; return removeProperty(propertyID, notifyChanged, exceptionCode); }
470
471     void clear();
472
473     void setChanged();
474  
475     // setLengthProperty treats integers as pixels! (Needed for conversion of HTML attributes.)
476     void setLengthProperty(int propertyId, const DOMString &value, bool important, bool multiLength = false);
477     void setStringProperty(int propertyId, const DOMString &value, CSSPrimitiveValue::UnitTypes, bool important = false); // parsed string value
478     void setImageProperty(int propertyId, const DOMString &URL, bool important = false);
479  
480     // The following parses an entire new style declaration.
481     void parseDeclaration(const DOMString &styleDeclaration);
482
483     // Besides adding the properties, this also removes any existing properties with these IDs.
484     // It does no notification since it's called by the parser.
485     void addParsedProperties(const CSSProperty * const *, int numProperties);
486  
487     CSSMutableStyleDeclarationImpl *copyBlockProperties() const;
488     void removeBlockProperties();
489     void removePropertiesInSet(const int *set, unsigned length);
490
491     void merge(CSSMutableStyleDeclarationImpl *, bool argOverridesOnConflict = true);
492  
493 private:
494     DOMString getShortHandValue(const int* properties, int number) const;
495     DOMString get4Values(const int* properties) const;
496  
497     QValueList<CSSProperty> m_values;
498     NodeImpl *m_node;
499 };
500
501 } // namespace
502
503 #endif