Logo ROOT  
Reference Guide
Loading...
Searching...
No Matches
TSVG.cxx
Go to the documentation of this file.
1// @(#)root/postscript:$Id$
2// Author: Olivier Couet
3
4/*************************************************************************
5 * Copyright (C) 1995-2000, Rene Brun and Fons Rademakers. *
6 * All rights reserved. *
7 * *
8 * For the licensing terms see $ROOTSYS/LICENSE. *
9 * For the list of contributors see $ROOTSYS/README/CREDITS. *
10 *************************************************************************/
11
12#ifdef WIN32
13#pragma optimize("",off)
14#endif
15
16#include <cstdlib>
17#include <cstring>
18#include <cctype>
19#include <cmath>
20#include <fstream>
21
22#include "TROOT.h"
23#include "TDatime.h"
24#include "TBase64.h"
25#include "TColor.h"
26#include "TVirtualPad.h"
27#include "TPoints.h"
28#include "TSVG.h"
29#include "TStyle.h"
30#include "TMath.h"
31#include "TObjString.h"
32#include "TObjArray.h"
33#include "snprintf.h"
34
37
38const Double_t kEpsilon = 1e-9;
39
40/** \class TSVG
41\ingroup PS
42
43\brief Interface to SVG
44
45[SVG](http://www.w3.org/Graphics/SVG/Overview.htm8)
46(Scalable Vector Graphics) is a language for describing
47two-dimensional graphics in XML. SVG allows high quality vector graphics in
48HTML pages.
49
50To print a ROOT canvas "c1" into an SVG file simply do:
51~~~ {.cpp}
52 c1->Print("c1.svg");
53~~~
54The result is the ASCII file `c1.svg`.
55
56It can be open directly using a web browser or included in a html document
57the following way:
58~~~ {.cpp}
59<embed width="95%" height="500" src="c1.svg">
60~~~
61It is best viewed with Internet Explorer and you need the
62[Adobe SVG Viewer](http://www.adobe.com/svg/viewer/install/main.html)
63
64To zoom using the Adobe SVG Viewer, position the mouse over
65the area you want to zoom and click the right button.
66
67To define the zoom area,
68use Control+drag to mark the boundaries of the zoom area.
69
70To pan, use Alt+drag.
71By clicking with the right mouse button on the SVG graphics you will get
72a pop-up menu giving other ways to interact with the image.
73
74SVG files can be used directly in compressed mode to minimize the time
75transfer over the network. Compressed SVG files should be created using
76`gzip` on a normal ASCII SVG file and should then be renamed
77using the file extension `.svgz`.
78*/
79
80////////////////////////////////////////////////////////////////////////////////
81/// Default SVG constructor
82
84{
85 gVirtualPS = this;
86 SetTitle("SVG");
87}
88
89////////////////////////////////////////////////////////////////////////////////
90/// Initialize the SVG interface
91///
92/// - fname : SVG file name
93/// - wtype : SVG workstation type. Not used in the SVG driver. But as TSVG
94/// inherits from TVirtualPS it should be kept. Anyway it is not
95/// necessary to specify this parameter at creation time because it
96/// has a default value (which is ignore in the SVG case).
97
98TSVG::TSVG(const char *fname, Int_t wtype, Bool_t compact) : TVirtualPS(fname, wtype)
99{
100 SetTitle("SVG");
101 fCompact = compact;
102 Open(fname, wtype);
103}
104
105////////////////////////////////////////////////////////////////////////////////
106/// Open a SVG file
107
108void TSVG::Open(const char *fname, Int_t wtype)
109{
110 if (fStream) {
111 Warning("Open", "SVG file already open");
112 return;
113 }
114
115 fLenBuffer = 0;
116 fType = std::abs(wtype);
117 SetLineJoin(gStyle->GetJoinLinePS());
118 SetLineCap(gStyle->GetCapLinePS());
119 SetLineScale(gStyle->GetLineScalePS());
120 gStyle->GetPaperSize(fXsize, fYsize);
121 Float_t xrange, yrange;
122 if (gPad) {
123 Double_t ww = gPad->GetWw();
124 Double_t wh = gPad->GetWh();
125 ww *= gPad->GetWNDC();
126 wh *= gPad->GetHNDC();
127 Double_t ratio = wh/ww;
128 xrange = fXsize;
129 yrange = fXsize*ratio;
130 if (yrange > fYsize) { yrange = fYsize; xrange = yrange/ratio;}
131 fXsize = xrange; fYsize = yrange;
132 }
133
134 // Open OS file
135 if (!OpenStream(fname)) {
136 Error("Open", "Cannot open file: %s", fname);
137 return;
138 }
139
140 gVirtualPS = this;
141
142 ClearBuffer();
143
145
146 fRange = kFALSE;
147
148 // Set a default range
150
151 NewPage();
152}
153
154////////////////////////////////////////////////////////////////////////////////
155/// Default SVG destructor
156
158{
159 Close();
160}
161
162////////////////////////////////////////////////////////////////////////////////
163/// Close a SVG file
164
166{
167 if (!gVirtualPS || !fStream)
168 return;
169 if (gPad)
170 gPad->Update();
171 PrintStr("</svg>@");
172
173 // Close file stream
174 CloseStream();
175
176 gVirtualPS = nullptr;
177}
178
179////////////////////////////////////////////////////////////////////////////////
180/// Activate an already open SVG file
181
183{
184 // fType is used to know if the SVG file is open. Unlike TPostScript, TSVG
185 // has no "workstation type". In fact there is only one SVG type.
186
187 if (!fType) {
188 Error("On", "no SVG file open");
189 Off();
190 return;
191 }
192 gVirtualPS = this;
193}
194
195////////////////////////////////////////////////////////////////////////////////
196/// Deactivate an already open SVG file
197
199{
200 gVirtualPS = nullptr;
201}
202
203////////////////////////////////////////////////////////////////////////////////
204/// Draw a Box
205
207{
208 Double_t x[4], y[4];
209 Double_t ix1 = XtoSVG(TMath::Min(x1,x2));
210 Double_t ix2 = XtoSVG(TMath::Max(x1,x2));
211 Double_t iy1 = YtoSVG(TMath::Min(y1,y2));
212 Double_t iy2 = YtoSVG(TMath::Max(y1,y2));
213 Int_t fillis = fFillStyle/1000;
214 Int_t fillsi = fFillStyle%1000;
215
216 if (fillis == 3 || fillis == 2) {
217 if (fillsi > 99) {
218 x[0] = x1; y[0] = y1;
219 x[1] = x2; y[1] = y1;
220 x[2] = x2; y[2] = y2;
221 x[3] = x1; y[3] = y2;
222 return;
223 }
224 if (fillsi > 0 && fillsi < 26) {
225 x[0] = x1; y[0] = y1;
226 x[1] = x2; y[1] = y1;
227 x[2] = x2; y[2] = y2;
228 x[3] = x1; y[3] = y2;
229 DrawPS(-4, &x[0], &y[0]);
230 }
231 if (fillsi == -3) {
232 PrintStr("@");
233 PrintFast(9,"<rect x=\"");
234 WriteReal(ix1, kFALSE);
235 PrintFast(5,"\" y=\"");
236 WriteReal(iy2, kFALSE);
237 PrintFast(9,"\" width=\"");
238 WriteReal(ix2-ix1, kFALSE);
239 PrintFast(10,"\" height=\"");
240 WriteReal(iy1-iy2, kFALSE);
241 PrintFast(7,"\" fill=");
243 PrintFast(2,"/>");
244 }
245 }
246 if (fillis == 1) {
247 PrintStr("@");
248 PrintFast(9,"<rect x=\"");
249 WriteReal(ix1, kFALSE);
250 PrintFast(5,"\" y=\"");
251 WriteReal(iy2, kFALSE);
252 PrintFast(9,"\" width=\"");
253 WriteReal(ix2-ix1, kFALSE);
254 PrintFast(10,"\" height=\"");
255 WriteReal(iy1-iy2, kFALSE);
256 PrintFast(7,"\" fill=");
258 PrintFast(2,"/>");
259 }
260 if (fillis == 0) {
261 if (fLineWidth<=0) return;
262 PrintStr("@");
263 PrintFast(9,"<rect x=\"");
264 WriteReal(ix1, kFALSE);
265 PrintFast(5,"\" y=\"");
266 WriteReal(iy2, kFALSE);
267 PrintFast(9,"\" width=\"");
268 WriteReal(ix2-ix1, kFALSE);
269 PrintFast(10,"\" height=\"");
270 WriteReal(iy1-iy2, kFALSE);
271 PrintFast(21,"\" fill=\"none\" stroke=");
273 PrintFast(2,"/>");
274 }
275}
276
277////////////////////////////////////////////////////////////////////////////////
278/// Print a svg path statement for specified points
279
280void TSVG::PrintPath(Bool_t convert, Int_t n, Double_t *xps, Double_t *yps, Bool_t close_path)
281{
282 Double_t idx = 0, idy = 0;
283
284 Double_t ixd0 = convert ? XtoSVG(xps[0]) : xps[0];
285 Double_t iyd0 = convert ? YtoSVG(yps[0]) : yps[0];
286 Double_t firstx = ixd0, firsty = iyd0;
287
288 PrintFast(1,"M");
289 WriteReal(ixd0, kFALSE);
290 PrintFast(1,",");
291 WriteReal(iyd0, kFALSE);
292
293 for (Int_t i = 1; i < n; i++) {
294 Double_t ixdi = convert ? XtoSVG(xps[i]) : xps[i];
295 Double_t iydi = convert ? YtoSVG(yps[i]) : yps[i];
296
297 Double_t ix = ixdi - ixd0;
298 Double_t iy = iydi - iyd0;
299
300 if (fCompact && (TMath::Abs(ix) < kEpsilon))
301 ix = 0;
302 if (fCompact && (TMath::Abs(iy) < kEpsilon))
303 iy = 0;
304
305 ixd0 = ixdi;
306 iyd0 = iydi;
307 if(ix && iy) {
308 if(idx) {
309 MovePS(idx, 0);
310 idx = 0;
311 }
312 if(idy) {
313 MovePS(0, idy);
314 idy = 0;
315 }
316 MovePS(ix, iy);
317 continue;
318 }
319 if (ix) {
320 if(idy) {
321 MovePS(0, idy);
322 idy = 0;
323 }
324 if(!idx || (ix*idx > 0)) {
325 idx += ix;
326 } else {
327 MovePS(idx, 0);
328 idx = ix;
329 }
330 continue;
331 }
332 if(iy) {
333 if(idx) {
334 MovePS(idx, 0);
335 idx = 0;
336 }
337 if(!idy || (iy*idy > 0)) {
338 idy += iy;
339 } else {
340 MovePS(0, idy);
341 idy = iy;
342 }
343 }
344 }
345 if(idx)
346 MovePS(idx, 0);
347 if(idy)
348 MovePS(0, idy);
349
350 if (close_path || ((TMath::Abs(ixd0 - firstx) < kEpsilon) && (TMath::Abs(iyd0 - firsty) < kEpsilon)))
351 PrintFast(1, "z");
352}
353
354////////////////////////////////////////////////////////////////////////////////
355/// Draw a Frame around a box
356///
357/// - mode = -1 the box looks as it is behind the screen
358/// - mode = 1 the box looks as it is in front of the screen
359/// - border is the border size in already pre-computed SVG units dark is the
360/// color for the dark part of the frame light is the color for the light
361/// part of the frame
362
364 Int_t mode, Int_t border, Int_t dark, Int_t light)
365{
366 Double_t xps[7], yps[7];
367
368 //- Draw top&left part of the box
369 xps[0] = XtoSVG(xl); yps[0] = YtoSVG(yl);
370 xps[1] = xps[0] + border; yps[1] = yps[0] - border;
371 xps[2] = xps[1]; yps[2] = YtoSVG(yt) + border;
372 xps[3] = XtoSVG(xt) - border; yps[3] = yps[2];
373 xps[4] = XtoSVG(xt); yps[4] = YtoSVG(yt);
374 xps[5] = xps[0]; yps[5] = yps[4];
375 xps[6] = xps[0]; yps[6] = yps[0];
376
377 PrintStr("@");
378 PrintFast(9,"<path d=\"");
379 PrintPath(kFALSE, 7, xps, yps);
380 PrintFast(7,"\" fill=");
381 SetColorAlpha(mode == -1 ? dark : light);
383 PrintFast(2,"/>");
384
385 //- Draw bottom&right part of the box
386 xps[0] = XtoSVG(xl); yps[0] = YtoSVG(yl);
387 xps[1] = xps[0] + border; yps[1] = yps[0] - border;
388 xps[2] = XtoSVG(xt) - border; yps[2] = yps[1];
389 xps[3] = xps[2]; yps[3] = YtoSVG(yt) + border;
390 xps[4] = XtoSVG(xt); yps[4] = YtoSVG(yt);
391 xps[5] = xps[4]; yps[5] = yps[0];
392 xps[6] = xps[0]; yps[6] = yps[0];
393
394 PrintStr("@");
395 PrintFast(9,"<path d=\"");
396 PrintPath(kFALSE, 7, xps, yps);
397 PrintFast(7,"\" fill=");
398 SetColorAlpha(mode == -1 ? light : dark);
400 PrintFast(2,"/>");
401}
402
403////////////////////////////////////////////////////////////////////////////////
404/// Draw a PolyLine
405///
406/// Draw a polyline through the points xy.
407/// - If NN=1 moves only to point x,y.
408/// - If NN=0 the x,y are written in the SVG file
409/// according to the current transformation.
410/// - If NN>0 the line is clipped as a line.
411/// - If NN<0 the line is clipped as a fill area.
412
414{
415 Warning("DrawPolyLine", "not implemented");
416}
417
418////////////////////////////////////////////////////////////////////////////////
419/// Draw a PolyLine in NDC space
420///
421/// Draw a polyline through the points xy.
422/// --If NN=1 moves only to point x,y.
423/// --If NN=0 the x,y are written in the SVG file
424/// according to the current transformation.
425/// --If NN>0 the line is clipped as a line.
426/// - If NN<0 the line is clipped as a fill area.
427
429{
430 Warning("DrawPolyLineNDC", "not implemented");
431}
432
433////////////////////////////////////////////////////////////////////////////////
434/// Implementation of polymarker printing
435
436template<class T>
437void TSVG::PrintPolyMarker(Int_t n, T *xw, T* yw)
438{
441
442 if (ms == 4)
443 ms = 24;
444 else if (ms >= 6 && ms <= 8)
445 ms = 20;
446 else if (ms >= 9 && ms <= 19)
447 ms = 1;
448
449 // Define the marker size
451 if (fMarkerStyle == 1 || (fMarkerStyle >= 9 && fMarkerStyle <= 19)) msize = 0.01;
452 if (fMarkerStyle == 6) msize = 0.02;
453 if (fMarkerStyle == 7) msize = 0.04;
454
455 const Int_t kBASEMARKER = 8;
456 Float_t sbase = msize*kBASEMARKER;
457 Float_t s2x = sbase / Float_t(gPad->GetWw() * gPad->GetAbsWNDC());
458 msize = this->UtoSVG(s2x) - this->UtoSVG(0);
459
460 Double_t m = msize;
461 Double_t m2 = m/2;
462 Double_t m3 = m/3;
463 Double_t m6 = m/6;
464 Double_t m4 = m/4.;
465 Double_t m8 = m/8.;
466 Double_t m0 = m/10.;
467
468 // Draw the marker according to the type
469 PrintStr("@");
470 if ((ms > 19 && ms < 24) || ms == 29 || ms == 33 || ms == 34 ||
471 ms == 39 || ms == 41 || ms == 43 || ms == 45 ||
472 ms == 47 || ms == 48 || ms == 49) {
473 PrintStr("<g fill=");
475 PrintStr(">");
476 } else {
477 PrintStr("<g stroke=");
479 PrintStr(" stroke-width=\"");
481 PrintStr("\" fill=\"none\"");
483 PrintStr(">");
484 }
485 for (Int_t i = 0; i < n; i++) {
486 Double_t ix = XtoSVG(xw[i]);
487 Double_t iy = YtoSVG(yw[i]);
488 PrintStr("@");
489 // Dot (.)
490 if (ms == 1) {
491 PrintStr("<line x1=\"");
492 WriteReal(ix-1, kFALSE);
493 PrintStr("\" y1=\"");
494 WriteReal(iy, kFALSE);
495 PrintStr("\" x2=\"");
496 WriteReal(ix, kFALSE);
497 PrintStr("\" y2=\"");
498 WriteReal(iy, kFALSE);
499 PrintStr("\"/>");
500 // Plus (+)
501 } else if (ms == 2) {
502 PrintStr("<line x1=\"");
503 WriteReal(ix-m2, kFALSE);
504 PrintStr("\" y1=\"");
505 WriteReal(iy, kFALSE);
506 PrintStr("\" x2=\"");
507 WriteReal(ix+m2, kFALSE);
508 PrintStr("\" y2=\"");
509 WriteReal(iy, kFALSE);
510 PrintStr("\"/>");
511
512 PrintStr("<line x1=\"");
513 WriteReal(ix, kFALSE);
514 PrintStr("\" y1=\"");
515 WriteReal(iy-m2, kFALSE);
516 PrintStr("\" x2=\"");
517 WriteReal(ix, kFALSE);
518 PrintStr("\" y2=\"");
519 WriteReal(iy+m2, kFALSE);
520 PrintStr("\"/>");
521 // X shape (X)
522 } else if (ms == 5) {
523 PrintStr("<line x1=\"");
524 WriteReal(ix-m2*0.707, kFALSE);
525 PrintStr("\" y1=\"");
526 WriteReal(iy-m2*0.707, kFALSE);
527 PrintStr("\" x2=\"");
528 WriteReal(ix+m2*0.707, kFALSE);
529 PrintStr("\" y2=\"");
530 WriteReal(iy+m2*0.707, kFALSE);
531 PrintStr("\"/>");
532
533 PrintStr("<line x1=\"");
534 WriteReal(ix-m2*0.707, kFALSE);
535 PrintStr("\" y1=\"");
536 WriteReal(iy+m2*0.707, kFALSE);
537 PrintStr("\" x2=\"");
538 WriteReal(ix+m2*0.707, kFALSE);
539 PrintStr("\" y2=\"");
540 WriteReal(iy-m2*0.707, kFALSE);
541 PrintStr("\"/>");
542 // Asterisk shape (*)
543 } else if (ms == 3 || ms == 31) {
544 PrintStr("<line x1=\"");
545 WriteReal(ix-m2, kFALSE);
546 PrintStr("\" y1=\"");
547 WriteReal(iy, kFALSE);
548 PrintStr("\" x2=\"");
549 WriteReal(ix+m2, kFALSE);
550 PrintStr("\" y2=\"");
551 WriteReal(iy, kFALSE);
552 PrintStr("\"/>");
553
554 PrintStr("<line x1=\"");
555 WriteReal(ix, kFALSE);
556 PrintStr("\" y1=\"");
557 WriteReal(iy-m2, kFALSE);
558 PrintStr("\" x2=\"");
559 WriteReal(ix, kFALSE);
560 PrintStr("\" y2=\"");
561 WriteReal(iy+m2, kFALSE);
562 PrintStr("\"/>");
563
564 PrintStr("<line x1=\"");
565 WriteReal(ix-m2*0.707, kFALSE);
566 PrintStr("\" y1=\"");
567 WriteReal(iy-m2*0.707, kFALSE);
568 PrintStr("\" x2=\"");
569 WriteReal(ix+m2*0.707, kFALSE);
570 PrintStr("\" y2=\"");
571 WriteReal(iy+m2*0.707, kFALSE);
572 PrintStr("\"/>");
573
574 PrintStr("<line x1=\"");
575 WriteReal(ix-m2*0.707, kFALSE);
576 PrintStr("\" y1=\"");
577 WriteReal(iy+m2*0.707, kFALSE);
578 PrintStr("\" x2=\"");
579 WriteReal(ix+m2*0.707, kFALSE);
580 PrintStr("\" y2=\"");
581 WriteReal(iy-m2*0.707, kFALSE);
582 PrintStr("\"/>");
583 // Circle
584 } else if (ms == 24 || ms == 20) {
585 PrintStr("<circle cx=\"");
586 WriteReal(ix, kFALSE);
587 PrintStr("\" cy=\"");
588 WriteReal(iy, kFALSE);
589 PrintStr("\" r=\"");
590 if (m2<=0) m2=1;
591 WriteReal(m2, kFALSE);
592 PrintStr("\"/>");
593 // Square
594 } else if (ms == 25 || ms == 21) {
595 PrintStr("<rect x=\"");
596 WriteReal(ix-m2, kFALSE);
597 PrintStr("\" y=\"");
598 WriteReal(iy-m2, kFALSE);
599 PrintStr("\" width=\"");
601 PrintStr("\" height=\"");
603 PrintStr("\"/>");
604 // Down triangle
605 } else if (ms == 26 || ms == 22) {
606 PrintStr("<polygon points=\"");
607 WriteReal(ix); PrintStr(","); WriteReal(iy-m2);
608 WriteReal(ix+m2); PrintStr(","); WriteReal(iy+m2);
609 WriteReal(ix-m2); PrintStr(","); WriteReal(iy+m2);
610 PrintStr("\"/>");
611 // Up triangle
612 } else if (ms == 23 || ms == 32) {
613 PrintStr("<polygon points=\"");
614 WriteReal(ix-m2); PrintStr(","); WriteReal(iy-m2);
615 WriteReal(ix+m2); PrintStr(","); WriteReal(iy-m2);
616 WriteReal(ix); PrintStr(","); WriteReal(iy+m2);
617 PrintStr("\"/>");
618 // Diamond
619 } else if (ms == 27 || ms == 33) {
620 PrintStr("<polygon points=\"");
621 WriteReal(ix); PrintStr(","); WriteReal(iy-m2);
622 WriteReal(ix+m3); PrintStr(","); WriteReal(iy);
623 WriteReal(ix); PrintStr(","); WriteReal(iy+m2);
624 WriteReal(ix-m3); PrintStr(","); WriteReal(iy);
625 PrintStr("\"/>");
626 // Cross
627 } else if (ms == 28 || ms == 34) {
628 PrintStr("<polygon points=\"");
629 WriteReal(ix-m6); PrintStr(","); WriteReal(iy-m6);
630 WriteReal(ix-m6); PrintStr(","); WriteReal(iy-m2);
631 WriteReal(ix+m6); PrintStr(","); WriteReal(iy-m2);
632 WriteReal(ix+m6); PrintStr(","); WriteReal(iy-m6);
633 WriteReal(ix+m2); PrintStr(","); WriteReal(iy-m6);
634 WriteReal(ix+m2); PrintStr(","); WriteReal(iy+m6);
635 WriteReal(ix+m6); PrintStr(","); WriteReal(iy+m6);
636 WriteReal(ix+m6); PrintStr(","); WriteReal(iy+m2);
637 WriteReal(ix-m6); PrintStr(","); WriteReal(iy+m2);
638 WriteReal(ix-m6); PrintStr(","); WriteReal(iy+m6);
639 WriteReal(ix-m2); PrintStr(","); WriteReal(iy+m6);
640 WriteReal(ix-m2); PrintStr(","); WriteReal(iy-m6);
641 PrintStr("\"/>");
642 } else if (ms == 29 || ms == 30) {
643 PrintStr("<polygon points=\"");
644 WriteReal(ix); PrintStr(","); WriteReal(iy+m2);
645 WriteReal(ix+0.112255*m); PrintStr(","); WriteReal(iy+0.15451*m);
646 WriteReal(ix+0.47552*m); PrintStr(","); WriteReal(iy+0.15451*m);
647 WriteReal(ix+0.181635*m); PrintStr(","); WriteReal(iy-0.05902*m);
648 WriteReal(ix+0.29389*m); PrintStr(","); WriteReal(iy-0.40451*m);
649 WriteReal(ix); PrintStr(","); WriteReal(iy-0.19098*m);
650 WriteReal(ix-0.29389*m); PrintStr(","); WriteReal(iy-0.40451*m);
651 WriteReal(ix-0.181635*m); PrintStr(","); WriteReal(iy-0.05902*m);
652 WriteReal(ix-0.47552*m); PrintStr(","); WriteReal(iy+0.15451*m);
653 WriteReal(ix-0.112255*m); PrintStr(","); WriteReal(iy+0.15451*m);
654 PrintStr("\"/>");
655 } else if (ms == 35) {
656 PrintStr("<polygon points=\"");
657 WriteReal(ix-m2); PrintStr(","); WriteReal(iy );
658 WriteReal(ix ); PrintStr(","); WriteReal(iy-m2);
659 WriteReal(ix+m2); PrintStr(","); WriteReal(iy );
660 WriteReal(ix ); PrintStr(","); WriteReal(iy+m2);
661 WriteReal(ix-m2); PrintStr(","); WriteReal(iy );
662 WriteReal(ix+m2); PrintStr(","); WriteReal(iy );
663 WriteReal(ix ); PrintStr(","); WriteReal(iy+m2);
664 WriteReal(ix ); PrintStr(","); WriteReal(iy-m2);
665 PrintStr("\"/>");
666 } else if (ms == 36) {
667 PrintStr("<polygon points=\"");
668 WriteReal(ix-m2); PrintStr(","); WriteReal(iy-m2);
669 WriteReal(ix+m2); PrintStr(","); WriteReal(iy-m2);
670 WriteReal(ix+m2); PrintStr(","); WriteReal(iy+m2);
671 WriteReal(ix-m2); PrintStr(","); WriteReal(iy+m2);
672 WriteReal(ix-m2); PrintStr(","); WriteReal(iy-m2);
673 WriteReal(ix+m2); PrintStr(","); WriteReal(iy+m2);
674 WriteReal(ix-m2); PrintStr(","); WriteReal(iy+m2);
675 WriteReal(ix+m2); PrintStr(","); WriteReal(iy-m2);
676 PrintStr("\"/>");
677 } else if (ms == 37 || ms == 39) {
678 PrintStr("<polygon points=\"");
679 WriteReal(ix ); PrintStr(","); WriteReal(iy );
680 WriteReal(ix+m4); PrintStr(","); WriteReal(iy+m2);
681 WriteReal(ix-m4); PrintStr(","); WriteReal(iy+m2);
682 WriteReal(ix ); PrintStr(","); WriteReal(iy );
683 WriteReal(ix-m4); PrintStr(","); WriteReal(iy-m2);
684 WriteReal(ix-m2); PrintStr(","); WriteReal(iy);
685 WriteReal(ix ); PrintStr(","); WriteReal(iy );
686 WriteReal(ix+m2); PrintStr(","); WriteReal(iy );
687 WriteReal(ix+m4); PrintStr(","); WriteReal(iy-m2);
688 WriteReal(ix ); PrintStr(","); WriteReal(iy );
689 PrintStr("\"/>");
690 } else if (ms == 38) {
691 PrintStr("<polygon points=\"");
692 WriteReal(ix-m2); PrintStr(","); WriteReal(iy );
693 WriteReal(ix-m2); PrintStr(","); WriteReal(iy-m4);
694 WriteReal(ix-m4); PrintStr(","); WriteReal(iy-m2);
695 WriteReal(ix+m4); PrintStr(","); WriteReal(iy-m2);
696 WriteReal(ix+m2); PrintStr(","); WriteReal(iy-m4);
697 WriteReal(ix+m2); PrintStr(","); WriteReal(iy+m4);
698 WriteReal(ix+m4); PrintStr(","); WriteReal(iy+m2);
699 WriteReal(ix-m4); PrintStr(","); WriteReal(iy+m2);
700 WriteReal(ix-m2); PrintStr(","); WriteReal(iy+m4);
701 WriteReal(ix-m2); PrintStr(","); WriteReal(iy );
702 WriteReal(ix+m2); PrintStr(","); WriteReal(iy );
703 WriteReal(ix ); PrintStr(","); WriteReal(iy );
704 WriteReal(ix ); PrintStr(","); WriteReal(iy-m2);
705 WriteReal(ix ); PrintStr(","); WriteReal(iy+m2);
706 WriteReal(ix ); PrintStr(","); WriteReal(iy);
707 PrintStr("\"/>");
708 } else if (ms == 40 || ms == 41) {
709 PrintStr("<polygon points=\"");
710 WriteReal(ix ); PrintStr(","); WriteReal(iy );
711 WriteReal(ix+m4); PrintStr(","); WriteReal(iy+m2);
712 WriteReal(ix+m2); PrintStr(","); WriteReal(iy+m4);
713 WriteReal(ix ); PrintStr(","); WriteReal(iy );
714 WriteReal(ix+m2); PrintStr(","); WriteReal(iy-m4);
715 WriteReal(ix+m4); PrintStr(","); WriteReal(iy-m2);
716 WriteReal(ix ); PrintStr(","); WriteReal(iy );
717 WriteReal(ix-m4); PrintStr(","); WriteReal(iy-m2);
718 WriteReal(ix-m2); PrintStr(","); WriteReal(iy-m4);
719 WriteReal(ix ); PrintStr(","); WriteReal(iy );
720 WriteReal(ix-m2); PrintStr(","); WriteReal(iy+m4);
721 WriteReal(ix-m4); PrintStr(","); WriteReal(iy+m2);
722 WriteReal(ix ); PrintStr(","); WriteReal(iy );
723 PrintStr("\"/>");
724 } else if (ms == 42 || ms == 43) {
725 PrintStr("<polygon points=\"");
726 WriteReal(ix ); PrintStr(","); WriteReal(iy+m2);
727 WriteReal(ix-m8); PrintStr(","); WriteReal(iy+m8);
728 WriteReal(ix-m2); PrintStr(","); WriteReal(iy );
729 WriteReal(ix-m8); PrintStr(","); WriteReal(iy-m8);
730 WriteReal(ix ); PrintStr(","); WriteReal(iy-m2);
731 WriteReal(ix+m8); PrintStr(","); WriteReal(iy-m8);
732 WriteReal(ix+m2); PrintStr(","); WriteReal(iy );
733 WriteReal(ix+m8); PrintStr(","); WriteReal(iy+m8);
734 WriteReal(ix ); PrintStr(","); WriteReal(iy+m2);
735 PrintStr("\"/>");
736 } else if (ms == 44) {
737 PrintStr("<polygon points=\"");
738 WriteReal(ix ); PrintStr(","); WriteReal(iy );
739 WriteReal(ix+m4); PrintStr(","); WriteReal(iy+m2);
740 WriteReal(ix-m4); PrintStr(","); WriteReal(iy+m2);
741 WriteReal(ix+m4); PrintStr(","); WriteReal(iy-m2);
742 WriteReal(ix-m4); PrintStr(","); WriteReal(iy-m2);
743 WriteReal(ix ); PrintStr(","); WriteReal(iy );
744 WriteReal(ix+m2); PrintStr(","); WriteReal(iy+m4);
745 WriteReal(ix+m2); PrintStr(","); WriteReal(iy-m4);
746 WriteReal(ix-m2); PrintStr(","); WriteReal(iy+m4);
747 WriteReal(ix-m2); PrintStr(","); WriteReal(iy-m4);
748 WriteReal(ix ); PrintStr(","); WriteReal(iy );
749 PrintStr("\"/>");
750 } else if (ms == 45) {
751 PrintStr("<polygon points=\"");
752 WriteReal(ix+m0); PrintStr(","); WriteReal(iy+m0);
753 WriteReal(ix+m4); PrintStr(","); WriteReal(iy+m2);
754 WriteReal(ix-m4); PrintStr(","); WriteReal(iy+m2);
755 WriteReal(ix-m0); PrintStr(","); WriteReal(iy+m0);
756 WriteReal(ix-m2); PrintStr(","); WriteReal(iy+m4);
757 WriteReal(ix-m2); PrintStr(","); WriteReal(iy-m4);
758 WriteReal(ix-m0); PrintStr(","); WriteReal(iy-m0);
759 WriteReal(ix-m4); PrintStr(","); WriteReal(iy-m2);
760 WriteReal(ix+m4); PrintStr(","); WriteReal(iy-m2);
761 WriteReal(ix+m0); PrintStr(","); WriteReal(iy-m0);
762 WriteReal(ix+m2); PrintStr(","); WriteReal(iy-m4);
763 WriteReal(ix+m2); PrintStr(","); WriteReal(iy+m4);
764 WriteReal(ix+m0); PrintStr(","); WriteReal(iy+m0);
765 PrintStr("\"/>");
766 } else if (ms == 46 || ms == 47) {
767 PrintStr("<polygon points=\"");
768 WriteReal(ix ); PrintStr(","); WriteReal(iy+m4);
769 WriteReal(ix-m4); PrintStr(","); WriteReal(iy+m2);
770 WriteReal(ix-m2); PrintStr(","); WriteReal(iy+m4);
771 WriteReal(ix-m4); PrintStr(","); WriteReal(iy );
772 WriteReal(ix-m2); PrintStr(","); WriteReal(iy-m4);
773 WriteReal(ix-m4); PrintStr(","); WriteReal(iy-m2);
774 WriteReal(ix ); PrintStr(","); WriteReal(iy-m4);
775 WriteReal(ix+m4); PrintStr(","); WriteReal(iy-m2);
776 WriteReal(ix+m2); PrintStr(","); WriteReal(iy-m4);
777 WriteReal(ix+m4); PrintStr(","); WriteReal(iy );
778 WriteReal(ix+m2); PrintStr(","); WriteReal(iy+m4);
779 WriteReal(ix+m4); PrintStr(","); WriteReal(iy+m2);
780 WriteReal(ix ); PrintStr(","); WriteReal(iy+m4);
781 PrintStr("\"/>");
782 } else if (ms == 48) {
783 PrintStr("<polygon points=\"");
784 WriteReal(ix ); PrintStr(","); WriteReal(iy+m4*1.01);
785 WriteReal(ix-m4); PrintStr(","); WriteReal(iy+m2);
786 WriteReal(ix-m2); PrintStr(","); WriteReal(iy+m4);
787 WriteReal(ix-m4); PrintStr(","); WriteReal(iy );
788 WriteReal(ix-m2); PrintStr(","); WriteReal(iy-m4);
789 WriteReal(ix-m4); PrintStr(","); WriteReal(iy-m2);
790 WriteReal(ix ); PrintStr(","); WriteReal(iy-m4);
791 WriteReal(ix+m4); PrintStr(","); WriteReal(iy-m2);
792 WriteReal(ix+m2); PrintStr(","); WriteReal(iy-m4);
793 WriteReal(ix+m4); PrintStr(","); WriteReal(iy );
794 WriteReal(ix+m2); PrintStr(","); WriteReal(iy+m4);
795 WriteReal(ix+m4); PrintStr(","); WriteReal(iy+m2);
796 WriteReal(ix ); PrintStr(","); WriteReal(iy+m4*0.99);
797 WriteReal(ix+m4*0.99); PrintStr(","); WriteReal(iy );
798 WriteReal(ix ); PrintStr(","); WriteReal(iy-m4*0.99);
799 WriteReal(ix-m4*0.99); PrintStr(","); WriteReal(iy );
800 WriteReal(ix ); PrintStr(","); WriteReal(iy+m4*0.99);
801 PrintStr("\"/>");
802 } else if (ms == 49) {
803 PrintStr("<polygon points=\"");
804 WriteReal(ix-m6); PrintStr(","); WriteReal(iy-m6*1.01);
805 WriteReal(ix-m6); PrintStr(","); WriteReal(iy-m2);
806 WriteReal(ix+m6); PrintStr(","); WriteReal(iy-m2);
807 WriteReal(ix+m6); PrintStr(","); WriteReal(iy-m6);
808 WriteReal(ix+m2); PrintStr(","); WriteReal(iy-m6);
809 WriteReal(ix+m2); PrintStr(","); WriteReal(iy+m6);
810 WriteReal(ix+m6); PrintStr(","); WriteReal(iy+m6);
811 WriteReal(ix+m6); PrintStr(","); WriteReal(iy+m2);
812 WriteReal(ix-m6); PrintStr(","); WriteReal(iy+m2);
813 WriteReal(ix-m6); PrintStr(","); WriteReal(iy+m6);
814 WriteReal(ix-m2); PrintStr(","); WriteReal(iy+m6);
815 WriteReal(ix-m2); PrintStr(","); WriteReal(iy-m6);
816 WriteReal(ix-m6); PrintStr(","); WriteReal(iy-m6*0.99);
817 WriteReal(ix-m6); PrintStr(","); WriteReal(iy+m6);
818 WriteReal(ix+m6); PrintStr(","); WriteReal(iy+m6);
819 WriteReal(ix+m6); PrintStr(","); WriteReal(iy-m6);
820 PrintStr("\"/>");
821 } else {
822 PrintStr("<line x1=\"");
823 WriteReal(ix-1, kFALSE);
824 PrintStr("\" y1=\"");
825 WriteReal(iy, kFALSE);
826 PrintStr("\" x2=\"");
827 WriteReal(ix, kFALSE);
828 PrintStr("\" y2=\"");
829 WriteReal(iy, kFALSE);
830 PrintStr("\"/>");
831 }
832 }
833 PrintStr("@");
834 PrintStr("</g>");
835}
836
837////////////////////////////////////////////////////////////////////////////////
838/// Paint PolyMarker
839
841{
843}
844
845
846////////////////////////////////////////////////////////////////////////////////
847/// Paint PolyMarker
848
853
854
855////////////////////////////////////////////////////////////////////////////////
856/// Print line style attributes on the end of "path" string
857
859{
860 PrintFast(21,"\" fill=\"none\" stroke=");
862 if(fLineWidth > 1.) {
863 PrintFast(15," stroke-width=\"");
865 PrintFast(1,"\"");
866 }
867 if (fLineStyle > 1) {
868 PrintFast(19," stroke-dasharray=\"");
869 TString st = (TString)gStyle->GetLineStyleString(fLineStyle);
870 TObjArray *tokens = st.Tokenize(" ");
871 for (Int_t j = 0; j<tokens->GetEntries(); j++) {
872 Int_t it;
873 sscanf(((TObjString*)tokens->At(j))->GetName(), "%d", &it);
874 if (j>0) PrintFast(1,",");
875 WriteReal(it/4);
876 }
877 delete tokens;
878 PrintFast(1,"\"");
879 }
880}
881
882////////////////////////////////////////////////////////////////////////////////
883/// Print line join attributes - if present
884
886{
887 if (fgLineJoin)
888 PrintStr(TString::Format(" stroke-linejoin=\"%s\"", fgLineJoin == 1 ? "round" : "bevel"));
889 if (fgLineCap)
890 PrintStr(TString::Format(" stroke-linecap=\"%s\"", fgLineCap == 1 ? "round" : "square"));
891}
892
893
894////////////////////////////////////////////////////////////////////////////////
895/// This function defines a path with xw and yw and draw it according the
896/// value of nn:
897///
898/// - If nn>0 a line is drawn.
899/// - If nn<0 a closed polygon is drawn.
900
902{
903 Int_t n, fais = 0, fasi = 0;
904
905 if (nn > 0) {
906 if (fLineWidth <= 0)
907 return;
908 n = nn;
909 } else {
910 n = -nn;
911 fais = fFillStyle/1000;
912 fasi = fFillStyle%1000;
913 if (fais == 3 || fais == 2) {
914 if (fasi > 100 && fasi <125) {
915 return;
916 }
917 if (fasi > 0 && fasi < 26) {
918 }
919 }
920 }
921
922 if(n <= 1) {
923 Error("DrawPS", "Two points are needed");
924 return;
925 }
926
927 PrintStr("@");
928 PrintFast(9,"<path d=\"");
929
930 PrintPath(kTRUE, n, xw, yw, nn < 0);
931
932 if (nn > 0)
934 else {
935 PrintFast(7,"\" fill=");
936 if (fais == 0) {
937 PrintFast(14,"\"none\" stroke=");
939 } else {
941 }
942 }
944 PrintFast(2,"/>");
945}
946
947////////////////////////////////////////////////////////////////////////////////
948/// This method draw N segments
950{
951 if (fLineWidth < 0)
952 return;
953
954 if(n < 1) {
955 Error("DrawSegments", "At least one segment has to be provided");
956 return;
957 }
958
959 PrintStr("@");
960 PrintFast(9,"<path d=\"");
961
962 for(Int_t i = 0; i < 2*n; i += 2) {
963 Double_t ixd0 = XtoSVG(xw[i]);
964 Double_t iyd0 = YtoSVG(yw[i]);
965 Double_t ixd1 = XtoSVG(xw[i+1]);
966 Double_t iyd1 = YtoSVG(yw[i+1]);
967
968 Double_t dx = ixd1 - ixd0;
969 Double_t dy = iyd1 - iyd0;
970
971 if (fCompact && (TMath::Abs(dx) < kEpsilon))
972 dx = 0;
973 if (fCompact && (TMath::Abs(dy) < kEpsilon))
974 dy = 0;
975
976 if (dx || dy) {
977 PrintFast(1,"M");
978 WriteReal(ixd0, kFALSE);
979 PrintFast(1,",");
980 WriteReal(iyd0, kFALSE);
981 MovePS(dx, dy);
982 }
983 }
984
987 PrintFast(2,"/>");
988}
989
990
991////////////////////////////////////////////////////////////////////////////////
992/// Begin the Cell Array painting
993
995{
996 Double_t svgx1 = XtoSVG(x1);
997 Double_t svgx2 = XtoSVG(x1 + (x2 - x1) * width);
998 Double_t svgy1 = YtoSVG(y1);
999 Double_t svgy2 = YtoSVG(y1 - (y2 - y1) * height);
1000
1001 PrintStr("@<g transform=\"translate(");
1002 WriteReal(svgx1, kFALSE);
1003 WriteReal(svgy1, kTRUE);
1004 PrintStr(") scale(");
1005 WriteReal((svgx2 - svgx1) / width, kFALSE);
1006 WriteReal((svgy2 - svgy1) / height, kTRUE);
1007 PrintStr(")\">@");
1008 PrintStr(TString::Format("<image width=\"%d\" height=\"%d\" href=\"data:image/png;base64,", width, height));
1009}
1010
1011////////////////////////////////////////////////////////////////////////////////
1012/// Paint the Cell Array as single pixel
1013
1015{
1016 Warning("CellArrayFill", "not implemented");
1017}
1018
1019////////////////////////////////////////////////////////////////////////////////
1020/// Paint the Cell Array as png image
1021/// Disabled in compact mode to avoid creation of large SVG files
1022
1023void TSVG::CellArrayPng(char *buffer, int size)
1024{
1025 if (!fCompact) {
1026 TString base64 = TBase64::Encode(reinterpret_cast<char *>(buffer), size);
1027 PrintFast(base64.Length(), base64.Data());
1028 }
1029}
1030
1031////////////////////////////////////////////////////////////////////////////////
1032/// End the Cell Array painting
1033
1035{
1036 PrintStr("\"></image>@");
1037 PrintStr("</g>@");
1038}
1039
1040////////////////////////////////////////////////////////////////////////////////
1041/// Initialize the SVG file. The main task of the function is to output the
1042/// SVG header file which consist in `<title>`, `<desc>` and `<defs>`. The
1043/// HeaderPS provided by the user program is written in the `<defs>` part.
1044
1046{
1047 // Title
1048 PrintStr("<title>@");
1049 PrintStr(GetName());
1050 PrintStr("@");
1051 PrintStr("</title>@");
1052
1053 if (fCompact)
1054 return;
1055
1056 // Description
1057 PrintStr("<desc>@");
1058 PrintFast(22,"Creator: ROOT Version ");
1059 PrintStr(gROOT->GetVersion());
1060 PrintStr("@");
1061 PrintFast(14,"CreationDate: ");
1062 TDatime t;
1063 PrintStr(t.AsString());
1064 //Check a special header is defined in the current style
1065 Int_t nh = strlen(gStyle->GetHeaderPS());
1066 if (nh) {
1067 PrintFast(nh,gStyle->GetHeaderPS());
1068 }
1069 PrintStr("</desc>@");
1070
1071 // Definitions
1072 PrintStr("<defs>@");
1073 PrintStr("</defs>@");
1074
1075}
1076
1077////////////////////////////////////////////////////////////////////////////////
1078/// Write float value into output stream
1079/// In compact form try to store only first 2-3 significant digits
1080
1082{
1083 if (fCompact) {
1084 auto a = std::abs(r);
1085 if (a > 10)
1086 TVirtualPS::WriteInteger(std::lround(r), space);
1087 else if (a < 0.005)
1088 TVirtualPS::WriteReal(r, space);
1089 else {
1090 char str[15];
1091 snprintf(str, 15, (a > 1) ? "%3.1f" : "%5.3f", r);
1092 if(space)
1093 PrintFast(1," ");
1094 PrintStr(str);
1095 }
1096 } else
1097 TVirtualPS::WriteReal(r, space);
1098}
1099
1100////////////////////////////////////////////////////////////////////////////////
1101/// Move to a new position (ix, iy). The move is done in relative coordinates
1102/// which allows to have short numbers which decrease the size of the file.
1103/// This function use the full power of the SVG's paths by using the
1104/// horizontal and vertical move whenever it is possible.
1105
1107{
1108 if (ix != 0 && iy != 0) {
1109 PrintFast(1,"l");
1110 WriteReal(ix);
1111 PrintFast(1,",");
1112 WriteReal(iy);
1113 } else if (ix != 0) {
1114 PrintFast(1,"h");
1115 WriteReal(ix);
1116 } else if (iy != 0) {
1117 PrintFast(1,"v");
1118 WriteReal(iy);
1119 }
1120}
1121
1122////////////////////////////////////////////////////////////////////////////////
1123/// Start the SVG page. This function initialize the pad conversion
1124/// coefficients and output the `<svg>` directive which is close later in the
1125/// the function Close.
1126
1128{
1129 // Compute pad conversion coefficients
1130 if (gPad) {
1131 Double_t ww = gPad->GetWw();
1132 Double_t wh = gPad->GetWh();
1133 fYsize = fXsize*wh/ww;
1134 } else {
1135 fYsize = 27;
1136 }
1137
1138 // <svg> directive. It defines the viewBox.
1139 if(!fBoundingBox) {
1140 PrintStr("@<?xml version=\"1.0\" standalone=\"no\"?>");
1141 PrintStr("@<svg width=\"");
1143 PrintStr("\" height=\"");
1146 PrintStr("\" viewBox=\"0 0");
1149 PrintStr("\" xmlns=\"http://www.w3.org/2000/svg\" shape-rendering=\"crispEdges\">");
1150 PrintStr("@");
1151 Initialize();
1153 }
1154}
1155
1156////////////////////////////////////////////////////////////////////////////////
1157/// Set the range for the paper in centimetres
1158
1159void TSVG::Range(Float_t xsize, Float_t ysize)
1160{
1161 fXsize = xsize;
1162 fYsize = ysize;
1163 fRange = kTRUE;
1164}
1165
1166////////////////////////////////////////////////////////////////////////////////
1167/// Set color index for fill areas
1168
1170{
1171 fFillColor = cindex;
1172}
1173
1174////////////////////////////////////////////////////////////////////////////////
1175/// Set color index for lines
1176
1178{
1179 fLineColor = cindex;
1180}
1181
1182////////////////////////////////////////////////////////////////////////////////
1183/// Set the value of the global parameter TSVG::fgLineJoin.
1184/// This parameter determines the appearance of joining lines in a SVG
1185/// output.
1186/// It takes one argument which may be:
1187/// - 0 (miter join)
1188/// - 1 (round join)
1189/// - 2 (bevel join)
1190/// The default value is 0 (miter join).
1191///
1192/// \image html postscript_1.png
1193///
1194/// To change the line join behaviour just do:
1195/// ~~~ {.cpp}
1196/// gStyle->SetJoinLinePS(2); // Set the PS line join to bevel.
1197/// ~~~
1198
1199void TSVG::SetLineJoin( Int_t linejoin )
1200{
1201 fgLineJoin = linejoin;
1202 if (fgLineJoin<0) fgLineJoin=0;
1203 if (fgLineJoin>2) fgLineJoin=2;
1204}
1205
1206////////////////////////////////////////////////////////////////////////////////
1207/// Set the value of the global parameter TSVG::fgLineCap.
1208/// This parameter determines the appearance of line caps in a SVG
1209/// output.
1210/// It takes one argument which may be:
1211/// - 0 (butt caps)
1212/// - 1 (round caps)
1213/// - 2 (projecting caps)
1214/// The default value is 0 (butt caps).
1215///
1216/// \image html postscript_2.png
1217///
1218/// To change the line cap behaviour just do:
1219/// ~~~ {.cpp}
1220/// gStyle->SetCapLinePS(2); // Set the PS line cap to projecting.
1221/// ~~~
1222
1224{
1225 fgLineCap = linecap;
1226 if (fgLineCap<0) fgLineCap=0;
1227 if (fgLineCap>2) fgLineCap=2;
1228}
1229
1230////////////////////////////////////////////////////////////////////////////////
1231/// Change the line style
1232///
1233/// - linestyle = 2 dashed
1234/// - linestyle = 3 dotted
1235/// - linestyle = 4 dash-dotted
1236/// - linestyle = else solid (1 in is used most of the time)
1237
1239{
1240 fLineStyle = linestyle;
1241}
1242
1243////////////////////////////////////////////////////////////////////////////////
1244/// Set the lines width.
1245
1247{
1248 fLineWidth = linewidth;
1249}
1250
1251////////////////////////////////////////////////////////////////////////////////
1252/// Set color index for markers.
1253
1255{
1256 fMarkerColor = cindex;
1257}
1258
1259////////////////////////////////////////////////////////////////////////////////
1260/// Set RGBa color with its color index
1261
1262void TSVG::SetColorAlpha(Int_t color, Bool_t fill, Bool_t stroke)
1263{
1264 if (color < 0)
1265 color = 0;
1266 TColor *col = gROOT->GetColor(color);
1267 if (col) {
1268 SetColor(col->GetRed(), col->GetGreen(), col->GetBlue());
1269 Float_t a = col->GetAlpha();
1270 if ((a < 1.) && fill)
1271 PrintStr(TString::Format(" fill-opacity=\"%3.2f\"",a));
1272 if ((a < 1.) && stroke)
1273 PrintStr(TString::Format(" stroke-opacity=\"%3.2f\"",a));
1274 } else {
1275 SetColor(1., 1., 1.);
1276 }
1277}
1278
1279////////////////////////////////////////////////////////////////////////////////
1280/// Set RGB (without alpha channel) color with its color index
1281
1283{
1284 if (color < 0) color = 0;
1285 TColor *col = gROOT->GetColor(color);
1286 if (col) {
1287 SetColor(col->GetRed(), col->GetGreen(), col->GetBlue());
1288 } else {
1289 SetColor(1., 1., 1.);
1290 }
1291}
1292
1293////////////////////////////////////////////////////////////////////////////////
1294/// Set color with its R G B components
1295///
1296/// - r: % of red in [0,1]
1297/// --g: % of green in [0,1]
1298/// - b: % of blue in [0,1]
1299
1301{
1302 if (r <= 0. && g <= 0. && b <= 0. ) {
1303 PrintFast(7,"\"black\"");
1304 } else if (r >= 1. && g >= 1. && b >= 1. ) {
1305 PrintFast(7,"\"white\"");
1306 } else {
1307 char str[12];
1308 snprintf(str,12,"\"#%2.2x%2.2x%2.2x\"",Int_t(255.*r)
1309 ,Int_t(255.*g)
1310 ,Int_t(255.*b));
1311 PrintStr(str);
1312 }
1313}
1314
1315////////////////////////////////////////////////////////////////////////////////
1316/// Set color index for text
1317
1319{
1320 fTextColor = cindex;
1321}
1322
1323////////////////////////////////////////////////////////////////////////////////
1324/// Draw text
1325///
1326/// - xx: x position of the text
1327/// - yy: y position of the text
1328/// - chars: text to be drawn
1329
1330void TSVG::Text(Double_t xx, Double_t yy, const char *chars)
1331{
1332 static const char *fontFamily[] = {
1333 "Times" , "Times" , "Times",
1334 "Helvetica", "Helvetica", "Helvetica" , "Helvetica",
1335 "Courier" , "Courier" , "Courier" , "Courier",
1336 "Times" ,"Times" , "ZapfDingbats", "Times"};
1337
1338 static const char *fontWeight[] = {
1339 "normal", "bold", "bold",
1340 "normal", "normal", "bold" , "bold",
1341 "normal", "normal", "bold" , "bold",
1342 "normal", "normal", "normal", "normal"};
1343
1344 static const char *fontStyle[] = {
1345 "italic", "normal" , "italic",
1346 "normal", "oblique", "normal", "oblique",
1347 "normal", "oblique", "normal", "oblique",
1348 "normal", "normal" , "normal", "italic"};
1349
1350 Double_t ix = XtoSVG(xx);
1351 Double_t iy = YtoSVG(yy);
1352 Double_t txalh = fTextAlign/10;
1353 if (txalh <1) txalh = 1; else if (txalh > 3) txalh = 3;
1354 Double_t txalv = fTextAlign%10;
1355 if (txalv <1) txalv = 1; else if (txalv > 3) txalv = 3;
1356
1357 Double_t wh = (Double_t)gPad->GetPadWidth();
1358 Double_t hh = (Double_t)gPad->GetPadHeight();
1359 Float_t fontrap = 1.09; //scale down compared to X11
1360 Float_t ftsize;
1361
1362 Int_t font = abs(fTextFont)/10;
1363 if (font > 15 || font < 1)
1364 font = 1;
1365 if (wh < hh) {
1366 ftsize = fTextSize*fXsize*gPad->GetAbsWNDC();
1367 } else {
1368 ftsize = fTextSize*fYsize*gPad->GetAbsHNDC();
1369 }
1370 Int_t ifont = font-1;
1371
1372 Double_t fontsize = CMtoSVG(ftsize/fontrap);
1373 if( fontsize <= 0) return;
1374
1375 if (txalv == 3) iy = iy+fontsize;
1376 if (txalv == 2) iy = iy+(fontsize/2);
1377
1378 if (fTextAngle != 0.) {
1379 PrintStr("@");
1380 PrintFast(21,"<g transform=\"rotate(");
1382 PrintFast(1,",");
1383 WriteReal(ix, kFALSE);
1384 PrintFast(1,",");
1385 WriteReal(iy, kFALSE);
1386 PrintFast(3,")\">");
1387 }
1388
1389 PrintStr("@");
1390 PrintFast(30,"<text xml:space=\"preserve\" x=\"");
1391 WriteReal(ix, kFALSE);
1392 PrintFast(5,"\" y=\"");
1393 WriteReal(iy, kFALSE);
1394 PrintFast(1,"\"");
1395 if (txalh == 2) {
1396 PrintFast(21," text-anchor=\"middle\"");
1397 } else if (txalh == 3) {
1398 PrintFast(18," text-anchor=\"end\"");
1399 }
1400 PrintFast(6," fill=");
1402 PrintFast(12," font-size=\"");
1403 WriteReal(fontsize, kFALSE);
1404 PrintFast(15,"\" font-family=\"");
1405 PrintStr(fontFamily[ifont]);
1406 if (strcmp(fontWeight[ifont],"normal")) {
1407 PrintFast(15,"\" font-weight=\"");
1408 PrintStr(fontWeight[ifont]);
1409 }
1410 if (strcmp(fontStyle[ifont],"normal")) {
1411 PrintFast(14,"\" font-style=\"");
1412 PrintStr(fontStyle[ifont]);
1413 }
1414 PrintFast(2,"\">");
1415
1416 if (font == 12 || font == 15) {
1417 Int_t ichar = chars[0]+848;
1418 Int_t ic = ichar;
1419
1420 // Math Symbols (cf: http://www.fileformat.info/info/unicode/category/Sm/list.htm)
1421 if (ic == 755) ichar = 8804;
1422 if (ic == 759) ichar = 9827;
1423 if (ic == 760) ichar = 9830;
1424 if (ic == 761) ichar = 9829;
1425 if (ic == 762) ichar = 9824;
1426 if (ic == 766) ichar = 8594;
1427 if (ic == 776) ichar = 247;
1428 if (ic == 757) ichar = 8734;
1429 if (ic == 758) ichar = 402;
1430 if (ic == 771) ichar = 8805;
1431 if (ic == 774) ichar = 8706;
1432 if (ic == 775) ichar = 8226;
1433 if (ic == 779) ichar = 8776;
1434 if (ic == 805) ichar = 8719;
1435 if (ic == 821) ichar = 8721;
1436 if (ic == 834) ichar = 8747;
1437 if (ic == 769) ichar = 177;
1438 if (ic == 772) ichar = 215;
1439 if (ic == 768) ichar = 176;
1440 if (ic == 791) ichar = 8745;
1441 if (ic == 793) ichar = 8835; // SUPERSET OF
1442 if (ic == 794) ichar = 8839; // SUPERSET OF OR EQUAL TO
1443 if (ic == 795) ichar = 8836; // NOT A SUBSET OF
1444 if (ic == 796) ichar = 8834;
1445 if (ic == 893) ichar = 8722;
1446 if (ic == 803) ichar = 169; // COPYRIGHT SIGN
1447 if (ic == 819) ichar = 169; // COPYRIGHT SIGN
1448 if (ic == 804) ichar = 8482;
1449 if (ic == 770) ichar = 34;
1450 if (ic == 823) ichar = 10072;
1451 if (ic == 781) ichar = 10072;
1452 if (ic == 824) ichar = 9117; // LEFT PARENTHESIS LOWER HOOK
1453 if (ic == 822) ichar = 9115; // LEFT PARENTHESIS UPPER HOOK
1454 if (ic == 767) ichar = 8595; // DOWNWARDS ARROW
1455 if (ic == 763) ichar = 8596; // LEFT RIGHT ARROW
1456 if (ic == 764) ichar = 8592; // LEFTWARDS ARROW
1457 if (ic == 788) ichar = 8855; // CIRCLED TIMES
1458 if (ic == 784) ichar = 8501;
1459 if (ic == 777) ichar = 8800;
1460 if (ic == 797) ichar = 8838;
1461 if (ic == 800) ichar = 8736;
1462 if (ic == 812) ichar = 8656; // LEFTWARDS DOUBLE ARROW
1463 if (ic == 817) ichar = 60; // LESS-THAN SIGN
1464 if (ic == 833) ichar = 62; // GREATER-THAN SIGN
1465 if (ic == 778) ichar = 8803; // STRICTLY EQUIVALENT TO
1466 if (ic == 809) ichar = 8743; // LOGICAL AND
1467 if (ic == 802) ichar = 9415; // CIRCLED LATIN CAPITAL LETTER R
1468 if (ic == 780) ichar = 8230; // HORIZONTAL ELLIPSIS
1469 if (ic == 801) ichar = 8711; // NABLA
1470 if (ic == 783) ichar = 8629; // DOWNWARDS ARROW WITH CORNER LEFTWARDS
1471 if (ic == 782) ichar = 8213;
1472 if (ic == 799) ichar = 8713;
1473 if (ic == 792) ichar = 8746;
1474 if (ic == 828) ichar = 9127;
1475 if (ic == 765) ichar = 8593; // UPWARDS ARROW
1476 if (ic == 789) ichar = 8853; // CIRCLED PLUS
1477 if (ic == 813) ichar = 8657; // UPWARDS DOUBLE ARROW
1478 if (ic == 773) ichar = 8733; // PROPORTIONAL TO
1479 if (ic == 790) ichar = 8709; // EMPTY SET
1480 if (ic == 810) ichar = 8744;
1481 if (ic == 756) ichar = 8260;
1482 if (ic == 807) ichar = 8231;
1483 if (ic == 808) ichar = 8989; // TOP RIGHT CORNER
1484 if (ic == 814) ichar = 8658; // RIGHTWARDS DOUBLE ARROW
1485 if (ic == 806) ichar = 8730; // SQUARE ROOT
1486 if (ic == 827) ichar = 9123;
1487 if (ic == 829) ichar = 9128;
1488 if (ic == 786) ichar = 8476;
1489 if (ic == 785) ichar = 8465;
1490 if (ic == 787) ichar = 8472;
1491
1492 // Greek characters
1493 if (ic == 918) ichar = 934;
1494 if (ic == 919) ichar = 915;
1495 if (ic == 920) ichar = 919;
1496 if (ic == 923) ichar = 922;
1497 if (ic == 924) ichar = 923;
1498 if (ic == 925) ichar = 924;
1499 if (ic == 926) ichar = 925;
1500 if (ic == 929) ichar = 920;
1501 if (ic == 930) ichar = 929;
1502 if (ic == 936) ichar = 926;
1503 if (ic == 915) ichar = 935;
1504 if (ic == 937) ichar = 936;
1505 if (ic == 935) ichar = 937;
1506 if (ic == 938) ichar = 918;
1507 if (ic == 951) ichar = 947;
1508 if (ic == 798) ichar = 949;
1509 if (ic == 970) ichar = 950;
1510 if (ic == 952) ichar = 951;
1511 if (ic == 961) ichar = 952;
1512 if (ic == 955) ichar = 954;
1513 if (ic == 956) ichar = 955;
1514 if (ic == 957) ichar = 956;
1515 if (ic == 958) ichar = 957;
1516 if (ic == 968) ichar = 958;
1517 if (ic == 934) ichar = 962;
1518 if (ic == 962) ichar = 961;
1519 if (ic == 966) ichar = 969;
1520 if (ic == 950) ichar = 966;
1521 if (ic == 947) ichar = 967;
1522 if (ic == 969) ichar = 968;
1523 if (ic == 967) ichar = 969;
1524 if (ic == 954) ichar = 966;
1525 if (ic == 922) ichar = 952;
1526 if (ic == 753) ichar = 965;
1527 PrintStr(TString::Format("&#%4.4d;",ichar));
1528 } else {
1529 Int_t len=strlen(chars);
1530 for (Int_t i=0; i<len;i++) {
1531 if (chars[i]!='\n') {
1532 if (chars[i]=='<') {
1533 PrintFast(4,"&lt;");
1534 } else if (chars[i]=='>') {
1535 PrintFast(4,"&gt;");
1536 } else if (chars[i]=='\305') {
1537 PrintFast(7,"&#8491;"); // ANGSTROM SIGN
1538 } else if (chars[i]=='\345') {
1539 PrintFast(6,"&#229;");
1540 } else if (chars[i]=='&') {
1541 PrintFast(5,"&amp;");
1542 } else {
1543 PrintFast(1,&chars[i]);
1544 }
1545 }
1546 }
1547 }
1548
1549 PrintStr("@");
1550 PrintFast(7,"</text>");
1551
1552 if (fTextAngle != 0.) {
1553 PrintStr("@");
1554 PrintFast(4,"</g>");
1555 }
1556}
1557
1558////////////////////////////////////////////////////////////////////////////////
1559/// Draw text with URL.
1560///
1561
1562void TSVG::TextUrl(Double_t x, Double_t y, const char *chars, const char *url)
1563{
1564 PrintStr("@");
1565 PrintFast(9,"<a href=\"");
1566 PrintStr(url);
1567 PrintFast(2,"\">");
1568 PrintStr("@");
1569 Text(x, y, chars);
1570 PrintStr("@");
1571 PrintFast(4,"</a>");
1572 PrintStr("@");
1573}
1574
1575////////////////////////////////////////////////////////////////////////////////
1576/// Write a string of characters in NDC
1577
1578void TSVG::TextNDC(Double_t u, Double_t v, const char *chars)
1579{
1580 Double_t x = gPad->GetX1() + u*(gPad->GetX2() - gPad->GetX1());
1581 Double_t y = gPad->GetY1() + v*(gPad->GetY2() - gPad->GetY1());
1582 Text(x, y, chars);
1583}
1584
1585////////////////////////////////////////////////////////////////////////////////
1586/// Convert U from NDC coordinate to SVG
1587
1589{
1590 Double_t cm = fXsize*(gPad->GetAbsXlowNDC() + u*gPad->GetAbsWNDC());
1591 return 0.5 + 72*cm/2.54;
1592}
1593
1594////////////////////////////////////////////////////////////////////////////////
1595/// Convert V from NDC coordinate to SVG
1596
1598{
1599 Double_t cm = fYsize*(gPad->GetAbsYlowNDC() + v*gPad->GetAbsHNDC());
1600 return 0.5 + 72*cm/2.54;
1601}
1602
1603////////////////////////////////////////////////////////////////////////////////
1604/// Convert X from world coordinate to SVG
1605
1607{
1608 Double_t u = (x - gPad->GetX1())/(gPad->GetX2() - gPad->GetX1());
1609 return UtoSVG(u);
1610}
1611
1612////////////////////////////////////////////////////////////////////////////////
1613/// Convert Y from world coordinate to SVG
1614
1616{
1617 Double_t v = (y - gPad->GetY1())/(gPad->GetY2() - gPad->GetY1());
1618 return fYsizeSVG-VtoSVG(v);
1619}
1620
1621////////////////////////////////////////////////////////////////////////////////
1622/// Not needed in SVG case
1623
1625{
1626 Warning("TSVG::DrawPS", "not yet implemented");
1627}
ROOT::R::TRInterface & r
Definition Object.C:4
#define b(i)
Definition RSha256.hxx:100
#define g(i)
Definition RSha256.hxx:105
#define a(i)
Definition RSha256.hxx:99
#define e(i)
Definition RSha256.hxx:103
size_t size(const MatrixT &matrix)
retrieve the size of a square matrix
int Int_t
Signed integer 4 bytes (int).
Definition RtypesCore.h:59
short Width_t
Line width (short).
Definition RtypesCore.h:98
bool Bool_t
Boolean (0=false, 1=true) (bool).
Definition RtypesCore.h:77
constexpr Bool_t kFALSE
Definition RtypesCore.h:108
double Double_t
Double 8 bytes.
Definition RtypesCore.h:73
short Color_t
Color number (short).
Definition RtypesCore.h:99
short Style_t
Style number (short).
Definition RtypesCore.h:96
float Float_t
Float 4 bytes (float).
Definition RtypesCore.h:71
constexpr Bool_t kTRUE
Definition RtypesCore.h:107
const char Option_t
Option string (const char).
Definition RtypesCore.h:80
#define gROOT
Definition TROOT.h:417
const Double_t kEpsilon
Definition TSVG.cxx:38
externTStyle * gStyle
Definition TStyle.h:442
externTVirtualPS * gVirtualPS
Definition TVirtualPS.h:88
#define gPad
#define snprintf
Definition civetweb.c:1579
Style_t fFillStyle
Fill area style.
Definition TAttFill.h:25
Color_t fFillColor
Fill area color.
Definition TAttFill.h:24
Width_t fLineWidth
Line width.
Definition TAttLine.h:26
Style_t fLineStyle
Line style.
Definition TAttLine.h:25
Color_t fLineColor
Line color.
Definition TAttLine.h:24
Color_t fMarkerColor
Marker color.
Definition TAttMarker.h:24
static Style_t GetMarkerStyleBase(Style_t style)
Size_t fMarkerSize
Marker size.
Definition TAttMarker.h:26
Style_t fMarkerStyle
Marker style.
Definition TAttMarker.h:25
static Width_t GetMarkerLineWidth(Style_t style)
Color_t fTextColor
Text color.
Definition TAttText.h:27
Float_t fTextAngle
Text angle.
Definition TAttText.h:24
Font_t fTextFont
Text font.
Definition TAttText.h:28
Short_t fTextAlign
Text alignment.
Definition TAttText.h:26
Float_t fTextSize
Text size.
Definition TAttText.h:25
static TString Encode(const char *data)
Transform data into a null terminated base64 string.
Definition TBase64.cxx:106
Float_t GetRed() const
Definition TColor.h:61
Float_t GetAlpha() const
Definition TColor.h:67
Float_t GetBlue() const
Definition TColor.h:63
Float_t GetGreen() const
Definition TColor.h:62
This class stores the date and time with a precision of one second in an unsigned 32 bit word (950130...
Definition TDatime.h:37
const char * AsString() const
Return the date & time as a string (ctime() format).
Definition TDatime.cxx:101
virtual void SetTitle(const char *title="")
Set the title of the TNamed.
Definition TNamed.cxx:173
const char * GetName() const override
Returns name of object.
Definition TNamed.h:49
An array of TObjects.
Definition TObjArray.h:31
Int_t GetEntries() const override
Return the number of objects in array (i.e.
TObject * At(Int_t idx) const override
Definition TObjArray.h:170
Collectable string class.
Definition TObjString.h:28
virtual void Warning(const char *method, const char *msgfmt,...) const
Issue warning message.
Definition TObject.cxx:1084
virtual void Error(const char *method, const char *msgfmt,...) const
Issue error message.
Definition TObject.cxx:1098
2-D graphics point (world coordinates).
Definition TPoints.h:19
static Int_t fgLineJoin
Appearance of joining lines.
Definition TSVG.h:31
void PrintPolyMarker(Int_t n, T *x, T *y)
Implementation of polymarker printing.
Definition TSVG.cxx:437
Double_t UtoSVG(Double_t u)
Convert U from NDC coordinate to SVG.
Definition TSVG.cxx:1588
void MovePS(Double_t x, Double_t y)
Move to a new position (ix, iy).
Definition TSVG.cxx:1106
void DrawFrame(Double_t xl, Double_t yl, Double_t xt, Double_t yt, Int_t mode, Int_t border, Int_t dark, Int_t light) override
Draw a Frame around a box.
Definition TSVG.cxx:363
void DrawPolyLineNDC(Int_t, TPoints *)
Draw a PolyLine in NDC space.
Definition TSVG.cxx:428
Double_t fYsizeSVG
Page's Y size in SVG units.
Definition TSVG.h:29
void CellArrayPng(char *buffer, int size) override
Paint the Cell Array as png image Disabled in compact mode to avoid creation of large SVG files.
Definition TSVG.cxx:1023
void DrawPolyMarker(Int_t n, Float_t *x, Float_t *y) override
Paint PolyMarker.
Definition TSVG.cxx:840
void TextUrl(Double_t x, Double_t y, const char *string, const char *url) override
Draw text with URL.
Definition TSVG.cxx:1562
void Close(Option_t *opt="") override
Close a SVG file.
Definition TSVG.cxx:165
void DrawBox(Double_t x1, Double_t y1, Double_t x2, Double_t y2) override
Draw a Box.
Definition TSVG.cxx:206
Bool_t fRange
True when a range has been defined.
Definition TSVG.h:28
void Text(Double_t x, Double_t y, const char *string) override
Draw text.
Definition TSVG.cxx:1330
Double_t YtoSVG(Double_t y)
Convert Y from world coordinate to SVG.
Definition TSVG.cxx:1615
void PrintLineJointAttributes()
Print line join attributes - if present.
Definition TSVG.cxx:885
void SetFillColor(Color_t cindex=1) override
Set color index for fill areas.
Definition TSVG.cxx:1169
void SetLineWidth(Width_t linewidth=1) override
Set the lines width.
Definition TSVG.cxx:1246
void Initialize()
Initialize the SVG file.
Definition TSVG.cxx:1045
void DrawPS(Int_t n, Float_t *xw, Float_t *yw) override
Not needed in SVG case.
Definition TSVG.cxx:1624
void CellArrayEnd() override
End the Cell Array painting.
Definition TSVG.cxx:1034
void CellArrayFill(Int_t r, Int_t g, Int_t b) override
Paint the Cell Array as single pixel.
Definition TSVG.cxx:1014
void NewPage() override
Start the SVG page.
Definition TSVG.cxx:1127
void PrintLineStyleOnEndOfPath()
Print line style attributes on the end of "path" string.
Definition TSVG.cxx:858
void SetColor(Int_t color=1)
Set RGB (without alpha channel) color with its color index.
Definition TSVG.cxx:1282
Int_t fType
Workstation type used to know if the SVG is open.
Definition TSVG.h:25
void SetLineCap(Int_t linecap=0)
Set the value of the global parameter TSVG::fgLineCap.
Definition TSVG.cxx:1223
void DrawPolyLine(Int_t, TPoints *)
Draw a PolyLine.
Definition TSVG.cxx:413
void Off()
Deactivate an already open SVG file.
Definition TSVG.cxx:198
void Range(Float_t xrange, Float_t yrange)
Set the range for the paper in centimetres.
Definition TSVG.cxx:1159
void SetLineScale(Float_t=3)
Definition TSVG.h:78
void CellArrayBegin(Int_t W, Int_t H, Double_t x1, Double_t x2, Double_t y1, Double_t y2) override
Begin the Cell Array painting.
Definition TSVG.cxx:994
void SetLineStyle(Style_t linestyle=1) override
Change the line style.
Definition TSVG.cxx:1238
void On()
Activate an already open SVG file.
Definition TSVG.cxx:182
TSVG()
Default SVG constructor.
Definition TSVG.cxx:83
void SetTextColor(Color_t cindex=1) override
Set color index for text.
Definition TSVG.cxx:1318
Double_t CMtoSVG(Double_t u)
Definition TSVG.h:50
Double_t XtoSVG(Double_t x)
Convert X from world coordinate to SVG.
Definition TSVG.cxx:1606
Bool_t fCompact
True when the SVG header is printed.
Definition TSVG.h:26
Bool_t fBoundingBox
True when the SVG header is printed.
Definition TSVG.h:27
Float_t fXsize
Page size along X.
Definition TSVG.h:23
void SetMarkerColor(Color_t cindex=1) override
Set color index for markers.
Definition TSVG.cxx:1254
Float_t fYsize
Page size along Y.
Definition TSVG.h:24
void DrawSegments(Int_t n, Double_t *xw, Double_t *yw) override
This method draw N segments.
Definition TSVG.cxx:949
void TextNDC(Double_t u, Double_t v, const char *string)
Write a string of characters in NDC.
Definition TSVG.cxx:1578
~TSVG() override
Default SVG destructor.
Definition TSVG.cxx:157
void SetLineColor(Color_t cindex=1) override
Set color index for lines.
Definition TSVG.cxx:1177
void SetColorAlpha(Int_t color=1, Bool_t fill=kTRUE, Bool_t stroke=kTRUE)
Set RGBa color with its color index.
Definition TSVG.cxx:1262
void SetLineJoin(Int_t linejoin=0)
Set the value of the global parameter TSVG::fgLineJoin.
Definition TSVG.cxx:1199
void PrintPath(Bool_t convert, Int_t n, Double_t *xs, Double_t *ys, Bool_t close_path=kTRUE)
Print a svg path statement for specified points.
Definition TSVG.cxx:280
void Open(const char *filename, Int_t type=-111) override
Open a SVG file.
Definition TSVG.cxx:108
void WriteReal(Float_t r, Bool_t space=kTRUE) override
Write float value into output stream In compact form try to store only first 2-3 significant digits.
Definition TSVG.cxx:1081
static Int_t fgLineCap
Appearance of line caps.
Definition TSVG.h:32
Double_t VtoSVG(Double_t v)
Convert V from NDC coordinate to SVG.
Definition TSVG.cxx:1597
Basic string class.
Definition TString.h:138
Ssiz_t Length() const
Definition TString.h:425
const char * Data() const
Definition TString.h:384
TObjArray * Tokenize(const TString &delim) const
This function is used to isolate sequential tokens in a TString.
Definition TString.cxx:2270
static TString Format(const char *fmt,...)
Static method which formats a string using a printf style format descriptor and return a TString.
Definition TString.cxx:2385
Int_t fLenBuffer
Definition TVirtualPS.h:38
virtual void WriteInteger(Int_t i, Bool_t space=kTRUE)
Write one Integer to the file.
void CloseStream()
Close existing stream.
virtual void PrintStr(const char *string="")
Output the string str in the output buffer.
virtual void PrintFast(Int_t nch, const char *string="")
Fast version of Print.
std::ofstream * fStream
Definition TVirtualPS.h:41
Bool_t OpenStream(const char *fname, Bool_t binary=kFALSE)
Open output stream.
void ClearBuffer()
Clear content of internal buffer.
TVirtualPS(const TVirtualPS &)=delete
virtual void WriteReal(Float_t r, Bool_t space=kTRUE)
Write a Real number to the file.
Double_t y[n]
Definition legend1.C:17
Double_t x[n]
Definition legend1.C:17
const Int_t n
Definition legend1.C:16
Short_t Max(Short_t a, Short_t b)
Returns the largest of a and b.
Definition TMathBase.h:249
Double_t Floor(Double_t x)
Rounds x downward, returning the largest integral value that is not greater than x.
Definition TMath.h:691
Short_t Min(Short_t a, Short_t b)
Returns the smallest of a and b.
Definition TMathBase.h:197
Short_t Abs(Short_t d)
Returns the absolute value of parameter Short_t d.
Definition TMathBase.h:122
TMarker m
Definition textangle.C:8