Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2025-01-18 10:12:02

0001 // @(#)root/gl:$Id$
0002 // Author:  Richard Maunder  25/05/2005
0003 
0004 /*************************************************************************
0005  * Copyright (C) 1995-2004, Rene Brun and Fons Rademakers.               *
0006  * All rights reserved.                                                  *
0007  *                                                                       *
0008  * For the licensing terms see $ROOTSYS/LICENSE.                         *
0009  * For the list of contributors see $ROOTSYS/README/CREDITS.             *
0010  *************************************************************************/
0011 
0012 #ifndef ROOT_TGLUtil
0013 #define ROOT_TGLUtil
0014 
0015 #include "Rtypes.h"
0016 #include "TError.h"
0017 
0018 #include <vector>
0019 #include <cmath>
0020 #include <cassert>
0021 #include <utility>
0022 
0023 class TString;
0024 class TGLBoundingBox;
0025 class TGLCamera;
0026 
0027 class TAttMarker;
0028 class TAttLine;
0029 
0030 class GLUtesselator;
0031 
0032 namespace Rgl
0033 {
0034    enum EOverlap
0035    {
0036       kInside = 0,
0037       kPartial,
0038       kOutside
0039    };
0040 }
0041 
0042 enum EGLCoordType
0043 {
0044    kGLCartesian,
0045    kGLPolar,
0046    kGLCylindrical,
0047    kGLSpherical
0048 };
0049 
0050 enum EGLPlotType
0051 {
0052    kGLLegoPlot,
0053    kGLSurfacePlot,
0054    kGLBoxPlot,
0055    kGLTF3Plot,
0056    kGLStackPlot,
0057    kGLParametricPlot,
0058    kGLIsoPlot,
0059    kGL5D,
0060    kGLTH3Composition,
0061    kGLVoxel,
0062    kGLDefaultPlot
0063 };
0064 
0065 
0066 // TODO: Split these into own h/cxx files - too long now!
0067 
0068 //////////////////////////////////////////////////////////////////////////
0069 //                                                                      //
0070 // TGLVertex3                                                           //
0071 //                                                                      //
0072 // 3 component (x/y/z) vertex class                                     //
0073 //                                                                      //
0074 // This is part of collection of utility classes for GL in TGLUtil.h/cxx//
0075 // These provide const and non-const accessors Arr() / CArr() to a GL   //
0076 // compatible internal field - so can be used directly with OpenGL C API//
0077 // calls. They are not intended to be fully featured just provide       //
0078 // minimum required.                                                    //
0079 //////////////////////////////////////////////////////////////////////////
0080 
0081 class TGLVector3; // Forward declare for Shift()
0082 
0083 class TGLVertex3
0084 {
0085 protected:
0086    // Fields
0087    Bool_t ValidIndex(UInt_t index) const { return (index < 3); }
0088    Double_t fVals[3];
0089 
0090 public:
0091    TGLVertex3();
0092    TGLVertex3(Double_t x, Double_t y, Double_t z);
0093    TGLVertex3(Double_t* v);
0094    TGLVertex3(const TGLVertex3 & other);
0095    ~TGLVertex3();
0096 
0097    Bool_t       operator == (const TGLVertex3 & rhs) const;
0098    TGLVertex3 & operator =  (const TGLVertex3 & rhs);
0099    TGLVertex3 & operator *= (Double_t f);
0100    TGLVertex3   operator -  () const;
0101    const TGLVertex3 & operator -= (const TGLVector3 & val);
0102    const TGLVertex3 & operator += (const TGLVector3 & val);
0103 
0104    // Manipulators
0105    void Fill(Double_t val);
0106    void Set(Double_t x, Double_t y, Double_t z);
0107    void Set(const Double_t* xyz);
0108    void Set(const TGLVertex3 & other);
0109    void Shift(TGLVector3 & shift);
0110    void Shift(Double_t xDelta, Double_t yDelta, Double_t zDelta);
0111    void Negate();
0112 
0113    void Minimum(const TGLVertex3 & other);
0114    void Maximum(const TGLVertex3 & other);
0115 
0116    // Accessors
0117          Double_t & operator [] (Int_t index);
0118    const Double_t & operator [] (Int_t index) const;
0119    Double_t   X() const { return fVals[0]; }
0120    Double_t & X()       { return fVals[0]; }
0121    Double_t   Y() const { return fVals[1]; }
0122    Double_t & Y()       { return fVals[1]; }
0123    Double_t   Z() const { return fVals[2]; }
0124    Double_t & Z()       { return fVals[2]; }
0125 
0126    const Double_t * CArr() const { return fVals; }
0127    Double_t *       Arr()        { return fVals; }
0128 
0129    void Dump() const;
0130 
0131    ClassDefNV(TGLVertex3,1); // GL 3 component vertex helper/wrapper class
0132 };
0133 
0134 //______________________________________________________________________________
0135 inline TGLVertex3 operator*(Double_t f, const TGLVertex3& v)
0136 {
0137    return TGLVertex3(f*v.X(), f*v.Y(), f*v.Z());
0138 }
0139 
0140 //______________________________________________________________________________
0141 inline void TGLVertex3::Negate()
0142 {
0143    fVals[0] = -fVals[0];
0144    fVals[1] = -fVals[1];
0145    fVals[2] = -fVals[2];
0146 }
0147 
0148 //______________________________________________________________________________
0149 inline Bool_t TGLVertex3::operator == (const TGLVertex3 & rhs) const
0150 {
0151    return (fVals[0] == rhs.fVals[0] && fVals[1] == rhs.fVals[1] && fVals[2] == rhs.fVals[2]);
0152 }
0153 
0154 //______________________________________________________________________________
0155 inline TGLVertex3 & TGLVertex3::operator = (const TGLVertex3 & rhs)
0156 {
0157    // Check for self-assignment
0158    if (this != &rhs) {
0159       Set(rhs);
0160    }
0161    return *this;
0162 }
0163 
0164 // operator -= & operator += inline needs to be defered until full TGLVector3 definition
0165 
0166 //______________________________________________________________________________
0167 inline TGLVertex3 TGLVertex3::operator - () const
0168 {
0169    return TGLVertex3(-fVals[0], -fVals[1], -fVals[2]);
0170 }
0171 
0172 //______________________________________________________________________________
0173 inline TGLVertex3& TGLVertex3::operator *= (Double_t f)
0174 {
0175    fVals[0] *= f;
0176    fVals[1] *= f;
0177    fVals[2] *= f;
0178    return *this;
0179 }
0180 
0181 //______________________________________________________________________________
0182 inline Double_t & TGLVertex3::operator [] (Int_t index)
0183 {
0184    /*if (!ValidIndex(index)) {
0185       assert(kFALSE);
0186       return fVals[0];
0187    } else {*/
0188       return fVals[index];
0189    //}
0190 }
0191 
0192 //______________________________________________________________________________
0193 inline const Double_t& TGLVertex3::operator [] (Int_t index) const
0194 {
0195    /*if (!ValidIndex(index)) {
0196       assert(kFALSE);
0197       return fVals[0];
0198    } else {*/
0199       return fVals[index];
0200    //}
0201 }
0202 
0203 //______________________________________________________________________________
0204 inline void TGLVertex3::Fill(Double_t val)
0205 {
0206    Set(val,val,val);
0207 }
0208 
0209 //______________________________________________________________________________
0210 inline void TGLVertex3::Set(Double_t x, Double_t y, Double_t z)
0211 {
0212    fVals[0]=x;
0213    fVals[1]=y;
0214    fVals[2]=z;
0215 }
0216 
0217 //______________________________________________________________________________
0218 inline void TGLVertex3::Set(const Double_t* xyz)
0219 {
0220    fVals[0]=xyz[0];
0221    fVals[1]=xyz[1];
0222    fVals[2]=xyz[2];
0223 }
0224 
0225 //______________________________________________________________________________
0226 inline void TGLVertex3::Set(const TGLVertex3 & other)
0227 {
0228    fVals[0]=other.fVals[0];
0229    fVals[1]=other.fVals[1];
0230    fVals[2]=other.fVals[2];
0231 }
0232 
0233 
0234 //////////////////////////////////////////////////////////////////////////
0235 //                                                                      //
0236 // TGLVector3                                                           //
0237 //                                                                      //
0238 // 3 component (x/y/z) vector class                                     //
0239 //                                                                      //
0240 // This is part of collection of utility classes for GL in TGLUtil.h/cxx//
0241 // These provide const and non-const accessors Arr() / CArr() to a GL   //
0242 // compatible internal field - so can be used directly with OpenGL C API//
0243 // calls. They are not intended to be fully featured just provide       //
0244 // minimum required.                                                    //
0245 //////////////////////////////////////////////////////////////////////////
0246 
0247 class TGLVector3 : public TGLVertex3
0248 {
0249 public:
0250    TGLVector3() = default;
0251    TGLVector3(Double_t x, Double_t y, Double_t z);
0252    TGLVector3(const Double_t *src);
0253 
0254    TGLVector3& operator = (const TGLVertex3& v)
0255    { fVals[0] = v[0]; fVals[1] = v[1]; fVals[2] = v[2]; return *this; }
0256 
0257    TGLVector3 & operator /= (Double_t val);
0258    TGLVector3   operator -  () const;
0259 
0260    Double_t Mag() const;
0261    void     Normalise();
0262 
0263    ClassDefNV(TGLVector3,1); // GL 3 component vector helper/wrapper class
0264 };
0265 
0266 // Inline for TGLVertex3 requiring full TGLVector definition
0267 //______________________________________________________________________________
0268 inline const TGLVertex3 & TGLVertex3::operator -= (const TGLVector3 & vec)
0269 {
0270    fVals[0] -= vec[0]; fVals[1] -= vec[1]; fVals[2] -= vec[2];
0271    return *this;
0272 }
0273 
0274 // Inline for TGLVertex3 requiring full TGLVector definition
0275 //______________________________________________________________________________
0276 inline const TGLVertex3 & TGLVertex3::operator += (const TGLVector3 & vec)
0277 {
0278    fVals[0] += vec[0]; fVals[1] += vec[1]; fVals[2] += vec[2];
0279    return *this;
0280 }
0281 
0282 //______________________________________________________________________________
0283 inline TGLVector3 & TGLVector3::operator /= (Double_t val)
0284 {
0285    fVals[0] /= val;
0286    fVals[1] /= val;
0287    fVals[2] /= val;
0288    return *this;
0289 }
0290 
0291 //______________________________________________________________________________
0292 inline TGLVector3 TGLVector3::operator - () const
0293 {
0294    return TGLVector3(-fVals[0], -fVals[1], -fVals[2]);
0295 }
0296 
0297 //______________________________________________________________________________
0298 inline Double_t TGLVector3::Mag() const
0299 {
0300    return std::sqrt(fVals[0]*fVals[0] + fVals[1]*fVals[1] + fVals[2]*fVals[2]);
0301 }
0302 
0303 //______________________________________________________________________________
0304 inline void TGLVector3::Normalise()
0305 {
0306    Double_t mag = Mag();
0307    if ( mag == 0.0 ) {
0308       Error("TGLVector3::Normalise", "vector has zero magnitude");
0309       return;
0310    }
0311    fVals[0] /= mag;
0312    fVals[1] /= mag;
0313    fVals[2] /= mag;
0314 }
0315 
0316 //______________________________________________________________________________
0317 inline Double_t Dot(const TGLVector3 & v1, const TGLVector3 & v2)
0318 {
0319    return v1[0]*v2[0] + v1[1]*v2[1] + v1[2]*v2[2];
0320 }
0321 
0322 //______________________________________________________________________________
0323 inline TGLVector3 Cross(const TGLVector3 & v1, const TGLVector3 & v2)
0324 {
0325     return TGLVector3(v1[1]*v2[2] - v2[1]*v1[2],
0326                       v1[2]*v2[0] - v2[2]*v1[0],
0327                       v1[0]*v2[1] - v2[0]*v1[1]);
0328 }
0329 
0330 //______________________________________________________________________________
0331 inline const TGLVector3 operator / (const TGLVector3 & vec, Double_t val)
0332 {
0333    return TGLVector3(vec[0] / val, vec[1] / val, vec[2] / val);
0334 }
0335 
0336 //______________________________________________________________________________
0337 inline const TGLVector3 operator * (const TGLVector3 & vec, Double_t val)
0338 {
0339    return TGLVector3(vec[0] * val, vec[1] * val, vec[2] * val);
0340 }
0341 
0342 //______________________________________________________________________________
0343 // Vertex + Vector => Vertex
0344 inline TGLVertex3 operator + (const TGLVertex3 & vertex1, const TGLVector3 & vertex2)
0345 {
0346    return TGLVertex3(vertex1[0] + vertex2[0], vertex1[1] + vertex2[1], vertex1[2] + vertex2[2]);
0347 }
0348 
0349 //______________________________________________________________________________
0350 // Vertex - Vertex => Vector
0351 inline TGLVector3 operator - (const TGLVertex3 & vertex1, const TGLVertex3 & vertex2)
0352 {
0353    return TGLVector3(vertex1[0] - vertex2[0], vertex1[1] - vertex2[1], vertex1[2] - vertex2[2]);
0354 }
0355 
0356 //______________________________________________________________________________
0357 // Vector + Vector => Vector
0358 inline TGLVector3 operator + (const TGLVector3 & vector1, const TGLVector3 & vector2)
0359 {
0360    return TGLVector3(vector1[0] + vector2[0], vector1[1] + vector2[1], vector1[2] + vector2[2]);
0361 }
0362 
0363 //______________________________________________________________________________
0364 // Vector - Vector => Vector
0365 inline TGLVector3 operator - (const TGLVector3 & vector1, const TGLVector3 & vector2)
0366 {
0367    return TGLVector3(vector1[0] - vector2[0], vector1[1] - vector2[1], vector1[2] - vector2[2]);
0368 }
0369 
0370 //______________________________________________________________________________
0371 // Dot-product
0372 inline Double_t operator * (const TGLVector3 & a, const TGLVector3 & b)
0373 {
0374    return a[0]*b[0] + a[1]*b[1] + a[2]*b[2];
0375 }
0376 
0377 //////////////////////////////////////////////////////////////////////////
0378 //                                                                      //
0379 // TGLLine3                                                             //
0380 //                                                                      //
0381 // 3D space, fixed length, line class, with direction / length 'vector',//
0382 // passing through point 'vertex'. Just wraps a TGLVector3 / TGLVertex3 //
0383 // pair.                                                                //
0384 //////////////////////////////////////////////////////////////////////////
0385 
0386 class TGLLine3
0387 {
0388 private:
0389    // Fields
0390    TGLVertex3 fVertex; //! Start vertex of line
0391    TGLVector3 fVector; //! Vector of line from fVertex
0392 
0393 public:
0394    TGLLine3(const TGLVertex3 & start, const TGLVertex3 & end);
0395    TGLLine3(const TGLVertex3 & start, const TGLVector3 & vector);
0396    ~TGLLine3() = default;
0397 
0398    void Set(const TGLVertex3 & start, const TGLVertex3 & end);
0399    void Set(const TGLVertex3 & start, const TGLVector3 & vector);
0400 
0401    // Bitwise copy constructor and = operator are fine
0402 
0403    // Accessors
0404    const TGLVertex3 & Start()  const { return fVertex; }
0405    const TGLVertex3   End()    const { return fVertex + fVector; }
0406    const TGLVector3 & Vector() const { return fVector; }
0407 
0408    // Debug
0409    void Draw() const;
0410 
0411    ClassDefNV(TGLLine3,0); // GL line wrapper class
0412 };
0413 
0414 //////////////////////////////////////////////////////////////////////////
0415 //                                                                      //
0416 // TGLRect                                                              //
0417 //                                                                      //
0418 // Viewport (pixel base) 2D rectangle class                             //
0419 //////////////////////////////////////////////////////////////////////////
0420 
0421 class TGLRect
0422 {
0423 private:
0424    // Fields
0425    Int_t    fX, fY;           //! Corner
0426    Int_t    fWidth, fHeight;  //! Positive width/height
0427 
0428 public:
0429    TGLRect();
0430    TGLRect(Int_t x, Int_t y, Int_t width, Int_t height);
0431    TGLRect(Int_t x, Int_t y, UInt_t width, UInt_t height);
0432    virtual ~TGLRect();
0433 
0434    // Bitwise copy const & =op are ok at present
0435 
0436    // Manipulators
0437    void Set(Int_t x, Int_t y, Int_t width, Int_t height);
0438    void SetCorner(Int_t x, Int_t y);
0439    void Offset(Int_t dX, Int_t dY);
0440    void Expand(Int_t x, Int_t y);
0441 
0442    // Accessors
0443    const Int_t* CArr() const { return &fX; }
0444          Int_t* CArr()       { return &fX; }
0445 
0446    Int_t    X()       const { return fX; }
0447    Int_t &  X()             { return fX; }
0448    Int_t    Y()       const { return fY; }
0449    Int_t &  Y()             { return fY; }
0450    Int_t    Width()   const { return fWidth; }
0451    Int_t &  Width()         { return fWidth; }
0452    Int_t    Height()  const { return fHeight; }
0453    Int_t &  Height()        { return fHeight; }
0454    Int_t    CenterX() const { return fX + fWidth/2; }
0455    Int_t    CenterY() const { return fY + fHeight/2; }
0456    Int_t    Left()    const { return fX; }
0457    Int_t    Right()   const { return fX + fWidth; }
0458    Int_t    Top()     const { return fY; }
0459    Int_t    Bottom()  const { return fY + fHeight; }
0460 
0461    Int_t Diagonal() const;
0462    Int_t Longest() const;
0463 
0464    Double_t Aspect() const;
0465    Rgl::EOverlap Overlap(const TGLRect & other) const;
0466 
0467    ClassDef(TGLRect,0); // GL rect helper/wrapper class
0468 };
0469 
0470 //______________________________________________________________________________
0471 inline void TGLRect::Set(Int_t x, Int_t y, Int_t width, Int_t height)
0472 {
0473    fX = x;
0474    fY = y;
0475    fWidth = width;
0476    fHeight = height;
0477 }
0478 
0479 //______________________________________________________________________________
0480 inline void TGLRect::SetCorner(Int_t x, Int_t y)
0481 {
0482    fX = x;
0483    fY = y;
0484 }
0485 
0486 //______________________________________________________________________________
0487 inline void TGLRect::Offset(Int_t dX, Int_t dY)
0488 {
0489    fX += dX;
0490    fY += dY;
0491 }
0492 
0493 //______________________________________________________________________________
0494 inline Int_t TGLRect::Longest() const
0495 {
0496    return fWidth > fHeight ? fWidth : fHeight;
0497 }
0498 
0499 //______________________________________________________________________________
0500 inline Double_t TGLRect::Aspect() const
0501 {
0502    // Return aspect ratio (width/height)
0503    if (fHeight == 0) {
0504       return 0.0;
0505    } else {
0506       return static_cast<Double_t>(fWidth) / static_cast<Double_t>(fHeight);
0507    }
0508 }
0509 
0510 //////////////////////////////////////////////////////////////////////////
0511 //                                                                      //
0512 // TGLPlane                                                             //
0513 //                                                                      //
0514 // 3D plane class - of format Ax + By + Cz + D = 0                      //
0515 //                                                                      //
0516 // This is part of collection of simple utility classes for GL only in  //
0517 // TGLUtil.h/cxx. These provide const and non-const accessors Arr() &   //
0518 // CArr() to a GL compatible internal field - so can be used directly   //
0519 // with OpenGL C API calls - which TVector3 etc cannot (easily).        //
0520 // They are not intended to be fully featured just provide minimum      //
0521 // required.                                                            //
0522 //////////////////////////////////////////////////////////////////////////
0523 
0524 class TGLPlane
0525 {
0526 private:
0527    // Fields
0528    Double_t fVals[4];
0529 
0530    // Methods
0531    void Normalise();
0532 
0533 public:
0534    TGLPlane();
0535    TGLPlane(const TGLPlane & other);
0536    TGLPlane(Double_t a, Double_t b, Double_t c, Double_t d);
0537    TGLPlane(Double_t eq[4]);
0538    TGLPlane(const TGLVector3 & norm, const TGLVertex3 & point);
0539    TGLPlane(const TGLVertex3 & p1, const TGLVertex3 & p2, const TGLVertex3 & p3);
0540    ~TGLPlane() = default;
0541 
0542    TGLPlane &operator=(const TGLPlane &src);
0543 
0544    // Manipulators
0545    void Set(const TGLPlane & other);
0546    void Set(Double_t a, Double_t b, Double_t c, Double_t d);
0547    void Set(Double_t eq[4]);
0548    void Set(const TGLVector3 & norm, const TGLVertex3 & point);
0549    void Set(const TGLVertex3 & p1, const TGLVertex3 & p2, const TGLVertex3 & p3);
0550    void Negate();
0551 
0552    // Accessors
0553    Double_t A() const { return fVals[0]; }
0554    Double_t B() const { return fVals[1]; }
0555    Double_t C() const { return fVals[2]; }
0556    Double_t D() const { return fVals[3]; }
0557 
0558    TGLVector3 Norm() const { return TGLVector3( fVals[0], fVals[1], fVals[2]); }
0559    Double_t DistanceTo(const TGLVertex3 & vertex) const;
0560    TGLVertex3 NearestOn(const TGLVertex3 & point) const;
0561 
0562    // Internal data accessors - for GL API
0563    const Double_t * CArr() const { return fVals; }
0564    Double_t * Arr() { return fVals; }
0565 
0566    void Dump() const;
0567 
0568    ClassDefNV(TGLPlane,0); // GL plane helper/wrapper class
0569 };
0570 
0571 typedef std::vector<TGLPlane>                 TGLPlaneSet_t;
0572 typedef std::vector<TGLPlane>::iterator       TGLPlaneSet_i;
0573 typedef std::vector<TGLPlane>::const_iterator TGLPlaneSet_ci;
0574 
0575 // Some free functions for planes
0576 std::pair<Bool_t, TGLLine3>   Intersection(const TGLPlane & p1, const TGLPlane & p2);
0577 std::pair<Bool_t, TGLVertex3> Intersection(const TGLPlane & p1, const TGLPlane & p2, const TGLPlane & p3);
0578 std::pair<Bool_t, TGLVertex3> Intersection(const TGLPlane & plane, const TGLLine3 & line, Bool_t extend);
0579 
0580 
0581 //////////////////////////////////////////////////////////////////////////
0582 //                                                                      //
0583 // TGLMatrix                                                            //
0584 //                                                                      //
0585 // 16 component (4x4) transform matrix - column MAJOR as per GL.        //
0586 // Provides limited support for adjusting the translation, scale and    //
0587 // rotation components.                                                 //
0588 //                                                                      //
0589 // This is part of collection of simple utility classes for GL only in  //
0590 // TGLUtil.h/cxx. These provide const and non-const accessors Arr() &   //
0591 // CArr() to a GL compatible internal field - so can be used directly   //
0592 // with OpenGL C API calls - which TVector3 etc cannot (easily).        //
0593 // They are not intended to be fully featured just provide minimum      //
0594 // required.                                                            //
0595 //////////////////////////////////////////////////////////////////////////
0596 
0597 class TGLMatrix
0598 {
0599 private:
0600    // Fields
0601    Double_t fVals[16]; // Column MAJOR as per OGL
0602 
0603    // Methods
0604    Bool_t ValidIndex(UInt_t index) const { return (index < 16); }
0605 
0606 public:
0607    TGLMatrix();
0608    TGLMatrix(Double_t x, Double_t y, Double_t z);
0609    TGLMatrix(const TGLVertex3 & translation);
0610    TGLMatrix(const TGLVertex3 & origin, const TGLVector3 & zAxis, const TGLVector3 & xAxis);
0611    TGLMatrix(const TGLVertex3 & origin, const TGLVector3 & zAxis);
0612    TGLMatrix(const Double_t vals[16]);
0613    TGLMatrix(const TGLMatrix & other);
0614    virtual ~TGLMatrix();
0615 
0616    // Operators
0617    TGLMatrix & operator =(const TGLMatrix & rhs);
0618    Double_t  & operator [] (Int_t index);
0619    Double_t    operator [] (Int_t index) const;
0620 
0621    void MultRight(const TGLMatrix & rhs);
0622    void MultLeft (const TGLMatrix & lhs);
0623    TGLMatrix & operator*=(const TGLMatrix & rhs) { MultRight(rhs); return *this; }
0624 
0625    // Manipulators
0626    void Set(const TGLVertex3 & origin, const TGLVector3 & zAxis, const TGLVector3 & xAxis = nullptr);
0627    void Set(const Double_t vals[16]);
0628    void SetIdentity();
0629 
0630    void SetTranslation(Double_t x, Double_t y, Double_t z);
0631    void SetTranslation(const TGLVertex3 & translation);
0632 
0633    void Translate(const TGLVector3 & vect);
0634    void MoveLF(Int_t ai, Double_t amount);
0635    void Move3LF(Double_t x, Double_t y, Double_t z);
0636 
0637    void Scale(const TGLVector3 & scale);
0638    void Rotate(const TGLVertex3 & pivot, const TGLVector3 & axis, Double_t angle);
0639    void RotateLF(Int_t i1, Int_t i2, Double_t amount);
0640    void RotatePF(Int_t i1, Int_t i2, Double_t amount);
0641    void TransformVertex(TGLVertex3 & vertex) const;
0642    void Transpose3x3();
0643    Double_t Invert();
0644 
0645    // Accesors
0646    TGLVector3  GetTranslation() const;
0647    TGLVector3  GetScale() const;
0648    Bool_t      IsScalingForRender() const;
0649 
0650    void SetBaseVec(Int_t b, Double_t x, Double_t y, Double_t z);
0651    void SetBaseVec(Int_t b, const TGLVector3& v);
0652    void SetBaseVec(Int_t b, Double_t* x);
0653 
0654    TGLVector3 GetBaseVec(Int_t b) const;
0655    void       GetBaseVec(Int_t b, TGLVector3& v) const;
0656    void       GetBaseVec(Int_t b, Double_t* x) const;
0657 
0658    TGLVector3 Multiply(const TGLVector3& v, Double_t w=1) const;
0659    TGLVector3 Rotate(const TGLVector3& v) const;
0660    void       MultiplyIP(TGLVector3& v, Double_t w=1) const;
0661    void       RotateIP(TGLVector3& v) const;
0662 
0663    // Internal data accessors - for GL API
0664    const Double_t * CArr() const { return fVals; }
0665    Double_t * Arr() { return fVals; }
0666 
0667    void Dump() const;
0668 
0669    ClassDef(TGLMatrix,1); // GL matrix helper/wrapper class
0670 };
0671 
0672 //______________________________________________________________________________
0673 inline TGLMatrix & TGLMatrix::operator =(const TGLMatrix & rhs)
0674 {
0675    // Check for self-assignment
0676    if (this != &rhs) {
0677       Set(rhs.fVals);
0678    }
0679    return *this;
0680 }
0681 
0682 //______________________________________________________________________________
0683 inline Double_t & TGLMatrix::operator [] (Int_t index)
0684 {
0685    /*if (!ValidIndex(index)) {
0686       assert(kFALSE);
0687       return fVals[0];
0688    } else {*/
0689       return fVals[index];
0690    //}
0691 }
0692 
0693 //______________________________________________________________________________
0694 inline Double_t TGLMatrix::operator [] (Int_t index) const
0695 {
0696    /*if (!ValidIndex(index)) {
0697       assert(kFALSE);
0698       return fVals[0];
0699    } else {*/
0700       return fVals[index];
0701    //}
0702 }
0703 
0704 //______________________________________________________________________________
0705 inline TGLMatrix operator * (const TGLMatrix & lhs, const TGLMatrix & rhs)
0706 {
0707    TGLMatrix res;
0708 
0709    res[ 0] = rhs[ 0] * lhs[ 0] + rhs[ 1] * lhs[ 4] + rhs[ 2] * lhs[ 8] + rhs[ 3] * lhs[12];
0710    res[ 1] = rhs[ 0] * lhs[ 1] + rhs[ 1] * lhs[ 5] + rhs[ 2] * lhs[ 9] + rhs[ 3] * lhs[13];
0711    res[ 2] = rhs[ 0] * lhs[ 2] + rhs[ 1] * lhs[ 6] + rhs[ 2] * lhs[10] + rhs[ 3] * lhs[14];
0712    res[ 3] = rhs[ 0] * lhs[ 3] + rhs[ 1] * lhs[ 7] + rhs[ 2] * lhs[11] + rhs[ 3] * lhs[15];
0713 
0714    res[ 4] = rhs[ 4] * lhs[ 0] + rhs[ 5] * lhs[ 4] + rhs[ 6] * lhs[ 8] + rhs[ 7] * lhs[12];
0715    res[ 5] = rhs[ 4] * lhs[ 1] + rhs[ 5] * lhs[ 5] + rhs[ 6] * lhs[ 9] + rhs[ 7] * lhs[13];
0716    res[ 6] = rhs[ 4] * lhs[ 2] + rhs[ 5] * lhs[ 6] + rhs[ 6] * lhs[10] + rhs[ 7] * lhs[14];
0717    res[ 7] = rhs[ 4] * lhs[ 3] + rhs[ 5] * lhs[ 7] + rhs[ 6] * lhs[11] + rhs[ 7] * lhs[15];
0718 
0719    res[ 8] = rhs[ 8] * lhs[ 0] + rhs[ 9] * lhs[ 4] + rhs[10] * lhs[ 8] + rhs[11] * lhs[12];
0720    res[ 9] = rhs[ 8] * lhs[ 1] + rhs[ 9] * lhs[ 5] + rhs[10] * lhs[ 9] + rhs[11] * lhs[13];
0721    res[10] = rhs[ 8] * lhs[ 2] + rhs[ 9] * lhs[ 6] + rhs[10] * lhs[10] + rhs[11] * lhs[14];
0722    res[11] = rhs[ 8] * lhs[ 3] + rhs[ 9] * lhs[ 7] + rhs[10] * lhs[11] + rhs[11] * lhs[15];
0723 
0724    res[12] = rhs[12] * lhs[ 0] + rhs[13] * lhs[ 4] + rhs[14] * lhs[ 8] + rhs[15] * lhs[12];
0725    res[13] = rhs[12] * lhs[ 1] + rhs[13] * lhs[ 5] + rhs[14] * lhs[ 9] + rhs[15] * lhs[13];
0726    res[14] = rhs[12] * lhs[ 2] + rhs[13] * lhs[ 6] + rhs[14] * lhs[10] + rhs[15] * lhs[14];
0727    res[15] = rhs[12] * lhs[ 3] + rhs[13] * lhs[ 7] + rhs[14] * lhs[11] + rhs[15] * lhs[15];
0728 
0729    return res;
0730 }
0731 
0732 //______________________________________________________________________________
0733 inline void TGLMatrix::SetBaseVec(Int_t b, Double_t x, Double_t y, Double_t z)
0734 {
0735    Double_t* C = fVals + 4*--b;
0736    C[0] = x; C[1] = y; C[2] = z;
0737 }
0738 
0739 //______________________________________________________________________________
0740 inline void TGLMatrix::SetBaseVec(Int_t b, const TGLVector3& v)
0741 {
0742    Double_t* C = fVals + 4*--b;
0743    C[0] = v[0]; C[1] = v[1]; C[2] = v[2];
0744 }
0745 
0746 //______________________________________________________________________________
0747 inline void TGLMatrix::SetBaseVec(Int_t b, Double_t* x)
0748 {
0749    Double_t* C = fVals + 4*--b;
0750    C[0] = x[0]; C[1] = x[1]; C[2] = x[2];
0751 }
0752 
0753 //______________________________________________________________________________
0754 inline TGLVector3 TGLMatrix::GetBaseVec(Int_t b) const
0755 {
0756    return TGLVector3(&fVals[4*--b]);
0757 }
0758 
0759 //______________________________________________________________________________
0760 inline void TGLMatrix::GetBaseVec(Int_t b, TGLVector3& v) const
0761 {
0762    const Double_t* C = fVals + 4*--b;
0763    v[0] = C[0]; v[1] = C[1]; v[2] = C[2];
0764 }
0765 
0766 //______________________________________________________________________________
0767 inline void TGLMatrix::GetBaseVec(Int_t b, Double_t* x) const
0768 {
0769    const Double_t* C = fVals + 4*--b;
0770    x[0] = C[0], x[1] = C[1], x[2] = C[2];
0771 }
0772 
0773 
0774 //////////////////////////////////////////////////////////////////////////
0775 //
0776 // TGLColor
0777 //
0778 // Encapsulate color in preferred GL format - UChar_t RGBA array.
0779 // Color index is also cached for easier interfacing with the
0780 // traditional ROOT graphics.
0781 //
0782 //////////////////////////////////////////////////////////////////////////
0783 
0784 class TGLColor
0785 {
0786 protected:
0787    UChar_t         fRGBA[4];
0788    mutable Short_t fIndex;
0789 
0790 public:
0791    TGLColor();
0792    TGLColor(Int_t r, Int_t g, Int_t b, Int_t a=255);
0793    TGLColor(Float_t r, Float_t g, Float_t b, Float_t a=1);
0794    TGLColor(Color_t color_index, Char_t transparency=0);
0795    TGLColor(const TGLColor& c);
0796 
0797    TGLColor& operator=(const TGLColor& c);
0798 
0799    UChar_t*        Arr()       { return fRGBA; }
0800    const UChar_t* CArr() const { return fRGBA; }
0801 
0802    UChar_t GetRed()   const { return fRGBA[0]; }
0803    UChar_t GetGreen() const { return fRGBA[1]; }
0804    UChar_t GetBlue()  const { return fRGBA[2]; }
0805    UChar_t GetAlpha() const { return fRGBA[3]; }
0806 
0807    Color_t GetColorIndex()   const;
0808    Char_t  GetTransparency() const;
0809 
0810    void SetRed(Int_t v)   { fRGBA[0] = v; }
0811    void SetGreen(Int_t v) { fRGBA[1] = v; }
0812    void SetBlue(Int_t v)  { fRGBA[2] = v; }
0813    void SetAlpha(Int_t v) { fRGBA[3] = v; }
0814 
0815    void SetColor(Int_t r, Int_t g, Int_t b, Int_t a=255);
0816    void SetColor(Float_t r, Float_t g, Float_t b, Float_t a=1);
0817    void SetColor(Color_t color_index);
0818    void SetColor(Color_t color_index, Char_t transparency);
0819    void SetTransparency(Char_t transparency);
0820 
0821    TString AsString() const;
0822 
0823    ClassDefNV(TGLColor, 0); // Color in preferred GL format - RGBA.
0824 };
0825 
0826 
0827 //////////////////////////////////////////////////////////////////////////
0828 //
0829 // TGLColorSet
0830 //
0831 // A collection of colors used for OpenGL rendering.
0832 //
0833 //////////////////////////////////////////////////////////////////////////
0834 
0835 class TGLColorSet
0836 {
0837 protected:
0838    TGLColor        fBackground;
0839    TGLColor        fForeground;
0840    TGLColor        fOutline;
0841    TGLColor        fMarkup;
0842    TGLColor        fSelection[5];   // Colors for shape-selection-levels
0843 
0844 public:
0845    TGLColorSet();
0846    TGLColorSet(const TGLColorSet& s);
0847    ~TGLColorSet() = default;
0848 
0849    TGLColorSet& operator=(const TGLColorSet& s);
0850 
0851    TGLColor& Background()       { return fBackground; }
0852    TGLColor& Foreground()       { return fForeground; }
0853    TGLColor& Outline()          { return fOutline; }
0854    TGLColor& Markup()           { return fMarkup;  }
0855    TGLColor& Selection(Int_t i) { return fSelection[i]; }
0856 
0857    const TGLColor& Background()       const { return fBackground; }
0858    const TGLColor& Foreground()       const { return fForeground; }
0859    const TGLColor& Outline()          const { return fOutline; }
0860    const TGLColor& Markup()           const { return fMarkup;  }
0861    const TGLColor& Selection(Int_t i) const { return fSelection[i]; }
0862 
0863    void StdDarkBackground();
0864    void StdLightBackground();
0865 
0866    ClassDefNV(TGLColorSet, 0); // Collection of colors used for GL rendering.
0867 };
0868 
0869 //////////////////////////////////////////////////////////////////////////
0870 //                                                                      //
0871 // TGLUtil                                                              //
0872 //                                                                      //
0873 // Wrapper class for various misc static functions - error checking,    //
0874 // draw helpers etc.                                                    //
0875 //                                                                      //
0876 //////////////////////////////////////////////////////////////////////////
0877 
0878 class TGLUtil
0879 {
0880 public:
0881    class TColorLocker
0882    {
0883    public:
0884       TColorLocker()          { LockColor();   }
0885       virtual ~TColorLocker() { UnlockColor(); }
0886 
0887       ClassDef(TColorLocker,0); // Lock/unlock color in constructor/destructor.
0888    };
0889 
0890    class TDrawQualityModifier
0891    {
0892       Int_t fOldQuality;
0893    public:
0894       TDrawQualityModifier(Int_t dq) :
0895       fOldQuality(GetDrawQuality()) {SetDrawQuality(dq); }
0896 
0897       virtual ~TDrawQualityModifier()
0898       { SetDrawQuality(fOldQuality); }
0899 
0900       ClassDef(TDrawQualityModifier,0); // Set/restore draw quality in constructor/destructor.
0901    };
0902 
0903    class TDrawQualityScaler
0904    {
0905       Int_t fOldQuality;
0906    public:
0907       TDrawQualityScaler(Float_t fac) :
0908       fOldQuality(GetDrawQuality()) {SetDrawQuality((Int_t)(fac*fOldQuality)); }
0909 
0910       virtual ~TDrawQualityScaler()
0911       { SetDrawQuality(fOldQuality); }
0912 
0913       ClassDef(TDrawQualityScaler,0); // Multiply/restore draw quality in constructor/destructor.
0914    };
0915 
0916 private:
0917    static UInt_t fgDefaultDrawQuality;
0918    static UInt_t fgDrawQuality;
0919 
0920    static UInt_t fgColorLockCount;
0921 
0922    static Float_t fgPointSize;
0923    static Float_t fgLineWidth;
0924    static Float_t fgPointSizeScale;
0925    static Float_t fgLineWidthScale;
0926 
0927    static Float_t fgScreenScalingFactor;
0928    static Float_t fgPointLineScalingFactor;
0929    static Int_t   fgPickingRadius;
0930 
0931    static Float_t fgSimpleAxisWidthScale;
0932    static Float_t fgSimpleAxisBBoxScale;
0933 
0934    TGLUtil(const TGLUtil&) = delete;
0935    TGLUtil& operator=(const TGLUtil&) = delete;
0936 
0937 public:
0938    virtual ~TGLUtil() {}
0939    static void InitializeIfNeeded();
0940 
0941    // Error checking
0942    static Int_t  CheckError(const char * loc);
0943 
0944    // Polygon tesselator for direct drawing
0945    static GLUtesselator* GetDrawTesselator3fv();
0946    static GLUtesselator* GetDrawTesselator4fv();
0947    static GLUtesselator* GetDrawTesselator3dv();
0948    static GLUtesselator* GetDrawTesselator4dv();
0949 
0950    // Some simple shape drawing utils
0951    enum ELineHeadShape { kLineHeadNone, kLineHeadArrow, kLineHeadBox };
0952    enum EAxesType      { kAxesNone, kAxesEdge, kAxesOrigin };
0953 
0954    static UInt_t GetDrawQuality();
0955    static void   SetDrawQuality(UInt_t dq);
0956    static void   ResetDrawQuality();
0957    static UInt_t GetDefaultDrawQuality();
0958    static void   SetDefaultDrawQuality(UInt_t dq);
0959 
0960    static UInt_t LockColor();
0961    static UInt_t UnlockColor();
0962    static Bool_t IsColorLocked();
0963 
0964    static void Color(const TGLColor& color);
0965    static void ColorAlpha(const TGLColor& color, UChar_t alpha);
0966    static void ColorAlpha(const TGLColor& color, Float_t alpha);
0967    static void ColorAlpha(Color_t color_index, Float_t alpha=1);
0968    static void ColorTransparency(Color_t color_index, Char_t transparency=0);
0969    static void Color3ub(UChar_t r, UChar_t g, UChar_t b);
0970    static void Color4ub(UChar_t r, UChar_t g, UChar_t b, UChar_t a);
0971    static void Color3ubv(const UChar_t* rgb);
0972    static void Color4ubv(const UChar_t* rgba);
0973    static void Color3f(Float_t r, Float_t g, Float_t b);
0974    static void Color4f(Float_t r, Float_t g, Float_t b, Float_t a);
0975    static void Color3fv(const Float_t* rgb);
0976    static void Color4fv(const Float_t* rgba);
0977 
0978    // Coordinate conversion and extra scaling (needed for osx retina)
0979    static void    PointToViewport(Int_t& x, Int_t& y);
0980    static void    PointToViewport(Int_t& x, Int_t& y, Int_t& w, Int_t& h);
0981    static Float_t GetScreenScalingFactor();
0982    static Float_t GetPointLineScalingFactor();
0983    static Int_t   GetPickingRadius();
0984 
0985    static Float_t GetPointSizeScale();
0986    static void    SetPointSizeScale(Float_t scale);
0987    static Float_t GetLineWidthScale();
0988    static void    SetLineWidthScale(Float_t scale);
0989 
0990    static void    PointSize(Float_t point_size);
0991    static void    LineWidth(Float_t line_width);
0992 
0993    static Float_t PointSize();
0994    static Float_t LineWidth();
0995 
0996    static void BeginExtendPickRegion(Float_t scale);
0997    static void EndExtendPickRegion();
0998 
0999    static void RenderPolyMarkers(const TAttMarker& marker, Char_t transp,
1000                                  Float_t* p, Int_t n,
1001                                  Int_t pick_radius=0, Bool_t selection=kFALSE,
1002                                  Bool_t sec_selection=kFALSE);
1003 
1004    static void RenderPolyMarkers(const TAttMarker &marker, const std::vector<Double_t> &points,
1005                                  Double_t dX, Double_t dY, Double_t dZ);
1006 
1007    static void RenderPoints(const TAttMarker& marker,
1008                             Float_t* p, Int_t n,
1009                             Int_t pick_radius=0, Bool_t selection=kFALSE,
1010                             Bool_t sec_selection=kFALSE);
1011 
1012    static void RenderPoints(const TAttMarker& marker,
1013                             const std::vector<Double_t> &points);
1014 
1015    static void RenderCrosses(const TAttMarker& marker,
1016                              Float_t* p, Int_t n,
1017                              Bool_t sec_selection=kFALSE);
1018 
1019    static void RenderCrosses(const TAttMarker& marker,
1020                              const std::vector<Double_t> &points,
1021                              Double_t dX, Double_t dY, Double_t dZ);
1022 
1023    static void RenderPolyLine(const TAttLine& aline, Char_t transp,
1024                               Float_t* p, Int_t n,
1025                               Int_t pick_radius=0, Bool_t selection=kFALSE);
1026 
1027    static void BeginAttLine(const TAttLine& aline, Char_t transp,
1028                             Int_t pick_radius=0, Bool_t selection=kFALSE);
1029    static void EndAttLine(Int_t pick_radius=0, Bool_t selection=kFALSE);
1030 
1031    // TODO: These draw routines should take LOD hints
1032    static void SetDrawColors(const UChar_t rgba[4]);
1033    static void DrawSphere(const TGLVertex3 & position, Double_t radius, const UChar_t rgba[4]);
1034    static void DrawLine(const TGLLine3 & line, ELineHeadShape head, Double_t size, const UChar_t rgba[4]);
1035    static void DrawLine(const TGLVertex3 & start, const TGLVector3 & vector, ELineHeadShape head,
1036                         Double_t size, const UChar_t rgba[4]);
1037    static void DrawRing(const TGLVertex3 & center, const TGLVector3 & normal,
1038                         Double_t radius, const UChar_t* rgba);
1039 
1040    static void DrawReferenceMarker(const TGLCamera  & camera,
1041                                    const TGLVertex3 & pos,
1042                                          Float_t      radius = 3,
1043                                    const UChar_t    * rgba   = nullptr);
1044    static void DrawSimpleAxes(const TGLCamera      & camera,
1045                               const TGLBoundingBox & bbox,
1046                                     Int_t            axesType,
1047                                     Float_t          labelScale = 1);
1048    static void DrawNumber(const TString    & num,
1049                           const TGLVertex3 & pos,
1050                                 Bool_t       center = kFALSE);
1051 
1052    static void SetSimpleAxisWidthScale(Float_t s);
1053    static void SetSimpleAxisBBoxScale(Float_t s);
1054 
1055    // Frequently used colors.
1056    static const UChar_t fgRed[4];
1057    static const UChar_t fgGreen[4];
1058    static const UChar_t fgBlue[4];
1059    static const UChar_t fgYellow[4];
1060    static const UChar_t fgWhite[4];
1061    static const UChar_t fgGrey[4];
1062 
1063    ClassDef(TGLUtil,0); // Wrapper class for misc GL pieces
1064 };
1065 
1066 /**************************************************************************/
1067 
1068 class TGLCapabilitySwitch
1069 {
1070 private:
1071    TGLCapabilitySwitch(const TGLCapabilitySwitch &);
1072    TGLCapabilitySwitch &operator = (const TGLCapabilitySwitch &);
1073 
1074    Int_t    fWhat;
1075    Bool_t   fState;
1076    Bool_t   fFlip;
1077 
1078    void SetState(Bool_t s);
1079 
1080 public:
1081    TGLCapabilitySwitch(Int_t what, Bool_t state);
1082    ~TGLCapabilitySwitch();
1083 };
1084 
1085 class TGLCapabilityEnabler
1086 {
1087 private:
1088    TGLCapabilityEnabler(const TGLCapabilityEnabler &);
1089    TGLCapabilityEnabler &operator = (const TGLCapabilityEnabler &);
1090 
1091    Int_t    fWhat;
1092    Bool_t   fFlip;
1093 
1094 public:
1095    TGLCapabilityEnabler(Int_t what, Bool_t state);
1096    ~TGLCapabilityEnabler();
1097 };
1098 
1099 class TGLFloatHolder
1100 {
1101    TGLFloatHolder(const TGLFloatHolder&) = delete;
1102    TGLFloatHolder& operator=(const TGLFloatHolder&) = delete;
1103 
1104    Int_t    fWhat;
1105    Float_t  fState;
1106    Bool_t   fFlip;
1107    void   (*fFoo)(Float_t);
1108 
1109 public:
1110    TGLFloatHolder(Int_t what, Float_t state, void (*foo)(Float_t));
1111    ~TGLFloatHolder();
1112 };
1113 
1114 class TGLEnableGuard {
1115 private:
1116    Int_t fCap;
1117 
1118 public:
1119    TGLEnableGuard(Int_t cap);
1120    ~TGLEnableGuard();
1121 
1122 private:
1123    TGLEnableGuard(const TGLEnableGuard &);
1124    TGLEnableGuard &operator = (const TGLEnableGuard &);
1125 };
1126 
1127 class TGLDisableGuard {
1128 private:
1129    Int_t fCap;
1130 
1131 public:
1132    TGLDisableGuard(Int_t cap);
1133    ~TGLDisableGuard();
1134 
1135 private:
1136    TGLDisableGuard(const TGLDisableGuard &);
1137    TGLDisableGuard &operator = (const TGLDisableGuard &);
1138 };
1139 
1140 class TGLSelectionBuffer {
1141    std::vector<UChar_t> fBuffer;
1142    Int_t                fWidth;
1143    Int_t                fHeight;
1144 
1145 public:
1146    TGLSelectionBuffer();
1147    virtual ~TGLSelectionBuffer();
1148 
1149    void           ReadColorBuffer(Int_t width, Int_t height);
1150    void           ReadColorBuffer(Int_t x, Int_t y, Int_t width, Int_t height);
1151    const UChar_t *GetPixelColor(Int_t px, Int_t py)const;
1152 
1153 private:
1154    TGLSelectionBuffer(const TGLSelectionBuffer &);
1155    TGLSelectionBuffer &operator = (const TGLSelectionBuffer &);
1156 
1157    ClassDef(TGLSelectionBuffer, 0); //Holds color buffer content for selection
1158 };
1159 
1160 template<class T>
1161 class TGL2DArray : public std::vector<T> {
1162 private:
1163    Int_t fRowLen;
1164    Int_t fMaxRow;
1165    typedef typename std::vector<T>::size_type size_type;
1166 
1167 public:
1168    TGL2DArray() : fRowLen(0), fMaxRow(0){}
1169    void SetMaxRow(Int_t max)
1170    {
1171       fMaxRow = max;
1172    }
1173    void SetRowLen(Int_t len)
1174    {
1175       fRowLen = len;
1176    }
1177    const T *operator [] (size_type ind)const
1178    {
1179       return &std::vector<T>::operator [](ind * fRowLen);
1180    }
1181    T *operator [] (size_type ind)
1182    {
1183       return &std::vector<T>::operator [] (ind * fRowLen);
1184    }
1185 };
1186 
1187 class TGLPlotCoordinates;
1188 class TGLQuadric;
1189 class TAxis;
1190 
1191 namespace Rgl {
1192 
1193 extern const Float_t gRedEmission[];
1194 extern const Float_t gGreenEmission[];
1195 extern const Float_t gBlueEmission[];
1196 extern const Float_t gOrangeEmission[];
1197 extern const Float_t gWhiteEmission[];
1198 extern const Float_t gGrayEmission[];
1199 extern const Float_t gNullEmission[];
1200 
1201 typedef std::pair<Int_t, Int_t> BinRange_t;
1202 typedef std::pair<Double_t, Double_t> Range_t;
1203 
1204 void ObjectIDToColor(Int_t objectID, Bool_t highColor);
1205 Int_t ColorToObjectID(const UChar_t *color, Bool_t highColor);
1206 void DrawQuadOutline(const TGLVertex3 &v1, const TGLVertex3 &v2,
1207                      const TGLVertex3 &v3, const TGLVertex3 &v4);
1208 void DrawQuadFilled(const TGLVertex3 &v0, const TGLVertex3 &v1,
1209                     const TGLVertex3 &v2, const TGLVertex3 &v3,
1210                     const TGLVector3 &normal);
1211 void DrawQuadFilled(const Double_t *v0, const Double_t *v1,
1212                     const Double_t *v2, const Double_t *v3,
1213                     const Double_t *normal);
1214 
1215 void DrawSmoothFace(const TGLVertex3 &v1, const TGLVertex3 &v2,
1216                      const TGLVertex3 &v3, const TGLVector3 &norm1,
1217                      const TGLVector3 &norm2, const TGLVector3 &norm3);
1218 void DrawBoxFront(Double_t xMin, Double_t xMax, Double_t yMin, Double_t yMax,
1219                   Double_t zMin, Double_t zMax, Int_t fp);
1220 
1221 void DrawTransparentBox(Double_t xMin, Double_t xMax, Double_t yMin, Double_t yMax,
1222                         Double_t zMin, Double_t zMax, Int_t fp);
1223 
1224 
1225 void DrawBoxFrontTextured(Double_t xMin, Double_t xMax, Double_t yMin,
1226                           Double_t yMax, Double_t zMin, Double_t zMax,
1227                           Double_t tMin, Double_t tMax, Int_t front);
1228 
1229 void DrawBoxWithGradientFill(Double_t y1, Double_t y2, Double_t x1, Double_t x2,
1230                              const Double_t *rgba1, const Double_t *rgba2);
1231 
1232 void DrawQuadStripWithRadialGradientFill(unsigned nPoints, const Double_t *inner, const Double_t *innerRGBA,
1233                                         const Double_t *outer, const Double_t *outerRGBA);
1234 
1235 void DrawTrapezoidTextured(const Double_t ver[][2], Double_t zMin, Double_t zMax,
1236                            Double_t tMin, Double_t tMax);
1237 void DrawTrapezoidTextured(const Double_t ver[][3], Double_t texMin, Double_t texMax);
1238 void DrawTrapezoidTextured2(const Double_t ver[][2], Double_t zMin, Double_t zMax,
1239                             Double_t tMin, Double_t tMax);
1240 
1241 void DrawCylinder(TGLQuadric *quadric, Double_t xMin, Double_t xMax, Double_t yMin,
1242                   Double_t yMax, Double_t zMin, Double_t zMax);
1243 void DrawSphere(TGLQuadric *quadric, Double_t xMin, Double_t xMax, Double_t yMin,
1244                 Double_t yMax, Double_t zMin, Double_t zMax);
1245 void DrawError(Double_t xMin, Double_t xMax, Double_t yMin,
1246                Double_t yMax, Double_t zMin, Double_t zMax);
1247 
1248 void DrawTrapezoid(const Double_t ver[][2], Double_t zMin, Double_t zMax, Bool_t color = kTRUE);
1249 void DrawTrapezoid(const Double_t ver[][3]);
1250 
1251 void DrawAxes(Int_t frontPoint, const Int_t *viewport, const TGLVertex3 *box2D,
1252               const TGLPlotCoordinates *plotCoord, TAxis *xAxis, TAxis *yAxis,
1253               TAxis *zAxis);
1254 void SetZLevels(TAxis *zAxis, Double_t zMin, Double_t zMax,
1255                 Double_t zScale, std::vector<Double_t> &zLevels);
1256 
1257 void DrawFaceTextured(const TGLVertex3 &v1, const TGLVertex3 &v2, const TGLVertex3 &v3,
1258                       Double_t t1, Double_t t2, Double_t t3, const TGLVector3 &norm1,
1259                       const TGLVector3 &norm2, const TGLVector3 &norm3);
1260 void DrawFaceTextured(const TGLVertex3 &v1, const TGLVertex3 &v2, const TGLVertex3 &v3,
1261                       Double_t t1, Double_t t2, Double_t t3, Double_t z, const TGLVector3 &planeNormal);
1262 void GetColor(Float_t v, Float_t vmin, Float_t vmax, Int_t type, Float_t *rgba);
1263 
1264 class TGuardBase {
1265 private:
1266    mutable Bool_t fActive;
1267 
1268    TGuardBase &operator = (const TGuardBase &rhs) = delete;
1269 protected:
1270    TGuardBase()
1271       : fActive(kTRUE)
1272    {
1273    }
1274    TGuardBase(const TGuardBase &rhs)
1275       : fActive(kTRUE)
1276    {
1277       rhs.fActive = kFALSE;
1278    }
1279 
1280    Bool_t IsActive()const
1281    {
1282       return fActive;
1283    }
1284 
1285 public:
1286    void Stop()const
1287    {
1288       fActive = kFALSE;
1289    }
1290 };
1291 
1292 template<class Func, class Arg>
1293 class TOneArgGuard : public TGuardBase {
1294 private:
1295    Func fFunc;
1296    Arg  fArg;
1297 public:
1298    TOneArgGuard(Func f, Arg a)
1299       : fFunc(f), fArg(a)
1300    {
1301    }
1302    ~TOneArgGuard()
1303    {
1304       if (IsActive())
1305          fFunc(fArg);
1306    }
1307 };
1308 
1309 template<class Func, class Arg1, class Arg2>
1310 class TTwoArgsGuard : public TGuardBase {
1311 private:
1312    Func fFunc;
1313    Arg1 fArg1;
1314    Arg2 fArg2;
1315 
1316 public:
1317    TTwoArgsGuard(Func f, Arg1 a1, Arg2 a2)
1318       : fFunc(f), fArg1(a1), fArg2(a2)
1319    {
1320    }
1321    ~TTwoArgsGuard()
1322    {
1323       if (IsActive())
1324          fFunc(fArg1, fArg2);
1325    }
1326 };
1327 
1328 template<class Func, class Arg>
1329 TOneArgGuard<Func, Arg> make_guard(Func f, Arg a)
1330 {
1331    return TOneArgGuard<Func, Arg>(f, a);
1332 }
1333 
1334 template<class Func, class Arg1, class Arg2>
1335 TTwoArgsGuard<Func, Arg1, Arg2> make_guard(Func f, Arg1 a1, Arg2 a2)
1336 {
1337    return TTwoArgsGuard<Func, Arg1, Arg2>(f, a1, a2);
1338 }
1339 
1340 }//namespace Rgl.
1341 
1342 class TGLLevelPalette {
1343 private:
1344    std::vector<UChar_t>         fTexels;
1345    const std::vector<Double_t> *fContours;
1346    UInt_t                       fPaletteSize;
1347    mutable UInt_t               fTexture;
1348    Int_t                        fMaxPaletteSize;
1349    Rgl::Range_t                 fZRange;
1350 
1351    TGLLevelPalette(const TGLLevelPalette&) = delete;
1352    TGLLevelPalette& operator=(const TGLLevelPalette&) = delete;
1353 
1354 public:
1355    TGLLevelPalette();
1356 
1357    Bool_t GeneratePalette(UInt_t paletteSize, const Rgl::Range_t &zRange, Bool_t checkSize = kTRUE);
1358 
1359    void   SetContours(const std::vector<Double_t> *contours);
1360 
1361    void   EnableTexture(Int_t mode)const;
1362    void   DisableTexture()const;
1363 
1364    Int_t  GetPaletteSize()const;
1365 
1366    Double_t       GetTexCoord(Double_t z)const;
1367 
1368    const UChar_t *GetColour(Double_t z)const;
1369    const UChar_t *GetColour(Int_t ind)const;
1370 };
1371 
1372 #endif // ROOT_TGLUtil