Logo ROOT  
Reference Guide
Loading...
Searching...
No Matches
TGLLegoPainter.cxx
Go to the documentation of this file.
1// @(#)root/gl:$Id$
2// Author: Timur Pocheptsov 14/06/2006
3
4/*************************************************************************
5 * Copyright (C) 1995-2004, 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#include <algorithm>
12#include <cctype>
13
14#include "KeySymbols.h"
15#include "TVirtualX.h"
16#include "Buttons.h"
17#include "TString.h"
18#include "TColor.h"
19#include "TROOT.h"
20#include "TStyle.h"
21#include "TAxis.h"
22#include "TMath.h"
23#include "TH1.h"
24
25#include "TGLLegoPainter.h"
26#include "TGLPlotCamera.h"
27#include "TGLIncludes.h"
28
29/** \class TGLLegoPainter
30\ingroup opengl
31Plot-painter implementing LEGO rendering of TH2 histograms in
32cartesian, polar, cylindrical and spherical coordinates.
33*/
34
35
36////////////////////////////////////////////////////////////////////////////////
37///Ctor.
38
46
47////////////////////////////////////////////////////////////////////////////////
48///Obtain bin's info (i, j, value).
49
51{
52 fBinInfo = "";
53
54 if (fSelectedPart) {
56 if (fHist->Class())
57 fBinInfo += fHist->Class()->GetName();
58 fBinInfo += "::";
59 fBinInfo += fHist->GetName();
60 } else if (!fHighColor) {
61 const Int_t binI = (fSelectedPart - fSelectionBase) / fCoord->GetNYBins() + fCoord->GetFirstXBin();
62 const Int_t binJ = (fSelectedPart - fSelectionBase) % fCoord->GetNYBins() + fCoord->GetFirstYBin();
63 fBinInfo.Form("(binx = %d; biny = %d; binc = %f)", binI, binJ,
64 fHist->GetBinContent(binI, binJ));
65 } else
66 fBinInfo = "Switch to true-color mode to obtain correct info";
67 }
68
69 return (Char_t *)fBinInfo.Data();
70}
71
72////////////////////////////////////////////////////////////////////////////////
73///Select method.
74
76{
78 switch (fCoord->GetCoordType()) {
79 case kGLCartesian:
80 ret = InitGeometryCartesian(); break;
81 case kGLPolar:
82 ret = InitGeometryPolar(); break;
83 case kGLCylindrical:
85 case kGLSpherical:
86 ret = InitGeometrySpherical(); break;
87 default:
88 return kFALSE;
89 }
90 if (ret && fCamera) fCamera->SetViewVolume(fBackBox.Get3DBox());
91 return ret;
92}
93
94////////////////////////////////////////////////////////////////////////////////
95///Geometry for lego in cartesian coords.
96
98{
99 if (!fCoord->SetRanges(fHist, fDrawErrors, kFALSE))
100 return kFALSE;
101
102 fBackBox.SetPlotBox(fCoord->GetXRangeScaled(), fCoord->GetYRangeScaled(), fCoord->GetZRangeScaled());
103
104 //Find bin edges
105 const Int_t nX = fCoord->GetNXBins();
106 const Double_t barWidth = fHist->GetBarWidth(), barOffset = fHist->GetBarOffset();
107 const TGLVertex3 *frame = fBackBox.Get3DBox();
108 fXEdges.resize(nX);
109
110 if (fCoord->GetXLog()) {
111 for (Int_t i = 0, ir = fCoord->GetFirstXBin(); i < nX; ++i, ++ir) {
112 const Double_t xWidth = fXAxis->GetBinWidth(ir);
113 Double_t low = fXAxis->GetBinLowEdge(ir) + xWidth * barOffset;
114 fXEdges[i].first = TMath::Log10(low) * fCoord->GetXScale();
115 fXEdges[i].second = TMath::Log10(low + xWidth * barWidth) * fCoord->GetXScale();
116 if (fXEdges[i].second > frame[1].X())
117 fXEdges[i].second = frame[1].X();
118 if (fXEdges[i].first < frame[0].X())
119 fXEdges[i].first = frame[0].X();
120 if (fXEdges[i].second < frame[0].X())
121 fXEdges[i].second = frame[0].X();
122 }
123 } else {
124 for (Int_t i = 0, ir = fCoord->GetFirstXBin(); i < nX; ++i, ++ir) {
125 const Double_t xWidth = fXAxis->GetBinWidth(ir);
126 fXEdges[i].first = (fXAxis->GetBinLowEdge(ir) + xWidth * barOffset) * fCoord->GetXScale();
127 fXEdges[i].second = fXEdges[i].first + xWidth * barWidth * fCoord->GetXScale();
128 if (fXEdges[i].second > frame[1].X())
129 fXEdges[i].second = frame[1].X();
130 if (fXEdges[i].first < frame[0].X())
131 fXEdges[i].first = frame[0].X();
132 if (fXEdges[i].second < frame[0].X())
133 fXEdges[i].second = frame[0].X();
134 }
135 }
136
137 const Int_t nY = fCoord->GetNYBins();
138 fYEdges.resize(nY);
139
140 if (fCoord->GetYLog()) {
141 for (Int_t j = 0, jr = fCoord->GetFirstYBin(); j < nY; ++j, ++jr) {
142 const Double_t yWidth = fYAxis->GetBinWidth(jr);
143 Double_t low = fYAxis->GetBinLowEdge(jr) + yWidth * barOffset;
144 fYEdges[j].first = TMath::Log10(low) * fCoord->GetYScale();
145 fYEdges[j].second = TMath::Log10(low + yWidth * barWidth) * fCoord->GetYScale();
146 if (fYEdges[j].second > frame[2].Y())
147 fYEdges[j].second = frame[2].Y();
148 if (fYEdges[j].first < frame[0].Y())
149 fYEdges[j].first = frame[0].Y();
150 if (fYEdges[j].second < frame[0].Y())
151 fYEdges[j].second = frame[0].Y();
152 }
153 } else {
154 for (Int_t j = 0, jr = fCoord->GetFirstYBin(); j < nY; ++j, ++jr) {
155 const Double_t yWidth = fYAxis->GetBinWidth(jr);
156 fYEdges[j].first = (fYAxis->GetBinLowEdge(jr) + yWidth * barOffset) * fCoord->GetYScale();
157 fYEdges[j].second = fYEdges[j].first + yWidth * barWidth * fCoord->GetYScale();
158 if (fYEdges[j].second > frame[2].Y())
159 fYEdges[j].second = frame[2].Y();
160 if (fYEdges[j].first < frame[0].Y())
161 fYEdges[j].first = frame[0].Y();
162 if (fYEdges[j].second < frame[0].Y())
163 fYEdges[j].second = frame[0].Y();
164 }
165 }
166
167 fMinZ = frame[0].Z();
168 if (fMinZ < 0.)
169 frame[4].Z() > 0. ? fMinZ = 0. : fMinZ = frame[4].Z();
170
171 if (fCoord->Modified()) {
173 fXOZSectionPos = frame[0].Y();
174 fYOZSectionPos = frame[0].X();
175 fXOYSectionPos = frame[0].Z();
176 fCoord->ResetModified();
177 Rgl::SetZLevels(fZAxis, fCoord->GetZRange().first, fCoord->GetZRange().second, fCoord->GetZScale(), fZLevels);
178 }
179
180 fMinMaxVal.first = fHist->GetBinContent(fCoord->GetFirstXBin(), fCoord->GetFirstYBin());
181 fMinMaxVal.second = fMinMaxVal.first;
182
183 for (Int_t i = fCoord->GetFirstXBin(), e = fCoord->GetLastXBin(); i <= e; ++i) {
184 for (Int_t j = fCoord->GetFirstYBin(), e1 = fCoord->GetLastYBin(); j <= e1; ++j) {
185 Double_t val = fHist->GetBinContent(i, j);
186 fMinMaxVal.first = TMath::Min(fMinMaxVal.first, val);
187 fMinMaxVal.second = TMath::Max(fMinMaxVal.second, val);
188 }
189 }
190
191 ClampZ(fMinMaxVal.first);
192 ClampZ(fMinMaxVal.second);
193
194 return kTRUE;
195}
196
197////////////////////////////////////////////////////////////////////////////////
198///Geometry for lego in polar coords.
199
201{
202 if (!fCoord->SetRanges(fHist, kFALSE, kFALSE))
203 return kFALSE;
204
205 fBackBox.SetPlotBox(fCoord->GetXRangeScaled(), fCoord->GetYRangeScaled(), fCoord->GetZRangeScaled());
206
207 if (fCoord->Modified()) {
209 fCoord->ResetModified();
210 }
211
212 const Int_t nY = fCoord->GetNYBins();//yBins.second - yBins.first + 1;
213 fYEdges.resize(nY);
214
215 for (Int_t j = 0, jr = fCoord->GetFirstYBin(); j < nY; ++j, ++jr) {
216 fYEdges[j].first = ((fYAxis->GetBinLowEdge(jr)) - fCoord->GetYRange().first) /
217 fCoord->GetYLength() * fCoord->GetYScale();
218 fYEdges[j].second = ((fYAxis->GetBinUpEdge(jr)) - fCoord->GetYRange().first) /
219 fCoord->GetYLength() * fCoord->GetYScale();
220 }
221
222 const Int_t nX = fCoord->GetNXBins();
223 fCosSinTableX.resize(nX + 1);
224 const Double_t fullAngle = fXAxis->GetXmax() - fXAxis->GetXmin();
225 const Double_t phiLow = fXAxis->GetXmin();
226 Double_t angle = 0;
227 for (Int_t i = 0, ir = fCoord->GetFirstXBin(); i < nX; ++i, ++ir) {
228 angle = (fXAxis->GetBinLowEdge(ir) - phiLow) / fullAngle * TMath::TwoPi();
229 fCosSinTableX[i].first = TMath::Cos(angle);
230 fCosSinTableX[i].second = TMath::Sin(angle);
231 }
232 angle = (fXAxis->GetBinUpEdge(fCoord->GetLastXBin()) - phiLow) / fullAngle * TMath::TwoPi();
233 fCosSinTableX[nX].first = TMath::Cos(angle);
234 fCosSinTableX[nX].second = TMath::Sin(angle);
235
236 fMinZ = fBackBox.Get3DBox()[0].Z();
237 if (fMinZ < 0.)
238 fBackBox.Get3DBox()[4].Z() > 0. ? fMinZ = 0. : fMinZ = fBackBox.Get3DBox()[4].Z();
239
240 fMinMaxVal.first = fHist->GetBinContent(fCoord->GetFirstXBin(), fCoord->GetFirstYBin());
241 fMinMaxVal.second = fMinMaxVal.first;
242
243 for (Int_t i = fCoord->GetFirstXBin(), e = fCoord->GetLastXBin(); i <= e; ++i) {
244 for (Int_t j = fCoord->GetFirstYBin(), e1 = fCoord->GetLastYBin(); j <= e1; ++j) {
245 Double_t val = fHist->GetBinContent(i, j);
246 fMinMaxVal.first = TMath::Min(fMinMaxVal.first, val);
247 fMinMaxVal.second = TMath::Max(fMinMaxVal.second, val);
248 }
249 }
250
251 ClampZ(fMinMaxVal.first);
252 ClampZ(fMinMaxVal.second);
253
254 return kTRUE;
255}
256
257////////////////////////////////////////////////////////////////////////////////
258///Geometry for lego in cylindrical coords.
259
261{
262 if (!fCoord->SetRanges(fHist, kFALSE, kFALSE))
263 return kFALSE;
264
265 fBackBox.SetPlotBox(fCoord->GetXRangeScaled(), fCoord->GetYRangeScaled(), fCoord->GetZRangeScaled());
266
267 const Int_t nY = fCoord->GetNYBins();
268 fYEdges.resize(nY);
269
270 if (fCoord->GetYLog()) {
271 for (Int_t j = 0, jr = fCoord->GetFirstYBin(); j < nY; ++j, ++jr) {
272 fYEdges[j].first = TMath::Log10(fYAxis->GetBinLowEdge(jr)) * fCoord->GetYScale();
273 fYEdges[j].second = TMath::Log10(fYAxis->GetBinUpEdge(jr)) * fCoord->GetYScale();
274 }
275 } else {
276 for (Int_t j = 0, jr = fCoord->GetFirstYBin(); j < nY; ++j, ++jr) {
277 fYEdges[j].first = fYAxis->GetBinLowEdge(jr) * fCoord->GetYScale();
278 fYEdges[j].second = fYAxis->GetBinUpEdge(jr) * fCoord->GetYScale();
279 }
280 }
281
282 const Int_t nX = fCoord->GetNXBins();
283 fCosSinTableX.resize(nX + 1);
284 const Double_t fullAngle = fXAxis->GetXmax() - fXAxis->GetXmin();
285 const Double_t phiLow = fXAxis->GetXmin();
286 Double_t angle = 0.;
287 for (Int_t i = 0, ir = fCoord->GetFirstXBin(); i < nX; ++i, ++ir) {
288 angle = (fXAxis->GetBinLowEdge(ir) - phiLow) / fullAngle * TMath::TwoPi();
289 fCosSinTableX[i].first = TMath::Cos(angle);
290 fCosSinTableX[i].second = TMath::Sin(angle);
291 }
292 angle = (fXAxis->GetBinUpEdge(fCoord->GetLastXBin()) - phiLow) / fullAngle * TMath::TwoPi();
293 fCosSinTableX[nX].first = TMath::Cos(angle);
294 fCosSinTableX[nX].second = TMath::Sin(angle);
295
296 if (fCoord->Modified()) {
298 fCoord->ResetModified();
299 }
300
301 fMinZ = fCoord->GetZRange().first;
302 if (fMinZ < 0.)
303 fCoord->GetZRange().second > 0. ? fMinZ = 0. : fMinZ = fCoord->GetZRange().second;
304
305
306 fMinMaxVal.first = fHist->GetBinContent(fCoord->GetFirstXBin(), fCoord->GetFirstYBin());
307 fMinMaxVal.second = fMinMaxVal.first;
308
309 for (Int_t i = fCoord->GetFirstXBin(), e = fCoord->GetLastXBin(); i <= e; ++i) {
310 for (Int_t j = fCoord->GetFirstYBin(), e1 = fCoord->GetLastYBin(); j <= e1; ++j) {
311 Double_t val = fHist->GetBinContent(i, j);
312 fMinMaxVal.first = TMath::Min(fMinMaxVal.first, val);
313 fMinMaxVal.second = TMath::Max(fMinMaxVal.second, val);
314 }
315 }
316
317 return kTRUE;
318}
319
320////////////////////////////////////////////////////////////////////////////////
321///Geometry for lego in spherical coords.
322
324{
325 if (!fCoord->SetRanges(fHist, kFALSE, kFALSE))
326 return kFALSE;
327
328 fBackBox.SetPlotBox(fCoord->GetXRangeScaled(), fCoord->GetYRangeScaled(), fCoord->GetZRangeScaled());
329
330 const Int_t nY = fCoord->GetNYBins();
331 fCosSinTableY.resize(nY + 1);
332 const Double_t fullTheta = fYAxis->GetXmax() - fYAxis->GetXmin();
333 const Double_t thetaLow = fYAxis->GetXmin();
334 Double_t angle = 0.;
335 for (Int_t j = 0, jr = fCoord->GetFirstYBin(); j < nY; ++j, ++jr) {
336 angle = (fYAxis->GetBinLowEdge(jr) - thetaLow) / fullTheta * TMath::Pi();
337 fCosSinTableY[j].first = TMath::Cos(angle);
338 fCosSinTableY[j].second = TMath::Sin(angle);
339 }
340 angle = (fYAxis->GetBinUpEdge(fCoord->GetLastYBin()) - thetaLow) / fullTheta * TMath::Pi();
341 fCosSinTableY[nY].first = TMath::Cos(angle);
342 fCosSinTableY[nY].second = TMath::Sin(angle);
343
344 const Int_t nX = fCoord->GetNXBins();
345 fCosSinTableX.resize(nX + 1);
346 const Double_t fullPhi = fXAxis->GetXmax() - fXAxis->GetXmin();
347 const Double_t phiLow = fXAxis->GetXmin();
348
349 for (Int_t i = 0, ir = fCoord->GetFirstXBin(); i < nX; ++i, ++ir) {
350 angle = (fXAxis->GetBinLowEdge(ir) - phiLow) / fullPhi * TMath::TwoPi();
351 fCosSinTableX[i].first = TMath::Cos(angle);
352 fCosSinTableX[i].second = TMath::Sin(angle);
353 }
354
355 angle = (fXAxis->GetBinUpEdge(fCoord->GetLastXBin()) - phiLow) / fullPhi * TMath::TwoPi();
356 fCosSinTableX[nX].first = TMath::Cos(angle);
357 fCosSinTableX[nX].second = TMath::Sin(angle);
358
359 fMinZ = fCoord->GetZRange().first;
360 if (fMinZ < 0.)
361 fCoord->GetZRange().second > 0. ? fMinZ = 0. : fMinZ = fCoord->GetZRange().second;
362
363 fMinMaxVal.first = fHist->GetBinContent(fCoord->GetFirstXBin(), fCoord->GetFirstYBin());
364 fMinMaxVal.second = fMinMaxVal.first;
365
366 for (Int_t i = fCoord->GetFirstXBin(), e = fCoord->GetLastXBin(); i <= e; ++i) {
367 for (Int_t j = fCoord->GetFirstYBin(), e1 = fCoord->GetLastYBin(); j <= e1; ++j) {
368 Double_t val = fHist->GetBinContent(i, j);
369 fMinMaxVal.first = TMath::Min(fMinMaxVal.first, val);
370 fMinMaxVal.second = TMath::Max(fMinMaxVal.second, val);
371 }
372 }
373
374
375 return kTRUE;
376}
377
378////////////////////////////////////////////////////////////////////////////////
379///User clicks on a lego with middle mouse button (middle for pad).
380
382{
383 fMousePosition.fX = px;
384 fMousePosition.fY = fCamera->GetHeight() - py;
385 fCamera->StartPan(px, py);
386 fBoxCut.StartMovement(px, py);
387}
388
389////////////////////////////////////////////////////////////////////////////////
390///Move lego or section.
391
393{
397
398 fCamera->SetCamera();
399 fCamera->Apply(fPadPhi, fPadTheta);
400 fCamera->Pan(px, py);
401
404 } else if (fSelectedPart > 0) {
405 //Convert py into bottom-top orientation.
406 py = fCamera->GetHeight() - py;
407
410
411 fCamera->SetCamera();
412 fCamera->Apply(fPadPhi, fPadTheta);
413
414 if (!fHighColor) {
415 if (fBoxCut.IsActive() && (fSelectedPart >= kXAxis && fSelectedPart <= kZAxis))
416 fBoxCut.MoveBox(px, py, fSelectedPart);
417 else
418 MoveSection(px, py);
419 } else
420 MoveSection(px, py);
421
424 }
425
426 fMousePosition.fX = px, fMousePosition.fY = py;
428}
429
430////////////////////////////////////////////////////////////////////////////////
431///Parse additional options.
432
434{
435 const Ssiz_t legoPos = option.Index("lego");//"lego" _already_ _exists_ in a string.
436 if (legoPos + 4 < option.Length() && isdigit(option[legoPos + 4])) {
437 switch (option[legoPos + 4] - '0') {
438 case 1:
440 break;
441 case 2:
443 break;
444 case 3:
446 break;
447 default:
449 break;
450 }
451 } else
453 //check 'e' option
454 Ssiz_t ePos = option.Index("e");
455 if (ePos == legoPos + 1)
456 ePos = option.Index("e", legoPos + 4);
457 fDrawErrors = ePos != kNPOS ? kTRUE : kFALSE;
458
459 option.Index("z") == kNPOS ? fDrawPalette = kFALSE : fDrawPalette = kTRUE;
460}
461
462////////////////////////////////////////////////////////////////////////////////
463///Initialize some gl state variables.
464
466{
467 glEnable(GL_DEPTH_TEST);
468 glEnable(GL_LIGHTING);
469 glEnable(GL_LIGHT0);
470 //For lego, back polygons are culled (but not for sections).
471 glEnable(GL_CULL_FACE);
472 glCullFace(GL_BACK);
473
474 glLightModeli(GL_LIGHT_MODEL_TWO_SIDE, GL_TRUE);
475}
476
477////////////////////////////////////////////////////////////////////////////////
478///Return some gl states to original values.
479
481{
482 glDisable(GL_DEPTH_TEST);
483 glDisable(GL_LIGHTING);
484 glDisable(GL_LIGHT0);
485 glDisable(GL_CULL_FACE);
486 glLightModeli(GL_LIGHT_MODEL_TWO_SIDE, GL_FALSE);
487}
488
489////////////////////////////////////////////////////////////////////////////////
490///Select method corresponding to coordinate system.
491
493{
494 //Shift plot to point of origin.
495 const Rgl::PlotTranslation trGuard(this);
496
497 switch (fCoord->GetCoordType()) {
498 case kGLCartesian:
499 return DrawLegoCartesian();
500 case kGLPolar:
501 return DrawLegoPolar();
502 case kGLCylindrical:
503 return DrawLegoCylindrical();
504 case kGLSpherical:
505 return DrawLegoSpherical();
506 default:;
507 }
508}
509
510////////////////////////////////////////////////////////////////////////////////
511///Lego in cartesian system.
512
514{
515 if (fCoord->GetCoordType() == kGLCartesian) {
517 const TGLDisableGuard cullGuard(GL_CULL_FACE);
518 DrawSections();
519 }
520
521 //const TGLDisableGuard depthTest(GL_DEPTH_TEST); //[0-0]
522
523 if (!fSelectionPass) {
524 glEnable(GL_POLYGON_OFFSET_FILL);//[0
525 glPolygonOffset(1.f, 1.f);
526 SetLegoColor();
527 if (fXOZSectionPos > fBackBox.Get3DBox()[0].Y() || fYOZSectionPos> fBackBox.Get3DBox()[0].X()) {
528 //Lego is semi-transparent if we have any sections.
529 glEnable(GL_BLEND);//[1
530 glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
531 }
532 }
533
534 //Using front point, find the correct order to draw bars from
535 //back to front (it's important only for semi-transparent lego).
536 //Only in cartesian.
537 const Int_t nX = fXEdges.size();
538 const Int_t nY = fYEdges.size();
539 const Int_t frontPoint = fBackBox.GetFrontPoint();
540 Int_t iInit = 0, jInit = 0, irInit = fCoord->GetFirstXBin(), jrInit = fCoord->GetFirstYBin();
541 const Int_t addI = frontPoint == 2 || frontPoint == 1 ? 1 : (iInit = nX - 1, irInit = fCoord->GetLastXBin(), -1);
542 const Int_t addJ = frontPoint == 2 || frontPoint == 3 ? 1 : (jInit = nY - 1, jrInit = fCoord->GetLastYBin(), -1);
543
545 if (!PreparePalette()) {
548 } else
549 fPalette.EnableTexture(GL_MODULATE);
550 }
551
554
555 for(Int_t i = iInit, ir = irInit; addI > 0 ? i < nX : i >= 0; i += addI, ir += addI) {
556 for(Int_t j = jInit, jr = jrInit; addJ > 0 ? j < nY : j >= 0; j += addJ, jr += addJ) {
557 Double_t zMax = fHist->GetBinContent(ir, jr) * fCoord->GetFactor();
558 if (!ClampZ(zMax))
559 continue;
560
561 const Int_t binID = fSelectionBase + i * fCoord->GetNYBins() + j;
562
565 else if(!fHighColor && fSelectedPart == binID)
566 glMaterialfv(GL_FRONT, GL_EMISSION, Rgl::gOrangeEmission);
567
568 if (fLegoType == kCylindricBars) {
569 Rgl::DrawCylinder(&fQuadric, fXEdges[i].first, fXEdges[i].second, fYEdges[j].first,
570 fYEdges[j].second, fMinZ, zMax);
571 } else if (fLegoType == kColorLevel && !fSelectionPass) {
572 Rgl::DrawBoxFrontTextured(fXEdges[i].first, fXEdges[i].second, fYEdges[j].first,
573 fYEdges[j].second, fMinZ, zMax, fPalette.GetTexCoord(fMinZ),
574 fPalette.GetTexCoord(zMax), frontPoint);
575 } else {
576 Rgl::DrawBoxFront(fXEdges[i].first, fXEdges[i].second, fYEdges[j].first,
577 fYEdges[j].second, fMinZ, zMax, frontPoint);
578 }
579
580 if (!fHighColor && !fSelectionPass && fSelectedPart == binID)
581 glMaterialfv(GL_FRONT, GL_EMISSION, Rgl::gNullEmission);
582 }
583 }
584
586 fPalette.DisableTexture();
587
588 //Draw outlines for non-cylindrical bars.
589 if (!fSelectionPass) {
590 glDisable(GL_POLYGON_OFFSET_FILL);//0]
591 const TGLDisableGuard lightGuard(GL_LIGHTING);//[2 - 2]
592 if (fXOZSectionPos <= fBackBox.Get3DBox()[0].Y() && fYOZSectionPos <= fBackBox.Get3DBox()[0].X())
593 glColor3d(0., 0., 0.);
594 else
595 glColor4d(0., 0., 0., 0.4);
596 glPolygonMode(GL_FRONT, GL_LINE);//[3
597
598 const TGLEnableGuard blendGuard(GL_BLEND);//[4-4] + 1]
599 glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
600 const TGLEnableGuard smoothGuard(GL_LINE_SMOOTH);//[5-5]
601 glHint(GL_LINE_SMOOTH_HINT, GL_NICEST);
602
603 for(Int_t i = iInit, ir = irInit; addI > 0 ? i < nX : i >= 0; i += addI, ir += addI) {
604 for(Int_t j = jInit, jr = jrInit; addJ > 0 ? j < nY : j >= 0; j += addJ, jr += addJ) {
605 Double_t zMax = fHist->GetBinContent(ir, jr) * fCoord->GetFactor();
606 if (!ClampZ(zMax))
607 continue;
608 if (fLegoType != kCylindricBars) {
609 Rgl::DrawBoxFront(fXEdges[i].first, fXEdges[i].second, fYEdges[j].first,
610 fYEdges[j].second, fMinZ, zMax, frontPoint);
611 }
612 if (fDrawErrors && zMax > 0.) {
613 Double_t errorZMax = (fHist->GetBinContent(ir, jr) + fHist->GetBinError(ir, jr)) * fCoord->GetFactor();
614 ClampZ(errorZMax);
615 Rgl::DrawError(fXEdges[i].first, fXEdges[i].second, fYEdges[j].first,
616 fYEdges[j].second, zMax, errorZMax);
617 }
618 }
619 }
620
621 glPolygonMode(GL_FRONT, GL_FILL);//3]
622 }
623
625 DrawPalette();
626}
627
628////////////////////////////////////////////////////////////////////////////////
629///Lego in polar system.
630
632{
633 const Int_t nX = fCosSinTableX.size() - 1;
634 const Int_t nY = fYEdges.size();
635
636 if (!fSelectionPass) {
637 SetLegoColor();
638 glEnable(GL_POLYGON_OFFSET_FILL);
639 glPolygonOffset(1.f, 1.f);
640 }
641
642 Double_t points[4][2] = {};
643
645 if (!PreparePalette()) {
648 } else
649 fPalette.EnableTexture(GL_MODULATE);
650 }
651
654
655 for(Int_t i = 0, ir = fCoord->GetFirstXBin(); i < nX; ++i, ++ir) {
656 for(Int_t j = 0, jr = fCoord->GetFirstYBin(); j < nY; ++j, ++jr) {
657 Double_t zMax = fHist->GetBinContent(ir, jr);
658 if (!ClampZ(zMax))
659 continue;
660 points[0][0] = fYEdges[j].first * fCosSinTableX[i].first;
661 points[0][1] = fYEdges[j].first * fCosSinTableX[i].second;
662 points[1][0] = fYEdges[j].second * fCosSinTableX[i].first;
663 points[1][1] = fYEdges[j].second * fCosSinTableX[i].second;
664 points[2][0] = fYEdges[j].second * fCosSinTableX[i + 1].first;
665 points[2][1] = fYEdges[j].second * fCosSinTableX[i + 1].second;
666 points[3][0] = fYEdges[j].first * fCosSinTableX[i + 1].first;
667 points[3][1] = fYEdges[j].first * fCosSinTableX[i + 1].second;
668
669 const Int_t binID = fSelectionBase + i * fCoord->GetNYBins() + j;
670
673 else if(!fHighColor && fSelectedPart == binID)
674 glMaterialfv(GL_FRONT, GL_EMISSION, Rgl::gOrangeEmission);
675
678 fPalette.GetTexCoord(zMax));
679 else
681
682 if (!fHighColor && !fSelectionPass && fSelectedPart == binID)
683 glMaterialfv(GL_FRONT, GL_EMISSION, Rgl::gNullEmission);
684 }
685 }
686
688 fPalette.DisableTexture();
689
690 //Draw outlines.
691 if (!fSelectionPass) {
692 glDisable(GL_POLYGON_OFFSET_FILL);//0]
693 const TGLDisableGuard lightGuard(GL_LIGHTING);//[2-2]
694 glColor3d(0., 0., 0.);
695 glPolygonMode(GL_FRONT, GL_LINE);//[3
696 const TGLEnableGuard blendGuard(GL_BLEND);
697 glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
698 const TGLEnableGuard smoothGuard(GL_LINE_SMOOTH);
699 glHint(GL_LINE_SMOOTH_HINT, GL_NICEST);
700
701 for(Int_t i = 0, ir = fCoord->GetFirstXBin(); i < nX; ++i, ++ir) {
702 for(Int_t j = 0, jr = fCoord->GetFirstYBin(); j < nY; ++j, ++jr) {
703 Double_t zMax = fHist->GetBinContent(ir, jr);
704 if (!ClampZ(zMax))
705 continue;
706 points[0][0] = fYEdges[j].first * fCosSinTableX[i].first;
707 points[0][1] = fYEdges[j].first * fCosSinTableX[i].second;
708 points[1][0] = fYEdges[j].second * fCosSinTableX[i].first;
709 points[1][1] = fYEdges[j].second * fCosSinTableX[i].second;
710 points[2][0] = fYEdges[j].second * fCosSinTableX[i + 1].first;
711 points[2][1] = fYEdges[j].second * fCosSinTableX[i + 1].second;
712 points[3][0] = fYEdges[j].first * fCosSinTableX[i + 1].first;
713 points[3][1] = fYEdges[j].first * fCosSinTableX[i + 1].second;
715 }
716 }
717
718 glPolygonMode(GL_FRONT, GL_FILL);//3]
719 }
720
722 DrawPalette();
723}
724
725////////////////////////////////////////////////////////////////////////////////
726///Lego in cylindrical system.
727
729{
730 const Int_t nX = fCosSinTableX.size() - 1;
731 const Int_t nY = fYEdges.size();
732 Double_t legoR = gStyle->GetLegoInnerR();
733 if (legoR > 1. || legoR < 0.)
734 legoR = 0.5;
735 const Double_t rRange = fCoord->GetZLength();
736
737 if (!fSelectionPass) {
738 SetLegoColor();
739 glEnable(GL_POLYGON_OFFSET_FILL);
740 glPolygonOffset(1.f, 1.f);
741 }
742
743 Double_t points[4][2] = {};
744 const Double_t sc = (1 - legoR) * fCoord->GetXScale();
745 legoR *= fCoord->GetXScale();
746
748 if (!PreparePalette()) {
751 } else
752 fPalette.EnableTexture(GL_MODULATE);
753 }
754
757
758 for(Int_t i = 0, ir = fCoord->GetFirstXBin(); i < nX; ++i, ++ir) {
759 for(Int_t j = 0, jr = fCoord->GetFirstYBin(); j < nY; ++j, ++jr) {
760 Double_t zMin = legoR + (fMinZ - fCoord->GetZRange().first) / rRange * sc;
761 Double_t zMax = legoR + (fHist->GetBinContent(ir, jr) - fCoord->GetZRange().first) / rRange * sc;
762 if (zMin > zMax)
763 std::swap(zMin, zMax);
764
765 points[0][0] = fCosSinTableX[i].first * zMin;
766 points[0][1] = fCosSinTableX[i].second * zMin;
767 points[1][0] = fCosSinTableX[i].first * zMax;
768 points[1][1] = fCosSinTableX[i].second * zMax;
769 points[2][0] = fCosSinTableX[i + 1].first * zMax;
770 points[2][1] = fCosSinTableX[i + 1].second * zMax;
771 points[3][0] = fCosSinTableX[i + 1].first * zMin;
772 points[3][1] = fCosSinTableX[i + 1].second * zMin;
773
774 const Int_t binID = fSelectionBase + i * fCoord->GetNYBins() + j;
775
778 else if(!fHighColor && fSelectedPart == binID)
779 glMaterialfv(GL_FRONT, GL_EMISSION, Rgl::gOrangeEmission);
780
783 fPalette.GetTexCoord(fMinZ), fPalette.GetTexCoord(fHist->GetBinContent(ir, jr)));
784 }else
785 Rgl::DrawTrapezoid(points, fYEdges[j].first, fYEdges[j].second);
786
787 if(!fSelectionPass && !fHighColor && fSelectedPart == binID)
788 glMaterialfv(GL_FRONT, GL_EMISSION, Rgl::gNullEmission);
789 }
790 }
791
793 fPalette.DisableTexture();
794
795 //Draw outlines.
796 if (!fSelectionPass) {
797 glDisable(GL_POLYGON_OFFSET_FILL);//0]
798 const TGLDisableGuard lightGuard(GL_LIGHTING);//[2-2]
799 glColor3d(0., 0., 0.);
800 glPolygonMode(GL_FRONT, GL_LINE);//[3
801
802 const TGLEnableGuard blendGuard(GL_BLEND);
803 glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
804 const TGLEnableGuard smoothGuard(GL_LINE_SMOOTH);
805 glHint(GL_LINE_SMOOTH_HINT, GL_NICEST);
806
807 for(Int_t i = 0, ir = fCoord->GetFirstXBin(); i < nX; ++i, ++ir) {
808 for(Int_t j = 0, jr = fCoord->GetFirstYBin(); j < nY; ++j, ++jr) {
809 Double_t zMin = legoR + (fMinZ - fCoord->GetZRange().first) / rRange * sc;
810 Double_t zMax = legoR + (fHist->GetBinContent(ir, jr) - fCoord->GetZRange().first) / rRange * sc;
811 if (zMin > zMax)
812 std::swap(zMin, zMax);
813
814 points[0][0] = fCosSinTableX[i].first * zMin;
815 points[0][1] = fCosSinTableX[i].second * zMin;
816 points[1][0] = fCosSinTableX[i].first * zMax;
817 points[1][1] = fCosSinTableX[i].second * zMax;
818 points[2][0] = fCosSinTableX[i + 1].first * zMax;
819 points[2][1] = fCosSinTableX[i + 1].second * zMax;
820 points[3][0] = fCosSinTableX[i + 1].first * zMin;
821 points[3][1] = fCosSinTableX[i + 1].second * zMin;
822 Rgl::DrawTrapezoid(points, fYEdges[j].first, fYEdges[j].second);
823 }
824 }
825
826 glPolygonMode(GL_FRONT, GL_FILL);//3]
827 }
828
830 DrawPalette();
831}
832
833////////////////////////////////////////////////////////////////////////////////
834///Lego in spherical system.
835
837{
838 const Int_t nX = fCosSinTableX.size() - 1;
839 const Int_t nY = fCosSinTableY.size() - 1;
840 const Double_t rRange = fCoord->GetZLength();
841 Double_t legoR = gStyle->GetLegoInnerR();
842 if (legoR > 1. || legoR < 0.)
843 legoR = 0.5;
844
845 if (!fSelectionPass) {
846 SetLegoColor();
847 glEnable(GL_POLYGON_OFFSET_FILL);
848 glPolygonOffset(1.f, 1.f);
849 }
850
851 Double_t points[8][3] = {};
852 const Double_t sc = 1 - legoR;
853
855 if (!PreparePalette()) {
858 } else
859 fPalette.EnableTexture(GL_MODULATE);
860 }
861
864
865 for(Int_t i = 0, ir = fCoord->GetFirstXBin(); i < nX; ++i, ++ir) {
866 for(Int_t j = 0, jr = fCoord->GetFirstYBin(); j < nY; ++j, ++jr) {
867 Double_t zMin = legoR + (fMinZ - fCoord->GetZRange().first) / rRange * sc;
868 Double_t zMax = legoR + (fHist->GetBinContent(ir, jr) - fCoord->GetZRange().first) / rRange * sc;
869 if (zMin > zMax)
870 std::swap(zMin, zMax);
871
872 points[4][0] = zMin * fCosSinTableY[j].second * fCosSinTableX[i].first;
873 points[4][1] = zMin * fCosSinTableY[j].second * fCosSinTableX[i].second;
874 points[4][2] = zMin * fCosSinTableY[j].first;
875 points[5][0] = zMin * fCosSinTableY[j].second * fCosSinTableX[i + 1].first;
876 points[5][1] = zMin * fCosSinTableY[j].second * fCosSinTableX[i + 1].second;
877 points[5][2] = zMin * fCosSinTableY[j].first;
878 points[6][0] = zMax * fCosSinTableY[j].second * fCosSinTableX[i + 1].first;
879 points[6][1] = zMax * fCosSinTableY[j].second * fCosSinTableX[i + 1].second;
880 points[6][2] = zMax * fCosSinTableY[j].first;
881 points[7][0] = zMax * fCosSinTableY[j].second * fCosSinTableX[i].first;
882 points[7][1] = zMax * fCosSinTableY[j].second * fCosSinTableX[i].second;
883 points[7][2] = zMax * fCosSinTableY[j].first;
884 points[0][0] = zMin * fCosSinTableY[j + 1].second * fCosSinTableX[i].first;
885 points[0][1] = zMin * fCosSinTableY[j + 1].second * fCosSinTableX[i].second;
886 points[0][2] = zMin * fCosSinTableY[j + 1].first;
887 points[1][0] = zMin * fCosSinTableY[j + 1].second * fCosSinTableX[i + 1].first;
888 points[1][1] = zMin * fCosSinTableY[j + 1].second * fCosSinTableX[i + 1].second;
889 points[1][2] = zMin * fCosSinTableY[j + 1].first;
890 points[2][0] = zMax * fCosSinTableY[j + 1].second * fCosSinTableX[i + 1].first;
891 points[2][1] = zMax * fCosSinTableY[j + 1].second * fCosSinTableX[i + 1].second;
892 points[2][2] = zMax * fCosSinTableY[j + 1].first;
893 points[3][0] = zMax * fCosSinTableY[j + 1].second * fCosSinTableX[i].first;
894 points[3][1] = zMax * fCosSinTableY[j + 1].second * fCosSinTableX[i].second;
895 points[3][2] = zMax * fCosSinTableY[j + 1].first;
896
897 const Int_t binID = fSelectionBase + i * fCoord->GetNYBins() + j;
898
901 else if(!fHighColor && fSelectedPart == binID)
902 glMaterialfv(GL_FRONT, GL_EMISSION, Rgl::gOrangeEmission);
905 fPalette.GetTexCoord(fHist->GetBinContent(ir, jr)));
906 else
908
909 if(!fHighColor && fSelectedPart == binID)
910 glMaterialfv(GL_FRONT, GL_EMISSION, Rgl::gNullEmission);
911 }
912 }
913
915 fPalette.DisableTexture();
916
917 //Draw outlines.
918 if (!fSelectionPass) {
919 glDisable(GL_POLYGON_OFFSET_FILL);//0]
920 const TGLDisableGuard lightGuard(GL_LIGHTING);//[2-2]
921 glColor3d(0., 0., 0.);
922 glPolygonMode(GL_FRONT, GL_LINE);//[3
923 const TGLEnableGuard blendGuard(GL_BLEND);
924 glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
925 const TGLEnableGuard smoothGuard(GL_LINE_SMOOTH);
926 glHint(GL_LINE_SMOOTH_HINT, GL_NICEST);
927
928 for(Int_t i = 0, ir = fCoord->GetFirstXBin(); i < nX; ++i, ++ir) {
929 for(Int_t j = 0, jr = fCoord->GetFirstYBin(); j < nY; ++j, ++jr) {
930 Double_t zMin = legoR + (fMinZ - fCoord->GetZRange().first) / rRange * sc;
931 Double_t zMax = legoR + (fHist->GetBinContent(ir, jr) - fCoord->GetZRange().first) / rRange * sc;
932 if (zMin > zMax)
933 std::swap(zMin, zMax);
934
935 points[4][0] = zMin * fCosSinTableY[j].second * fCosSinTableX[i].first;
936 points[4][1] = zMin * fCosSinTableY[j].second * fCosSinTableX[i].second;
937 points[4][2] = zMin * fCosSinTableY[j].first;
938 points[5][0] = zMin * fCosSinTableY[j].second * fCosSinTableX[i + 1].first;
939 points[5][1] = zMin * fCosSinTableY[j].second * fCosSinTableX[i + 1].second;
940 points[5][2] = zMin * fCosSinTableY[j].first;
941 points[6][0] = zMax * fCosSinTableY[j].second * fCosSinTableX[i + 1].first;
942 points[6][1] = zMax * fCosSinTableY[j].second * fCosSinTableX[i + 1].second;
943 points[6][2] = zMax * fCosSinTableY[j].first;
944 points[7][0] = zMax * fCosSinTableY[j].second * fCosSinTableX[i].first;
945 points[7][1] = zMax * fCosSinTableY[j].second * fCosSinTableX[i].second;
946 points[7][2] = zMax * fCosSinTableY[j].first;
947 points[0][0] = zMin * fCosSinTableY[j + 1].second * fCosSinTableX[i].first;
948 points[0][1] = zMin * fCosSinTableY[j + 1].second * fCosSinTableX[i].second;
949 points[0][2] = zMin * fCosSinTableY[j + 1].first;
950 points[1][0] = zMin * fCosSinTableY[j + 1].second * fCosSinTableX[i + 1].first;
951 points[1][1] = zMin * fCosSinTableY[j + 1].second * fCosSinTableX[i + 1].second;
952 points[1][2] = zMin * fCosSinTableY[j + 1].first;
953 points[2][0] = zMax * fCosSinTableY[j + 1].second * fCosSinTableX[i + 1].first;
954 points[2][1] = zMax * fCosSinTableY[j + 1].second * fCosSinTableX[i + 1].second;
955 points[2][2] = zMax * fCosSinTableY[j + 1].first;
956 points[3][0] = zMax * fCosSinTableY[j + 1].second * fCosSinTableX[i].first;
957 points[3][1] = zMax * fCosSinTableY[j + 1].second * fCosSinTableX[i].second;
958 points[3][2] = zMax * fCosSinTableY[j + 1].first;
960 }
961 }
962
963 glPolygonMode(GL_FRONT, GL_FILL);//3]
964 }
965
967 DrawPalette();
968}
969
970////////////////////////////////////////////////////////////////////////////////
971///Set lego's color.
972
974{
975 Float_t diffColor[] = {0.8f, 0.8f, 0.8f, 0.15f};
976
977 if (fLegoType != kColorLevel && fHist->GetFillColor() != kWhite)
978 if (const TColor *c = gROOT->GetColor(fHist->GetFillColor()))
979 c->GetRGB(diffColor[0], diffColor[1], diffColor[2]);
980
981 glMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, diffColor);
982 const Float_t specColor[] = {1.f, 1.f, 1.f, 1.f};
983 glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, specColor);
984 glMaterialf(GL_FRONT_AND_BACK, GL_SHININESS, 70.f);
985}
986
987////////////////////////////////////////////////////////////////////////////////
988///XOZ plane parallel section.
989
991{
992 Int_t binY = -1;
993
994 for (Int_t i = 0, e = fYEdges.size(); i < e; ++i) {
995 if (fYEdges[i].first <= fXOZSectionPos && fXOZSectionPos <= fYEdges[i].second) {
996 binY = i;
997 break;
998 }
999 }
1000
1001 if (binY >= 0) {
1002 binY += fCoord->GetFirstYBin();
1003 glColor3d(1., 0., 0.);
1004 glLineWidth(3.f);
1005 //Draw 2d hist on the profile's plane.
1006 for (UInt_t i = 0, ir = fCoord->GetFirstXBin(), e = fXEdges.size(); i < e; ++i, ++ir) {
1007 Double_t zMax = fHist->GetBinContent(Int_t(ir), binY);
1008 if (!ClampZ(zMax))
1009 continue;
1010
1011 glBegin(GL_LINE_LOOP);
1012 glVertex3d(fXEdges[i].first, fXOZSectionPos, fMinZ);
1013 glVertex3d(fXEdges[i].first, fXOZSectionPos, zMax);
1014 glVertex3d(fXEdges[i].second, fXOZSectionPos, zMax);
1015 glVertex3d(fXEdges[i].second, fXOZSectionPos, fMinZ);
1016 glEnd();
1017 }
1018
1019 glLineWidth(1.f);
1020 }
1021}
1022
1023////////////////////////////////////////////////////////////////////////////////
1024///YOZ plane parallel section.
1025
1027{
1028 Int_t binX = -1;
1029
1030 for (Int_t i = 0, e = fXEdges.size(); i < e; ++i) {
1031 if (fXEdges[i].first <= fYOZSectionPos && fYOZSectionPos <= fXEdges[i].second) {
1032 binX = i;
1033 break;
1034 }
1035 }
1036
1037 if (binX >= 0) {
1038 binX += fCoord->GetFirstXBin();//fBinsX.first;
1039 glColor3d(1., 0., 0.);
1040 glLineWidth(3.f);
1041 //Draw 2d hist on the profile's plane.
1042 for (UInt_t i = 0, ir = fCoord->GetFirstYBin(), e = fYEdges.size(); i < e; ++i, ++ir) {
1043 Double_t zMax = fHist->GetBinContent(binX, ir);
1044 if (!ClampZ(zMax))
1045 continue;
1046
1047 glBegin(GL_LINE_LOOP);
1048 glVertex3d(fYOZSectionPos, fYEdges[i].first, fMinZ);
1049 glVertex3d(fYOZSectionPos, fYEdges[i].first, zMax);
1050 glVertex3d(fYOZSectionPos, fYEdges[i].second, zMax);
1051 glVertex3d(fYOZSectionPos, fYEdges[i].second, fMinZ);
1052 glEnd();
1053 }
1054
1055 glLineWidth(1.f);
1056 }
1057}
1058
1059////////////////////////////////////////////////////////////////////////////////
1060///Empty. No such sections for lego.
1061
1063{
1064}
1065
1066////////////////////////////////////////////////////////////////////////////////
1067///Remove all sections and repaint.
1068
1070{
1071 const TGLVertex3 *frame = fBackBox.Get3DBox();
1072 if (event == kButton1Double && (fXOZSectionPos > frame[0].Y() || fYOZSectionPos > frame[0].X())) {
1073 fXOZSectionPos = frame[0].Y();
1074 fYOZSectionPos = frame[0].X();
1075 if (fBoxCut.IsActive())
1076 fBoxCut.TurnOnOff();
1077 //gGLManager->PaintSingleObject(this);
1078 if (!gVirtualX->IsCmdThread())
1079 gROOT->ProcessLineFast(Form("((TGLPlotPainter *)0x%zx)->Paint()", (size_t)this));
1080 else
1081 Paint();
1082 } else if (event == kKeyPress && (py == kKey_c || py == kKey_C)) {
1083 Info("ProcessEvent", "Box cut does not exist for lego");
1084 }
1085}
1086
1087////////////////////////////////////////////////////////////////////////////////
1088///Clamp z value.
1089
1091{
1092 if (fCoord->GetZLog())
1093 if (zVal <= 0.)
1094 return kFALSE;
1095 else
1096 zVal = TMath::Log10(zVal) * fCoord->GetZScale();
1097 else
1098 zVal *= fCoord->GetZScale();
1099
1100 const TGLVertex3 *frame = fBackBox.Get3DBox();
1101
1102 if (zVal > frame[4].Z())
1103 zVal = frame[4].Z();
1104 else if (zVal < frame[0].Z())
1105 zVal = frame[0].Z();
1106
1107 return kTRUE;
1108}
1109
1110////////////////////////////////////////////////////////////////////////////////
1111///Initialize color palette.
1112
1114{
1115 if(fMinMaxVal.first == fMinMaxVal.second)
1116 return kFALSE;//must be std::abs(fMinMaxVal.second - fMinMaxVal.first) < ...
1117
1118 //User-defined contours are disabled, to be fixed in a future.
1119 if (fHist->TestBit(TH1::kUserContour))
1120 fHist->ResetBit(TH1::kUserContour);
1121
1122 UInt_t paletteSize = gStyle->GetNumberContours();
1123 if (!paletteSize)
1124 paletteSize = 20;
1125
1126 return fPalette.GeneratePalette(paletteSize, Rgl::Range_t(fMinZ, fMinMaxVal.second));
1127}
1128
1129////////////////////////////////////////////////////////////////////////////////
1130///Draw. Palette.
1131///Originally, fCamera was never null.
1132///It can be a null now because of gl-viewer.
1133
1135{
1136 if (!fCamera) {
1137 //Thank you, gl-viewer!
1138 return;
1139 }
1140
1142
1143 glFinish();
1144
1145 fCamera->SetCamera();
1146 fCamera->Apply(fPadPhi, fPadTheta);
1147}
1148
1149////////////////////////////////////////////////////////////////////////////////
1150///Draw. Palette. Axis.
1151
1153{
1154 gVirtualX->SetDrawMode(TVirtualX::kCopy);//TCanvas by default sets in kInverse
1155 Rgl::DrawPaletteAxis(fCamera, fMinMaxVal, fCoord->GetCoordType() == kGLCartesian ? fCoord->GetZLog() : kFALSE);
1156}
@ kKeyPress
Definition Buttons.h:20
@ kButton1Double
Definition Buttons.h:24
@ kKey_C
Definition KeySymbols.h:128
@ kKey_c
Definition KeySymbols.h:160
#define c(i)
Definition RSha256.hxx:101
#define e(i)
Definition RSha256.hxx:103
char * ret
Definition Rotated.cxx:221
int Int_t
Signed integer 4 bytes (int).
Definition RtypesCore.h:59
int Ssiz_t
String size (currently int).
Definition RtypesCore.h:81
char Char_t
Character 1 byte (char).
Definition RtypesCore.h:51
unsigned int UInt_t
Unsigned integer 4 bytes (unsigned int).
Definition RtypesCore.h:60
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
constexpr Ssiz_t kNPOS
The equivalent of std::string::npos for the ROOT class TString.
Definition RtypesCore.h:131
float Float_t
Float 4 bytes (float).
Definition RtypesCore.h:71
constexpr Bool_t kTRUE
Definition RtypesCore.h:107
@ kWhite
Definition Rtypes.h:66
#define X(type, name)
void Info(const char *location, const char *msgfmt,...)
Use this function for informational messages.
Definition TError.cxx:241
@ kGLSpherical
Definition TGLUtil.h:47
@ kGLCylindrical
Definition TGLUtil.h:46
@ kGLPolar
Definition TGLUtil.h:45
@ kGLCartesian
Definition TGLUtil.h:44
#define gROOT
Definition TROOT.h:417
char * Form(const char *fmt,...)
Formats a string in a circular formatting buffer.
Definition TString.cxx:2496
externTStyle * gStyle
Definition TStyle.h:442
#define gVirtualX
Definition TVirtualX.h:375
point * points
Definition X3DBuffer.c:22
Bool_t InitGeometryCartesian()
Geometry for lego in cartesian coords.
Bool_t PreparePalette() const
Initialize color palette.
void DrawSectionXOZ() const override
XOZ plane parallel section.
void DrawSectionXOY() const override
Empty. No such sections for lego.
void DrawLegoSpherical() const
Lego in spherical system.
std::vector< Rgl::Range_t > fXEdges
void StartPan(Int_t px, Int_t py) override
User clicks on a lego with middle mouse button (middle for pad).
Bool_t InitGeometryCylindrical()
Geometry for lego in cylindrical coords.
void AddOption(const TString &stringOption) override
Parse additional options.
TGLLevelPalette fPalette
void InitGL() const override
Initialize some gl state variables.
char * GetPlotInfo(Int_t px, Int_t py) override
Obtain bin's info (i, j, value).
void DrawLegoPolar() const
Lego in polar system.
void DrawSectionYOZ() const override
YOZ plane parallel section.
void Pan(Int_t px, Int_t py) override
Move lego or section.
Bool_t ClampZ(Double_t &zVal) const
Clamp z value.
Bool_t InitGeometrySpherical()
Geometry for lego in spherical coords.
void DrawPlot() const override
Select method corresponding to coordinate system.
TGLQuadric fQuadric
TGLLegoPainter(const TGLLegoPainter &)
void DrawPalette() const
Draw.
void DrawLegoCartesian() const
Lego in cartesian system.
void SetLegoColor() const
Set lego's color.
std::vector< Rgl::Range_t > fYEdges
std::vector< CosSin_t > fCosSinTableX
Rgl::Range_t fMinMaxVal
void DeInitGL() const override
Return some gl states to original values.
void DrawLegoCylindrical() const
Lego in cylindrical system.
std::vector< CosSin_t > fCosSinTableY
Bool_t InitGeometryPolar()
Geometry for lego in polar coords.
void ProcessEvent(Int_t event, Int_t px, Int_t py) override
Remove all sections and repaint.
ELegoType fLegoType
Bool_t InitGeometry() override
Select method.
void DrawPaletteAxis() const override
Draw. Palette. Axis.
Camera for TGLPlotPainter and sub-classes.
Helper class for plot-painters holding information about axis ranges, numbers of bins and flags if ce...
void DrawSections() const
Draw sections (if any).
TGLPlotPainter(TH1 *hist, TGLPlotCamera *camera, TGLPlotCoordinates *coord, Bool_t xoySelectable, Bool_t xozSelectable, Bool_t yozSelectable)
TGLPlotPainter's ctor.
std::vector< Double_t > fZLevels
Double_t fXOYSectionPos
void RestoreModelviewMatrix() const
Double_t fXOZSectionPos
TGLPlotCoordinates * fCoord
void Paint() override
Draw lego/surf/whatever you can.
TGLPlotBox fBackBox
void SaveProjectionMatrix() const
void SaveModelviewMatrix() const
void MoveSection(Int_t px, Int_t py)
Create dynamic profile using selected plane.
TGLPlotCamera * fCamera
void RestoreProjectionMatrix() const
Double_t fYOZSectionPos
3 component (x/y/z) vertex class.
Definition TGLUtil.h:84
Double_t X() const
Definition TGLUtil.h:119
Double_t Z() const
Definition TGLUtil.h:123
Double_t Y() const
Definition TGLUtil.h:121
TH1 is the base class of all histogram classes in ROOT.
Definition TH1.h:109
@ kUserContour
User specified contour levels.
Definition TH1.h:404
Basic string class.
Definition TString.h:138
Ssiz_t Length() const
Definition TString.h:425
Ssiz_t Index(const char *pat, Ssiz_t i=0, ECaseCompare cmp=kExact) const
Definition TString.h:660
void DrawTrapezoid(const Double_t ver[][2], Double_t zMin, Double_t zMax, Bool_t color=kTRUE)
Definition TGLUtil.cxx:3347
void DrawTrapezoidTextured(const Double_t ver[][2], Double_t zMin, Double_t zMax, Double_t tMin, Double_t tMax)
In polar coordinates, box became trapezoid.
Definition TGLUtil.cxx:3417
const Float_t gNullEmission[]
Definition TGLUtil.cxx:2846
void ObjectIDToColor(Int_t objectID, Bool_t highColor)
Object id encoded as rgb triplet.
Definition TGLUtil.cxx:2890
void SetZLevels(TAxis *zAxis, Double_t zMin, Double_t zMax, Double_t zScale, std::vector< Double_t > &zLevels)
Definition TGLUtil.cxx:3819
void DrawPalette(const TGLPlotCamera *camera, const TGLLevelPalette &palette)
Draw. Palette.
void DrawPaletteAxis(const TGLPlotCamera *camera, const Range_t &minMax, Bool_t logZ)
void DrawTrapezoidTextured2(const Double_t ver[][2], Double_t zMin, Double_t zMax, Double_t tMin, Double_t tMax)
In polar coordinates, box became trapezoid.
Definition TGLUtil.cxx:3494
void DrawCylinder(TGLQuadric *quadric, Double_t xMin, Double_t xMax, Double_t yMin, Double_t yMax, Double_t zMin, Double_t zMax)
Cylinder for lego3.
Definition TGLUtil.cxx:3243
void DrawError(Double_t xMin, Double_t xMax, Double_t yMin, Double_t yMax, Double_t zMin, Double_t zMax)
Definition TGLUtil.cxx:3297
std::pair< Double_t, Double_t > Range_t
Definition TGLUtil.h:1202
void DrawBoxFront(Double_t xMin, Double_t xMax, Double_t yMin, Double_t yMax, Double_t zMin, Double_t zMax, Int_t fp)
Draws lego's bar as a 3d box.
Definition TGLUtil.cxx:3006
void DrawBoxFrontTextured(Double_t xMin, Double_t xMax, Double_t yMin, Double_t yMax, Double_t zMin, Double_t zMax, Double_t tMin, Double_t tMax, Int_t front)
Draws lego's bar as a 3d box LULULULU.
Definition TGLUtil.cxx:3133
const Float_t gOrangeEmission[]
Definition TGLUtil.cxx:2843
Short_t Max(Short_t a, Short_t b)
Returns the largest of a and b.
Definition TMathBase.h:249
Short_t Min(Short_t a, Short_t b)
Returns the smallest of a and b.
Definition TMathBase.h:197
Double_t Cos(Double_t)
Returns the cosine of an angle of x radians.
Definition TMath.h:605
constexpr Double_t Pi()
Definition TMath.h:40
Double_t Sin(Double_t)
Returns the sine of an angle of x radians.
Definition TMath.h:599
Double_t Log10(Double_t x)
Returns the common (base-10) logarithm of x.
Definition TMath.h:773
constexpr Double_t TwoPi()
Definition TMath.h:47