KaliVeda
Toolkit for HIC analysis
Loading...
Searching...
No Matches
KVGaxis.cpp
1//Created by KVClassFactory on Wed Jun 19 16:07:04 2013
2//Author: dgruyer
3
4#include "KVGaxis.h"
5#include "TMath.h"
6
7#include "Riostream.h"
8#include "TROOT.h"
9#include "TGaxis.h"
10#include "TVirtualPad.h"
11//#include "TPad.h"
12#include "TVirtualX.h"
13#include "TLine.h"
14#include "TLatex.h"
15#include "TStyle.h"
16#include "TF1.h"
17#include "TAxis.h"
18#include "THashList.h"
19#include "TObjString.h"
20#include "TMath.h"
21#include "THLimitsFinder.h"
22#include "TColor.h"
23#include "TClass.h"
24#include "TTimeStamp.h"
25#include "TSystem.h"
26
27Int_t fgMaxDigits = 5;
28const Int_t kHori = BIT(9);
29
31
32
33
34
36{
37 fNbins = 0;
38 fBins = 0;
39 fLabels = 0;
40 fFormat = "%lf";
41 // Default constructor
42}
43
44
45
46//KVGaxis::KVGaxis(const KVGaxis& obj) : TGaxis()
47//{
48// // Copy constructor
49// // This ctor is used to make a copy of an existing object (for example
50// // when a method returns an object), and it is always a good idea to
51// // implement it.
52// // If your class allocates memory in its constructor(s) then it is ESSENTIAL :-)
53
54// obj.Copy(*this);
55//}
56
57
58
60
61KVGaxis::KVGaxis(Double_t xmin, Double_t ymin, Double_t xmax, Double_t ymax, Double_t wmin, Double_t wmax, Int_t ndiv, Option_t* chopt, Double_t gridlength) :
62 TGaxis(xmin, ymin, xmax, ymax, wmin, wmax, ndiv, chopt, gridlength)
63{
64 fNbins = 0;
65 fBins = 0;
66 fLabels = 0;
67 fFormat = "%lf";
68 // Write your code here
69}
70
71
72
73
75
76KVGaxis::KVGaxis(Double_t xmin, Double_t ymin, Double_t xmax, Double_t ymax, const char* funcname, Int_t ndiv, Option_t* chopt, Double_t gridlength) :
77 TGaxis(xmin, ymin, xmax, ymax, funcname, ndiv, chopt, gridlength)
78{
79 fNbins = 0;
80 fBins = 0;
81 fLabels = 0;
82 fFormat = "%lf";
83 // Write your code here
84}
85
86
87
89
90KVGaxis::KVGaxis(Double_t xmin, Double_t ymin, Double_t xmax, Double_t ymax, Int_t nbins, Double_t* bins, Double_t wmin, Double_t wmax, Int_t ndiv, Option_t* chopt, Double_t gridlength, char** labels):
91 TGaxis(xmin, ymin, xmax, ymax, (wmin == wmax ? (xmin == xmax ? ymin : xmin) : wmin), (wmin == wmax ? (xmin == xmax ? ymax : xmax) : wmax), ndiv, chopt, gridlength)
92{
93 fNbins = nbins;
94 fBins = bins;
95 fNdiv = fNbins;
96 fFormat = "%lf";
97 fLabels = labels;
98}
99
100
101
102
105
107{
108 // Destructor
109}
110
111
112
113//void KVGaxis::Copy(TObject& obj) const
114//{
115// // This method copies the current state of 'this' object into 'obj'
116// // You should add here any member variables, for example:
117// // (supposing a member variable KVGaxis::fToto)
118// // CastedObj.fToto = fToto;
119// // or
120// // CastedObj.SetToto( GetToto() );
121
122// TGaxis::Copy(obj);
123// //KVGaxis& CastedObj = (KVGaxis&)obj;
124//}
125
126
127
129
131 Double_t& wmin, Double_t& wmax, Int_t& ndiv, Option_t* chopt,
132 Double_t gridlength, Bool_t drawGridOnly)
133{
134 const char* where = "PaintAxis";
135
136 TString opt(chopt);
137 if (!fNbins) return TGaxis::PaintAxis(xmin, ymin, xmax, ymax, wmin, wmax, ndiv, chopt, gridlength, drawGridOnly);
138
139 Double_t alfa, beta, ratio1, ratio2, grid_side;
140 Double_t axis_lengthN = 0;
141 Double_t axis_length0 = 0;
142 Double_t axis_length1 = 0;
143 Double_t axis_length;
144 Double_t atick[3];
145 Double_t tick_side;
146 Double_t charheight;
147 Double_t phil, phi, sinphi, cosphi, asinphi, acosphi;
148 Double_t binLow = 0., binLow2 = 0., binLow3 = 0.;
149 Double_t binHigh = 0., binHigh2 = 0., binHigh3 = 0.;
150 Double_t binWidth = 0., binWidth2 = 0., binWidth3 = 0.;
151 Double_t xpl1, xpl2, ypl1, ypl2;
152 Double_t xtick = 0;
153 Double_t xtick0, xtick1, dxtick = 0;
154 Double_t ytick, ytick0, ytick1;
155 Double_t wlabel, dwlabel;
156 Double_t xfactor, yfactor;
157 Double_t xlabel, ylabel, dxlabel;
158 Double_t xone, xtwo;
159 Double_t rlab;
160 Double_t x0, x1, y0, y1, xx0, xx1, yy0, yy1;
161 xx0 = xx1 = yy0 = yy1 = 0;
162 Double_t xxmin, xxmax, yymin, yymax;
163 xxmin = xxmax = yymin = yymax = 0;
164 Double_t xlside, xmside;
165 Double_t ww, af, rne;
166 Double_t xx, yy;
167 Double_t xmnlog, x00, x11, h2, h2sav, axmul, y;
168 Float_t chupxvsav, chupyvsav;
169 Double_t rtxw, rtyw;
170 Int_t nlabels, nticks, nticks0, nticks1;
171 Int_t i, j, k, l, decade, ltick;
172 Int_t mside, lside;
173 Int_t nexe = 0;
174 Int_t lnlen = 0;
175 Int_t iexe, if1, if2, na, nf, ih1, ih2, nbinin, nch, kmod;
176 Int_t optionLog, optionBlank, optionVert, optionPlus, optionMinus, optionUnlab, optionPara;
177 Int_t optionDown, optionRight, optionLeft, optionCent, optionEqual, optionDecimals = 0, optionDot;
178 Int_t optionY, optionText, optionGrid, optionSize, optionNoopt, optionInt, optionM, optionUp, optionX;
179 Int_t optionTime;
180 Int_t first, last, labelnumber;
181 Int_t xalign, yalign;
182 Int_t nn1, nn2, nn3, n1a, n2a, n3a, nb2, nb3;
183 Int_t nbins = 10, n1aold, nn1old;
184 n1aold = nn1old = 0;
185 Int_t ndyn;
186 Int_t nhilab = 0;
187 Int_t idn;
188 Bool_t flexe = 0;
189 Bool_t flexpo, flexne;
190 char* label;
191 char* chtemp;
192 char* coded;
193 char chlabel[256];
194 char kchtemp[256];
195 char chcoded[8];
196 TLine* linegrid;
197 TString timeformat;
198 time_t timelabel;
199 Double_t timed, wTimeIni;
200 struct tm* utctis;
201 Double_t rangeOffset = 0;
202
203 Double_t epsilon = 1e-5;
204 const Double_t kPI = TMath::Pi();
205 //*-*-______________________________________
206
207 Double_t rwmi = wmin;
208 Double_t rwma = wmax;
209 chtemp = &kchtemp[0];
210 label = &chlabel[0];
211 linegrid = 0;
212
213 fFunction = (TF1*)gROOT->GetFunction(fFunctionName.Data());
214
215 Bool_t noExponent = TestBit(TAxis::kNoExponent);
216
217 //*-*- If moreLogLabels = kTRUE more Log Intermediate Labels are drawn.
218 Bool_t moreLogLabels = TestBit(TAxis::kMoreLogLabels);
219
220 //*-*- the following parameters correspond to the pad range in NDC
221 //*-*- and the WC coordinates in the pad
222
223 Double_t padh = gPad->GetWh() * gPad->GetAbsHNDC();
224 Double_t rwxmin = gPad->GetX1();
225 Double_t rwxmax = gPad->GetX2();
226 Double_t rwymin = gPad->GetY1();
227 Double_t rwymax = gPad->GetY2();
228
229 if (strchr(chopt, 'G')) optionLog = 1;
230 else optionLog = 0;
231 if (strchr(chopt, 'B')) optionBlank = 1;
232 else optionBlank = 0;
233 if (strchr(chopt, 'V')) optionVert = 1;
234 else optionVert = 0;
235 if (strchr(chopt, '+')) optionPlus = 1;
236 else optionPlus = 0;
237 if (strchr(chopt, '-')) optionMinus = 1;
238 else optionMinus = 0;
239 if (strchr(chopt, 'U')) optionUnlab = 1;
240 else optionUnlab = 0;
241 if (strchr(chopt, 'P')) optionPara = 1;
242 else optionPara = 0;
243 if (strchr(chopt, 'O')) optionDown = 1;
244 else optionDown = 0;
245 if (strchr(chopt, 'R')) optionRight = 1;
246 else optionRight = 0;
247 if (strchr(chopt, 'L')) optionLeft = 1;
248 else optionLeft = 0;
249 if (strchr(chopt, 'C')) optionCent = 1;
250 else optionCent = 0;
251 if (strchr(chopt, '=')) optionEqual = 1;
252 else optionEqual = 0;
253 if (strchr(chopt, 'Y')) optionY = 1;
254 else optionY = 0;
255 if (strchr(chopt, 'T')) optionText = 1;
256 else optionText = 0;
257 if (strchr(chopt, 'W')) optionGrid = 1;
258 else optionGrid = 0;
259 if (strchr(chopt, 'S')) optionSize = 1;
260 else optionSize = 0;
261 if (strchr(chopt, 'N')) optionNoopt = 1;
262 else optionNoopt = 0;
263 if (strchr(chopt, 'I')) optionInt = 1;
264 else optionInt = 0;
265 if (strchr(chopt, 'M')) optionM = 1;
266 else optionM = 0;
267 if (strchr(chopt, '0')) optionUp = 1;
268 else optionUp = 0;
269 if (strchr(chopt, 'X')) optionX = 1;
270 else optionX = 0;
271 if (strchr(chopt, 't')) optionTime = 1;
272 else optionTime = 0;
273 if (strchr(chopt, '.')) optionDot = 1;
274 else optionDot = 0;
275 if (TestBit(TAxis::kTickPlus)) optionPlus = 2;
276 if (TestBit(TAxis::kTickMinus)) optionMinus = 2;
277 if (TestBit(TAxis::kCenterLabels)) optionM = 1;
278 if (TestBit(TAxis::kDecimals)) optionDecimals = 1;
279 if (!gStyle->GetStripDecimals()) optionDecimals = 1;
280 if (fAxis) {
281 if (fAxis->GetLabels()) {
282 optionM = 1;
283 optionText = 1;
284 ndiv = fAxis->GetLast() - fAxis->GetFirst() + 1;
285 }
286 }
287 if (ndiv < 0) {
288 Error(where, "Invalid number of divisions: %d", ndiv);
289 return;
290 }
291
292 if (fNbins) {
293 optionNoopt = kTRUE;
294 optionSize = 1;
295 }
296
297 //*-*- Set the grid length
298
299 if (optionGrid) {
300 if (gridlength == 0) gridlength = 0.8;
301 linegrid = new TLine();
302 linegrid->SetLineColor(gStyle->GetGridColor());
303 if (linegrid->GetLineColor() == 0) linegrid->SetLineColor(GetLineColor());
304 linegrid->SetLineStyle(gStyle->GetGridStyle());
305 linegrid->SetLineWidth(gStyle->GetGridWidth());
306 }
307
308 //*-*- No labels if the axis label offset is big.
309 //*-*- In that case the labels are not visible anyway.
310
311 if (GetLabelOffset() > 1.1) optionUnlab = 1;
312
313 //*-*- Determine time format
314
315 Int_t idF = fTimeFormat.Index("%F");
316 if (idF >= 0) {
317 timeformat = fTimeFormat(0, idF);
318 }
319 else {
320 timeformat = fTimeFormat;
321 }
322
323 //GMT option
324 if (fTimeFormat.Index("GMT") >= 0) optionTime = 2;
325
326 // Determine the time offset and correct for time offset not being integer.
327 Double_t timeoffset = 0;
328 if (optionTime) {
329 if (idF >= 0) {
330 Int_t lnF = fTimeFormat.Length();
331 TString stringtimeoffset = fTimeFormat(idF + 2, lnF);
332 Int_t year, mm, dd, hh, mi, ss;
333 if (sscanf(stringtimeoffset.Data(), "%d-%d-%d %d:%d:%d", &year, &mm, &dd, &hh, &mi, &ss) == 6) {
334 struct tm tp;
335 tp.tm_year = year - 1900;
336 tp.tm_mon = mm - 1;
337 tp.tm_mday = dd;
338 tp.tm_hour = hh;
339 tp.tm_min = mi;
340 tp.tm_sec = ss;
341 tp.tm_isdst = -1; //automatic determination of daylight saving time
342 TString tz = (TString)gSystem->Getenv("TZ"); //save timezone
343 Bool_t isUTC = kFALSE;
344 if (gSystem->Getenv("TZ") && tz.Length() == 0) isUTC = kTRUE;
345 gSystem->Setenv("TZ", "UTC"); //sets timezone to UTC
346 tzset();
347 timeoffset = mktime(&tp);
348 //restore TZ
349 if (tz.Length()) {
350 gSystem->Setenv("TZ", tz.Data());
351 }
352 else {
353 if (isUTC) gSystem->Setenv("TZ", "");
354 else gSystem->Unsetenv("TZ");
355 }
356 tzset();
357 // Add the time offset's decimal part if it is there
358 Int_t ids = stringtimeoffset.Index("s");
359 if (ids >= 0) {
360 Float_t dp;
361 Int_t lns = stringtimeoffset.Length();
362 TString sdp = stringtimeoffset(ids + 1, lns);
363 sscanf(sdp.Data(), "%g", &dp);
364 timeoffset += dp;
365 }
366 }
367 else {
368 Error(where, "Time offset has not the right format");
369 }
370 }
371 else {
372 timeoffset = gStyle->GetTimeOffset();
373 }
374 wmin += timeoffset - (int)(timeoffset);
375 wmax += timeoffset - (int)(timeoffset);
376
377 // correct for time offset at a good limit (min, hour, day, month, year)
378 struct tm* tp0;
379 time_t timetp = (time_t)((Long_t)(timeoffset));
381 Long_t rangeBase = 60;
382 if (range > 60) rangeBase = 60 * 20; // minutes
383 if (range > 3600) rangeBase = 3600 * 20; // hours
384 if (range > 86400) rangeBase = 86400 * 20; // days
385 if (range > 2419200) rangeBase = 31556736; // months (average # days)
386 rangeOffset = (Double_t)((Long_t)(timeoffset) % rangeBase);
387 if (range > 31536000) {
388 tp0 = gmtime(&timetp);
389 tp0->tm_mon = 0;
390 tp0->tm_mday = 1;
391 tp0->tm_hour = 0;
392 tp0->tm_min = 0;
393 tp0->tm_sec = 0;
394 tp0->tm_isdst = 1; // daylight saving time is on.
395 rangeBase = (timetp - mktime(tp0)); // years
396 rangeOffset = (Double_t)(rangeBase);
397 }
398 wmax += rangeOffset;
399 wmin += rangeOffset;
400 }
401
402 //*-*- Determine number of divisions 1, 2 and 3
403 n1a = ndiv % 100;
404 n2a = (ndiv % 10000 - n1a) / 100;
405 n3a = ndiv / 10000;
406 nn3 = TMath::Max(n3a, 1);
407 nn2 = TMath::Max(n2a, 1) * nn3;
408 nn1 = TMath::Max(n1a, 1) * nn2 + 1;
409 nticks = nn1;
410
411 nn3 = 1;
412 nn2 = 1;
413 nn1 = fNbins;
414 nticks = nn1;
415
416
417 //*-*- Axis bining optimization is ignored if:
418 //*-*- - the first and the last label are equal
419 //*-*- - the number of divisions is 0
420 //*-*- - less than 1 primary division is requested
421 //*-*- - logarithmic scale is requested
422
423 if (wmin == wmax || ndiv == 0 || n1a <= 1 || optionLog) {
424 optionNoopt = 1;
425 optionInt = 0;
426 }
427
428 //*-*- Axis bining optimization
429 if ((wmax - wmin) < 1 && optionInt) {
430 Error(where, "option I not available");
431 optionInt = 0;
432 }
433 if (!optionNoopt || optionInt) {
434
435 //*-*- Primary divisions optimization
436 //*-*- When integer labelling is required, Optimize is invoked first
437 //*-*- and only if the result is not an integer labelling, AdjustBinSize is invoked.
438
439 THLimitsFinder::Optimize(wmin, wmax, n1a, binLow, binHigh, nbins, binWidth, fChopt.Data());
440 if (optionInt) {
441 if (binLow != Double_t(int(binLow)) || binWidth != Double_t(int(binWidth))) {
442 AdjustBinSize(wmin, wmax, n1a, binLow, binHigh, nbins, binWidth);
443 }
444 }
445 if ((wmin - binLow) > epsilon) {
446 binLow += binWidth;
447 nbins--;
448 }
449 if ((binHigh - wmax) > epsilon) {
450 binHigh -= binWidth;
451 nbins--;
452 }
453 if (xmax == xmin) {
454 rtyw = (ymax - ymin) / (wmax - wmin);
455 xxmin = xmin;
456 xxmax = xmax;
457 yymin = rtyw * (binLow - wmin) + ymin;
458 yymax = rtyw * (binHigh - wmin) + ymin;
459 }
460 else {
461 rtxw = (xmax - xmin) / (wmax - wmin);
462 xxmin = rtxw * (binLow - wmin) + xmin;
463 xxmax = rtxw * (binHigh - wmin) + xmin;
464 if (ymax == ymin) {
465 yymin = ymin;
466 yymax = ymax;
467 }
468 else {
469 alfa = (ymax - ymin) / (xmax - xmin);
470 beta = (ymin * xmax - ymax * xmin) / (xmax - xmin);
471 yymin = alfa * xxmin + beta;
472 yymax = alfa * xxmax + beta;
473 }
474 }
475 if (fFunction) {
476 yymin = ymin;
477 yymax = ymax;
478 xxmin = xmin;
479 xxmax = xmax;
480 }
481 else {
482 wmin = binLow;
483 wmax = binHigh;
484 }
485
486 //*-*- Secondary divisions optimization
487 nb2 = n2a;
488 if (!optionNoopt && n2a > 1 && binWidth > 0) {
489 THLimitsFinder::Optimize(wmin, wmin + binWidth, n2a, binLow2, binHigh2, nb2, binWidth2, fChopt.Data());
490 }
491
492 //*-*- Tertiary divisions optimization
493 nb3 = n3a;
494 if (!optionNoopt && n3a > 1 && binWidth2 > 0) {
495 THLimitsFinder::Optimize(binLow2, binLow2 + binWidth2, n3a, binLow3, binHigh3, nb3, binWidth3, fChopt.Data());
496 }
497 n1aold = n1a;
498 nn1old = nn1;
499 n1a = nbins;
500 nn3 = TMath::Max(nb3, 1);
501 nn2 = TMath::Max(nb2, 1) * nn3;
502 nn1 = TMath::Max(n1a, 1) * nn2 + 1;
503 nticks = nn1;
504 }
505
506 //*-*- Coordinates are normalized
507
508 ratio1 = 1 / (rwxmax - rwxmin);
509 ratio2 = 1 / (rwymax - rwymin);
510 x0 = ratio1 * (xmin - rwxmin);
511 x1 = ratio1 * (xmax - rwxmin);
512 y0 = ratio2 * (ymin - rwymin);
513 y1 = ratio2 * (ymax - rwymin);
514 if (!optionNoopt || optionInt) {
515 xx0 = ratio1 * (xxmin - rwxmin);
516 xx1 = ratio1 * (xxmax - rwxmin);
517 yy0 = ratio2 * (yymin - rwymin);
518 yy1 = ratio2 * (yymax - rwymin);
519 }
520
521 if ((x0 == x1) && (y0 == y1)) {
522 Error(where, "length of axis is 0");
523 return;
524 }
525
526 //*-*- Return wmin, wmax and the number of primary divisions
527 if (optionX) {
528 ndiv = n1a;
529 return;
530 }
531
532 Int_t maxDigits = 5;
533 if (fAxis) maxDigits = fgMaxDigits;
534
535 TLatex* textaxis = new TLatex();
536 SetLineStyle(1); // axis line style
537 textaxis->SetTextColor(GetTextColor());
538 textaxis->SetTextFont(GetTextFont());
539
540 if (!gPad->IsBatch()) {
541 gVirtualX->GetCharacterUp(chupxvsav, chupyvsav);
542 gVirtualX->SetClipOFF(gPad->GetCanvasID());
543 }
544
545 //*-*- Compute length of axis
546 axis_length = TMath::Sqrt((x1 - x0) * (x1 - x0) + (y1 - y0) * (y1 - y0));
547 if (axis_length == 0) {
548 Error(where, "length of axis is 0");
549 goto L210;
550 }
551 if (!optionNoopt || optionInt) {
552 axis_lengthN = TMath::Sqrt((xx1 - xx0) * (xx1 - xx0) + (yy1 - yy0) * (yy1 - yy0));
553 axis_length0 = TMath::Sqrt((xx0 - x0) * (xx0 - x0) + (yy0 - y0) * (yy0 - y0));
554 axis_length1 = TMath::Sqrt((x1 - xx1) * (x1 - xx1) + (y1 - yy1) * (y1 - yy1));
555 if (axis_lengthN < epsilon) {
556 optionNoopt = 1;
557 optionInt = 0;
558 wmin = rwmi;
559 wmax = rwma;
560 n1a = n1aold;
561 nn1 = nn1old;
562 nticks = nn1;
563 if (optionTime) {
564 wmin += timeoffset - (int)(timeoffset) + rangeOffset;
565 wmax += timeoffset - (int)(timeoffset) + rangeOffset;
566 }
567 }
568 }
569
570 if (x0 == x1) {
571 phi = 0.5 * kPI;
572 phil = phi;
573 }
574 else {
575 phi = TMath::ATan2((y1 - y0), (x1 - x0));
576 Int_t px0 = gPad->UtoPixel(x0);
577 Int_t py0 = gPad->VtoPixel(y0);
578 Int_t px1 = gPad->UtoPixel(x1);
579 Int_t py1 = gPad->VtoPixel(y1);
580 if (x0 < x1) phil = TMath::ATan2(Double_t(py0 - py1), Double_t(px1 - px0));
581 else phil = TMath::ATan2(Double_t(py1 - py0), Double_t(px0 - px1));
582 }
583 cosphi = TMath::Cos(phi);
584 sinphi = TMath::Sin(phi);
585 acosphi = TMath::Abs(cosphi);
586 asinphi = TMath::Abs(sinphi);
587 if (acosphi <= epsilon) {
588 acosphi = 0;
589 cosphi = 0;
590 }
591 if (asinphi <= epsilon) {
592 asinphi = 0;
593 sinphi = 0;
594 }
595
596 //*-*- mside positive, tick marks on positive side
597 //*-*- mside negative, tick marks on negative side
598 //*-*- mside zero, tick marks on both sides
599 //*-*- Default is positive except for vertical axis
600
601 mside = 1;
602 if (x0 == x1 && y1 > y0) mside = -1;
603 if (optionPlus) mside = 1;
604 if (optionMinus) mside = -1;
605 if (optionPlus && optionMinus) mside = 0;
606 xmside = mside;
607 lside = -mside;
608 if (optionEqual) lside = mside;
609 if (optionPlus && optionMinus) {
610 lside = -1;
611 if (optionEqual) lside = 1;
612 }
613 xlside = lside;
614
615 //*-*- Tick marks size
616 if (xmside >= 0) tick_side = 1;
617 else tick_side = -1;
618 if (optionSize) atick[0] = tick_side * axis_length * fTickSize;
619 else atick[0] = tick_side * axis_length * 0.03;
620
621 atick[1] = 0.5 * atick[0];
622 atick[2] = 0.5 * atick[1];
623
624 //*-*- Set the side of the grid
625 if ((x0 == x1) && (y1 > y0)) grid_side = -1;
626 else grid_side = 1;
627
628 //*-*- Compute Values if Function is given
629 if (fFunction) {
630 rwmi = fFunction->Eval(wmin);
631 rwma = fFunction->Eval(wmax);
632 if (rwmi > rwma) {
633 Double_t t = rwma;
634 rwma = rwmi;
635 rwmi = t;
636 }
637 }
638
639 //*-*- Draw the axis if needed...
640 if (!optionBlank) {
641 xpl1 = x0;
642 xpl2 = x1;
643 ypl1 = y0;
644 ypl2 = y1;
645 PaintLineNDC(xpl1, ypl1, xpl2, ypl2);
646 }
647
648 //*-*- Draw axis title if it exists
649 if (!drawGridOnly && strlen(GetTitle())) {
650 textaxis->SetTextSize(GetTitleSize());
651 charheight = GetTitleSize();
652 if ((GetTextFont() % 10) > 2) {
653 charheight = charheight / gPad->GetWh();
654 }
655 Double_t toffset = GetTitleOffset();
657 if (x1 == x0) ylabel = xlside * 1.6 * charheight * toffset;
658 else ylabel = xlside * 1.3 * charheight * toffset;
659 if (y1 == y0) ylabel = xlside * 1.6 * charheight * toffset;
660 Double_t axispos;
661 if (TestBit(TAxis::kCenterTitle)) axispos = 0.5 * axis_length;
662 else axispos = axis_length;
664 if (x1 >= x0) {
665 if (TestBit(TAxis::kCenterTitle)) textaxis->SetTextAlign(22);
666 else textaxis->SetTextAlign(12);
667 Rotate(axispos, ylabel, cosphi, sinphi, x0, y0, xpl1, ypl1);
668 }
669 else {
670 if (TestBit(TAxis::kCenterTitle)) textaxis->SetTextAlign(22);
671 else textaxis->SetTextAlign(32);
672 Rotate(axispos, ylabel, cosphi, sinphi, x0, y0, xpl1, ypl1);
673 }
674 textaxis->PaintLatex(gPad->GetX1() + xpl1 * (gPad->GetX2() - gPad->GetX1()),
675 gPad->GetY1() + ypl1 * (gPad->GetY2() - gPad->GetY1()),
676 phil = (kPI + phil) * 180 / kPI,
677 GetTitleSize(),
678 GetTitle());
679 }
680 else {
681 if (x1 >= x0) {
682 if (TestBit(TAxis::kCenterTitle)) textaxis->SetTextAlign(22);
683 else textaxis->SetTextAlign(32);
684 Rotate(axispos, ylabel, cosphi, sinphi, x0, y0, xpl1, ypl1);
685 }
686 else {
687 if (TestBit(TAxis::kCenterTitle)) textaxis->SetTextAlign(22);
688 else textaxis->SetTextAlign(12);
689 Rotate(axispos, ylabel, cosphi, sinphi, x0, y0, xpl1, ypl1);
690 }
691 textaxis->PaintLatex(gPad->GetX1() + xpl1 * (gPad->GetX2() - gPad->GetX1()),
692 gPad->GetY1() + ypl1 * (gPad->GetY2() - gPad->GetY1()),
693 phil * 180 / kPI,
694 GetTitleSize(),
695 GetTitle());
696 }
697 }
698
699 //*-*- No bining
700
701 if (ndiv == 0)goto L210;
702 if (wmin == wmax) {
703 Error(where, "wmin (%f) == wmax (%f)", wmin, wmax);
704 goto L210;
705 }
706
707 //*-*- Labels preparation:
708 //*-*- Get character height
709 //*-*- Compute the labels orientation in case of overlaps
710 //*-*- (with alphanumeric labels for horizontal axis).
711
712 charheight = GetLabelSize();
713 if (optionText && GetLabelFont() % 10 != 3) charheight *= 0.66666;
714 textaxis->SetTextFont(GetLabelFont());
715 if ((GetLabelFont() % 10 < 2) && optionLog) // force TLatex mode in PaintLatex
716 textaxis->SetTextFont((Int_t)(GetLabelFont() / 10) * 10 + 2);
717 textaxis->SetTextColor(GetLabelColor());
718 textaxis->SetTextSize(charheight);
719 textaxis->SetTextAngle(GetTextAngle());
720 if (GetLabelFont() % 10 > 2) {
721 charheight /= padh;
722 }
723 if (!optionUp && !optionDown && !optionY && !optionUnlab) {
724 if (!drawGridOnly && optionText && ((ymin == ymax) || (xmin == xmax))) {
725 textaxis->SetTextAlign(32);
726 optionText = 2;
727 Int_t nl = fAxis->GetLast() - fAxis->GetFirst() + 1;
728 Double_t angle = 0;
729 for (i = fAxis->GetFirst(); i <= fAxis->GetLast(); i++) {
730 textaxis->SetText(0, 0, fAxis->GetBinLabel(i));
731 if (textaxis->GetXsize() < (xmax - xmin) / nl) continue;
732 angle = -20;
733 break;
734 }
735 for (i = fAxis->GetFirst(); i <= fAxis->GetLast(); i++) {
736 if ((!strcmp(fAxis->GetName(), "xaxis") && !gPad->TestBit(kHori))
737 || (!strcmp(fAxis->GetName(), "yaxis") && gPad->TestBit(kHori))) {
738 if (nl > 50) angle = 90;
743 if (angle == 0) textaxis->SetTextAlign(23);
744 if (angle == -20) textaxis->SetTextAlign(12);
745 Double_t s = -3;
746 if (ymin == gPad->GetUymax()) {
747 if (angle == 0) textaxis->SetTextAlign(21);
748 s = 3;
749 }
750 textaxis->PaintLatex(fAxis->GetBinCenter(i),
751 ymin + s * fAxis->GetLabelOffset() * (gPad->GetUymax() - gPad->GetUymin()),
752 angle,
753 textaxis->GetTextSize(),
754 fAxis->GetBinLabel(i));
755 }
756 else if ((!strcmp(fAxis->GetName(), "yaxis") && !gPad->TestBit(kHori))
757 || (!strcmp(fAxis->GetName(), "xaxis") && gPad->TestBit(kHori))) {
758 Double_t s = -3;
759 if (xmin == gPad->GetUxmax()) {
760 textaxis->SetTextAlign(12);
761 s = 3;
762 }
763 textaxis->PaintLatex(xmin + s * fAxis->GetLabelOffset() * (gPad->GetUxmax() - gPad->GetUxmin()),
765 0,
766 textaxis->GetTextSize(),
767 fAxis->GetBinLabel(i));
768 }
769 else {
770 textaxis->PaintLatex(xmin - 3 * fAxis->GetLabelOffset() * (gPad->GetUxmax() - gPad->GetUxmin()),
771 ymin + (i - 0.5) * (ymax - ymin) / nl,
772 0,
773 textaxis->GetTextSize(),
774 fAxis->GetBinLabel(i));
775 }
776 }
777 }
778 }
779
780 //*-*- Now determine orientation of labels on axis
781 if (!gPad->IsBatch()) {
782 if (cosphi > 0) gVirtualX->SetCharacterUp(-sinphi, cosphi);
783 else gVirtualX->SetCharacterUp(sinphi, -cosphi);
784 if (x0 == x1) gVirtualX->SetCharacterUp(0, 1);
785 if (optionVert) gVirtualX->SetCharacterUp(0, 1);
786 if (optionPara) gVirtualX->SetCharacterUp(-sinphi, cosphi);
787 if (optionDown) gVirtualX->SetCharacterUp(cosphi, sinphi);
788 }
789
790 //*-*- Now determine text alignment
791 xalign = 2;
792 yalign = 1;
793 if (x0 == x1) xalign = 3;
794 if (y0 != y1) yalign = 2;
795 if (optionCent) xalign = 2;
796 if (optionRight) xalign = 3;
797 if (optionLeft) xalign = 1;
798 if (TMath::Abs(cosphi) > 0.9) {
799 xalign = 2;
800 }
801 else {
802 if (cosphi * sinphi > 0) xalign = 1;
803 if (cosphi * sinphi < 0) xalign = 3;
804 }
805 textaxis->SetTextAlign(10 * xalign + yalign);
806
807 //*-*- Position of labels in Y
808 if (x0 == x1) {
809 if (optionPlus && !optionMinus) {
810 if (optionEqual) ylabel = fLabelOffset / 2 + atick[0];
811 else ylabel = -fLabelOffset;
812 }
813 else {
814 ylabel = fLabelOffset;
815 if (lside < 0) ylabel += atick[0];
816 }
817 }
818 else if (y0 == y1) {
819 if (optionMinus && !optionPlus) {
820 if ((GetLabelFont() % 10) == 3) {
821 ylabel = fLabelOffset + 0.5 *
822 ((gPad->AbsPixeltoY(0) - gPad->AbsPixeltoY((Int_t)fLabelSize)) /
823 (gPad->GetY2() - gPad->GetY1()));
824 }
825 else {
826 ylabel = fLabelOffset + 0.5 * fLabelSize;
827 }
828 ylabel += TMath::Abs(atick[0]);
829 }
830 else {
831 ylabel = -fLabelOffset;
832 if (mside <= 0) ylabel -= TMath::Abs(atick[0]);
833 }
834 if (optionLog) ylabel -= 0.5 * charheight;
835 }
836 else {
837 if (mside + lside >= 0) ylabel = fLabelOffset;
838 else ylabel = -fLabelOffset;
839 }
840 if (optionText) ylabel /= 2;
841
842 //*-*- Draw the linear tick marks if needed...
843 if (!optionLog) {
844 if (ndiv) {
845 if (fNbins) nticks = fNbins;
846 if (fFunction) {
847 dxtick = (binHigh - binLow) / Double_t(nticks - 1);
848 }
849 else {
850 if (optionNoopt && !optionInt) dxtick = axis_length / Double_t(nticks - 1);
851 else dxtick = axis_lengthN / Double_t(nticks - 1);
852 if (fNbins) dxtick = axis_length / (fWmax - fWmin);
853 }
854 for (k = 0; k < nticks; k++) {
855 ltick = 2;
856 if (k % nn3 == 0) ltick = 1;
857 if (k % nn2 == 0) ltick = 0;
858 if (fFunction) {
859 Double_t xf = binLow + Double_t(k) * dxtick;
860 Double_t zz = fFunction->Eval(xf) - rwmi;
861 xtick = zz * axis_length / TMath::Abs(rwma - rwmi);
862 }
863 else {
864 if (fNbins) xtick = (fBins[k] - fWmin) * dxtick;
865 else xtick = Double_t(k) * dxtick;
866 }
867 ytick = 0;
868 if (!mside) ytick -= atick[ltick];
869 if (optionNoopt && !optionInt) {
870 Rotate(xtick, ytick, cosphi, sinphi, x0, y0, xpl2, ypl2);
871 Rotate(xtick, atick[ltick], cosphi, sinphi, x0, y0, xpl1, ypl1);
872 }
873 else {
874 Rotate(xtick, ytick, cosphi, sinphi, xx0, yy0, xpl2, ypl2);
875 Rotate(xtick, atick[ltick], cosphi, sinphi, xx0, yy0, xpl1, ypl1);
876 }
877 if (optionVert) {
878 if ((x0 != x1) && (y0 != y1)) {
879 if (mside) {
880 xpl1 = xpl2;
881 if (cosphi > 0) ypl1 = ypl2 + atick[ltick];
882 else ypl1 = ypl2 - atick[ltick];
883 }
884 else {
885 xpl1 = 0.5 * (xpl1 + xpl2);
886 xpl2 = xpl1;
887 ypl1 = 0.5 * (ypl1 + ypl2) + atick[ltick];
888 ypl2 = 0.5 * (ypl1 + ypl2) - atick[ltick];
889 }
890 }
891 }
892 if (!drawGridOnly) PaintLineNDC(xpl1, ypl1, xpl2, ypl2);
893
894 if (optionGrid) {
895 if (ltick == 0) {
896 if (optionNoopt && !optionInt) {
897 Rotate(xtick, 0, cosphi, sinphi, x0, y0, xpl2, ypl2);
898 Rotate(xtick, grid_side * gridlength, cosphi, sinphi, x0, y0, xpl1, ypl1);
899 }
900 else {
901 Rotate(xtick, 0, cosphi, sinphi, xx0, yy0, xpl2, ypl2);
902 Rotate(xtick, grid_side * gridlength, cosphi, sinphi, xx0, yy0, xpl1, ypl1);
903 }
904 linegrid->PaintLineNDC(xpl1, ypl1, xpl2, ypl2);
905 }
906 }
907 }
908 xtick0 = 0;
909 xtick1 = xtick;
910
911 if (fFunction) axis_length0 = binLow - wmin;
912 if ((!optionNoopt || optionInt) && axis_length0) {
913 nticks0 = Int_t(axis_length0 / dxtick);
914 if (nticks0 > 1000) nticks0 = 1000;
915 for (k = 0; k <= nticks0; k++) {
916 ltick = 2;
917 if (k % nn3 == 0) ltick = 1;
918 if (k % nn2 == 0) ltick = 0;
919 ytick0 = 0;
920 if (!mside) ytick0 -= atick[ltick];
921 if (fFunction) {
922 xtick0 = (fFunction->Eval(binLow - Double_t(k) * dxtick) - rwmi)
923 * axis_length / TMath::Abs(rwma - rwmi);
924 }
925 Rotate(xtick0, ytick0, cosphi, sinphi, xx0, yy0, xpl2, ypl2);
926 Rotate(xtick0, atick[ltick], cosphi, sinphi, xx0, yy0, xpl1, ypl1);
927 if (optionVert) {
928 if ((x0 != x1) && (y0 != y1)) {
929 if (mside) {
930 xpl1 = xpl2;
931 if (cosphi > 0) ypl1 = ypl2 + atick[ltick];
932 else ypl1 = ypl2 - atick[ltick];
933 }
934 else {
935 xpl1 = 0.5 * (xpl1 + xpl2);
936 xpl2 = xpl1;
937 ypl1 = 0.5 * (ypl1 + ypl2) + atick[ltick];
938 ypl2 = 0.5 * (ypl1 + ypl2) - atick[ltick];
939 }
940 }
941 }
942 if (!drawGridOnly) PaintLineNDC(xpl1, ypl1, xpl2, ypl2);
943
944 if (optionGrid) {
945 if (ltick == 0) {
946 Rotate(xtick0, 0, cosphi, sinphi, xx0, yy0, xpl2, ypl2);
947 Rotate(xtick0, grid_side * gridlength, cosphi, sinphi, xx0, yy0, xpl1, ypl1);
948 linegrid->PaintLineNDC(xpl1, ypl1, xpl2, ypl2);
949 }
950 }
951 xtick0 -= dxtick;
952 }
953 }
954
955 if (fFunction) axis_length1 = wmax - binHigh;
956 if ((!optionNoopt || optionInt) && axis_length1) {
957 nticks1 = int(axis_length1 / dxtick);
958 if (nticks1 > 1000) nticks1 = 1000;
959 for (k = 0; k <= nticks1; k++) {
960 ltick = 2;
961 if (k % nn3 == 0) ltick = 1;
962 if (k % nn2 == 0) ltick = 0;
963 ytick1 = 0;
964 if (!mside) ytick1 -= atick[ltick];
965 if (fFunction) {
966 xtick1 = (fFunction->Eval(binHigh + Double_t(k) * dxtick) - rwmi)
967 * axis_length / TMath::Abs(rwma - rwmi);
968 }
969 Rotate(xtick1, ytick1, cosphi, sinphi, xx0, yy0, xpl2, ypl2);
970 Rotate(xtick1, atick[ltick], cosphi, sinphi, xx0, yy0, xpl1, ypl1);
971 if (optionVert) {
972 if ((x0 != x1) && (y0 != y1)) {
973 if (mside) {
974 xpl1 = xpl2;
975 if (cosphi > 0) ypl1 = ypl2 + atick[ltick];
976 else ypl1 = ypl2 - atick[ltick];
977 }
978 else {
979 xpl1 = 0.5 * (xpl1 + xpl2);
980 xpl2 = xpl1;
981 ypl1 = 0.5 * (ypl1 + ypl2) + atick[ltick];
982 ypl2 = 0.5 * (ypl1 + ypl2) - atick[ltick];
983 }
984 }
985 }
986 if (!drawGridOnly) PaintLineNDC(xpl1, ypl1, xpl2, ypl2);
987 if (optionGrid) {
988 if (ltick == 0) {
989 Rotate(xtick1, 0, cosphi, sinphi, xx0, yy0, xpl2, ypl2);
990 Rotate(xtick1, grid_side * gridlength, cosphi, sinphi, xx0, yy0, xpl1, ypl1);
991 linegrid->PaintLineNDC(xpl1, ypl1, xpl2, ypl2);
992 }
993 }
994 xtick1 += dxtick;
995 }
996 }
997 }
998 }
999
1000 //*-*- Draw the numeric labels if needed...
1001 if (!drawGridOnly && !optionUnlab) {
1002 if (!optionLog) {
1003 if (n1a) {
1004 //*-*- Spacing of labels
1005 if ((wmin == wmax) || (ndiv == 0)) {
1006 Error(where, "wmin (%f) == wmax (%f), or ndiv == 0", wmin, wmax);
1007 goto L210;
1008 }
1009 wlabel = wmin;
1010 dwlabel = (wmax - wmin) / Double_t(n1a);
1011 if (optionNoopt && !optionInt) dxlabel = axis_length / Double_t(n1a);
1012 else dxlabel = axis_lengthN / Double_t(n1a);
1013 if (fNbins) dxlabel = axis_length / (fWmax - fWmin);
1014
1015 if (!optionText && !optionTime) {
1016
1017 //*-*- We have to decide what format to generate
1018 //*-*- (for numeric labels only)
1019 //*-*- Test the magnitude, decide format
1020 flexe = kFALSE;
1021 nexe = 0;
1022 flexpo = kFALSE;
1023 flexne = kFALSE;
1025
1026 //*-*- First case : (wmax-wmin)/n1a less than 0.001
1027 //*-*- (0.001 fgMaxDigits of 5 (fgMaxDigits) characters). Then we use x 10 n
1028 //*-*- format. If af >=0 x10 n cannot be used
1029 Double_t xmicros = 0.00099;
1030 if (maxDigits) xmicros = TMath::Power(10, -maxDigits);
1031 if (!noExponent && (TMath::Abs(wmax - wmin) / Double_t(n1a)) < xmicros) {
1032 af = TMath::Log10(ww) + epsilon;
1033 if (af < 0) {
1034 flexe = kTRUE;
1035 nexe = int(af);
1036 iexe = TMath::Abs(nexe);
1037 if (iexe % 3 == 1) iexe += 2;
1038 else if (iexe % 3 == 2) iexe += 1;
1039 if (nexe < 0) nexe = -iexe;
1040 else nexe = iexe;
1041 wlabel = wlabel * TMath::Power(10, iexe);
1042 dwlabel = dwlabel * TMath::Power(10, iexe);
1043 if1 = maxDigits;
1044 if2 = maxDigits - 2;
1045 goto L110;
1046 }
1047 }
1048 if (ww >= 1) af = TMath::Log10(ww);
1049 else af = TMath::Log10(ww * 0.0001);
1050 af += epsilon;
1051 nf = Int_t(af) + 1;
1052 if (!noExponent && nf > maxDigits) flexpo = kTRUE;
1053 if (!noExponent && nf < -maxDigits) flexne = kTRUE;
1054
1055 //*-*- Use x 10 n format. (only powers of 3 allowed)
1056
1057 if (flexpo) {
1058 flexe = kTRUE;
1059 while (1) {
1060 nexe++;
1061 ww /= 10;
1062 wlabel /= 10;
1063 dwlabel /= 10;
1064 if (nexe % 3 == 0 && ww <= TMath::Power(10, maxDigits - 1)) break;
1065 }
1066 }
1067
1068 if (flexne) {
1069 flexe = kTRUE;
1070 rne = 1 / TMath::Power(10, maxDigits - 2);
1071 while (1) {
1072 nexe--;
1073 ww *= 10;
1074 wlabel *= 10;
1075 dwlabel *= 10;
1076 if (nexe % 3 == 0 && ww >= rne) break;
1077 }
1078 }
1079
1080 na = 0;
1081 for (i = maxDigits - 1; i > 0; i--) {
1082 if (TMath::Abs(ww) < TMath::Power(10, i)) na = maxDigits - i;
1083 }
1084 ndyn = n1a;
1085 while (ndyn) {
1086 Double_t wdyn = TMath::Abs((wmax - wmin) / ndyn);
1087 if (wdyn <= 0.999 && na < maxDigits - 2) {
1088 na++;
1089 ndyn /= 10;
1090 }
1091 else break;
1092 }
1093
1094 if2 = na;
1095 if1 = TMath::Max(nf + na, maxDigits) + 1;
1096L110:
1097 if (TMath::Min(wmin, wmax) < 0)if1 = if1 + 1;
1098 if1 = TMath::Min(if1, 32);
1099
1100 //*-*- In some cases, if1 and if2 are too small....
1101 while (dwlabel < TMath::Power(10, -if2)) {
1102 if1++;
1103 if2++;
1104 }
1105 coded = &chcoded[0];
1106 if (if1 > 14) if1 = 14;
1107 if (if2 > 14) if2 = 14;
1108 if (if2) snprintf(coded, 8, "%%%d.%df", if1, if2);
1109 else snprintf(coded, 8, "%%%d.%df", if1 + 1, 1);
1110 }
1111
1112 //*-*- We draw labels
1113
1114 snprintf(chtemp, 256, "%g", dwlabel);
1115 Int_t ndecimals = 0;
1116 if (optionDecimals) {
1117 char* dot = strchr(chtemp, '.');
1118 if (dot) {
1119 ndecimals = chtemp + strlen(chtemp) - dot;
1120 }
1121 else {
1122 char* exp;
1123 exp = strstr(chtemp, "e-");
1124 if (exp) {
1125 sscanf(&exp[2], "%d", &ndecimals);
1126 ndecimals++;
1127 }
1128 }
1129 }
1130 if (optionM) nlabels = n1a - 1;
1131 else nlabels = n1a;
1132 wTimeIni = wlabel;
1133 if (fNbins) nlabels = fNbins - 1;
1134 for (k = 0; k <= nlabels; k++) {
1135 if (fFunction) {
1136 Double_t xf = binLow + Double_t(k * nn2) * dxtick;
1137 Double_t zz = fFunction->Eval(xf) - rwmi;
1138 wlabel = xf;
1139 xlabel = zz * axis_length / TMath::Abs(rwma - rwmi);
1140 }
1141 else {
1142 if (fNbins) xlabel = dxlabel * (fBins[k] - fWmin);
1143 else xlabel = dxlabel * k;
1144 }
1145 if (optionM) xlabel += 0.5 * dxlabel;
1146
1147 if (!optionText && !optionTime) {
1148 snprintf(label, 256, &chcoded[0], wlabel);
1149 if (fNbins) label = Form(fFormat, fBins[k]);
1150 if (fLabels) label = Form("%s", fLabels[k]);
1151 label[28] = 0;
1152 wlabel += dwlabel;
1153
1154 LabelsLimits(label, first, last); //Eliminate blanks
1155
1156 if (label[first] == '.') { //check if '.' is preceded by a digit
1157 strncpy(chtemp, "0", 256);
1158 strlcat(chtemp, &label[first], 256);
1159 strncpy(label, chtemp, 256);
1160 first = 1;
1161 last = strlen(label);
1162 }
1163 if (label[first] == '-' && label[first + 1] == '.') {
1164 strncpy(chtemp, "-0", 256);
1165 strlcat(chtemp, &label[first + 1], 256);
1166 strncpy(label, chtemp, 256);
1167 first = 1;
1168 last = strlen(label);
1169 }
1170
1171 //*-*- We eliminate the non significant 0 after '.'
1172 if (ndecimals) {
1173 char* adot = strchr(label, '.');
1174 if (adot) adot[ndecimals] = 0;
1175 }
1176 else {
1177 while (label[last] == '0') {
1178 label[last] = 0;
1179 last--;
1180 }
1181 }
1182
1183 //*-*- We eliminate the dot, unless dot is forced.
1184 if (label[last] == '.') {
1185 if (!optionDot) {
1186 label[last] = 0;
1187 last--;
1188 }
1189 }
1190
1191 //*-*- Make sure the label is not "-0"
1192 if (last - first == 1 && label[first] == '-'
1193 && label[last] == '0') {
1194 strncpy(label, "0", 256);
1195 label[last] = 0;
1196 }
1197 if (fLabels) label = Form("%s", fLabels[k]);
1198 }
1199
1200 //*-*- Generate the time labels
1201
1202 if (optionTime) {
1203 timed = wlabel + (int)(timeoffset) - rangeOffset;
1204 timelabel = (time_t)((Long_t)(timed));
1205 if (optionTime == 1) {
1206 utctis = localtime(&timelabel);
1207 }
1208 else {
1209 utctis = gmtime(&timelabel);
1210 }
1211 TString timeformattmp;
1212 if (timeformat.Length() < 220) timeformattmp = timeformat;
1213 else timeformattmp = "#splitline{Format}{too long}";
1214
1215 //*-*- Appends fractionnal part if seconds displayed
1216 if (dwlabel < 0.9) {
1217 double tmpdb;
1218 int tmplast;
1219 snprintf(label, 256, "%%S%7.5f", modf(timed, &tmpdb));
1220 tmplast = strlen(label) - 1;
1221
1222 //*-*- We eliminate the non significiant 0 after '.'
1223 while (label[tmplast] == '0') {
1224 label[tmplast] = 0;
1225 tmplast--;
1226 }
1227
1228 timeformattmp.ReplaceAll("%S", label);
1229 //*-*- replace the "0." at the begining by "s"
1230 timeformattmp.ReplaceAll("%S0.", "%Ss");
1231
1232 }
1233
1234 strftime(label, 256, timeformattmp.Data(), utctis);
1235 strncpy(chtemp, &label[0], 256);
1236 first = 0;
1237 last = strlen(label) - 1;
1238 wlabel = wTimeIni + (k + 1) * dwlabel;
1239 }
1240
1241 //*-*- We generate labels (numeric or alphanumeric).
1242
1243// if(fLabels) label = fLabels[k];
1244 if (optionNoopt && !optionInt)
1245 Rotate(xlabel, ylabel, cosphi, sinphi, x0, y0, xx, yy);
1246 else Rotate(xlabel, ylabel, cosphi, sinphi, xx0, yy0, xx, yy);
1247 if (y0 == y1 && !optionDown && !optionUp) {
1248 yy -= 0.80 * charheight;
1249 }
1250 if (optionVert) {
1251 if (x0 != x1 && y0 != y1) {
1252 if (optionNoopt && !optionInt)
1253 Rotate(xlabel, 0, cosphi, sinphi, x0, y0, xx, yy);
1254 else Rotate(xlabel, 0, cosphi, sinphi, xx0, yy0, xx, yy);
1255 if (cosphi > 0) yy += ylabel;
1256 if (cosphi < 0) yy -= ylabel;
1257 }
1258 }
1259 if (!optionY || (x0 == x1)) {
1260 if (!optionText) {
1261 if (first > last) strncpy(chtemp, " ", 256);
1262 else strncpy(chtemp, &label[first], 256);
1263 textaxis->PaintLatex(gPad->GetX1() + xx * (gPad->GetX2() - gPad->GetX1()),
1264 gPad->GetY1() + yy * (gPad->GetY2() - gPad->GetY1()),
1265 0,
1266 textaxis->GetTextSize(),
1267 chtemp);
1268// Info(where,"label : %s,%s",chtemp,fLabels[k]);
1269 }
1270 else {
1271 if (optionText == 1) textaxis->PaintLatex(gPad->GetX1() + xx * (gPad->GetX2() - gPad->GetX1()),
1272 gPad->GetY1() + yy * (gPad->GetY2() - gPad->GetY1()),
1273 0,
1274 textaxis->GetTextSize(),
1275 fAxis->GetBinLabel(k + fAxis->GetFirst()));
1276 }
1277 }
1278 else {
1279
1280 //*-*- Text alignment is down
1281 if (!optionText) lnlen = last - first + 1;
1282 else {
1283 if (k + 1 > nhilab) lnlen = 0;
1284 }
1285 for (l = 1; l <= lnlen; l++) {
1286 if (!optionText) *chtemp = label[first + l - 2];
1287 else {
1288 if (lnlen == 0) strncpy(chtemp, " ", 256);
1289 else strncpy(chtemp, "1", 256);
1290 }
1291 textaxis->PaintLatex(gPad->GetX1() + xx * (gPad->GetX2() - gPad->GetX1()),
1292 gPad->GetY1() + yy * (gPad->GetY2() - gPad->GetY1()),
1293 0,
1294 textaxis->GetTextSize(),
1295 chtemp);
1296 yy -= charheight * 1.3;
1297 }
1298 }
1299 }
1300
1301 //*-*- We use the format x 10 ** n
1302
1303 if (flexe && !optionText && nexe) {
1304 snprintf(label, 256, "#times10^{%d}", nexe);
1305 if (x0 != x1) {
1306 xfactor = x1 - x0 + 0.1 * charheight;
1307 yfactor = 0;
1308 }
1309 else {
1310 xfactor = y1 - y0 + 0.1 * charheight;
1311 yfactor = 0;
1312 }
1313 Rotate(xfactor, yfactor, cosphi, sinphi, x0, y0, xx, yy);
1314 textaxis->SetTextAlign(11);
1315 if (GetLabelFont() % 10 < 2) // force TLatex mode in PaintLatex
1316 textaxis->SetTextFont((Int_t)(GetLabelFont() / 10) * 10 + 2);
1317 textaxis->PaintLatex(gPad->GetX1() + xx * (gPad->GetX2() - gPad->GetX1()),
1318 gPad->GetY1() + yy * (gPad->GetY2() - gPad->GetY1()),
1319 0,
1320 textaxis->GetTextSize(),
1321 label);
1322 }
1323 }
1324 }
1325 }
1326
1327 //*-*- Log axis
1328
1329 if (optionLog && ndiv) {
1330 UInt_t xi1 = 0, xi2, wi, yi1 = 0, yi2, hi, xl, xh;
1331 Bool_t firstintlab = kTRUE, overlap = kFALSE;
1332 if ((wmin == wmax) || (ndiv == 0)) {
1333 Error(where, "wmin (%f) == wmax (%f), or ndiv == 0", wmin, wmax);
1334 goto L210;
1335 }
1336 if (wmin <= 0) {
1337 Error(where, "negative logarithmic axis");
1338 goto L210;
1339 }
1340 if (wmax <= 0) {
1341 Error(where, "negative logarithmic axis");
1342 goto L210;
1343 }
1344 xmnlog = TMath::Log10(wmin);
1345 if (xmnlog > 0) xmnlog += 1.E-6;
1346 else xmnlog -= 1.E-6;
1347 x00 = 0;
1348 x11 = axis_length;
1349 h2 = TMath::Log10(wmax);
1350 h2sav = h2;
1351 if (h2 > 0) h2 += 1.E-6;
1352 else h2 -= 1.E-6;
1353 ih1 = int(xmnlog);
1354 ih2 = 1 + int(h2);
1355 nbinin = ih2 - ih1 + 1;
1356 axmul = (x11 - x00) / (h2sav - xmnlog);
1357
1358 //*-*- Plot decade and intermediate tick marks
1359 decade = ih1 - 2;
1360 labelnumber = ih1;
1361 if (xmnlog > 0 && (xmnlog - Double_t(ih1) > 0)) labelnumber++;
1362 for (j = 1; j <= nbinin; j++) {
1363
1364 //*-*- Plot decade
1365 firstintlab = kTRUE, overlap = kFALSE;
1366 decade++;
1367 if (x0 == x1 && j == 1) ylabel += charheight * 0.33;
1368 if (y0 == y1 && j == 1) ylabel -= charheight * 0.65;
1369 xone = x00 + axmul * (Double_t(decade) - xmnlog);
1370 //the following statement is a trick to circumvent a gcc bug
1371 if (j < 0) printf("j=%d\n", j);
1372 if (x00 > xone) goto L160;
1373 if ((xone - x11) > epsilon) break;
1374 xtwo = xone;
1375 y = 0;
1376 if (!mside) y -= atick[0];
1377 Rotate(xone, y, cosphi, sinphi, x0, y0, xpl2, ypl2);
1378 Rotate(xtwo, atick[0], cosphi, sinphi, x0, y0, xpl1, ypl1);
1379 if (optionVert) {
1380 if ((x0 != x1) && (y0 != y1)) {
1381 if (mside) {
1382 xpl1 = xpl2;
1383 if (cosphi > 0) ypl1 = ypl2 + atick[0];
1384 else ypl1 = ypl2 - atick[0];
1385 }
1386 else {
1387 xpl1 = 0.5 * (xpl1 + xpl2);
1388 xpl2 = xpl1;
1389 ypl1 = 0.5 * (ypl1 + ypl2) + atick[0];
1390 ypl2 = 0.5 * (ypl1 + ypl2) - atick[0];
1391 }
1392 }
1393 }
1394 if (!drawGridOnly) PaintLineNDC(xpl1, ypl1, xpl2, ypl2);
1395
1396 if (optionGrid) {
1397 Rotate(xone, 0, cosphi, sinphi, x0, y0, xpl2, ypl2);
1398 Rotate(xone, grid_side * gridlength, cosphi, sinphi, x0, y0, xpl1, ypl1);
1399 linegrid->PaintLineNDC(xpl1, ypl1, xpl2, ypl2);
1400 }
1401
1402 if (!drawGridOnly && !optionUnlab) {
1403
1404 //*-*- We generate labels (numeric only).
1405// if(fLabels) label = fLabels[k];
1406 if (noExponent) {
1407 rlab = TMath::Power(10, labelnumber);
1408 snprintf(label, 256, "%f", rlab);
1409 LabelsLimits(label, first, last);
1410 while (last > first) {
1411 if (label[last] != '0') break;
1412 label[last] = 0;
1413 last--;
1414 }
1415 if (label[last] == '.') {
1416 label[last] = 0;
1417 last--;
1418 }
1419 }
1420 else {
1421 snprintf(label, 256, "%d", labelnumber);
1422 LabelsLimits(label, first, last);
1423 }
1424 Rotate(xone, ylabel, cosphi, sinphi, x0, y0, xx, yy);
1425 if ((x0 == x1) && !optionPara) {
1426 if (lside < 0) {
1427 if (mside < 0) {
1428 if (labelnumber == 0) nch = 1;
1429 else nch = 2;
1430 xx += nch * charheight;
1431 }
1432 else {
1433 xx += 0.25 * charheight;
1434 }
1435 }
1436 xx += 0.25 * charheight;
1437 }
1438 if ((y0 == y1) && !optionDown && !optionUp) {
1439 if (noExponent) yy += 0.33 * charheight;
1440 }
1441 if (n1a == 0)goto L210;
1442 kmod = nbinin / n1a;
1443 if (kmod == 0) kmod = 1000000;
1444 if ((nbinin <= n1a) || (j == 1) || (j == nbinin) || ((nbinin > n1a)
1445 && (j % kmod == 0))) {
1446 if (labelnumber == 0) {
1447 textaxis->PaintTextNDC(xx, yy, "1");
1448 }
1449 else if (labelnumber == 1) {
1450 textaxis->PaintTextNDC(xx, yy, "10");
1451 }
1452 else {
1453 if (noExponent) {
1454 textaxis->PaintTextNDC(xx, yy, &label[first]);
1455 }
1456 else {
1457 snprintf(chtemp, 256, "10^{%d}", labelnumber);
1458 textaxis->PaintLatex(gPad->GetX1() + xx * (gPad->GetX2() - gPad->GetX1()),
1459 gPad->GetY1() + yy * (gPad->GetY2() - gPad->GetY1()),
1460 0, textaxis->GetTextSize(), chtemp);
1461
1462 }
1463 }
1464 }
1465 labelnumber++;
1466 }
1467L160:
1468 for (k = 2; k < 10; k++) {
1469
1470 //*-*- Plot intermediate tick marks
1471 xone = x00 + axmul * (TMath::Log10(Double_t(k)) + Double_t(decade) - xmnlog);
1472 if (x00 > xone) continue;
1473 if (xone > x11) goto L200;
1474 y = 0;
1475 if (!mside) y -= atick[1];
1476 xtwo = xone;
1477 Rotate(xone, y, cosphi, sinphi, x0, y0, xpl2, ypl2);
1478 Rotate(xtwo, atick[1], cosphi, sinphi, x0, y0, xpl1, ypl1);
1479 if (optionVert) {
1480 if ((x0 != x1) && (y0 != y1)) {
1481 if (mside) {
1482 xpl1 = xpl2;
1483 if (cosphi > 0) ypl1 = ypl2 + atick[1];
1484 else ypl1 = ypl2 - atick[1];
1485 }
1486 else {
1487 xpl1 = 0.5 * (xpl1 + xpl2);
1488 xpl2 = xpl1;
1489 ypl1 = 0.5 * (ypl1 + ypl2) + atick[1];
1490 ypl2 = 0.5 * (ypl1 + ypl2) - atick[1];
1491 }
1492 }
1493 }
1494 idn = n1a * 2;
1495 if ((nbinin <= idn) || ((nbinin > idn) && (k == 5))) {
1496 if (!drawGridOnly) PaintLineNDC(xpl1, ypl1, xpl2, ypl2);
1497
1498 //*-*- Draw the intermediate LOG labels if requested
1499
1500 if (moreLogLabels && !optionUnlab && !drawGridOnly && !overlap) {
1501 if (noExponent) {
1502 rlab = Double_t(k) * TMath::Power(10, labelnumber - 1);
1503 snprintf(chtemp, 256, "%g", rlab);
1504 }
1505 else {
1506 if (labelnumber - 1 == 0) {
1507 snprintf(chtemp, 256, "%d", k);
1508 }
1509 else if (labelnumber - 1 == 1) {
1510 snprintf(chtemp, 256, "%d", 10 * k);
1511 }
1512 else {
1513 snprintf(chtemp, 256, "%d#times10^{%d}", k, labelnumber - 1);
1514 }
1515 }
1516 Rotate(xone, ylabel, cosphi, sinphi, x0, y0, xx, yy);
1517 if ((x0 == x1) && !optionPara) {
1518 if (lside < 0) {
1519 if (mside < 0) {
1520 if (labelnumber == 0) nch = 1;
1521 else nch = 2;
1522 xx += nch * charheight;
1523 }
1524 else {
1525 if (labelnumber >= 0) xx += 0.25 * charheight;
1526 else xx += 0.50 * charheight;
1527 }
1528 }
1529 xx += 0.25 * charheight;
1530 }
1531 if ((y0 == y1) && !optionDown && !optionUp) {
1532 if (noExponent) yy += 0.33 * charheight;
1533 }
1534 if (optionVert) {
1535 if ((x0 != x1) && (y0 != y1)) {
1536 Rotate(xone, ylabel, cosphi, sinphi, x0, y0, xx, yy);
1537 if (cosphi > 0) yy += ylabel;
1538 else yy -= ylabel;
1539 }
1540 }
1541 textaxis->SetTitle(chtemp);
1542 Double_t u = gPad->GetX1() + xx * (gPad->GetX2() - gPad->GetX1());
1543 Double_t v = gPad->GetY1() + yy * (gPad->GetY2() - gPad->GetY1());
1544 if (firstintlab) {
1545 textaxis->GetBoundingBox(wi, hi);
1546 wi = (UInt_t)(wi * 1.3);
1547 hi *= (UInt_t)(hi * 1.3);
1548 xi1 = gPad->XtoAbsPixel(u);
1549 yi1 = gPad->YtoAbsPixel(v);
1550 firstintlab = kFALSE;
1551 textaxis->PaintLatex(u, v, 0, textaxis->GetTextSize(), chtemp);
1552 }
1553 else {
1554 xi2 = gPad->XtoAbsPixel(u);
1555 yi2 = gPad->YtoAbsPixel(v);
1556 xl = TMath::Min(xi1, xi2);
1557 xh = TMath::Max(xi1, xi2);
1558 if ((x0 == x1 && yi1 - hi <= yi2) || (y0 == y1 && xl + wi >= xh)) {
1559 overlap = kTRUE;
1560 }
1561 else {
1562 xi1 = xi2;
1563 yi1 = yi2;
1564 textaxis->GetBoundingBox(wi, hi);
1565 wi = (UInt_t)(wi * 1.3);
1566 hi *= (UInt_t)(hi * 1.3);
1567 textaxis->PaintLatex(u, v, 0, textaxis->GetTextSize(), chtemp);
1568 }
1569 }
1570 }
1571
1572 //*-*- Draw the intermediate LOG grid if only three decades are requested
1573 if (optionGrid && nbinin <= 5 && ndiv > 100) {
1574 Rotate(xone, 0, cosphi, sinphi, x0, y0, xpl2, ypl2);
1575 Rotate(xone, grid_side * gridlength, cosphi, sinphi, x0, y0, xpl1, ypl1);
1576 linegrid->PaintLineNDC(xpl1, ypl1, xpl2, ypl2);
1577 }
1578 } //endif ((nbinin <= idn) ||
1579 } //endfor (k=2;k<10;k++)
1580 } //endfor (j=1; j<=nbinin; j++)
1581L200:
1582 Int_t kuku = 0;
1583 if (kuku) { }
1584 } //endif (optionLog && ndiv)
1585
1586
1587L210:
1588 if (optionGrid) delete linegrid;
1589 delete textaxis;
1590}
1591
1592
1593
int Int_t
unsigned int UInt_t
long Long_t
#define e(i)
bool Bool_t
float Float_t
constexpr Bool_t kFALSE
double Double_t
constexpr Bool_t kTRUE
const char Option_t
#define BIT(n)
const Double_t kPI
Option_t Option_t TPoint TPoint const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize void char Point_t Rectangle_t wmin
Option_t Option_t TPoint TPoint const char x1
Option_t Option_t TPoint TPoint angle
Option_t Option_t TPoint TPoint const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize void char Point_t Rectangle_t wmax
Option_t Option_t TPoint TPoint const char y1
const Int_t kHori
float xmin
#define hi
float ymin
float xmax
float ymax
#define gROOT
char * Form(const char *fmt,...)
R__EXTERN TStyle * gStyle
R__EXTERN TSystem * gSystem
#define gPad
#define gVirtualX
#define snprintf
Extension of TGaxis class optimised for KVGraph visualisation.
Definition KVGaxis.h:18
Double_t * fBins
Definition KVGaxis.h:21
virtual void PaintAxis(Double_t xmin, Double_t ymin, Double_t xmax, Double_t ymax, Double_t &wmin, Double_t &wmax, Int_t &ndiv, Option_t *chopt="", Double_t gridlength=0, Bool_t drawGridOnly=kFALSE)
Definition KVGaxis.cpp:130
const char * fFormat
Definition KVGaxis.h:22
KVGaxis()
Definition KVGaxis.cpp:35
virtual ~KVGaxis()
Destructor.
Definition KVGaxis.cpp:106
char ** fLabels
Definition KVGaxis.h:23
Int_t fNbins
Definition KVGaxis.h:20
virtual Float_t GetLabelOffset() const
virtual Color_t GetLineColor() const
virtual void SetLineStyle(Style_t lstyle)
virtual void SetLineWidth(Width_t lwidth)
virtual void SetLineColor(Color_t lcolor)
virtual Float_t GetTextSize() const
virtual void SetTextAlign(Short_t align=11)
virtual Font_t GetTextFont() const
virtual Color_t GetTextColor() const
virtual void SetTextAngle(Float_t tangle=0)
virtual Float_t GetTextAngle() const
virtual void SetTextColor(Color_t tcolor=1)
virtual void SetTextFont(Font_t tfont=62)
virtual void SetTextSize(Float_t tsize=1)
virtual Double_t GetBinCenter(Int_t bin) const
kMoreLogLabels
const char * GetBinLabel(Int_t bin) const
Int_t GetLast() const
Int_t GetFirst() const
THashList * GetLabels() const
virtual Double_t Eval(Double_t x, Double_t y=0, Double_t z=0, Double_t t=0) const
virtual void PaintAxis(Double_t xmin, Double_t ymin, Double_t xmax, Double_t ymax, Double_t &wmin, Double_t &wmax, Int_t &ndiv, Option_t *chopt="", Double_t gridlength=0, Bool_t drawGridOnly=kFALSE)
TAxis * fAxis
TString fTimeFormat
TString fFunctionName
virtual void Rotate(Double_t X, Double_t Y, Double_t CFI, Double_t SFI, Double_t XT, Double_t YT, Double_t &U, Double_t &V)
Float_t GetLabelOffset() const
Float_t fTickSize
Int_t GetLabelFont() const
Float_t fLabelOffset
Float_t fLabelSize
Int_t fNdiv
const char * GetTitle() const override
TString fChopt
Float_t GetTitleOffset() const
TF1 * fFunction
Float_t GetTitleSize() const
virtual void AdjustBinSize(Double_t A1, Double_t A2, Int_t nold, Double_t &BinLow, Double_t &BinHigh, Int_t &nbins, Double_t &BinWidth)
Int_t GetLabelColor() const
Double_t fWmax
Double_t fWmin
void LabelsLimits(const char *label, Int_t &first, Int_t &last)
Float_t GetLabelSize() const
static void Optimize(Double_t A1, Double_t A2, Int_t nold, Double_t &BinLow, Double_t &BinHigh, Int_t &nbins, Double_t &BWID, Option_t *option="")
Double_t GetXsize()
void GetBoundingBox(UInt_t &w, UInt_t &h, Bool_t angle=kFALSE) override
virtual void PaintLatex(Double_t x, Double_t y, Double_t angle, Double_t size, const char *text)
virtual void PaintLineNDC(Double_t u1, Double_t v1, Double_t u2, Double_t v2)
virtual void SetTitle(const char *title="")
const char * GetName() const override
R__ALWAYS_INLINE Bool_t TestBit(UInt_t f) const
virtual void Error(const char *method, const char *msgfmt,...) const
Ssiz_t Length() const
const char * Data() const
TString & ReplaceAll(const char *s1, const char *s2)
Ssiz_t Index(const char *pat, Ssiz_t i=0, ECaseCompare cmp=kExact) const
Double_t GetTimeOffset() const
Color_t GetGridColor() const
Style_t GetGridStyle() const
Width_t GetGridWidth() const
Int_t GetStripDecimals() const
virtual const char * Getenv(const char *env)
virtual void Unsetenv(const char *name)
virtual void Setenv(const char *name, const char *value)
virtual void SetText(Double_t x, Double_t y, const char *text)
virtual void PaintTextNDC(Double_t u, Double_t v, const char *text)
double beta(double x, double y)
RVec< PromoteType< T > > exp(const RVec< T > &v)
Double_t y[n]
Double_t Min(Double_t a, Double_t b)
Double_t ATan2(Double_t y, Double_t x)
Double_t Power(Double_t x, Double_t y)
Double_t Sqrt(Double_t x)
Double_t Cos(Double_t)
constexpr Double_t Pi()
Double_t Abs(Double_t d)
Double_t Sin(Double_t)
Double_t Max(Double_t a, Double_t b)
Double_t Log10(Double_t x)
v
TLine l
ClassImp(TPyArg)
double epsilon