1/*
2 * Copyright (C) 2000 Lars Knoll (knoll@kde.org)
3 *           (C) 2000 Antti Koivisto (koivisto@kde.org)
4 *           (C) 2000 Dirk Mueller (mueller@kde.org)
5 * Copyright (C) 2003, 2005, 2006, 2007, 2008, 2010 Apple Inc. All rights reserved.
6 * Copyright (C) 2006 Graham Dennis (graham.dennis@gmail.com)
7 *
8 * This library is free software; you can redistribute it and/or
9 * modify it under the terms of the GNU Library General Public
10 * License as published by the Free Software Foundation; either
11 * version 2 of the License, or (at your option) any later version.
12 *
13 * This library is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
16 * Library General Public License for more details.
17 *
18 * You should have received a copy of the GNU Library General Public License
19 * along with this library; see the file COPYING.LIB.  If not, write to
20 * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
21 * Boston, MA 02110-1301, USA.
22 *
23 */
24
25#ifndef ContentData_h
26#define ContentData_h
27
28#include "core/rendering/style/CounterContent.h"
29#include "core/rendering/style/StyleImage.h"
30#include "wtf/OwnPtr.h"
31#include "wtf/PassOwnPtr.h"
32
33namespace WebCore {
34
35class Document;
36class RenderObject;
37class RenderStyle;
38
39class ContentData {
40    WTF_MAKE_FAST_ALLOCATED;
41public:
42    static PassOwnPtr<ContentData> create(PassRefPtr<StyleImage>);
43    static PassOwnPtr<ContentData> create(const String&);
44    static PassOwnPtr<ContentData> create(PassOwnPtr<CounterContent>);
45    static PassOwnPtr<ContentData> create(QuoteType);
46
47    virtual ~ContentData() { }
48
49    virtual bool isCounter() const { return false; }
50    virtual bool isImage() const { return false; }
51    virtual bool isQuote() const { return false; }
52    virtual bool isText() const { return false; }
53
54    virtual RenderObject* createRenderer(Document*, RenderStyle*) const = 0;
55
56    virtual PassOwnPtr<ContentData> clone() const;
57
58    ContentData* next() const { return m_next.get(); }
59    void setNext(PassOwnPtr<ContentData> next) { m_next = next; }
60
61    virtual bool equals(const ContentData&) const = 0;
62
63private:
64    virtual PassOwnPtr<ContentData> cloneInternal() const = 0;
65
66    OwnPtr<ContentData> m_next;
67};
68
69class ImageContentData : public ContentData {
70    friend class ContentData;
71public:
72    const StyleImage* image() const { return m_image.get(); }
73    StyleImage* image() { return m_image.get(); }
74    void setImage(PassRefPtr<StyleImage> image) { m_image = image; }
75
76    virtual bool isImage() const OVERRIDE { return true; }
77    virtual RenderObject* createRenderer(Document*, RenderStyle*) const OVERRIDE;
78
79    virtual bool equals(const ContentData& data) const OVERRIDE
80    {
81        if (!data.isImage())
82            return false;
83        return *static_cast<const ImageContentData&>(data).image() == *image();
84    }
85
86private:
87    ImageContentData(PassRefPtr<StyleImage> image)
88        : m_image(image)
89    {
90    }
91
92    virtual PassOwnPtr<ContentData> cloneInternal() const
93    {
94        RefPtr<StyleImage> image = const_cast<StyleImage*>(this->image());
95        return create(image.release());
96    }
97
98    RefPtr<StyleImage> m_image;
99};
100
101class TextContentData : public ContentData {
102    friend class ContentData;
103public:
104    const String& text() const { return m_text; }
105    void setText(const String& text) { m_text = text; }
106
107    virtual bool isText() const OVERRIDE { return true; }
108    virtual RenderObject* createRenderer(Document*, RenderStyle*) const OVERRIDE;
109
110    virtual bool equals(const ContentData& data) const OVERRIDE
111    {
112        if (!data.isText())
113            return false;
114        return static_cast<const TextContentData&>(data).text() == text();
115    }
116
117private:
118    TextContentData(const String& text)
119        : m_text(text)
120    {
121    }
122
123    virtual PassOwnPtr<ContentData> cloneInternal() const { return create(text()); }
124
125    String m_text;
126};
127
128class CounterContentData : public ContentData {
129    friend class ContentData;
130public:
131    const CounterContent* counter() const { return m_counter.get(); }
132    void setCounter(PassOwnPtr<CounterContent> counter) { m_counter = counter; }
133
134    virtual bool isCounter() const OVERRIDE { return true; }
135    virtual RenderObject* createRenderer(Document*, RenderStyle*) const OVERRIDE;
136
137private:
138    CounterContentData(PassOwnPtr<CounterContent> counter)
139        : m_counter(counter)
140    {
141    }
142
143    virtual PassOwnPtr<ContentData> cloneInternal() const
144    {
145        OwnPtr<CounterContent> counterData = adoptPtr(new CounterContent(*counter()));
146        return create(counterData.release());
147    }
148
149    virtual bool equals(const ContentData& data) const OVERRIDE
150    {
151        if (!data.isCounter())
152            return false;
153        return *static_cast<const CounterContentData&>(data).counter() == *counter();
154    }
155
156    OwnPtr<CounterContent> m_counter;
157};
158
159class QuoteContentData : public ContentData {
160    friend class ContentData;
161public:
162    QuoteType quote() const { return m_quote; }
163    void setQuote(QuoteType quote) { m_quote = quote; }
164
165    virtual bool isQuote() const OVERRIDE { return true; }
166    virtual RenderObject* createRenderer(Document*, RenderStyle*) const OVERRIDE;
167
168    virtual bool equals(const ContentData& data) const OVERRIDE
169    {
170        if (!data.isQuote())
171            return false;
172        return static_cast<const QuoteContentData&>(data).quote() == quote();
173    }
174
175private:
176    QuoteContentData(QuoteType quote)
177        : m_quote(quote)
178    {
179    }
180
181    virtual PassOwnPtr<ContentData> cloneInternal() const { return create(quote()); }
182
183    QuoteType m_quote;
184};
185
186inline bool operator==(const ContentData& a, const ContentData& b)
187{
188    return a.equals(b);
189}
190
191inline bool operator!=(const ContentData& a, const ContentData& b)
192{
193    return !(a == b);
194}
195
196} // namespace WebCore
197
198#endif // ContentData_h
199