1 // Copyright (c) 1996 James Clark
2 // See the file copying.txt for copying permission.
3 
4 #ifndef Style_INCLUDED
5 #define Style_INCLUDED 1
6 
7 #include "types.h"
8 #include "StringC.h"
9 #include "Named.h"
10 #include <stddef.h>
11 #include "ELObj.h"
12 #include "Vector.h"
13 #include "Ptr.h"
14 #include "Resource.h"
15 #include "Owner.h"
16 #include "Insn.h"
17 #include "FOTBuilder.h"
18 #include "Boolean.h"
19 #include "Node.h"
20 #include "Location.h"
21 #include "ProcessingMode.h"
22 
23 #ifdef DSSSL_NAMESPACE
24 namespace DSSSL_NAMESPACE {
25 #endif
26 
27 class StyleStack;
28 class Interpreter;
29 class VarStyleObj;
30 
31 // InheritedC represents the specification of a value
32 // of an inherited characteristic.
33 // It is also used as a prototype for other specifications of
34 // values for that characteristic:
35 // the identifier for an inherited characteristic contains the
36 // InheritedC that specifies its initial value.
37 
38 class InheritedC : public Resource {
39 public:
40   InheritedC(const Identifier *ident, unsigned index);
41   virtual ~InheritedC();
42   virtual void set(VM &vm, const VarStyleObj *, FOTBuilder &,
43                    ELObj *&, Vector<size_t> &dependencies) const = 0;
44   virtual ELObj *value(VM &, const VarStyleObj *, Vector<size_t> &) const = 0;
45   virtual ConstPtr<InheritedC> make(ELObj *, const Location &, Interpreter &) const = 0;
46   unsigned index() const;
47   const Identifier *identifier() const;
48   void setIdentifier(const Identifier *);
49 protected:
50   void invalidValue(const Location &, Interpreter &) const;
51 private:
52   const Identifier *ident_;
53   // The index of the inherited characteristic (not the specification).
54   unsigned index_;
55 };
56 
57 class VarInheritedC : public InheritedC {
58 public:
59   VarInheritedC(const ConstPtr<InheritedC> &, const InsnPtr &code, const Location &);
60   void set(VM &, const VarStyleObj *, FOTBuilder &, ELObj *&value,
61            Vector<size_t> &dependencies) const;
62   ELObj *value(VM &, const VarStyleObj *, Vector<size_t> &) const;
63   virtual ConstPtr<InheritedC> make(ELObj *, const Location &, Interpreter &) const;
64 private:
65   ConstPtr<InheritedC> inheritedC_;
66   InsnPtr code_;
67   Location loc_;
68 };
69 
70 class StyleObjIter {
71 public:
72   StyleObjIter();
73   void append(const Vector<ConstPtr<InheritedC> > *, const VarStyleObj *);
74   ConstPtr<InheritedC> next(const VarStyleObj *&);
75 private:
76   size_t i_;
77   size_t vi_;
78   Vector<const VarStyleObj *> styleVec_;
79   Vector<const Vector<ConstPtr<InheritedC> > *> vecs_;
80 };
81 
82 class StyleObj : public ELObj {
83 public:
84   StyleObj *asStyle();
85   virtual void appendIter(StyleObjIter &) const = 0;
86 };
87 
88 struct StyleSpec : public Resource {
89   StyleSpec(Vector<ConstPtr<InheritedC> > &, Vector<ConstPtr<InheritedC> > &);
90   Vector<ConstPtr<InheritedC> > forceSpecs;
91   Vector<ConstPtr<InheritedC> > specs;
92 };
93 
94 class BasicStyleObj : public StyleObj {
95 public:
96   virtual void appendIterForce(StyleObjIter &) const = 0;
97   virtual void appendIterNormal(StyleObjIter &) const = 0;
98 };
99 
100 class VarStyleObj : public BasicStyleObj {
101 public:
new(size_t,Collector & c)102   void *operator new(size_t, Collector &c) {
103     return c.allocateObject(1);
104   }
105   VarStyleObj(const ConstPtr<StyleSpec> &, StyleObj *use, ELObj **display,
106               const NodePtr &node);
107   ~VarStyleObj();
108   void appendIter(StyleObjIter &) const;
109   void appendIterForce(StyleObjIter &) const;
110   void appendIterNormal(StyleObjIter &) const;
111   const NodePtr &node() const;
112   ELObj **display() const;
113   void traceSubObjects(Collector &) const;
114 private:
115   ConstPtr<StyleSpec> styleSpec_;
116   StyleObj *use_;
117   ELObj **display_;
118   NodePtr node_;
119 };
120 
121 class OverriddenStyleObj : public StyleObj {
122 public:
123   OverriddenStyleObj(BasicStyleObj *basic, StyleObj *override);
124   void appendIter(StyleObjIter &) const;
125   void traceSubObjects(Collector &) const;
126 private:
127   BasicStyleObj *basic_;
128   StyleObj *override_;
129 };
130 
131 class MergeStyleObj : public StyleObj {
132 public:
new(size_t,Collector & c)133   void *operator new(size_t, Collector &c) {
134     return c.allocateObject(1);
135   }
136   MergeStyleObj();
137   void append(StyleObj *);
138   void appendIter(StyleObjIter &) const;
139   void traceSubObjects(Collector &) const;
140 private:
141   Vector<StyleObj *> styles_;
142 };
143 
144 class ColorObj : public ELObj {
145 public:
146   ColorObj *asColor();
147   virtual void set(FOTBuilder &) const = 0;
148   virtual void setBackground(FOTBuilder &) const = 0;
149 };
150 
151 class DeviceRGBColorObj : public ColorObj {
152 public:
153   DeviceRGBColorObj(unsigned char, unsigned char, unsigned char);
154   void set(FOTBuilder &) const;
155   void setBackground(FOTBuilder &) const;
156 private:
157   FOTBuilder::DeviceRGBColor color_;
158 };
159 
160 class ColorSpaceObj : public ELObj {
161 public:
162   ColorSpaceObj *asColorSpace();
163   virtual ELObj *makeColor(int argc, ELObj **argv, Interpreter &, const Location &) = 0;
164 };
165 
166 class DeviceRGBColorSpaceObj : public ColorSpaceObj {
167 public:
168   ELObj *makeColor(int argc, ELObj **argv, Interpreter &interp, const Location &);
169 };
170 
171 struct InheritedCInfo : public Resource {
172   InheritedCInfo(const ConstPtr<InheritedC> &, const VarStyleObj *,
173 		 unsigned valLevel, unsigned specLevel, const ProcessingMode::Rule *,
174 		 const Ptr<InheritedCInfo> &);
175   ConstPtr<InheritedC> spec;
176   Ptr<InheritedCInfo> prev;
177   unsigned valLevel;
178   unsigned specLevel;
179   const ProcessingMode::Rule *rule;
180   // If there are dependencies, then the cached value can only
181   // be used only when the "value" flow object is at this level.
182   ELObj *cachedValue;
183   const VarStyleObj *style;
184   // Includes both direct and indirect dependencies.
185   Vector<size_t> dependencies;
186 };
187 
188 struct PopList : public Resource {
189   PopList(const Ptr<PopList> &);
190   Vector<size_t> list;
191   // List of the indices of those ICs that have dependencies
192   // (ie that use actual-*) directly or indirectly.
193   Vector<size_t> dependingList;
194   Ptr<PopList> prev;
195 };
196 
197 class StyleStack {
198 public:
199   StyleStack();
200   // These append on to dependencies.
201   ELObj *actual(const ConstPtr<InheritedC> &, const Location &, Interpreter &,
202 		Vector<size_t> &dependencies);
203   ELObj *actual(const ConstPtr<InheritedC> &, Interpreter &,
204 		Vector<size_t> &dependencies);
205   ELObj *inherited(const ConstPtr<InheritedC> &, unsigned specLevel, Interpreter &,
206 		   Vector<size_t> &dependencies);
207   void push(StyleObj *, VM &, FOTBuilder &);
208   void pushStart();
209   void pushContinue(StyleObj *, const ProcessingMode::Rule *, const NodePtr &,
210 		    Messenger *);
211   void pushEnd(VM &, FOTBuilder &);
212   void pop();
pushEmpty()213   void pushEmpty() { level_++; }
popEmpty()214   void popEmpty() { level_--; }
level()215   unsigned level() const { return level_; }
216   void trace(Collector &) const;
217 private:
218   Vector<Ptr<InheritedCInfo> > inheritedCInfo_;
219   unsigned level_;
220   Ptr<PopList> popList_;
221 };
222 
223 inline
PopList(const Ptr<PopList> & p)224 PopList::PopList(const Ptr<PopList> &p)
225 : prev(p)
226 {
227 }
228 
229 inline
identifier()230 const Identifier *InheritedC::identifier() const
231 {
232   return ident_;
233 }
234 
235 inline
setIdentifier(const Identifier * ident)236 void InheritedC::setIdentifier(const Identifier *ident)
237 {
238   ident_ = ident;
239 }
240 
241 inline
index()242 unsigned InheritedC::index() const
243 {
244   return index_;
245 }
246 
247 inline
display()248 ELObj **VarStyleObj::display() const
249 {
250   return display_;
251 }
252 
253 inline
node()254 const NodePtr &VarStyleObj::node() const
255 {
256   return node_;
257 }
258 
259 inline
pushStart()260 void StyleStack::pushStart()
261 {
262   level_++;
263   popList_ = new PopList(popList_);
264 }
265 
266 inline
push(StyleObj * style,VM & vm,FOTBuilder & fotb)267 void StyleStack::push(StyleObj *style, VM &vm, FOTBuilder &fotb)
268 {
269   pushStart();
270   pushContinue(style, 0, NodePtr(), 0);
271   pushEnd(vm, fotb);
272 }
273 
274 inline
actual(const ConstPtr<InheritedC> & ic,Interpreter & interp,Vector<size_t> & dep)275 ELObj *StyleStack::actual(const ConstPtr<InheritedC> &ic,
276 			  Interpreter &interp,
277 			  Vector<size_t> &dep)
278 {
279   return actual(ic, Location(), interp, dep);
280 }
281 
282 #ifdef DSSSL_NAMESPACE
283 }
284 #endif
285 
286 #endif /* not Style_INCLUDED */
287