1 /************
2 *
3 *   This file is part of a tool for producing 3D content in the PRC format.
4 *   Copyright (C) 2008  Orest Shardt <shardtor (at) gmail dot com> and
5 *                       Michail Vidiassov <master@iaas.msu.ru>
6 *
7 *   This program is free software: you can redistribute it and/or modify
8 *   it under the terms of the GNU Lesser General Public License as published by
9 *   the Free Software Foundation, either version 3 of the License, or
10 *   (at your option) any later version.
11 *
12 *   This program 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
15 *   GNU Lesser General Public License for more details.
16 *
17 *   You should have received a copy of the GNU Lesser General Public License
18 *   along with this program.  If not, see <http://www.gnu.org/licenses/>.
19 *
20 *************/
21 
22 #ifndef __WRITE_PRC_H
23 #define __WRITE_PRC_H
24 #include <string>
25 #include <vector>
26 #include <deque>
27 #include <list>
28 
29 #include <map>
30 #include <iostream>
31 #include "PRCbitStream.h"
32 #include "PRC.h"
33 #include <float.h>
34 #include <math.h>
35 
36 static const uint32_t m1=(uint32_t)-1;
37 static const double pi=acos(-1.0);
38 
39 class PRCVector3d
40 {
41 public :
42  double x;
43  double y;
44  double z;
PRCVector3d()45  PRCVector3d() :
46  x(0), y(0), z(0) {}
PRCVector3d(double fx,double fy,double fz)47  PRCVector3d(double fx, double fy, double fz) :
48  x(fx), y(fy), z(fz) {}
49  PRCVector3d(const double c[], double fx=0, double fy=0, double fz=0) :
50  x(c?c[0]:fx), y(c?c[1]:fy), z(c?c[2]:fz) {}
PRCVector3d(const PRCVector3d & sVector3d)51  PRCVector3d(const PRCVector3d& sVector3d) :
52  x(sVector3d.x), y(sVector3d.y), z(sVector3d.z) {}
53 
Set(double fx,double fy,double fz)54  void Set(double fx, double fy, double fz)
55  { x = fx; y = fy; z = fz; }
Dot(const PRCVector3d & sPt)56  double Dot(const PRCVector3d & sPt) const
57  { return(x*sPt.x)+(y*sPt.y)+(z*sPt.z); }
LengthSquared()58  double LengthSquared()
59  { return(x*x+y*y+z*z); }
60 
61  friend PRCVector3d operator + (const PRCVector3d& a, const PRCVector3d& b)
62  { return PRCVector3d(a.x+b.x,a.y+b.y,a.z+b.z); }
63  friend PRCVector3d operator - (const PRCVector3d& a)
64  { return PRCVector3d(-a.x,-a.y,-a.z); }
65  friend PRCVector3d operator - (const PRCVector3d& a, const PRCVector3d& b)
66  { return PRCVector3d(a.x-b.x,a.y-b.y,a.z-b.z); }
67  friend PRCVector3d operator * (const PRCVector3d& a, const double d)
68  { return PRCVector3d(a.x*d,a.y*d,a.z*d); }
69  friend PRCVector3d operator * (const double d, const PRCVector3d& a)
70  { return PRCVector3d(a.x*d,a.y*d,a.z*d); }
71  friend PRCVector3d operator / (const PRCVector3d& a, const double d)
72  { return PRCVector3d(a.x/d,a.y/d,a.z/d); }
73  friend PRCVector3d operator * (const PRCVector3d& a, const PRCVector3d& b)
74  { return PRCVector3d((a.y*b.z)-(a.z*b.y), (a.z*b.x)-(a.x*b.z), (a.x*b.y)-(a.y*b.x)); }
75 
write(PRCbitStream & out)76  void write(PRCbitStream &out) { out << x << y << z; }
serializeVector3d(PRCbitStream & pbs)77  void serializeVector3d(PRCbitStream &pbs) const { pbs << x << y << z; }
serializeVector2d(PRCbitStream & pbs)78  void serializeVector2d(PRCbitStream &pbs) const { pbs << x << y; }
79 
80  double Length();
81  bool Normalize();
82 
83  bool operator==(const PRCVector3d &v) const
84  {
85   return x==v.x && y==v.y && z==v.z;
86  }
87  bool operator!=(const PRCVector3d &v) const
88  {
89   return !(x==v.x && y==v.y && z==v.z);
90  }
91  bool operator<(const PRCVector3d &v) const
92  {
93    if(x!=v.x)
94      return (x<v.x);
95    if(y!=v.y)
96      return (y<v.y);
97    return (z<v.z);
98  }
99  friend std::ostream& operator << (std::ostream& out, const PRCVector3d& v)
100  {
101    out << "(" << v.x << "," << v.y << "," << v.z << ")";
102    return out;
103  }
104 };
105 /*
106 class UUID
107 {
108   public:
109     UUID(uint32_t u0, uint32_t u1, uint32_t u2, uint32_t u3) :
110       id0(u0),id1(u1),id2(u2),id3(u3) {}
111     void write(PRCbitStream &out)
112     {
113       out << id0 << id1 << id2 << id3;
114     }
115   private:
116     uint32_t id0,id1,id2,id3;
117 }; */
118 
119 void writeUncompressedUnsignedInteger(std::ostream &out, uint32_t data);
120 
121 void writeUnit(PRCbitStream &,bool,double);
122 
123 void writeEmptyMarkups(PRCbitStream&);
124 
125 class UserData
126 {
127   public:
size(s)128     UserData(uint32_t s = 0, uint8_t* d = 0) : size(s),data(d) {}
129     void write(PRCbitStream&);
130   private:
131     uint32_t size;
132     uint8_t* data;
133 };
134 
135 struct PRCAttributeEntry
136 {
PRCAttributeEntryPRCAttributeEntry137 	PRCAttributeEntry() : title_is_integer(false) {}
PRCAttributeEntryPRCAttributeEntry138 	PRCAttributeEntry(uint32_t integer) : title_is_integer(true)
139   {
140     title_integer = integer;
141   }
PRCAttributeEntryPRCAttributeEntry142 	PRCAttributeEntry(const std::string &text) : title_is_integer(false)
143   {
144     title_text = text;
145   }
146   void serializeAttributeEntry(PRCbitStream&) const;
147   bool title_is_integer;
148   std::string title_text;
149   uint32_t title_integer;
150 };
151 
152 class PRCSingleAttribute : public PRCAttributeEntry
153 {
154   public:
PRCSingleAttribute()155   PRCSingleAttribute() : type(KEPRCModellerAttributeTypeNull) {}
PRCSingleAttribute(int32_t integer)156 	PRCSingleAttribute(int32_t integer) : PRCAttributeEntry(), type(KEPRCModellerAttributeTypeInt)
157   {
158     value.integer = integer;
159   }
PRCSingleAttribute(double real)160 	PRCSingleAttribute(double real) : PRCAttributeEntry(), type(KEPRCModellerAttributeTypeReal)
161   {
162     value.real = real;
163   }
PRCSingleAttribute(uint32_t time)164   PRCSingleAttribute(uint32_t time) : PRCAttributeEntry(), type(KEPRCModellerAttributeTypeTime)
165   {
166     value.time = time;
167   }
PRCSingleAttribute(const std::string & text)168 	PRCSingleAttribute(const std::string &text) : PRCAttributeEntry(), type(KEPRCModellerAttributeTypeString)
169   {
170     value_text = text;}
PRCSingleAttribute(uint32_t title,int32_t integer)171 	PRCSingleAttribute(uint32_t title, int32_t integer) : PRCAttributeEntry(title), type(KEPRCModellerAttributeTypeInt)
172   {
173     value.integer = integer;
174   }
PRCSingleAttribute(uint32_t title,double real)175 	PRCSingleAttribute(uint32_t title, double real) : PRCAttributeEntry(title), type(KEPRCModellerAttributeTypeReal)
176   {
177     value.real = real;
178   }
PRCSingleAttribute(uint32_t title,uint32_t time)179   PRCSingleAttribute(uint32_t title, uint32_t time) : PRCAttributeEntry(title), type(KEPRCModellerAttributeTypeTime)
180   {
181     value.time = time;
182   }
PRCSingleAttribute(uint32_t title,const std::string & text)183 	PRCSingleAttribute(uint32_t title, const std::string &text) : PRCAttributeEntry(title), type(KEPRCModellerAttributeTypeString)
184   {
185     value_text = text;
186   }
PRCSingleAttribute(const std::string title,int32_t integer)187 	PRCSingleAttribute(const std::string title, int32_t integer) : PRCAttributeEntry(title), type(KEPRCModellerAttributeTypeInt)
188   {
189     value.integer = integer;
190   }
PRCSingleAttribute(const std::string title,double real)191 	PRCSingleAttribute(const std::string title, double real) : PRCAttributeEntry(title), type(KEPRCModellerAttributeTypeReal)
192   {
193     value.real = real;
194   }
PRCSingleAttribute(const std::string title,uint32_t time)195   PRCSingleAttribute(const std::string title, uint32_t time) : PRCAttributeEntry(title), type(KEPRCModellerAttributeTypeTime)
196   {
197     value.time = time;
198   }
PRCSingleAttribute(const std::string title,const std::string & text)199 	PRCSingleAttribute(const std::string title, const std::string &text) : PRCAttributeEntry(title), type(KEPRCModellerAttributeTypeString)
200   {
201     value_text = text;
202   }
203   void serializeSingleAttribute(PRCbitStream&) const;
204   EPRCModellerAttributeType  type;
205   union PRCSingleAttributeData
206   {
207     int32_t integer;
208     double real;
209     uint32_t time;
210   } value;
211   std::string value_text;
212 };
213 
214 class PRCAttribute : public PRCAttributeEntry
215 {
216   public:
PRCAttribute()217   PRCAttribute() : PRCAttributeEntry() {}
PRCAttribute(uint32_t title)218 	PRCAttribute(uint32_t title) : PRCAttributeEntry(title) {}
PRCAttribute(const std::string title)219 	PRCAttribute(const std::string title) : PRCAttributeEntry(title) {}
220   void serializeAttribute(PRCbitStream &) const;
newKey()221   PRCSingleAttribute& newKey() { attribute_keys.resize(attribute_keys.size()+1); return attribute_keys.back(); }
addKey(const PRCSingleAttribute & key)222   void addKey(const PRCSingleAttribute &key) { attribute_keys.push_back(key); }
223   std::deque<PRCSingleAttribute> attribute_keys;
224 };
225 
226 typedef std::list<PRCAttribute> PRCAttributeList;
227 
228 class PRCAttributes
229 {
230   public:
231   void serializeAttributes(PRCbitStream&) const;
newAttribute()232   PRCAttribute& newAttribute() { attributes.push_front(PRCAttribute()); return attributes.front(); }
addAttribute(const PRCAttribute & attribute)233   void addAttribute(const PRCAttribute &attribute) { attributes.push_front(attribute); }
234   PRCAttributeList attributes;
235 };
236 
237 bool type_eligible_for_reference(uint32_t type);
238 uint32_t makeCADID();
239 uint32_t makePRCID();
240 
241 class ContentPRCBase : public PRCAttributes
242 {
243   public:
244   ContentPRCBase(uint32_t t, std::string n="") :
type(t)245     type(t),name(n),CAD_identifier(0), CAD_persistent_identifier(0), PRC_unique_identifier(0)
246   {
247     if(type_eligible_for_reference(type))
248     {
249       CAD_identifier = makeCADID();
250       PRC_unique_identifier = makePRCID();
251     }
252   }
253   void serializeContentPRCBase(PRCbitStream&) const;
getPRCID()254   uint32_t getPRCID() const { return PRC_unique_identifier; }
getType()255   uint32_t getType() const { return type; }
256   uint32_t type;
257   std::string name;
258   uint32_t CAD_identifier, CAD_persistent_identifier, PRC_unique_identifier;
259 };
260 
261 class PRCReferenceUniqueIdentifier
262 {
263 public:
PRCReferenceUniqueIdentifier()264   PRCReferenceUniqueIdentifier() :
265     type(0), unique_identifier(m1) {}
266   void serializeReferenceUniqueIdentifier(PRCbitStream&);
267   uint32_t type;
268 // bool reference_in_same_file_structure;
269 // PRCUniqueId target_file_structure;
270   uint32_t unique_identifier;
271 };
272 
273 extern std::string currentName;
274 void writeName(PRCbitStream&,const std::string&);
275 void resetName();
276 
277 extern uint32_t current_layer_index;
278 extern uint32_t current_index_of_line_style;
279 extern uint16_t current_behaviour_bit_field;
280 
281 void writeGraphics(PRCbitStream&,uint32_t=m1,uint32_t=m1,uint16_t=1,bool=false);
282 void resetGraphics();
283 
284 void resetGraphicsAndName();
285 
286 struct PRCRgbColor
287 {
288   PRCRgbColor(double r=0.0, double g=0.0, double b=0.0) :
redPRCRgbColor289     red(r), green(g), blue(b) {}
290   double red,green,blue;
291   void serializeRgbColor(PRCbitStream&);
292 
293   bool operator==(const PRCRgbColor &c) const
294   {
295     return (red==c.red && green==c.green && blue==c.blue);
296   }
297   bool operator!=(const PRCRgbColor &c) const
298   {
299     return !(red==c.red && green==c.green && blue==c.blue);
300   }
301   bool operator<(const PRCRgbColor &c) const
302   {
303     if(red!=c.red)
304       return (red<c.red);
305     if(green!=c.green)
306       return (green<c.green);
307     return (blue<c.blue);
308   }
309 };
310 
311 class PRCPicture : public ContentPRCBase
312 {
313 public:
314   PRCPicture(std::string n="") :
ContentPRCBase(PRC_TYPE_GRAPH_Picture,n)315   ContentPRCBase(PRC_TYPE_GRAPH_Picture,n), format(KEPRCPicture_PNG), uncompressed_file_index(m1), pixel_width(0), pixel_height(0) {}
316   void serializePicture(PRCbitStream&);
317   EPRCPictureDataFormat format;
318   uint32_t uncompressed_file_index;
319   uint32_t pixel_width;
320   uint32_t pixel_height;
321 };
322 
323 struct PRCVector2d
324 {
PRCVector2dPRCVector2d325   PRCVector2d() :
326   x(0.0), y(0.0) {}
PRCVector2dPRCVector2d327   PRCVector2d(double X, double Y) :
328   x(X), y(Y) {}
329   void serializeVector2d(PRCbitStream&);
330   double x;
331   double y;
332   PRCVector2d(const double c[], double fx=0, double fy=0) :
333   x(c?c[0]:fx), y(c?c[1]:fy) {}
PRCVector2dPRCVector2d334   PRCVector2d(const PRCVector2d& sVector2d) :
335   x(sVector2d.x), y(sVector2d.y) {}
336 
SetPRCVector2d337   void Set(double fx, double fy)
338   { x = fx; y = fy; }
DotPRCVector2d339   double Dot(const PRCVector2d & sPt) const
340   { return(x*sPt.x)+(y*sPt.y); }
LengthSquaredPRCVector2d341   double LengthSquared()
342   { return(x*x+y*y); }
343 
344   friend PRCVector2d operator + (const PRCVector2d& a, const PRCVector2d& b)
345   { return PRCVector2d(a.x+b.x,a.y+b.y); }
346   friend PRCVector2d operator - (const PRCVector2d& a)
347   { return PRCVector2d(-a.x,-a.y); }
348   friend PRCVector2d operator - (const PRCVector2d& a, const PRCVector2d& b)
349   { return PRCVector2d(a.x-b.x,a.y-b.y); }
350   friend PRCVector2d operator * (const PRCVector2d& a, const double d)
351   { return PRCVector2d(a.x*d,a.y*d); }
352   friend PRCVector2d operator * (const double d, const PRCVector2d& a)
353   { return PRCVector2d(a.x*d,a.y*d); }
354   friend PRCVector2d operator / (const PRCVector2d& a, const double d)
355   { return PRCVector2d(a.x/d,a.y/d); }
356 
357   double Length();
358   bool Normalize();
359 
360   bool operator==(const PRCVector2d &v) const
361   {
362     return x==v.x && y==v.y;
363   }
364   bool operator!=(const PRCVector2d &v) const
365   {
366     return !(x==v.x && y==v.y);
367   }
368   bool operator<(const PRCVector2d &v) const
369   {
370     if(x!=v.x)
371       return (x<v.x);
372     return (y<v.y);
373   }
374   friend std::ostream& operator << (std::ostream& out, const PRCVector2d& v)
375   {
376     out << "(" << v.x << "," << v.y << ")";
377     return out;
378   }
379 };
380 
381 class PRCTextureDefinition : public ContentPRCBase
382 {
383 public:
384   PRCTextureDefinition(std::string n="") :
ContentPRCBase(PRC_TYPE_GRAPH_TextureDefinition,n)385     ContentPRCBase(PRC_TYPE_GRAPH_TextureDefinition,n), picture_index(m1), texture_mapping_attribute(PRC_TEXTURE_MAPPING_DIFFUSE),
386     texture_mapping_attribute_intensity(1.0), texture_mapping_attribute_components(PRC_TEXTURE_MAPPING_COMPONENTS_RGBA),
387     texture_function(KEPRCTextureFunction_Modulate), texture_applying_mode(PRC_TEXTURE_APPLYING_MODE_NONE),
388     texture_wrapping_mode_S(KEPRCTextureWrappingMode_Unknown), texture_wrapping_mode_T(KEPRCTextureWrappingMode_Unknown) // ,
389     // texture_transformation(false), texture_flip_S(false), texture_flip_T(false),
390     // behaviour(PRC_TRANSFORMATION_Identity), scale(1.0,1.0), uniform_scale(1.0)
391     {}
392   void serializeTextureDefinition(PRCbitStream&);
393   uint32_t picture_index;
394   uint32_t texture_mapping_attribute;
395   double texture_mapping_attribute_intensity;
396   uint8_t texture_mapping_attribute_components;
397   EPRCTextureFunction texture_function;
398   uint8_t texture_applying_mode;
399   EPRCTextureWrappingMode texture_wrapping_mode_S;
400   EPRCTextureWrappingMode texture_wrapping_mode_T;
401   // bool texture_transformation;
402   // bool texture_flip_S;
403   // bool texture_flip_T;
404   // uint8_t behaviour;
405   // PRCVector2d origin;
406   // PRCVector2d X;
407   // PRCVector2d Y;
408   // PRCVector2d scale;
409   // double uniform_scale;
410   // double X_homegeneous_coord;
411   // double Y_homegeneous_coord;
412   // double origin_homegeneous_coord;
413 };
414 typedef std::deque <PRCTextureDefinition*>  PRCTextureDefinitionList;
415 
416 class PRCMaterial
417 {
418 public:
~PRCMaterial()419   virtual ~PRCMaterial() {}
420   virtual void serializeMaterial(PRCbitStream&) = 0;
421 };
422 typedef std::deque <PRCMaterial*>  PRCMaterialList;
423 
424 class PRCMaterialGeneric : public ContentPRCBase, public PRCMaterial
425 {
426 public:
427   PRCMaterialGeneric(std::string n="") :
ContentPRCBase(PRC_TYPE_GRAPH_Material,n)428     ContentPRCBase(PRC_TYPE_GRAPH_Material,n),
429     ambient(m1), diffuse(m1), emissive(m1), specular(m1),
430     shininess(0.0),
431     ambient_alpha(1.0), diffuse_alpha(1.0), emissive_alpha(1.0), specular_alpha(1.0)
432     {}
433   void serializeMaterialGeneric(PRCbitStream&);
serializeMaterial(PRCbitStream & pbs)434   void serializeMaterial(PRCbitStream &pbs) { serializeMaterialGeneric(pbs); }
435   uint32_t picture_index;
436   uint32_t ambient;
437   uint32_t diffuse;
438   uint32_t emissive;
439   uint32_t specular;
440   double shininess;
441   double ambient_alpha;
442   double diffuse_alpha;
443   double emissive_alpha;
444   double specular_alpha;
445 
446   bool operator==(const PRCMaterialGeneric &m) const
447   {
448     return (ambient==m.ambient && diffuse==m.diffuse && emissive==m.emissive && specular==m.specular && shininess==m.shininess &&
449             ambient_alpha==m.ambient_alpha && diffuse_alpha==m.diffuse_alpha && emissive_alpha==m.emissive_alpha && specular_alpha==m.specular_alpha);
450   }
451 };
452 
453 class PRCTextureApplication : public ContentPRCBase, public PRCMaterial
454 {
455 public:
456   PRCTextureApplication(std::string n="") :
ContentPRCBase(PRC_TYPE_GRAPH_TextureApplication,n)457     ContentPRCBase(PRC_TYPE_GRAPH_TextureApplication,n),
458     material_generic_index(m1), texture_definition_index(m1),
459     next_texture_index(m1), UV_coordinates_index(0)
460     {}
461   void serializeTextureApplication(PRCbitStream&);
serializeMaterial(PRCbitStream & pbs)462   void serializeMaterial(PRCbitStream &pbs) { serializeTextureApplication(pbs); }
463   uint32_t material_generic_index;
464   uint32_t texture_definition_index;
465   uint32_t next_texture_index;
466   uint32_t UV_coordinates_index;
467 };
468 
469 class PRCLinePattern : public ContentPRCBase
470 {
471 public:
472   PRCLinePattern(std::string n="") :
ContentPRCBase(PRC_TYPE_GRAPH_LinePattern,n)473   ContentPRCBase(PRC_TYPE_GRAPH_LinePattern,n),
474   phase(0), is_real_length(false) {}
475   void serializeLinePattern(PRCbitStream&);
476   std::vector<double> lengths;
477   double phase;
478   bool is_real_length;
479 };
480 typedef std::deque <PRCLinePattern*>  PRCLinePatternList;
481 
482 class PRCStyle : public ContentPRCBase
483 {
484 public:
485   PRCStyle(std::string n="") :
ContentPRCBase(PRC_TYPE_GRAPH_Style,n)486     ContentPRCBase(PRC_TYPE_GRAPH_Style,n), line_width(0.0), is_vpicture(false), line_pattern_vpicture_index(m1),
487     is_material(false), color_material_index(m1), is_transparency_defined(false), transparency(255), additional(0)
488     {}
489   void serializeCategory1LineStyle(PRCbitStream&);
490   double line_width;
491   bool is_vpicture;
492   uint32_t line_pattern_vpicture_index;
493   bool is_material;
494   uint32_t color_material_index;
495   bool is_transparency_defined;
496   uint8_t transparency;
497   uint8_t additional;
498 };
499 typedef std::deque <PRCStyle*>  PRCStyleList;
500 
501 class PRCTessFace
502 {
503 public:
PRCTessFace()504   PRCTessFace() :
505   start_wire(0), used_entities_flag(0),
506   start_triangulated(0), number_of_texture_coordinate_indexes(0),
507   is_rgba(false), behaviour(PRC_GRAPHICS_Show)
508   {}
509   void serializeTessFace(PRCbitStream&);
510   std::vector<uint32_t> line_attributes;
511   uint32_t start_wire;			// specifing bounding wire seems not to work as of Acrobat/Reader 9.2
512   std::vector<uint32_t> sizes_wire;	// specifing bounding wire seems not to work as of Acrobat/Reader 9.2
513   uint32_t used_entities_flag;
514   uint32_t start_triangulated;
515   std::vector<uint32_t> sizes_triangulated;
516   uint32_t number_of_texture_coordinate_indexes;
517   bool is_rgba;
518   std::vector<uint8_t> rgba_vertices;
519   uint32_t behaviour;
520 };
521 typedef std::deque <PRCTessFace*>  PRCTessFaceList;
522 
523 class PRCContentBaseTessData
524 {
525 public:
PRCContentBaseTessData()526   PRCContentBaseTessData() :
527   is_calculated(false) {}
528   void serializeContentBaseTessData(PRCbitStream&);
529   bool is_calculated;
530   std::vector<double> coordinates;
531 };
532 
533 class PRCTess : public PRCContentBaseTessData
534 {
535 public:
~PRCTess()536   virtual ~PRCTess() {}
537   virtual void serializeBaseTessData(PRCbitStream &pbs) = 0;
538 };
539 typedef std::deque <PRCTess*>  PRCTessList;
540 
541 class PRC3DTess : public PRCTess
542 {
543 public:
PRC3DTess()544   PRC3DTess() :
545   has_faces(false), has_loops(false),
546   crease_angle(25.8419)  // arccos(0.9), default found in Acrobat output
547   {}
~PRC3DTess()548   ~PRC3DTess() { for(PRCTessFaceList::iterator it=face_tessellation.begin(); it!=face_tessellation.end(); ++it) delete *it; }
549   void serialize3DTess(PRCbitStream&);
serializeBaseTessData(PRCbitStream & pbs)550   void serializeBaseTessData(PRCbitStream &pbs) { serialize3DTess(pbs); }
551   void addTessFace(PRCTessFace*& pTessFace);
552 
553   bool has_faces;
554   bool has_loops;
555   double crease_angle;
556   std::vector<double> normal_coordinate;
557   std::vector<uint32_t> wire_index;		// specifing bounding wire seems not to work as of Acrobat/Reader 9.2
558   std::vector<uint32_t> triangulated_index;
559   PRCTessFaceList face_tessellation;
560   std::vector<double> texture_coordinate;
561 };
562 
563 class PRC3DWireTess : public PRCTess
564 {
565 public:
PRC3DWireTess()566   PRC3DWireTess() :
567   is_rgba(false), is_segment_color(false) {}
568   void serialize3DWireTess(PRCbitStream&);
serializeBaseTessData(PRCbitStream & pbs)569   void serializeBaseTessData(PRCbitStream &pbs) { serialize3DWireTess(pbs); }
570 
571   bool is_rgba;
572   bool is_segment_color;
573   std::vector<uint32_t> wire_indexes;
574   std::vector<uint8_t> rgba_vertices;
575 };
576 
577 class PRCMarkupTess : public PRCTess
578 {
579 public:
PRCMarkupTess()580   PRCMarkupTess() :
581   behaviour(0)
582   {}
583   void serializeMarkupTess(PRCbitStream&);
serializeBaseTessData(PRCbitStream & pbs)584   void serializeBaseTessData(PRCbitStream &pbs) { serializeMarkupTess(pbs); }
585 
586   std::vector<uint32_t> codes;
587   std::vector<std::string> texts;
588   std::string label;
589   uint8_t behaviour;
590 };
591 
592 class PRCGraphics
593 {
594 public:
PRCGraphics()595   PRCGraphics() : layer_index(m1), index_of_line_style(m1), behaviour_bit_field(PRC_GRAPHICS_Show) {}
596   void serializeGraphics(PRCbitStream&);
597   void serializeGraphicsForced(PRCbitStream&);
has_graphics()598   bool has_graphics() { return (index_of_line_style!=m1 || layer_index!=m1 || behaviour_bit_field!=PRC_GRAPHICS_Show) ; }
599   uint32_t layer_index;
600   uint32_t index_of_line_style;
601   uint16_t behaviour_bit_field;
602 };
603 typedef std::deque <PRCGraphics*>  PRCGraphicsList;
604 
605 void writeGraphics(PRCbitStream&,const PRCGraphics&,bool=false);
606 
607 class PRCMarkup: public PRCGraphics, public ContentPRCBase
608 {
609 public:
610   PRCMarkup(std::string n="") :
ContentPRCBase(PRC_TYPE_MKP_Markup,n)611     ContentPRCBase(PRC_TYPE_MKP_Markup,n),
612     type(KEPRCMarkupType_Unknown), sub_type(KEPRCMarkupSubType_Unknown), index_tessellation(m1) {}
613   void serializeMarkup(PRCbitStream&);
614   EPRCMarkupType type;
615   EPRCMarkupSubType sub_type;
616 // vector<PRCReferenceUniqueIdentifier> linked_items;
617 // vector<PRCReferenceUniqueIdentifier> leaders;
618   uint32_t index_tessellation;
619 };
620 typedef std::deque <PRCMarkup*>  PRCMarkupList;
621 
622 class PRCAnnotationItem: public PRCGraphics, public ContentPRCBase
623 {
624 public:
625   PRCAnnotationItem(std::string n="") :
ContentPRCBase(PRC_TYPE_MKP_AnnotationItem,n)626     ContentPRCBase(PRC_TYPE_MKP_AnnotationItem,n) {}
627   void serializeAnnotationItem(PRCbitStream&);
serializeAnnotationEntity(PRCbitStream & pbs)628   void serializeAnnotationEntity(PRCbitStream &pbs) { serializeAnnotationItem(pbs); }
629   PRCReferenceUniqueIdentifier markup;
630 };
631 typedef std::deque <PRCAnnotationItem*>  PRCAnnotationItemList;
632 
633 class PRCRepresentationItemContent: public PRCGraphics, public ContentPRCBase
634 {
635 public:
636   PRCRepresentationItemContent(uint32_t t, std::string n="") :
ContentPRCBase(t,n)637     ContentPRCBase(t,n),
638     index_local_coordinate_system(m1), index_tessellation(m1) {}
639   void serializeRepresentationItemContent(PRCbitStream&);
640   uint32_t index_local_coordinate_system;
641   uint32_t index_tessellation;
642 };
643 
644 class PRCRepresentationItem : public PRCRepresentationItemContent
645 {
646 public:
647   PRCRepresentationItem(uint32_t t, std::string n="") :
PRCRepresentationItemContent(t,n)648     PRCRepresentationItemContent(t,n) {}
~PRCRepresentationItem()649   virtual ~PRCRepresentationItem() {}
650   virtual void serializeRepresentationItem(PRCbitStream &pbs) = 0;
651 };
652 typedef std::deque <PRCRepresentationItem*>  PRCRepresentationItemList;
653 
654 class PRCBrepModel : public PRCRepresentationItem
655 {
656 public:
657   PRCBrepModel(std::string n="") :
PRCRepresentationItem(PRC_TYPE_RI_BrepModel,n)658     PRCRepresentationItem(PRC_TYPE_RI_BrepModel,n), has_brep_data(true), context_id(m1), body_id(m1), is_closed(false) {}
659   void serializeBrepModel(PRCbitStream&);
serializeRepresentationItem(PRCbitStream & pbs)660   void serializeRepresentationItem(PRCbitStream &pbs) { serializeBrepModel(pbs); }
661   bool has_brep_data;
662   uint32_t context_id;
663   uint32_t body_id;
664   bool is_closed;
665 };
666 
667 class PRCPolyBrepModel : public PRCRepresentationItem
668 {
669 public:
670   PRCPolyBrepModel(std::string n="") :
PRCRepresentationItem(PRC_TYPE_RI_PolyBrepModel,n)671     PRCRepresentationItem(PRC_TYPE_RI_PolyBrepModel,n), is_closed(false) {}
672   void serializePolyBrepModel(PRCbitStream&);
serializeRepresentationItem(PRCbitStream & pbs)673   void serializeRepresentationItem(PRCbitStream &pbs) { serializePolyBrepModel(pbs); }
674   bool is_closed;
675 };
676 
677 class PRCPointSet : public PRCRepresentationItem
678 {
679 public:
680   PRCPointSet(std::string n="") :
PRCRepresentationItem(PRC_TYPE_RI_PointSet,n)681     PRCRepresentationItem(PRC_TYPE_RI_PointSet,n) {}
682   void serializePointSet(PRCbitStream&);
serializeRepresentationItem(PRCbitStream & pbs)683   void serializeRepresentationItem(PRCbitStream &pbs) { serializePointSet(pbs); }
684   std::vector<PRCVector3d> point;
685 };
686 
687 class PRCWire : public PRCRepresentationItem
688 {
689 public:
690   PRCWire(std::string n="") :
PRCRepresentationItem(PRC_TYPE_RI_Curve,n)691     PRCRepresentationItem(PRC_TYPE_RI_Curve,n), has_wire_body(true), context_id(m1), body_id(m1) {}
692   void serializeWire(PRCbitStream&);
serializeRepresentationItem(PRCbitStream & pbs)693   void serializeRepresentationItem(PRCbitStream &pbs) { serializeWire(pbs); }
694   bool has_wire_body;
695   uint32_t context_id;
696   uint32_t body_id;
697 };
698 
699 class PRCPolyWire : public PRCRepresentationItem
700 {
701 public:
702   PRCPolyWire(std::string n="") :
PRCRepresentationItem(PRC_TYPE_RI_PolyWire,n)703     PRCRepresentationItem(PRC_TYPE_RI_PolyWire,n) {}
704   void serializePolyWire(PRCbitStream&);
serializeRepresentationItem(PRCbitStream & pbs)705   void serializeRepresentationItem(PRCbitStream &pbs) { serializePolyWire(pbs); }
706 };
707 
708 class PRCSet : public PRCRepresentationItem
709 {
710 public:
711   PRCSet(std::string n="") :
PRCRepresentationItem(PRC_TYPE_RI_Set,n)712     PRCRepresentationItem(PRC_TYPE_RI_Set,n) {}
~PRCSet()713   ~PRCSet() { for(PRCRepresentationItemList::iterator it=elements.begin(); it!=elements.end(); ++it) delete *it; }
714   void serializeSet(PRCbitStream&);
serializeRepresentationItem(PRCbitStream & pbs)715   void serializeRepresentationItem(PRCbitStream &pbs) { serializeSet(pbs); }
716   uint32_t addBrepModel(PRCBrepModel*& pBrepModel);
717   uint32_t addPolyBrepModel(PRCPolyBrepModel*& pPolyBrepModel);
718   uint32_t addPointSet(PRCPointSet*& pPointSet);
719   uint32_t addSet(PRCSet*& pSet);
720   uint32_t addWire(PRCWire*& pWire);
721   uint32_t addPolyWire(PRCPolyWire*& pPolyWire);
722   uint32_t addRepresentationItem(PRCRepresentationItem*& pRepresentationItem);
723   PRCRepresentationItemList elements;
724 };
725 
726 class PRCTransformation3d
727 {
728 public:
~PRCTransformation3d()729   virtual ~PRCTransformation3d() {}
730   virtual void serializeTransformation3d(PRCbitStream&) const =0;
731 };
732 typedef std::deque <PRCTransformation3d*> PRCTransformation3dList;
733 
734 class PRCGeneralTransformation3d : public PRCTransformation3d
735 {
736 public:
PRCGeneralTransformation3d()737   PRCGeneralTransformation3d()
738   {
739     setidentity();
740   }
PRCGeneralTransformation3d(const double t[])741   PRCGeneralTransformation3d(const double t[])
742   {
743     set(t);
744   }
745 
746   void serializeGeneralTransformation3d(PRCbitStream&) const;
serializeTransformation3d(PRCbitStream & pbs)747   void serializeTransformation3d(PRCbitStream& pbs)  const { serializeGeneralTransformation3d(pbs); }
748   double mat[4][4];
749   bool operator==(const PRCGeneralTransformation3d &t) const
750   {
751     for (size_t i=0;i<4;i++)
752       for (size_t j=0;j<4;j++)
753         if(mat[i][j]!=t.mat[i][j])
754          return false;
755     return true;
756   }
757   bool operator<(const PRCGeneralTransformation3d &t) const
758   {
759     for (size_t i=0;i<4;i++)
760       for (size_t j=0;j<4;j++)
761         if(mat[i][j]!=t.mat[i][j])
762         {
763           return (mat[i][j]<t.mat[i][j]);
764         }
765     return false;
766   }
set(const double t[])767   void set(const double t[])
768   {
769     if(t!=NULL)
770      for (size_t i=0;i<4;i++)
771        for (size_t j=0;j<4;j++)
772          mat[i][j]=t[4*i+j];
773     else
774       setidentity();
775   }
setidentity()776   void setidentity()
777   {
778     mat[0][0]=1; mat[0][1]=0; mat[0][2]=0; mat[0][3]=0;
779     mat[1][0]=0; mat[1][1]=1; mat[1][2]=0; mat[1][3]=0;
780     mat[2][0]=0; mat[2][1]=0; mat[2][2]=1; mat[2][3]=0;
781     mat[3][0]=0; mat[3][1]=0; mat[3][2]=0; mat[3][3]=1;
782   }
isidtransform()783   bool isidtransform() const {
784     return(
785     mat[0][0]==1 && mat[0][1]==0 && mat[0][2]==0 && mat[0][3]==0 &&
786     mat[1][0]==0 && mat[1][1]==1 && mat[1][2]==0 && mat[1][3]==0 &&
787     mat[2][0]==0 && mat[2][1]==0 && mat[2][2]==1 && mat[2][3]==0 &&
788     mat[3][0]==0 && mat[3][1]==0 && mat[3][2]==0 && mat[3][3]==1);
789   }
isnotidtransform()790   bool isnotidtransform() const {
791     return !isidtransform();
792   }
M(size_t i,size_t j)793   double M(size_t i, size_t j) const {
794     // Like Fortran, PRC uses transposed (column-major) format!
795     return mat[j][i];
796   }
797 };
798 typedef std::deque <PRCGeneralTransformation3d> PRCGeneralTransformation3dList;
799 
800 class PRCCartesianTransformation3d : public PRCTransformation3d
801 {
802 public:
PRCCartesianTransformation3d()803   PRCCartesianTransformation3d() :
804     behaviour(PRC_TRANSFORMATION_Identity), origin(0.0,0.0,0.0), X(1.0,0.0,0.0), Y(0.0,1.0,0.0), Z(0.0,0.0,1.0),
805     scale(1.0,1.0,1.0), uniform_scale(1.0),
806     X_homogeneous_coord(0.0), Y_homogeneous_coord(0.0), Z_homogeneous_coord(0.0), origin_homogeneous_coord(1.0) {}
PRCCartesianTransformation3d(const double o[3],const double x[3],const double y[3],double sc)807   PRCCartesianTransformation3d(const double o[3], const double x[3], const double y[3], double sc) :
808     behaviour(PRC_TRANSFORMATION_Identity), origin(o,0.0,0.0,0.0), X(x,1.0,0.0,0.0), Y(y,0.0,1.0,0.0), Z(0.0,0.0,1.0),
809     scale(1.0,1.0,1.0), uniform_scale(sc),
810     X_homogeneous_coord(0.0), Y_homogeneous_coord(0.0), Z_homogeneous_coord(0.0), origin_homogeneous_coord(1.0)
811     {
812       if(origin!=PRCVector3d(0.0,0.0,0.0))
813         behaviour = behaviour | PRC_TRANSFORMATION_Translate;
814       if(X!=PRCVector3d(1.0,0.0,0.0) || Y!=PRCVector3d(0.0,1.0,0.0))
815         behaviour = behaviour | PRC_TRANSFORMATION_Rotate;
816       if(uniform_scale!=1)
817         behaviour = behaviour | PRC_TRANSFORMATION_Scale;
818     }
819   void serializeCartesianTransformation3d(PRCbitStream& pbs) const;
serializeTransformation3d(PRCbitStream & pbs)820   void serializeTransformation3d(PRCbitStream& pbs) const { serializeCartesianTransformation3d(pbs); }
821   uint8_t behaviour;
822   PRCVector3d origin;
823   PRCVector3d X;
824   PRCVector3d Y;
825   PRCVector3d Z;
826   PRCVector3d scale;
827   double uniform_scale;
828   double X_homogeneous_coord;
829   double Y_homogeneous_coord;
830   double Z_homogeneous_coord;
831   double origin_homogeneous_coord;
832   bool operator==(const PRCCartesianTransformation3d &t) const
833   {
834     return behaviour==t.behaviour && origin==t.origin && X==t.X && Y==t.Y && Z==t.Z && scale==t.scale && uniform_scale==t.uniform_scale &&
835            X_homogeneous_coord==t.X_homogeneous_coord && Y_homogeneous_coord==t.Y_homogeneous_coord &&
836            Z_homogeneous_coord==t.Z_homogeneous_coord && origin_homogeneous_coord==t.origin_homogeneous_coord;
837   }
838 };
839 
840 class PRCTransformation
841 {
842 public:
PRCTransformation()843   PRCTransformation() :
844     has_transformation(false), geometry_is_2D(false), behaviour(PRC_TRANSFORMATION_Identity),
845     origin(0.0,0.0,0.0), x_axis(1.0,0.0,0.0), y_axis(0.0,1.0,0.0), scale(1) {}
846   void serializeTransformation(PRCbitStream&);
847   bool has_transformation;
848   bool geometry_is_2D;
849   uint8_t behaviour;
850   PRCVector3d origin;
851   PRCVector3d x_axis;
852   PRCVector3d y_axis;
853   double scale;
854 };
855 
856 class PRCCoordinateSystem : public PRCRepresentationItem
857 {
858 public:
859   PRCCoordinateSystem(std::string n="") :
PRCRepresentationItem(PRC_TYPE_RI_CoordinateSystem,n)860   PRCRepresentationItem(PRC_TYPE_RI_CoordinateSystem,n), axis_set(NULL) {}
~PRCCoordinateSystem()861   ~PRCCoordinateSystem() { delete axis_set; }
862   void serializeCoordinateSystem(PRCbitStream&);
serializeRepresentationItem(PRCbitStream & pbs)863   void serializeRepresentationItem(PRCbitStream &pbs) { serializeCoordinateSystem(pbs); }
setAxisSet(PRCGeneralTransformation3d * & transform)864   void setAxisSet(PRCGeneralTransformation3d*& transform) { axis_set = transform; transform = NULL; }
setAxisSet(PRCCartesianTransformation3d * & transform)865   void setAxisSet(PRCCartesianTransformation3d*& transform) { axis_set = transform; transform = NULL; }
866   PRCTransformation3d *axis_set;
867   bool operator==(const PRCCoordinateSystem &t) const
868   {
869     if(index_local_coordinate_system!=t.index_local_coordinate_system)
870       return false;
871     PRCGeneralTransformation3d*       axis_set_general = dynamic_cast<PRCGeneralTransformation3d*>(axis_set);
872     PRCGeneralTransformation3d*     t_axis_set_general = dynamic_cast<PRCGeneralTransformation3d*>(t.axis_set);
873     PRCCartesianTransformation3d*   axis_set_cartesian = dynamic_cast<PRCCartesianTransformation3d*>(axis_set);
874     PRCCartesianTransformation3d* t_axis_set_cartesian = dynamic_cast<PRCCartesianTransformation3d*>(t.axis_set);
875     if(axis_set_general!=NULL)
876       return (t_axis_set_general!=NULL?(*axis_set_general==*t_axis_set_general):false);
877     if(axis_set_cartesian!=NULL)
878       return (t_axis_set_cartesian!=NULL?(*axis_set_cartesian==*t_axis_set_cartesian):false);
879     return false;
880   }
881 };
882 typedef std::deque <PRCCoordinateSystem*>  PRCCoordinateSystemList;
883 
884 struct PRCFontKey
885 {
886   uint32_t font_size;
887   uint8_t  attributes;
888 };
889 
890 class PRCFontKeysSameFont
891 {
892 public:
893   void serializeFontKeysSameFont(PRCbitStream&);
894   std::string font_name;
895   uint32_t char_set;
896   std::vector<PRCFontKey> font_keys;
897 
898 };
899 
900 // Topology
901 class PRCBaseGeometry : public PRCAttributes
902 {
903 public:
PRCBaseGeometry()904   PRCBaseGeometry() :
905     base_information(false), identifier(0) {}
906   PRCBaseGeometry(std::string n, uint32_t id = 0) :
base_information(true)907     base_information(true),name(n),identifier(id) {}
908   void serializeBaseGeometry(PRCbitStream&);
909   bool base_information;
910   std::string name;
911   uint32_t identifier;
912 };
913 
914 class PRCBoundingBox
915 {
916 public:
PRCBoundingBox()917   PRCBoundingBox() : min(0.0,0.0,0.0), max(0.0,0.0,0.0) {}
PRCBoundingBox(const PRCVector3d & m1,const PRCVector3d & m2)918   PRCBoundingBox(const PRCVector3d &m1, const PRCVector3d& m2) : min(m1),max(m2) {}
919   void serializeBoundingBox(PRCbitStream &pbs);
920   PRCVector3d min;
921   PRCVector3d max;
922 };
923 
924 class PRCDomain
925 {
926 public:
927   void serializeDomain(PRCbitStream &pbs);
928   PRCVector2d min;
929   PRCVector2d max;
930 };
931 
932 class PRCInterval
933 {
934 public:
PRCInterval()935   PRCInterval() : min(0), max(0) {}
PRCInterval(double m,double M)936   PRCInterval(double m, double M) : min(m), max(M) {}
937   void serializeInterval(PRCbitStream &pbs);
938   double min;
939   double max;
940 };
941 
942 class PRCParameterization
943 {
944 public:
PRCParameterization()945   PRCParameterization() : parameterization_coeff_a(1), parameterization_coeff_b(0) {}
PRCParameterization(double min,double max)946   PRCParameterization(double min, double max) : interval(min, max), parameterization_coeff_a(1), parameterization_coeff_b(0) {}
947   void serializeParameterization(PRCbitStream &pbs);
948   PRCInterval interval;
949   double parameterization_coeff_a;
950   double parameterization_coeff_b;
951 };
952 
953 class PRCUVParameterization
954 {
955 public:
PRCUVParameterization()956   PRCUVParameterization() : swap_uv(false),
957     parameterization_on_u_coeff_a(1), parameterization_on_v_coeff_a(1),
958     parameterization_on_u_coeff_b(0), parameterization_on_v_coeff_b(0) {}
959   void serializeUVParameterization(PRCbitStream &pbs);
960   bool swap_uv;
961   PRCDomain uv_domain;
962   double parameterization_on_u_coeff_a;
963   double parameterization_on_v_coeff_a;
964   double parameterization_on_u_coeff_b;
965   double parameterization_on_v_coeff_b;
966 };
967 
968 class PRCControlPoint
969 {
970 public:
PRCControlPoint()971   PRCControlPoint() :
972    x(0), y(0), z(0), w(1) {}
973   PRCControlPoint(double X, double Y, double Z=0, double W=1) :
x(X)974    x(X), y(Y), z(Z), w(W) {}
PRCControlPoint(const PRCVector3d & v)975   PRCControlPoint(const PRCVector3d &v) :
976    x(v.x), y(v.y), z(v.z), w(1) {}
977   void Set(double fx, double fy, double fz, double fw=1)
978    { x = fx; y = fy; z = fz; w = fw; }
979   double x;
980   double y;
981   double z;
982   double w;
983 };
984 
985 class PRCContentSurface: public PRCBaseGeometry
986 {
987 public:
PRCContentSurface()988   PRCContentSurface() :
989     PRCBaseGeometry(), extend_info(KEPRCExtendTypeNone) {}
PRCContentSurface(std::string n)990   PRCContentSurface(std::string n) :
991     PRCBaseGeometry(n,makeCADID()),extend_info(KEPRCExtendTypeNone) {}
992   void serializeContentSurface(PRCbitStream&);
993   EPRCExtendType extend_info;
994 };
995 
996 class PRCSurface : public PRCContentSurface
997 {
998 public:
PRCSurface()999   PRCSurface() :
1000     PRCContentSurface() {}
PRCSurface(std::string n)1001   PRCSurface(std::string n) :
1002     PRCContentSurface(n) {}
~PRCSurface()1003   virtual ~PRCSurface() {}
1004   virtual void  serializeSurface(PRCbitStream &pbs) = 0;
1005 };
1006 
1007 class PRCNURBSSurface : public PRCSurface
1008 {
1009 public:
PRCNURBSSurface()1010   PRCNURBSSurface() :
1011     PRCSurface(), knot_type(KEPRCKnotTypeUnspecified), surface_form(KEPRCBSplineSurfaceFormUnspecified) {}
PRCNURBSSurface(std::string n)1012   PRCNURBSSurface(std::string n) :
1013     PRCSurface(n), knot_type(KEPRCKnotTypeUnspecified), surface_form(KEPRCBSplineSurfaceFormUnspecified) {}
1014   void  serializeNURBSSurface(PRCbitStream &pbs);
serializeSurface(PRCbitStream & pbs)1015   void  serializeSurface(PRCbitStream &pbs) { serializeNURBSSurface(pbs); }
1016   bool is_rational;
1017   uint32_t degree_in_u;
1018   uint32_t degree_in_v;
1019   std::vector<PRCControlPoint> control_point;
1020   std::vector<double> knot_u;
1021   std::vector<double> knot_v;
1022   const EPRCKnotType knot_type;
1023   const EPRCBSplineSurfaceForm surface_form;
1024 };
1025 
1026 class PRCContentCurve: public PRCBaseGeometry
1027 {
1028 public:
PRCContentCurve()1029   PRCContentCurve() :
1030     PRCBaseGeometry(), extend_info(KEPRCExtendTypeNone), is_3d(true) {}
PRCContentCurve(std::string n)1031   PRCContentCurve(std::string n) :
1032     PRCBaseGeometry(n,makeCADID()),extend_info(KEPRCExtendTypeNone), is_3d(true) {}
1033   void serializeContentCurve(PRCbitStream&);
1034   EPRCExtendType extend_info;
1035   bool is_3d;
1036 };
1037 
1038 class PRCCurve : public PRCContentCurve
1039 {
1040 public:
PRCCurve()1041   PRCCurve() :
1042     PRCContentCurve() {}
PRCCurve(std::string n)1043   PRCCurve(std::string n) :
1044     PRCContentCurve(n) {}
~PRCCurve()1045   virtual ~PRCCurve() {}
1046   virtual void  serializeCurve(PRCbitStream &pbs) = 0;
1047 };
1048 typedef std::deque <PRCCurve*>  PRCCurveList;
1049 
1050 class PRCNURBSCurve : public PRCCurve
1051 {
1052 public:
PRCNURBSCurve()1053   PRCNURBSCurve() :
1054     PRCCurve(), knot_type(KEPRCKnotTypeUnspecified), curve_form(KEPRCBSplineCurveFormUnspecified) {}
PRCNURBSCurve(std::string n)1055   PRCNURBSCurve(std::string n) :
1056     PRCCurve(n), knot_type(KEPRCKnotTypeUnspecified), curve_form(KEPRCBSplineCurveFormUnspecified) {}
1057   void  serializeNURBSCurve(PRCbitStream &pbs);
serializeCurve(PRCbitStream & pbs)1058   void  serializeCurve(PRCbitStream &pbs) { serializeNURBSCurve(pbs); }
1059   bool is_rational;
1060   uint32_t degree;
1061   std::vector<PRCControlPoint> control_point;
1062   std::vector<double> knot;
1063   const EPRCKnotType knot_type;
1064   const EPRCBSplineCurveForm curve_form;
1065 };
1066 
1067 class PRCPolyLine : public PRCCurve, public PRCTransformation, public PRCParameterization
1068 {
1069 public:
PRCPolyLine()1070   PRCPolyLine() :
1071     PRCCurve() {}
PRCPolyLine(std::string n)1072   PRCPolyLine(std::string n) :
1073     PRCCurve(n) {}
1074   void  serializePolyLine(PRCbitStream &pbs);
serializeCurve(PRCbitStream & pbs)1075   void  serializeCurve(PRCbitStream &pbs) { serializePolyLine(pbs); }
1076   std::vector<PRCVector3d> point;
1077 };
1078 
1079 class PRCCircle : public PRCCurve, public PRCTransformation, public PRCParameterization
1080 {
1081 public:
PRCCircle()1082   PRCCircle() :
1083     PRCCurve(), PRCParameterization(0,2*pi) {}
PRCCircle(std::string n)1084   PRCCircle(std::string n) :
1085     PRCCurve(n), PRCParameterization(0,2*pi) {}
1086   void  serializeCircle(PRCbitStream &pbs);
serializeCurve(PRCbitStream & pbs)1087   void  serializeCurve(PRCbitStream &pbs) { serializeCircle(pbs); }
1088   double radius;
1089 };
1090 
1091 class PRCComposite : public PRCCurve, public PRCTransformation, public PRCParameterization
1092 {
1093 public:
PRCComposite()1094   PRCComposite() :
1095     PRCCurve() {}
PRCComposite(std::string n)1096   PRCComposite(std::string n) :
1097     PRCCurve(n) {}
1098   void  serializeComposite(PRCbitStream &pbs);
serializeCurve(PRCbitStream & pbs)1099   void  serializeCurve(PRCbitStream &pbs) { serializeComposite(pbs); }
1100   PRCCurveList base_curve;
1101   std::vector<bool> base_sense;
1102   bool is_closed;
1103 };
1104 
1105 class PRCBlend01 : public PRCSurface, public PRCTransformation, public PRCUVParameterization
1106 {
1107 public:
PRCBlend01()1108   PRCBlend01() :
1109     PRCSurface(), center_curve(NULL), origin_curve(NULL), tangent_curve(NULL) {}
PRCBlend01(std::string n)1110   PRCBlend01(std::string n) :
1111     PRCSurface(n), center_curve(NULL), origin_curve(NULL), tangent_curve(NULL) {}
~PRCBlend01()1112   ~PRCBlend01() { delete center_curve; delete origin_curve; delete tangent_curve; }
1113   void  serializeBlend01(PRCbitStream &pbs);
serializeSurface(PRCbitStream & pbs)1114   void  serializeSurface(PRCbitStream &pbs) { serializeBlend01(pbs); }
1115 // void  setCenterCurve (PRCCurve*& curve) { center_curve  = curve; curve = NULL; }
1116 // void  setOriginCurve (PRCCurve*& curve) { origin_curve  = curve; curve = NULL; }
1117 // void  setTangentCurve(PRCCurve*& curve) { tangent_curve = curve; curve = NULL; }
1118   PRCCurve* center_curve;
1119   PRCCurve* origin_curve;
1120   PRCCurve* tangent_curve;
1121 };
1122 
1123 class PRCRuled : public PRCSurface, public PRCTransformation, public PRCUVParameterization
1124 {
1125 public:
PRCRuled()1126   PRCRuled() :
1127     PRCSurface(), first_curve(NULL), second_curve(NULL) {}
PRCRuled(std::string n)1128   PRCRuled(std::string n) :
1129     PRCSurface(n) {}
~PRCRuled()1130   ~PRCRuled() { delete first_curve; delete second_curve; }
1131   void  serializeRuled(PRCbitStream &pbs);
serializeSurface(PRCbitStream & pbs)1132   void  serializeSurface(PRCbitStream &pbs) { serializeRuled(pbs); }
1133 // void  setFirstCurve(PRCCurve*&  curve) { first_curve  = curve; curve = NULL; }
1134 // void  setSecondCurve(PRCCurve*& curve) { second_curve = curve; curve = NULL; }
1135   PRCCurve* first_curve;
1136   PRCCurve* second_curve;
1137 };
1138 
1139 class PRCSphere : public PRCSurface, public PRCTransformation, public PRCUVParameterization
1140 {
1141 public:
PRCSphere()1142   PRCSphere() :
1143     PRCSurface() {}
PRCSphere(std::string n)1144   PRCSphere(std::string n) :
1145     PRCSurface(n) {}
1146   void  serializeSphere(PRCbitStream &pbs);
serializeSurface(PRCbitStream & pbs)1147   void  serializeSurface(PRCbitStream &pbs) { serializeSphere(pbs); }
1148   double radius;
1149 };
1150 
1151 class PRCCone : public PRCSurface, public PRCTransformation, public PRCUVParameterization
1152 {
1153 public:
PRCCone()1154   PRCCone() :
1155     PRCSurface() {}
PRCCone(std::string n)1156   PRCCone(std::string n) :
1157     PRCSurface(n) {}
1158   void  serializeCone(PRCbitStream &pbs);
serializeSurface(PRCbitStream & pbs)1159   void  serializeSurface(PRCbitStream &pbs) { serializeCone(pbs); }
1160   double bottom_radius;
1161   double semi_angle;
1162 };
1163 
1164 class PRCCylinder : public PRCSurface, public PRCTransformation, public PRCUVParameterization
1165 {
1166 public:
PRCCylinder()1167   PRCCylinder() :
1168     PRCSurface() {}
PRCCylinder(std::string n)1169   PRCCylinder(std::string n) :
1170     PRCSurface(n) {}
1171   void  serializeCylinder(PRCbitStream &pbs);
serializeSurface(PRCbitStream & pbs)1172   void  serializeSurface(PRCbitStream &pbs) { serializeCylinder(pbs); }
1173   double radius;
1174 };
1175 
1176 class PRCTorus : public PRCSurface, public PRCTransformation, public PRCUVParameterization
1177 {
1178 public:
PRCTorus()1179   PRCTorus() :
1180     PRCSurface() {}
PRCTorus(std::string n)1181   PRCTorus(std::string n) :
1182     PRCSurface(n) {}
1183   void  serializeTorus(PRCbitStream &pbs);
serializeSurface(PRCbitStream & pbs)1184   void  serializeSurface(PRCbitStream &pbs) { serializeTorus(pbs); }
1185   double major_radius;
1186   double minor_radius;
1187 };
1188 
1189 class PRCBaseTopology : public PRCAttributes
1190 {
1191 public:
PRCBaseTopology()1192   PRCBaseTopology() :
1193     base_information(false),identifier(0) {}
1194   PRCBaseTopology(std::string n, uint32_t id = 0) :
base_information(true)1195     base_information(true),name(n),identifier(id) {}
1196   void serializeBaseTopology(PRCbitStream&);
1197   bool base_information;
1198   std::string name;
1199   uint32_t identifier;
1200 };
1201 
1202 class PRCTopoItem
1203 {
1204 public:
~PRCTopoItem()1205   virtual ~PRCTopoItem() {}
1206   virtual void serializeTopoItem(PRCbitStream&)=0;
1207 };
1208 
1209 class PRCContentBody: public PRCBaseTopology
1210 {
1211 public:
PRCContentBody()1212   PRCContentBody() :
1213     PRCBaseTopology(), behavior(0) {}
PRCContentBody(std::string n)1214   PRCContentBody(std::string n) :
1215     PRCBaseTopology(n,makeCADID()), behavior(0) {}
1216   void serializeContentBody(PRCbitStream&);
1217   uint8_t behavior;
1218 };
1219 
1220 class PRCBody : public PRCContentBody, public PRCTopoItem
1221 {
1222 public:
PRCBody()1223   PRCBody() :
1224     PRCContentBody(), topo_item_type(PRC_TYPE_ROOT) {}
PRCBody(uint32_t tit)1225   PRCBody(uint32_t tit) :
1226     PRCContentBody(), topo_item_type(tit) {}
PRCBody(uint32_t tit,std::string n)1227   PRCBody(uint32_t tit, std::string n) :
1228     PRCContentBody(n), topo_item_type(tit) {}
~PRCBody()1229   virtual ~PRCBody() {}
1230   virtual void serializeBody(PRCbitStream &pbs) = 0;
serializeTopoItem(PRCbitStream & pbs)1231   void serializeTopoItem(PRCbitStream &pbs) { serializeBody(pbs); }
serialType()1232   uint32_t serialType() { return topo_item_type; }
serialTolerance()1233   virtual double serialTolerance() { return 0; }
1234   const uint32_t topo_item_type;
1235 };
1236 typedef std::deque <PRCBody*>  PRCBodyList;
1237 
1238 class PRCContentWireEdge : public PRCBaseTopology
1239 {
1240 public:
PRCContentWireEdge()1241   PRCContentWireEdge() :
1242     PRCBaseTopology(), curve_3d(NULL), has_curve_trim_interval(false) {}
PRCContentWireEdge(std::string n)1243   PRCContentWireEdge(std::string n) :
1244     PRCBaseTopology(n,makeCADID()), curve_3d(NULL), has_curve_trim_interval(false) {}
~PRCContentWireEdge()1245   ~PRCContentWireEdge() { delete curve_3d; }
1246   void serializeContentWireEdge(PRCbitStream &pbs);
1247 // void setCurve(PRCCurve*& curve) { curve_3d = curve; curve = NULL; }
1248   PRCCurve* curve_3d;
1249   bool has_curve_trim_interval;
1250   PRCInterval curve_trim_interval;
1251 };
1252 
1253 class PRCWireEdge : public PRCContentWireEdge, public PRCTopoItem
1254 {
1255 public:
1256   void serializeWireEdge(PRCbitStream &pbs);
serializeTopoItem(PRCbitStream & pbs)1257   void serializeTopoItem(PRCbitStream &pbs) { serializeWireEdge(pbs); }
1258 };
1259 
1260 class PRCSingleWireBody : public PRCBody
1261 {
1262 public:
PRCSingleWireBody()1263   PRCSingleWireBody() :
1264     PRCBody(PRC_TYPE_TOPO_SingleWireBody), wire_edge(NULL) {}
PRCSingleWireBody(std::string n)1265   PRCSingleWireBody(std::string n) :
1266     PRCBody(PRC_TYPE_TOPO_SingleWireBody, n), wire_edge(NULL) {}
~PRCSingleWireBody()1267   ~PRCSingleWireBody() { delete wire_edge; }
1268   void serializeSingleWireBody(PRCbitStream &pbs);
serializeBody(PRCbitStream & pbs)1269   void serializeBody(PRCbitStream &pbs) { serializeSingleWireBody(pbs); }
setWireEdge(PRCWireEdge * & wireEdge)1270   void setWireEdge(PRCWireEdge*& wireEdge) { wire_edge = wireEdge; wireEdge = NULL; }
1271   PRCWireEdge* wire_edge;
1272 };
1273 
1274 class PRCFace : public PRCBaseTopology, public PRCTopoItem, public PRCGraphics
1275 {
1276 public:
PRCFace()1277   PRCFace() :
1278     PRCBaseTopology(), base_surface(NULL), have_surface_trim_domain(false), have_tolerance(false), tolerance(0), number_of_loop(0), outer_loop_index(-1) {}
PRCFace(std::string n)1279   PRCFace(std::string n) :
1280     PRCBaseTopology(n,makeCADID()), base_surface(NULL), have_surface_trim_domain(false), have_tolerance(false), tolerance(0), number_of_loop(0), outer_loop_index(-1) {}
~PRCFace()1281   ~PRCFace() { delete base_surface; }
1282   void serializeFace(PRCbitStream &pbs);
serializeTopoItem(PRCbitStream & pbs)1283   void serializeTopoItem(PRCbitStream &pbs) { serializeFace(pbs); }
setBaseSurface(PRCSurface * & surface)1284   void setBaseSurface(PRCSurface*& surface) { base_surface = surface; surface = NULL; }
1285   PRCSurface *base_surface;
1286   const bool have_surface_trim_domain;
1287   PRCDomain surface_trim_domain;
1288   const bool have_tolerance;
1289   const double tolerance;
1290   const uint32_t number_of_loop;
1291   const int32_t outer_loop_index;
1292 // PRCLoopList loop;
1293 };
1294 typedef std::deque <PRCFace*>  PRCFaceList;
1295 
1296 class PRCShell : public PRCBaseTopology, public PRCTopoItem
1297 {
1298 public:
PRCShell()1299   PRCShell() :
1300     PRCBaseTopology(), shell_is_closed(false) {}
PRCShell(std::string n)1301   PRCShell(std::string n) :
1302     PRCBaseTopology(n,makeCADID()), shell_is_closed(false) {}
~PRCShell()1303   ~PRCShell() { for(PRCFaceList::iterator it=face.begin(); it!=face.end(); ++it) delete *it; }
1304   void serializeShell(PRCbitStream &pbs);
serializeTopoItem(PRCbitStream & pbs)1305   void serializeTopoItem(PRCbitStream &pbs) { serializeShell(pbs); }
1306   void addFace(PRCFace*& pFace, uint8_t orientation=2);
1307   bool shell_is_closed;
1308   PRCFaceList face;
1309   std::vector<uint8_t> orientation_surface_with_shell;
1310 };
1311 typedef std::deque <PRCShell*>  PRCShellList;
1312 
1313 class PRCConnex : public PRCBaseTopology, public PRCTopoItem
1314 {
1315 public:
PRCConnex()1316   PRCConnex() :
1317     PRCBaseTopology() {}
PRCConnex(std::string n)1318   PRCConnex(std::string n) :
1319     PRCBaseTopology(n,makeCADID()) {}
~PRCConnex()1320   ~PRCConnex() { for(PRCShellList::iterator it=shell.begin(); it!=shell.end(); ++it) delete *it; }
1321   void serializeConnex(PRCbitStream &pbs);
serializeTopoItem(PRCbitStream & pbs)1322   void serializeTopoItem(PRCbitStream &pbs) { serializeConnex(pbs); }
1323   void addShell(PRCShell*& pShell);
1324   PRCShellList shell;
1325 };
1326 typedef std::deque <PRCConnex*>  PRCConnexList;
1327 
1328 class PRCBrepData : public PRCBody, public PRCBoundingBox
1329 {
1330 public:
PRCBrepData()1331   PRCBrepData() :
1332     PRCBody(PRC_TYPE_TOPO_BrepData) {}
PRCBrepData(std::string n)1333   PRCBrepData(std::string n) :
1334     PRCBody(PRC_TYPE_TOPO_BrepData, n) {}
~PRCBrepData()1335   ~PRCBrepData() { for(PRCConnexList::iterator it=connex.begin(); it!=connex.end(); ++it) delete *it; }
1336   void serializeBrepData(PRCbitStream &pbs);
serializeBody(PRCbitStream & pbs)1337   void serializeBody(PRCbitStream &pbs) { serializeBrepData(pbs); }
1338   void addConnex(PRCConnex*& pConnex);
1339   PRCConnexList connex;
1340 };
1341 
1342 // For now - treat just the case of Bezier surfaces cubic 4x4 or linear 2x2
1343 class PRCCompressedFace : public PRCBaseTopology, public PRCGraphics
1344 {
1345 public:
PRCCompressedFace()1346   PRCCompressedFace() :
1347     PRCBaseTopology(), orientation_surface_with_shell(true), degree(0) {}
PRCCompressedFace(std::string n)1348   PRCCompressedFace(std::string n) :
1349     PRCBaseTopology(n,makeCADID()), orientation_surface_with_shell(true), degree(0) {}
1350   void serializeCompressedFace(PRCbitStream &pbs, double brep_data_compressed_tolerance);
1351   void serializeContentCompressedFace(PRCbitStream &pbs);
1352   void serializeCompressedAnaNurbs(PRCbitStream &pbs, double brep_data_compressed_tolerance);
1353   void serializeCompressedNurbs(PRCbitStream &pbs, double brep_data_compressed_tolerance);
1354   bool orientation_surface_with_shell;
1355   uint32_t degree;
1356   std::vector<PRCVector3d> control_point;
1357 };
1358 typedef std::deque <PRCCompressedFace*>  PRCCompressedFaceList;
1359 
1360 // For now - treat just the case of one connex/one shell
1361 class PRCCompressedBrepData : public PRCBody
1362 {
1363 public:
PRCCompressedBrepData()1364   PRCCompressedBrepData() :
1365     PRCBody(PRC_TYPE_TOPO_BrepDataCompress), serial_tolerance(0), brep_data_compressed_tolerance(0) {}
PRCCompressedBrepData(std::string n)1366   PRCCompressedBrepData(std::string n) :
1367     PRCBody(PRC_TYPE_TOPO_BrepDataCompress, n), serial_tolerance(0), brep_data_compressed_tolerance(0) {}
~PRCCompressedBrepData()1368   ~PRCCompressedBrepData() { for(PRCCompressedFaceList::iterator it=face.begin(); it!=face.end(); ++it) delete *it; }
1369   void serializeCompressedBrepData(PRCbitStream &pbs);
serializeBody(PRCbitStream & pbs)1370   void serializeBody(PRCbitStream &pbs) { serializeCompressedBrepData(pbs); }
1371   void serializeCompressedShell(PRCbitStream &pbs);
serialTolerance()1372   double serialTolerance() { return serial_tolerance; }
1373   double serial_tolerance;
1374   double brep_data_compressed_tolerance;
1375   PRCCompressedFaceList face;
1376 };
1377 
1378 class PRCTopoContext : public ContentPRCBase
1379 {
1380 public:
1381   PRCTopoContext(std::string n="") :
ContentPRCBase(PRC_TYPE_TOPO_Context,n)1382   ContentPRCBase(PRC_TYPE_TOPO_Context,n), behaviour(0), granularity(1), tolerance(0),
1383    have_smallest_face_thickness(false), smallest_thickness(0), have_scale(false), scale(1) {}
~PRCTopoContext()1384   ~PRCTopoContext() { for(PRCBodyList::iterator it=body.begin(); it!=body.end(); ++it) delete *it; }
1385   void serializeTopoContext(PRCbitStream&);
1386   void serializeContextAndBodies(PRCbitStream&);
1387   void serializeGeometrySummary(PRCbitStream&);
1388   void serializeContextGraphics(PRCbitStream&);
1389   uint32_t addSingleWireBody(PRCSingleWireBody*& body);
1390   uint32_t addBrepData(PRCBrepData*& body);
1391   uint32_t addCompressedBrepData(PRCCompressedBrepData*& body);
1392   uint8_t  behaviour;
1393   double granularity;
1394   double tolerance;
1395   bool have_smallest_face_thickness;
1396   double smallest_thickness;
1397   bool have_scale;
1398   double scale;
1399   PRCBodyList body;
1400 };
1401 typedef std::deque <PRCTopoContext*>  PRCTopoContextList;
1402 
1403 class PRCUniqueId
1404 {
1405 public:
PRCUniqueId()1406   PRCUniqueId() : id0(0), id1(0), id2(0), id3(0)  {}
1407   void serializeCompressedUniqueId(PRCbitStream&) const;
1408   void serializeFileStructureUncompressedUniqueId(std::ostream& out) const;
1409   uint32_t id0;
1410   uint32_t id1;
1411   uint32_t id2;
1412   uint32_t id3;
1413 };
1414 
1415 class PRCUnit
1416 {
1417 public:
PRCUnit()1418   PRCUnit() : unit_from_CAD_file(false), unit(1) {}
unit_from_CAD_file(ufcf)1419   PRCUnit(double u, bool ufcf=true) : unit_from_CAD_file(ufcf), unit(u) {}
1420   void serializeUnit(PRCbitStream&);
1421   bool unit_from_CAD_file;
1422   double unit;
1423 };
1424 
1425 class PRCProductOccurrence: public PRCGraphics, public ContentPRCBase
1426 {
1427 public:
1428   PRCProductOccurrence(std::string n="") :
ContentPRCBase(PRC_TYPE_ASM_ProductOccurence,n)1429     ContentPRCBase(PRC_TYPE_ASM_ProductOccurence,n),
1430     index_part(m1),
1431     index_prototype(m1), prototype_in_same_file_structure(true),
1432     index_external_data(m1), external_data_in_same_file_structure(true),
1433     product_behaviour(0), product_information_flags(0), product_load_status(KEPRCProductLoadStatus_Loaded),
1434     location(NULL) {}
~PRCProductOccurrence()1435   ~PRCProductOccurrence() { delete location; }
setLocation(PRCGeneralTransformation3d * & transform)1436   void setLocation(PRCGeneralTransformation3d*& transform) { location = transform; transform = NULL; }
1437   void serializeProductOccurrence(PRCbitStream&);
1438   uint32_t index_part;
1439   uint32_t index_prototype;
1440   bool prototype_in_same_file_structure;
1441   PRCUniqueId prototype_file_structure;
1442   uint32_t index_external_data;
1443   bool external_data_in_same_file_structure;
1444   PRCUniqueId external_data_file_structure;
1445   std::vector<uint32_t> index_son_occurrence;
1446   uint8_t product_behaviour;
1447   PRCUnit unit_information;
1448   uint8_t product_information_flags;
1449   EPRCProductLoadStatus product_load_status;
1450   PRCGeneralTransformation3d *location;
1451 };
1452 typedef std::deque <PRCProductOccurrence*>  PRCProductOccurrenceList;
1453 
1454 class PRCPartDefinition: public PRCGraphics, public ContentPRCBase, public PRCBoundingBox
1455 {
1456 public:
1457 	PRCPartDefinition(std::string n="") :
ContentPRCBase(PRC_TYPE_ASM_PartDefinition,n)1458     ContentPRCBase(PRC_TYPE_ASM_PartDefinition,n) {}
~PRCPartDefinition()1459   ~PRCPartDefinition() { for(PRCRepresentationItemList::iterator it=representation_item.begin(); it!=representation_item.end(); ++it) delete *it; }
1460 	void serializePartDefinition(PRCbitStream&);
1461 	uint32_t addBrepModel(PRCBrepModel*& pBrepModel);
1462 	uint32_t addPolyBrepModel(PRCPolyBrepModel*& pPolyBrepModel);
1463 	uint32_t addPointSet(PRCPointSet*& pPointSet);
1464 	uint32_t addSet(PRCSet*& pSet);
1465 	uint32_t addWire(PRCWire*& pWire);
1466 	uint32_t addPolyWire(PRCPolyWire*& pPolyWire);
1467 	uint32_t addRepresentationItem(PRCRepresentationItem*& pRepresentationItem);
1468 	PRCRepresentationItemList representation_item;
1469 };
1470 typedef std::deque <PRCPartDefinition*>  PRCPartDefinitionList;
1471 
1472 #endif //__WRITE_PRC_H
1473