EPSExporter.cpp
Go to the documentation of this file.
1 /*
2  This file is part of the VRender library.
3  Copyright (C) 2005 Cyril Soler (Cyril.Soler@imag.fr)
4  Version 1.0.0, released on June 27, 2005.
5 
6  http://artis.imag.fr/Members/Cyril.Soler/VRender
7 
8  VRender is free software; you can redistribute it and/or modify
9  it under the terms of the GNU General Public License as published by
10  the Free Software Foundation; either version 2 of the License, or
11  (at your option) any later version.
12 
13  VRender 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
16  GNU General Public License for more details.
17 
18  You should have received a copy of the GNU General Public License
19  along with VRender; if not, write to the Free Software Foundation, Inc.,
20  51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA.
21 */
22 
23 /****************************************************************************
24 
25  Copyright (C) 2002-2013 Gilles Debunne. All rights reserved.
26 
27  This file is part of the QGLViewer library version 2.4.0.
28 
29  http://www.libqglviewer.com - contact@libqglviewer.com
30 
31  This file may be used under the terms of the GNU General Public License
32  versions 2.0 or 3.0 as published by the Free Software Foundation and
33  appearing in the LICENSE file included in the packaging of this file.
34  In addition, as a special exception, Gilles Debunne gives you certain
35  additional rights, described in the file GPL_EXCEPTION in this package.
36 
37  libQGLViewer uses dual licensing. Commercial/proprietary software must
38  purchase a libQGLViewer Commercial License.
39 
40  This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
41  WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
42 
43 *****************************************************************************/
44 
45 #include <stdio.h>
46 #include "Primitive.h"
47 #include "Exporter.h"
48 #include "math.h"
49 
50 using namespace vrender ;
51 using namespace std ;
52 
53 const double EPSExporter::EPS_GOURAUD_THRESHOLD = 0.05 ;
54 const char *EPSExporter::CREATOR = "VRender library - (c) Cyril Soler 2005" ;
55 
56 float EPSExporter::last_r = -1.0 ;
57 float EPSExporter::last_g = -1.0 ;
58 float EPSExporter::last_b = -1.0 ;
59 
61 {
62  last_r = -1 ;
63  last_g = -1 ;
64  last_b = -1 ;
65 }
66 
67 void EPSExporter::writeHeader(QTextStream& out) const
68 {
69  /* Emit EPS header. */
70 
71  out << "%!PS-Adobe-2.0 EPSF-2.0\n";
72 
73  out << "%%%%HiResBoundingBox: " << _xmin << " " << _ymin << " " << _xmax << " " << _ymax << "\n";
74 
75  out << "%%%%Creator: " << CREATOR << " (using OpenGL feedback)\n";
76  out << "%%EndComments\n\ngsave\n\n";
77 
78  out << "%\n";
79  out << "% Contributors:\n";
80  out << "%\n";
81  out << "% Frederic Delhoume (delhoume@ilog.fr):\n";
82  out << "% Gouraud triangle PostScript fragment\n";
83  out << "%\n";
84  out << "% Cyril Soler (csoler@imag.fr):\n";
85  out << "% BSP Sort,\n";
86  out << "% Topological and advanced topological Sort,\n";
87  out << "% Hidden surface removal,\n";
88  out << "% Xfig3.2 (and EPS) format\n";
89  out << "%\n\n";
90 
91  out << "/threshold " << EPS_GOURAUD_THRESHOLD << " def\n";
92 
93  for(int i = 0; GOURAUD_TRIANGLE_EPS[i] != NULL; i++)
94  out << GOURAUD_TRIANGLE_EPS[i] << "\n";
95 #ifdef A_VOIR
96  out << "\n" << << " setlinewidth\n\n", _lineWidth;
97 #endif
98  /* Clear the background like OpenGL had it. */
99 
100  if(_clearBG)
101  {
102  out << _clearR << " " << _clearG << " " << _clearB << " setrgbcolor\n";
103  out << _xmin << " " << _ymin << " " << _xmax << " " << _ymax << " rectfill\n\n";
104  }
105 }
106 
107 void EPSExporter::writeFooter(QTextStream& out) const
108 {
109  out << "grestore\n\n";
110 
111  out << "% uncomment next line to be able to print to a printer.\n";
112  out << "% showpage\n";
113 }
114 
115 void PSExporter::writeFooter(QTextStream& out) const
116 {
117  out << "showpage\n";
118 }
119 
120 const char *EPSExporter::GOURAUD_TRIANGLE_EPS[] =
121 {
122  "/bd{bind def}bind def /triangle { aload pop ",
123  "setrgbcolor aload pop 5 3 roll 4 2 roll 3 2 roll exch moveto lineto ",
124  "lineto closepath fill } bd /computediff1 { 2 copy sub abs threshold ",
125  "ge {pop pop pop true} { exch 2 index sub abs threshold ge { pop pop ",
126  "true} { sub abs threshold ge } ifelse } ifelse } bd /computediff3 { 3 ",
127  "copy 0 get 3 1 roll 0 get 3 1 roll 0 get computediff1 {true} { 3 copy ",
128  "1 get 3 1 roll 1 get 3 1 roll 1 get computediff1 {true} { 3 copy 2 ",
129  "get 3 1 roll 2 get 3 1 roll 2 get computediff1 } ifelse } ifelse } ",
130  "bd /middlecolor { aload pop 4 -1 roll aload pop 4 -1 roll add 2 div 5 ",
131  "1 roll 3 -1 roll add 2 div 3 1 roll add 2 div 3 1 roll exch 3 array ",
132  "astore } bd /gdt { computediff3 { 4 -1 roll aload 7 1 roll ",
133  "6 -1 roll pop 3 -1 roll pop add 2 div 3 1 roll add 2 div exch 3 -1 roll ",
134  "aload 7 1 roll exch pop 4 -1 roll pop add 2 div 3 1 roll add 2 div ",
135  "exch 3 -1 roll aload 7 1 roll pop 3 -1 roll pop add 2 div 3 1 roll add ",
136  "2 div exch 7 3 roll 10 -3 roll dup 3 index middlecolor 4 1 roll 2 copy ",
137  "middlecolor 4 1 roll 3 copy pop middlecolor 4 1 roll 13 -1 roll aload ",
138  "pop 17 index 6 index 15 index 19 index 6 index 17 index 6 array astore ",
139  "10 index 10 index 14 index gdt 17 index 5 index 17 index ",
140  "19 index 5 index 19 index 6 array astore 10 index 9 index 13 index ",
141  "gdt 13 index 16 index 5 index 15 index 18 index 5 index 6 ",
142  "array astore 12 index 12 index 9 index gdt 17 index 16 ",
143  "index 15 index 19 index 18 index 17 index 6 array astore 10 index 12 ",
144  "index 14 index gdt 18 {pop} repeat } { aload pop 5 3 roll ",
145  "aload pop 7 3 roll aload pop 9 3 roll 8 index 6 index 4 index add add 3 ",
146  "div 10 1 roll 7 index 5 index 3 index add add 3 div 10 1 roll 6 index 4 ",
147  "index 2 index add add 3 div 10 1 roll 9 {pop} repeat 3 array astore ",
148  "triangle } ifelse } bd",
149  NULL
150 };
151 
152 void EPSExporter::spewPolygone(const Polygone *P, QTextStream& out)
153 {
154  int nvertices;
155  GLfloat red, green, blue;
156  bool smooth;
157 
158  nvertices = P->nbVertices() ;
159 
160  const Feedback3DColor& vertex = Feedback3DColor(P->sommet3DColor(0)) ;
161 
162  if(nvertices > 0)
163  {
164  red = vertex.red();
165  green = vertex.green();
166  blue = vertex.blue();
167 
168  smooth = false;
169 
170  for(int i=1;i < nvertices && !smooth; i++)
171  if(fabs(red - P->sommet3DColor(i).red()) > 0.01 || fabs(green - P->sommet3DColor(i).green()) > 0.01 || fabs(blue - P->sommet3DColor(i).blue()) > 0.01)
172  smooth = true;
173 
174  if(smooth && !_blackAndWhite)
175  {
176  /* Smooth shaded polygon; varying colors at vertices. */
177  /* Break polygon into "nvertices-2" triangle fans. */
178 
179  for (int j = 0; j < nvertices - 2; j++)
180  {
181  out << "[" << P->sommet3DColor(0).x() << " " << P->sommet3DColor(j + 1).x() << " " << P->sommet3DColor(j + 2).x()
182  << " " << P->sommet3DColor(0).y() << " " << P->sommet3DColor(j + 1).y() << " " << P->sommet3DColor(j + 2).y() << "]";
183 
184  out << " [" << P->sommet3DColor(0 ).red() << " " << P->sommet3DColor(0 ).green() << " " << P->sommet3DColor(0 ).blue()
185  << "] [" << P->sommet3DColor(j + 1).red() << " " << P->sommet3DColor(j + 1).green() << " " << P->sommet3DColor(j + 1).blue()
186  << "] [" << P->sommet3DColor(j + 2).red() << " " << P->sommet3DColor(j + 2).green() << " " << P->sommet3DColor(j + 2).blue() << "] gdt\n";
187 
188  last_r = last_g = last_b = -1.0 ;
189  }
190  }
191  else
192  {
193  /* Flat shaded polygon and white polygons; all vertex colors the same. */
194 
195  out << "newpath\n";
196 
197  if(_blackAndWhite)
198  setColor(out,1.0,1.0,1.0) ;
199  else
200  setColor(out,red,green,blue) ;
201 
202  /* Draw a filled triangle. */
203 
204  out << P->sommet3DColor(0).x() << " " << P->sommet3DColor(0).y() << " moveto\n";
205 
206  for (int i = 1; i < nvertices; i++)
207  out << P->sommet3DColor(i).x() << " " << P->sommet3DColor(i).y() << " lineto\n";
208 
209  out << "closepath fill\n\n";
210  }
211  }
212 }
213 
214 void EPSExporter::spewSegment(const Segment *S, QTextStream& out)
215 {
216  GLdouble dx, dy;
217  GLfloat dr, dg, db, absR, absG, absB, colormax;
218  int steps;
219  GLdouble xstep=0.0, ystep=0.0;
220  GLfloat rstep=0.0, gstep=0.0, bstep=0.0;
221  GLdouble xnext=0.0, ynext=0.0, distance=0.0;
222  GLfloat rnext=0.0, gnext=0.0, bnext=0.0;
223 
224  const Feedback3DColor& P1 = Feedback3DColor(S->sommet3DColor(0)) ;
225  const Feedback3DColor& P2 = Feedback3DColor(S->sommet3DColor(1)) ;
226 
227  dr = P2.red() - P1.red();
228  dg = P2.green() - P1.green();
229  db = P2.blue() - P1.blue();
230 
231  if((!_blackAndWhite)&&(dr != 0 || dg != 0 || db != 0))
232  {
233  /* Smooth shaded line. */
234 
235  dx = P2.x() - P1.x();
236  dy = P2.y() - P1.y();
237 
238  distance = sqrt(dx*dx + dy*dy);
239 
240  absR = fabs(dr);
241  absG = fabs(dg);
242  absB = fabs(db);
243 
244  colormax = max(absR, max(absG, absB));
245  steps = int(0.5f + max(1.0, colormax * distance * EPS_SMOOTH_LINE_FACTOR));
246 
247  xstep = dx / steps;
248  ystep = dy / steps;
249 
250  rstep = dr / steps;
251  gstep = dg / steps;
252  bstep = db / steps;
253 
254  xnext = P1.x();
255  ynext = P1.y();
256  rnext = P1.red();
257  gnext = P1.green();
258  bnext = P1.blue();
259 
260  /* Back up half a step; we want the end points to be
261  exactly the their endpoint colors. */
262 
263  xnext -= xstep / 2.0;
264  ynext -= ystep / 2.0;
265  rnext -= rstep / 2.0f;
266  gnext -= gstep / 2.0f;
267  bnext -= bstep / 2.0f;
268  }
269  else
270  steps = 0; /* Single color line. */
271 
272  if(_blackAndWhite)
273  setColor(out,0.0,0.0,0.0) ;
274  else
275  setColor(out,P1.red(),P1.green(),P1.blue()) ;
276 
277  out << P1.x() << " " << P1.y() << " moveto\n";
278 
279  for(int i = 0;i < steps;i++)
280  {
281  xnext += xstep;
282  ynext += ystep;
283  rnext += rstep;
284  gnext += gstep;
285  bnext += bstep;
286 
287  out << xnext << " " << ynext << " lineto stroke\n";
288  out << rnext << " " << gnext << " " << bnext << " setrgbcolor\n";
289  out << xnext << " " << ynext << " moveto\n";
290 
291  last_r = last_g = last_b = -1.0 ;
292  }
293  out << P2.x() << " " << P2.y() << " lineto stroke\n";
294 }
295 
296 void EPSExporter::spewPoint(const Point *P, QTextStream& out)
297 {
298  const Feedback3DColor& p = Feedback3DColor(P->sommet3DColor(0)) ;
299 
300  if(_blackAndWhite)
301  setColor(out,0.0,0.0,0.0) ;
302  else
303  setColor(out,p.red(),p.green(),p.blue()) ;
304 
305  out << p.x() << " " << p.y() << " " << (_pointSize / 2.0) << " 0 360 arc fill\n\n";
306 }
307 
308 void EPSExporter::setColor(QTextStream& out, float red, float green, float blue)
309 {
310  if(last_r != red || last_g != green || last_b != blue)
311  out << red << " " << green << " " << blue << " setrgbcolor\n";
312 
313  last_r = red ;
314  last_g = green ;
315  last_b = blue ;
316 }
317 
static float last_r
Definition: Exporter.h:117
static float last_g
Definition: Exporter.h:118
virtual unsigned int nbVertices() const
Definition: Primitive.h:197
FLOAT x() const
Definition: Primitive.h:82
virtual void spewPoint(const Point *, QTextStream &out)
static const char * CREATOR
Definition: Exporter.h:115
virtual void writeHeader(QTextStream &out) const
Definition: EPSExporter.cpp:67
virtual void spewSegment(const Segment *, QTextStream &out)
GLfloat green() const
Definition: Primitive.h:86
virtual const Feedback3DColor & sommet3DColor(int) const
Definition: Primitive.cpp:91
virtual void writeFooter(QTextStream &out) const
FLOAT y() const
Definition: Primitive.h:83
virtual const Feedback3DColor & sommet3DColor(int) const
Definition: Primitive.cpp:63
static const char * GOURAUD_TRIANGLE_EPS[]
Definition: Exporter.h:114
GLfloat blue() const
Definition: Primitive.h:87
virtual void spewPolygone(const Polygone *, QTextStream &out)
#define EPS_SMOOTH_LINE_FACTOR
Definition: Primitive.h:70
virtual const Feedback3DColor & sommet3DColor(int i) const
Definition: Primitive.cpp:68
static const double EPS_GOURAUD_THRESHOLD
Definition: Exporter.h:113
GLfloat red() const
Definition: Primitive.h:85
void setColor(QTextStream &out, float, float, float)
static float last_b
Definition: Exporter.h:119
virtual void writeFooter(QTextStream &out) const


octovis
Author(s): Kai M. Wurm , Armin Hornung
autogenerated on Mon Jun 10 2019 14:00:24