Skip to content
Snippets Groups Projects
Commit bdaa813c authored by Olivier Couet's avatar Olivier Couet
Browse files

From Timur:

TGLPadHistpainter/TGLAxisPainter/TGLLegoPainter - new hist-painter
infrastructure.

First version of TGLLegoPainter, the new class to support different types
of legos:
gl + lego(1)/lego2 + pol/cyl/sph
gl + lego3

TGLUtil : Small auxilary classes.

IMPORTANT: this lego painter is still experimantal and works only if
it's enabled in system.rootrc. By default, TGLHistPainter is used now.
To enable this new system the line:

Plugin.TGLHistPainter: * TGLHistPainter RGL "TGLHistPainter(TH1*)"

Must be replaced with

Plugin.TGLHistPainter: * TGLPadHistPainter RGL "TGLPadHistPainter(TH1*)"

in $ROOTSYS/etc/system.rootrc


git-svn-id: http://root.cern.ch/svn/root/trunk@15406 27541ba8-7e3a-0410-8455-c3a389f83636
parent 0b26819a
No related branches found
No related tags found
No related merge requests found
......@@ -67,6 +67,15 @@
#pragma link C++ class TGLSphere;
#pragma link C++ class TGLHistPainter;
#pragma link C++ class TGLViewerEditor;
#pragma link C++ class TGLPadHistPainter;
#pragma link C++ class TGLPlotPainter;
#pragma link C++ class TGLAxisPainter;
#pragma link C++ class TGL2DAxisPainter;
#pragma link C++ class TGLLegoPainter;
#pragma link C++ class TGLSelectionBuffer;
#pragma link C++ class TGLPlotFrame;
#ifndef _WIN32
#pragma link C++ class TX11GL;
#pragma link C++ class TX11GLManager;
......
// @(#)root/gl:$Name: $:$Id: TArcBall.h,v 1.8 2005/04/07 14:43:35 rdm Exp $
// @(#)root/gl:$Name: $:$Id: TArcBall.h,v 1.9 2005/11/29 09:25:51 couet Exp $
// Author: Timur Pocheptsov 03/08/2004
/*************************************************************************
......@@ -34,7 +34,7 @@ private:
protected:
void MapToSphere(const TPoint &NewPt, Double_t *NewVec)const;
public:
TArcBall(UInt_t NewWidth, UInt_t NewHeight);
TArcBall(UInt_t NewWidth = 100, UInt_t NewHeight = 100);
virtual ~TArcBall() { }
void SetBounds(UInt_t NewWidth, UInt_t NewHeight)
......
#ifndef ROOT_TGLAxisPainter
#define ROOT_TGLAxisPainter
#include <utility>
#include <vector>
#include "Rtypes.h"
/*
TGLAxisPainter defines interface for axis painters.
Now, we have only one concrete axis painter, which
uses TGAxis class and TVirtualX to do all work.
In future, TGAxis must be replaced by real
3d axis painter.
*/
class TGLPlotFrame;
class TGLAxisPainter {
public:
typedef std::pair<Double_t, Double_t> Range_t;
virtual ~TGLAxisPainter();
virtual void SetRanges(const Range_t &xRange, const Range_t &yRange, const Range_t &zRange) = 0;
virtual void SetZLevels(std::vector<Double_t> &zLevels) = 0;
virtual void Paint(Int_t context) = 0;
ClassDef(TGLAxisPainter, 0) //Base for axis painters
};
class TAxis;
class TH1;
/*
This painter obtains 3d coordinates converted into 2d coordinates in a window system,
draws them via TGAxis.
*/
class TGL2DAxisPainter : public TGLAxisPainter {
private:
Range_t fRangeX;
Range_t fRangeY;
Range_t fRangeZ;
TGLPlotFrame *fPlotFrame;
TAxis *fAxisX;
TAxis *fAxisY;
TAxis *fAxisZ;
public:
TGL2DAxisPainter(TH1 *hist);
void SetPlotFrame(TGLPlotFrame *frame);
void SetRanges(const Range_t &xRange, const Range_t &yRange, const Range_t &zRange);
void SetZLevels(std::vector<Double_t> &zLevels);
void Paint(Int_t context);
ClassDef(TGL2DAxisPainter, 0) //Default painter, uses TGAxis to make its work
};
#endif
#ifndef ROOT_TGLLegoPainter
#define ROOT_TGLLegoPainter
#include <utility>
#include <vector>
#ifndef ROOT_TGLPlotPainter
#include "TGLPlotPainter.h"
#endif
#ifndef ROOT_TGLQuadric
#include "TGLQuadric.h"
#endif
#ifndef ROOT_TArcBall
#include "TArcBall.h"
#endif
#ifndef ROOT_TGLUtil
#include "TGLUtil.h"
#endif
#ifndef ROOT_TPoint
#include "TPoint.h"
#endif
class TGLAxisPainter;
/*
TGLLegoPainter. The concrete implementation of abstract TGLPlotPainter.
*/
class TGLLegoPainter : public TGLPlotPainter, public TGLPlotFrame {
private:
enum ELegoType {
kColorSimple,
kColorLevel,
kCylindricBars
};
enum ESelectionType {
kSelectionSimple,//Histogramm can be selected as a whole object.
kSelectionFull //All parts are selectable.
};
typedef std::pair<Int_t, Int_t> Selection_t;
typedef std::pair<Double_t, Double_t> CosSin_t;
TH1 *fHist;
Int_t fGLContext;
EGLCoordType fCoordType;
BinRange_t fBinsX;
BinRange_t fBinsY;
Range_t fRangeX;
Range_t fRangeY;
Range_t fRangeZ;
Double_t fMinZ;
//Bars, cylinders or textured bars.
ELegoType fLegoType;
TGLSelectionBuffer fSelection;
Bool_t fSelectionPass;
Bool_t fUpdateSelection;
Selection_t fSelectedBin;
ESelectionType fSelectionMode;
Int_t fSelectedPlane;
TColor *fPadColor;
TColor *fFrameColor;
Double_t fXOZProfilePos;
Double_t fYOZProfilePos;
Bool_t fIsMoving;
std::vector<Double_t> fX;
std::vector<Double_t> fY;
std::vector<CosSin_t> fCosSinTableX;
std::vector<CosSin_t> fCosSinTableY;
TString fBinInfo;
Bool_t fAntiAliasing;
TGLAxisPainter *fAxisPainter;
std::vector<Double_t> fZLevels;
//Temporary stuff here, must be in TGLTexture1D
UInt_t fTextureName;
std::vector<UChar_t> fTexture;
TGLQuadric fQuadric;
Double_t fBinWidth;
void Enable1DTexture();
void Disable1DTexture();
TGLLegoPainter(const TGLLegoPainter &);
TGLLegoPainter &operator = (const TGLLegoPainter &);
public:
TGLLegoPainter(TH1 *hist, TGLAxisPainter *axisPainter, Int_t ctx = -1, EGLCoordType type = kGLCartesian,
Bool_t logX = kFALSE, Bool_t logY = kFALSE, Bool_t logZ = kFALSE);
//TGLPlotPainter's final-verriders
void Paint();
void SetGLContext(Int_t ctx);
char *GetObjectInfo(Int_t px, Int_t py);
Bool_t InitGeometry();
void StartRotation(Int_t px, Int_t py);
void StopRotation();
void Rotate(Int_t px, Int_t py);
void StartPan(Int_t px, Int_t py);
void Pan(Int_t px, Int_t py);
void StopPan();
TObject *Select(Int_t px, Int_t py);
void ZoomIn();
void ZoomOut();
void SetLogX(Bool_t logX);
void SetLogY(Bool_t logY);
void SetLogZ(Bool_t logZ);
void SetCoordType(EGLCoordType type);
void AddOption(const TString &stringOption);
void SetPadColor(TColor *padColor);
void SetFrameColor(TColor *frameColor);
void ProcessEvent(Int_t event, Int_t px, Int_t py);
private:
//Auxilary functions.
Bool_t InitGeometryCartesian();
Bool_t InitGeometryPolar();
Bool_t InitGeometryCylindrical();
Bool_t InitGeometrySpherical();
void InitGL();
Selection_t ColorToObject(const UChar_t *color);
void EncodeToColor(Int_t i, Int_t j)const;
void DrawPlot();
void DrawLegoCartesian();
void DrawLegoPolar();
void DrawLegoCylindrical();
void DrawLegoSpherical();
void SetLegoColor();
void ClearBuffers();
Bool_t MakeGLContextCurrent()const;
void SetSelectionMode();
void DrawFrame();
void DrawBackPlane(Int_t plane)const;
void DrawGrid(Int_t plane)const;
void MoveDynamicProfile(Int_t px, Int_t py);
void DrawShadow(Int_t plane)const;
void DrawProfiles();
void DrawProfileX();
void DrawProfileY();
//Auxiliary functions.
Bool_t ClampZ(Double_t &zVal)const;
static const Float_t fRedEmission[];
static const Float_t fNullEmission[];
static const Float_t fGreenEmission[];
ClassDef(TGLLegoPainter, 0)//Lego painter
};
#endif
#ifndef ROOT_TGLPadHistPainter
#define ROOT_TGLPadHistPainter
#include <memory>
#ifndef ROOT_TVirtualHistPainter
#include "TVirtualHistPainter.h"
#endif
#ifndef ROOT_TGLAxisPainter
#include "TGLAxisPainter.h"
#endif
#ifndef ROOT_TGLPlotPainter
#include "TGLPlotPainter.h"
#endif
/*
TGLPadHistPainter is a proxy class. It inherits TVirtualHistPainter and
overrides its virtual functions, but all actual work is done by :
THistPainter - I name it "default" painter, it's the member of type
TVirtualHistPainter * and loaded via plugin-manager
TGLLegoPainter - it draws different legoes (lego/lego1/lego2/lego3)
TGLSurfacePainter - supports surfaces (surf/surf1/surf2/surf3/surf4/surf5)
TGLBoxPainter - box option for tf3
TGLTF3Painter - TF3
TGLStackPainter
*/
class TString;
class TList;
class TF3;
class TH1;
class TGLPadHistPainter : public TVirtualHistPainter {
private:
//Dynamic type is THistPainter, no problems with simultaneous inheritance and membership
//TGLPadHistPainter delegates unsupported options/calls to this object
std::auto_ptr<TVirtualHistPainter> fDefaultPainter;
//This member can have different dynamic types: TGLLegoPainter, etc.
std::auto_ptr<TGLPlotPainter> fGLPainter;
TH1 *fHist;
TF3 *fF3;
TList *fStack;
EGLPlotType fPlotType;
//In future, when gl axis will be implemented, this
//axis painter must be replaced
TGL2DAxisPainter f2DAxisPainter;
public:
TGLPadHistPainter(TH1 *hist);
//TVirtualHistPainter final overriders
Int_t DistancetoPrimitive(Int_t px, Int_t py);
void DrawPanel();
void ExecuteEvent(Int_t event, Int_t px, Int_t py);
void FitPanel();
TList *GetContourList(Double_t contour)const;
char *GetObjectInfo(Int_t px, Int_t py)const;
TList *GetStack()const;
Bool_t IsInside(Int_t x, Int_t y);
Bool_t IsInside(Double_t x, Double_t y);
void Paint(Option_t *option);
void PaintStat(Int_t dostat, TF1 *fit);
void ProcessMessage(const char *message, const TObject *obj);
void SetHistogram(TH1 *hist);
void SetStack(TList *stack);
Int_t MakeCuts(char *cutsOpt);
void SetShowProjection(const char *option, Int_t nbins);
private:
struct TGLPlotOption_t;
TGLPlotOption_t ParsePaintOption(const TString &option)const;
void CreatePainter(const TGLPlotOption_t &parsed,
const TString &option);
TGLPadHistPainter(const TGLPadHistPainter &);
TGLPadHistPainter &operator = (const TGLPadHistPainter &);
ClassDef(TGLPadHistPainter, 0) //Proxy class for GL hist painter
};
#endif
#ifndef ROOT_TGLPainterAlgorithms
#define ROOT_TGLPainterAlgorithms
#include <utility>
#ifndef ROOT_TVirtualGL
#include "TVirtualGL.h"
#endif
#ifndef ROOT_TArcBall
#include "TArcBall.h"
#endif
#ifndef ROOT_TGLUtil
#include "TGLUtil.h"
#endif
#ifndef ROOT_TPoint
#include "TPoint.h"
#endif
class TString;
class TColor;
class TAxis;
class TH1;
/*
TGLPlotPainter class defines interface to different plot painters.
*/
enum EGLCoordType {
kGLCartesian,
kGLPolar,
kGLCylindrical,
kGLSpherical
};
enum EGLPlotType {
kGLLegoPlot,
kGLSurfacePlot,
kGLBoxPlot,
kGLTF3Plot,
kGLStackPlot,
kGLDefaultPlot
};
class TGLPlotPainter : public TVirtualGLPainter {
public:
virtual void SetGLContext(Int_t context) = 0;
//Shows info about an object under cursor.
virtual char *GetObjectInfo(Int_t px, Int_t py) = 0;
//Init geometry does plot's specific initialization.
//Such initialization can be done one time in constructor,
//without any InitGeometry call. But in case of pad,
//user can change something interactivly and
//painter should know about it to change its state.
virtual Bool_t InitGeometry() = 0;
virtual void StartRotation(Int_t px, Int_t py) = 0;
virtual void Rotate(Int_t px, Int_t py) = 0;
virtual void StopRotation() = 0;
virtual void StartPan(Int_t px, Int_t py) = 0;
//Pan function is already declared in TVirtualGLPainter
virtual void StopPan() = 0;
virtual void ZoomIn() = 0;
virtual void ZoomOut() = 0;
virtual void SetLogX(Bool_t logX) = 0;
virtual void SetLogY(Bool_t logY) = 0;
virtual void SetLogZ(Bool_t logZ) = 0;
virtual void SetCoordType(EGLCoordType type) = 0;
//Add string option, it can be a digit in "lego" or "surf"
//options, and it can be some others options - "e".
virtual void AddOption(const TString &stringOption) = 0;
//Used by GLpad
virtual void SetPadColor(TColor *color) = 0;
//Used by GLpad
virtual void SetFrameColor(TColor *color) = 0;
//Function to process additional events (some key presses etc.)
virtual void ProcessEvent(Int_t event, Int_t px, Int_t py) = 0;
ClassDef(TGLPlotPainter, 0) //Base for gl plots
};
/*
Auxilary class, which holds info about plot's back box and
sizes.
*/
class TGLPlotFrame {
friend class TGL2DAxisPainter;
protected:
typedef std::pair<Double_t, Double_t> Range_t;
typedef std::pair<Int_t, Int_t> BinRange_t;
TGLVertex3 fFrame[8];
static const Int_t fFramePlanes[][4];
static const Double_t fFrameNormals[][3];
static const Int_t fBackPairs[][2];
Bool_t fLogX;
Bool_t fLogY;
Bool_t fLogZ;
Double_t fScaleX;
Double_t fScaleY;
Double_t fScaleZ;
Int_t fFrontPoint;
TGLVertex3 f2DAxes[8];
TArcBall fArcBall;
Int_t fViewport[4];
TPoint fMousePosition;
TGLVector3 fPan;
Double_t fZoom;
Double_t fFrustum[4];
Double_t fShift;
Double_t fCenter[3];
Double_t fFactor;
TGLPlotFrame(Bool_t logX, Bool_t logY, Bool_t logZ);
virtual ~TGLPlotFrame();
void CalculateGLCameraParams(const Range_t &x, const Range_t &y, const Range_t &z);
void FindFrontPoint();
void SetTransformation();
void SetCamera();
protected:
static Bool_t ExtractAxisInfo(const TAxis *axis, Bool_t log, BinRange_t &bins, Range_t &range);
Bool_t ExtractAxisZInfo(TH1 *hist, Bool_t logZ, const BinRange_t &xBins,
const BinRange_t &yBins, Range_t &zRange);
static void AdjustShift(const TPoint &start, const TPoint &finish, TGLVector3 &shiftVec, const Int_t *viewport);
ClassDef(TGLPlotFrame, 0) //Auxilary class
};
class TGLQuadric;
namespace RootGL
{
void DrawCylinder(TGLQuadric *quadric, Double_t xMin, Double_t xMax, Double_t yMin,
Double_t yMax, Double_t zMin, Double_t zMax);
void DrawQuadOutline(const TGLVertex3 &v1, const TGLVertex3 &v2,
const TGLVertex3 &v3, const TGLVertex3 &v4);
void DrawQuadFilled(const TGLVertex3 &v0, const TGLVertex3 &v1, const TGLVertex3 &v2,
const TGLVertex3 &v3, const TGLVertex3 &normal);
void DrawBoxFront(Double_t xMin, Double_t xMax, Double_t yMin, Double_t yMax,
Double_t zMin, Double_t zMax, Int_t frontPoint);
void DrawBoxFrontTextured(Double_t x1, Double_t x2, Double_t y1, Double_t y2, Double_t z1,
Double_t z2, Double_t texMin, Double_t texMax, Int_t frontPoint);
void DrawTrapezoid(const Double_t ver[][2], Double_t zMin, Double_t zMax, Bool_t needNormals = kTRUE);
void DrawTrapezoid(const Double_t ver[][3]);
void DrawTrapezoidTextured(const Double_t ver[][2], Double_t zMin, Double_t zMax,
Double_t texMin, Double_t texMax);
void DrawTrapezoidTextured(const Double_t ver[][3], Double_t texMin, Double_t texMax);
void DrawTrapezoidTextured2(const Double_t ver[][2], Double_t zMin, Double_t zMax,
Double_t texMin, Double_t texMax);
}
#endif
// @(#)root/gl:$Name: $:$Id: TGLUtil.h,v 1.27 2006/02/21 16:39:49 brun Exp $
// @(#)root/gl:$Name: $:$Id: TGLUtil.h,v 1.28 2006/02/23 16:44:51 brun Exp $
// Author: Richard Maunder 25/05/2005
/*************************************************************************
......@@ -830,4 +830,53 @@ public:
ClassDef(TGLUtil,0) // Wrapper class for misc GL pieces
};
namespace RootGL {
class TGLEnableGuard {
private:
Int_t fCap;
public:
TGLEnableGuard(Int_t cap);
~TGLEnableGuard();
private:
TGLEnableGuard(const TGLEnableGuard &);
TGLEnableGuard &operator = (const TGLEnableGuard &);
};
class TGLDisableGuard {
private:
Int_t fCap;
public:
TGLDisableGuard(Int_t cap);
~TGLDisableGuard();
private:
TGLDisableGuard(const TGLDisableGuard &);
TGLDisableGuard &operator = (const TGLDisableGuard &);
};
}
class TGLSelectionBuffer {
std::vector<UChar_t> fBuffer;
Int_t fWidth;
Int_t fHeight;
public:
TGLSelectionBuffer();
virtual ~TGLSelectionBuffer();
void ReadColorBuffer(Int_t width, Int_t height);
const UChar_t *GetPixelColor(Int_t px, Int_t py)const;
private:
TGLSelectionBuffer(const TGLSelectionBuffer &);
TGLSelectionBuffer &operator = (const TGLSelectionBuffer &);
ClassDef(TGLSelectionBuffer, 0)//Holds color buffer content for selection
};
#endif // ROOT_TGLUtil
#include <string>
#include "THLimitsFinder.h"
#include "TVirtualPad.h"
#include "TVirtualGL.h"
#include "TVirtualX.h"
#include "TGaxis.h"
#include "TMath.h"
#include "TAxis.h"
#include "TH1.h"
#include "TGLAxisPainter.h"
#include "TGLPlotPainter.h"
ClassImp(TGLAxisPainter)
//______________________________________________________________________________
TGLAxisPainter::~TGLAxisPainter()
{
// TGLAxisPainter destructor.
}
ClassImp(TGL2DAxisPainter)
//______________________________________________________________________________
TGL2DAxisPainter::TGL2DAxisPainter(TH1 *hist)
: fPlotFrame(0),
fAxisX(hist->GetXaxis()),
fAxisY(hist->GetYaxis()),
fAxisZ(hist->GetZaxis())
{
//TGL2DAxisPainter constructor.
}
//______________________________________________________________________________
void TGL2DAxisPainter::SetPlotFrame(TGLPlotFrame *frame)
{
// Set plot frame.
fPlotFrame = frame;
}
//______________________________________________________________________________
void TGL2DAxisPainter::SetRanges(const Range_t &xRange, const Range_t &yRange, const Range_t &zRange)
{
// Set range.
fRangeX = xRange;
fRangeY = yRange;
fRangeZ = zRange;
}
//______________________________________________________________________________
void TGL2DAxisPainter::SetZLevels(std::vector<Double_t> &zLevels)
{
//Define levels for grid.
//copy vals, because Optimize can chnage them.
Double_t zMin = fRangeZ.first;
Double_t zMax = fRangeZ.second;
Int_t nDiv = fAxisZ->GetNdivisions() % 100;
Int_t nBins = 0;
Double_t binLow = 0., binHigh = 0., binWidth = 0.;
THLimitsFinder::Optimize(zMin, zMax, nDiv, binLow, binHigh, nBins, binWidth, " ");
zLevels.resize(nBins + 1);
for (Int_t i = 0; i < nBins + 1; ++i)
zLevels[i] = binLow + i * binWidth;
}
namespace {
void Draw2DAxis(TAxis *axis, Double_t xMin, Double_t yMin, Double_t xMax, Double_t yMax,
Double_t min, Double_t max, Bool_t log, Bool_t z = kFALSE)
{
//Axes are drawn with help of TGaxis class
std::string option;
option.reserve(20);
if (xMin > xMax || z) option += "SDH=+";
else option += "SDH=-";
if (log) option += 'G';
Int_t nDiv = axis->GetNdivisions();
if (nDiv < 0) {
option += 'N';
nDiv = -nDiv;
}
TGaxis axisPainter;
axisPainter.SetLineWidth(1);
static const Double_t zero = 0.001;
if (TMath::Abs(xMax - xMin) >= zero || TMath::Abs(yMax - yMin) >= zero) {
axisPainter.ImportAxisAttributes(axis);
axisPainter.SetLabelOffset(axis->GetLabelOffset() + axis->GetTickLength());
if (log) {
min = TMath::Power(10, min);
max = TMath::Power(10, max);
}
//Option time display is required ?
if (axis->GetTimeDisplay()) {
option += 't';
if (!strlen(axis->GetTimeFormatOnly()))
axisPainter.SetTimeFormat(axis->ChooseTimeFormat(max - min));
else
axisPainter.SetTimeFormat(axis->GetTimeFormat());
}
axisPainter.SetOption(option.c_str());
axisPainter.PaintAxis(xMin, yMin, xMax, yMax, min, max, nDiv, option.c_str());
}
}
const Int_t gFramePoints[][2] = {{3, 1}, {0, 2}, {1, 3}, {2, 0}};
//Each point has two "neighbouring axes" (left and right). Axes types are 1 (ordinata) and 0 (abscissa)
const Int_t gAxisType[][2] = {{1, 0}, {0, 1}, {1, 0}, {0, 1}};
}
//______________________________________________________________________________
void TGL2DAxisPainter::Paint(Int_t glContext)
{
//Using front point, find, where to draw axes and which labels to use for them
gGLManager->SelectOffScreenDevice(glContext);
gVirtualX->SetDrawMode(TVirtualX::kCopy);
const Int_t left = gFramePoints[fPlotFrame->fFrontPoint][0];
const Int_t right = gFramePoints[fPlotFrame->fFrontPoint][1];
const Double_t xLeft = gPad->AbsPixeltoX(Int_t(gPad->GetXlowNDC() * gPad->GetWw()
+ fPlotFrame->f2DAxes[left].X()));
const Double_t yLeft = gPad->AbsPixeltoY(Int_t(fPlotFrame->fViewport[3] - fPlotFrame->f2DAxes[left].Y()
+ (1 - gPad->GetHNDC() - gPad->GetYlowNDC()) * gPad->GetWh()
+ fPlotFrame->fViewport[1]));
const Double_t xMid = gPad->AbsPixeltoX(Int_t(gPad->GetXlowNDC() * gPad->GetWw()
+ fPlotFrame->f2DAxes[fPlotFrame->fFrontPoint].X()));
const Double_t yMid = gPad->AbsPixeltoY(Int_t(fPlotFrame->fViewport[3] - fPlotFrame->f2DAxes[fPlotFrame->fFrontPoint].Y()
+ (1 - gPad->GetHNDC() - gPad->GetYlowNDC()) * gPad->GetWh()
+ fPlotFrame->fViewport[1]));
const Double_t xRight = gPad->AbsPixeltoX(Int_t(gPad->GetXlowNDC() * gPad->GetWw()
+ fPlotFrame->f2DAxes[right].X()));
const Double_t yRight = gPad->AbsPixeltoY(Int_t(fPlotFrame->fViewport[3] - fPlotFrame->f2DAxes[right].Y()
+ (1 - gPad->GetHNDC() - gPad->GetYlowNDC()) * gPad->GetWh()
+ fPlotFrame->fViewport[1]));
const Double_t points[][2] = {
{fRangeX.first, fRangeY.first},
{fRangeX.second, fRangeY.first},
{fRangeX.second, fRangeY.second},
{fRangeX.first, fRangeY.second}
};
const Int_t leftType = gAxisType[fPlotFrame->fFrontPoint][0];
const Int_t rightType = gAxisType[fPlotFrame->fFrontPoint][1];
const Double_t leftLabel = points[left][leftType];
const Double_t leftMidLabel = points[fPlotFrame->fFrontPoint][leftType];
const Double_t rightMidLabel = points[fPlotFrame->fFrontPoint][rightType];
const Double_t rightLabel = points[right][rightType];
if (xLeft - xMid || yLeft - yMid) {//To supress error messages from TGaxis
TAxis *axis = leftType ? fAxisY : fAxisX;
if (leftLabel < leftMidLabel)
Draw2DAxis(axis, xLeft, yLeft, xMid, yMid, leftLabel, leftMidLabel, leftType ? fPlotFrame->fLogY : fPlotFrame->fLogX);
else
Draw2DAxis(axis, xMid, yMid, xLeft, yLeft, leftMidLabel, leftLabel, leftType ? fPlotFrame->fLogY : fPlotFrame->fLogX);
}
if (xRight - xMid || yRight - yMid) {//To supress error messages from TGaxis
TAxis *axis = rightType ? fAxisY : fAxisX;
if (rightMidLabel < rightLabel)
Draw2DAxis(axis, xMid, yMid, xRight, yRight, rightMidLabel, rightLabel, rightType ? fPlotFrame->fLogY : fPlotFrame->fLogX);
else
Draw2DAxis(axis, xRight, yRight, xMid, yMid, rightLabel, rightMidLabel, rightType ? fPlotFrame->fLogY : fPlotFrame->fLogX);
}
const Double_t xUp = gPad->AbsPixeltoX(Int_t(gPad->GetXlowNDC() * gPad->GetWw()
+ fPlotFrame->f2DAxes[left + 4].X()));
const Double_t yUp = gPad->AbsPixeltoY(Int_t(fPlotFrame->fViewport[3] - fPlotFrame->f2DAxes[left + 4].Y()
+ (1 - gPad->GetHNDC() - gPad->GetYlowNDC()) * gPad->GetWh()
+ fPlotFrame->fViewport[1]));
Draw2DAxis(fAxisZ, xLeft, yLeft, xUp, yUp, fRangeZ.first, fRangeZ.second, fPlotFrame->fLogZ, kTRUE);
gVirtualX->SelectWindow(gPad->GetPixmapID());
}
This diff is collapsed.
#include <cstring>
#include <cctype>
#include "TVirtualPad.h"
#include "TVirtualGL.h"
#include "KeySymbols.h"
#include "TF3.h"
#include "TGLPadHistPainter.h"
#include "TGLLegoPainter.h"
ClassImp(TGLPadHistPainter)
//______________________________________________________________________________
TGLPadHistPainter::TGLPadHistPainter(TH1 *hist)
: fDefaultPainter(TVirtualHistPainter::HistPainter(hist)),
fGLPainter(0),
fHist(hist),
fF3(0),
fStack(0),
fPlotType(kGLDefaultPlot),
f2DAxisPainter(hist)
{
//ROOT does not use exceptions, so, if default painter's creation failed,
//fDefaultPainter is 0. In each function, which use it, I have to check pointer first.
}
//______________________________________________________________________________
Int_t TGLPadHistPainter::DistancetoPrimitive(Int_t px, Int_t py)
{
//Selects plot or axis.
//9999 is the magic number, ROOT's classes use in DistancetoPrimitive.
if (fPlotType == kGLDefaultPlot)
return fDefaultPainter.get() ? fDefaultPainter->DistancetoPrimitive(px, py) : 9999;
else {
const Int_t glContext = gPad->GetGLDevice();
if (glContext != -1) {
fGLPainter->SetGLContext(glContext);
if (TObject *object = gGLManager->Select(fGLPainter.get(), px, py));
//gPad->SetSelected(object);
else
gPad->SetSelected(gPad);
} else {
Error("DistancetoPrimitive",
"Attempt to use TGLPadHistPainter, while the current pad (gPad) does support gl");
gPad->SetSelected(gPad);
}
return 0;
}
}
//______________________________________________________________________________
void TGLPadHistPainter::DrawPanel()
{
//Default implementation is OK.
if (fDefaultPainter.get())
fDefaultPainter->DrawPanel();
}
//______________________________________________________________________________
void TGLPadHistPainter::ExecuteEvent(Int_t event, Int_t px, Int_t py)
{
// Execute event.
if (fPlotType == kGLDefaultPlot) {
if(fDefaultPainter.get())
fDefaultPainter->ExecuteEvent(event, px, py);
} else {
const Int_t glContext = gPad->GetGLDevice();
if (glContext == -1) {
Error("ExecuteEvent",
"Attempt to use TGLPadHistPainter, while the current pad (gPad) does support gl");
return;
} else
fGLPainter->SetGLContext(glContext);
if (event != kKeyPress) {
py -= Int_t((1 - gPad->GetHNDC() - gPad->GetYlowNDC()) * gPad->GetWh());
px -= Int_t(gPad->GetXlowNDC() * gPad->GetWw());
}
switch (event) {
case kButton1Double:
fGLPainter->ProcessEvent(event, px, py);
break;
case kButton1Down :
fGLPainter->StartRotation(px, py);
gGLManager->MarkForDirectCopy(glContext, kTRUE);
break;
case kButton1Motion :
fGLPainter->Rotate(px, py);
gGLManager->PaintSingleObject(fGLPainter.get());
break;
case kButton1Up:
gGLManager->MarkForDirectCopy(glContext, kFALSE);
fGLPainter->StopRotation();
break;
case kButton2Up:
gGLManager->MarkForDirectCopy(glContext, kFALSE);
fGLPainter->StopPan();
break;
case kMouseMotion:
gPad->SetCursor(kRotate);
break;
case kButton2Down:
fGLPainter->StartPan(px, py);
gGLManager->MarkForDirectCopy(glContext, kTRUE);
break;
case kButton2Motion:
gGLManager->PanObject(fGLPainter.get(), px, py);
gGLManager->PaintSingleObject(fGLPainter.get());
break;
case kKeyPress:
case 5:
case 6:
gGLManager->MarkForDirectCopy(glContext, kTRUE);
if (event == 5 || py == kKey_J || py == kKey_j) {
fGLPainter->ZoomIn();
gGLManager->PaintSingleObject(fGLPainter.get());
} else if (event == 6 || py == kKey_K || py == kKey_k) {
fGLPainter->ZoomOut();
gGLManager->PaintSingleObject(fGLPainter.get());
}
gGLManager->MarkForDirectCopy(glContext, kFALSE);
break;
}
}
}
//______________________________________________________________________________
void TGLPadHistPainter::FitPanel()
{
//Default implementation is OK.
if (fDefaultPainter.get())
fDefaultPainter->FitPanel();
}
//______________________________________________________________________________
TList *TGLPadHistPainter::GetContourList(Double_t contour)const
{
// Get contour list.
return fDefaultPainter.get() ? fDefaultPainter->GetContourList(contour) : 0;
}
//______________________________________________________________________________
char *TGLPadHistPainter::GetObjectInfo(Int_t px, Int_t py)const
{
//Overrides TObject::GetObjectInfo.
//Displays the histogram info (bin number, contents, integral up to bin
//corresponding to cursor position px,py.
static char *errMsg = "TGLPadHistPainter::GetObjectInfo: Error in a hist painter\n";
if (fPlotType == kGLDefaultPlot)
return fDefaultPainter.get() ? fDefaultPainter->GetObjectInfo(px, py)
: errMsg;
else
return fGLPainter->GetObjectInfo(px, py);
}
//______________________________________________________________________________
TList *TGLPadHistPainter::GetStack()const
{
// Get stack.
return fStack;
}
//______________________________________________________________________________
Bool_t TGLPadHistPainter::IsInside(Int_t x, Int_t y)
{
//Returns kTRUE if the cell ix, iy is inside one of the graphical cuts.
if (fPlotType == kGLDefaultPlot)
return fDefaultPainter.get() ? fDefaultPainter->IsInside(x, y) : kFALSE;
return kFALSE;
}
//______________________________________________________________________________
Bool_t TGLPadHistPainter::IsInside(Double_t x, Double_t y)
{
//Returns kTRUE if the cell x, y is inside one of the graphical cuts.
if (fPlotType == kGLDefaultPlot)
return fDefaultPainter.get() ? fDefaultPainter->IsInside(x, y) : kFALSE;
return kFALSE;
}
//______________________________________________________________________________
void TGLPadHistPainter::PaintStat(Int_t dostat, TF1 *fit)
{
// Paint statistics.
if (fDefaultPainter.get())
fDefaultPainter->PaintStat(dostat, fit);
}
//______________________________________________________________________________
void TGLPadHistPainter::ProcessMessage(const char *m, const TObject *o)
{
// Process message.
if (!std::strcmp(m, "SetF3"))
fF3 = (TF3 *)o;//static_cast, followed by const_cast
if (fDefaultPainter.get())
fDefaultPainter->ProcessMessage(m, o);
}
//______________________________________________________________________________
void TGLPadHistPainter::SetHistogram(TH1 *h)
{
// Set histogram.
fHist = h;
if (fDefaultPainter.get())
fDefaultPainter->SetHistogram(h);
}
//______________________________________________________________________________
void TGLPadHistPainter::SetStack(TList *s)
{
// Set stack.
fStack = s;
if (fDefaultPainter.get())
fDefaultPainter->SetStack(s);
}
//______________________________________________________________________________
Int_t TGLPadHistPainter::MakeCuts(char *o)
{
// Make cuts.
if (fPlotType == kGLDefaultPlot && fDefaultPainter.get())
return fDefaultPainter->MakeCuts(o);
return 0;
}
struct TGLPadHistPainter::TGLPlotOption_t {
EGLPlotType fPlotType;
EGLCoordType fCoordType;
Bool_t fBackBox;
Bool_t fFrontBox;
Bool_t fLogX;
Bool_t fLogY;
Bool_t fLogZ;
};
//______________________________________________________________________________
void TGLPadHistPainter::Paint(Option_t *o)
{
//Final-overrider for TObject::Paint.
TString option(o);
option.ToLower();
const Ssiz_t glPos = option.Index("gl");
if (glPos != kNPOS)
option.Remove(glPos, 2);
else {
gPad->SetCopyGLDevice(kFALSE);
if (fDefaultPainter.get())
fDefaultPainter->Paint(o);//option.Data());
return;
}
CreatePainter(ParsePaintOption(option), option);
if (fPlotType == kGLDefaultPlot) {
gPad->SetCopyGLDevice(kFALSE);
if (fDefaultPainter.get())
fDefaultPainter->Paint(option.Data());
} else {
Int_t glContext = gPad->GetGLDevice();
if (glContext != -1) {
gPad->SetCopyGLDevice(kTRUE);
fGLPainter->SetGLContext(glContext);
if (fGLPainter->InitGeometry())
gGLManager->PaintSingleObject(fGLPainter.get());
}
}
}
//______________________________________________________________________________
TGLPadHistPainter::TGLPlotOption_t
TGLPadHistPainter::ParsePaintOption(const TString &option)const
{
//In principle, we can have several conflicting options: "lego surf pol sph",
//but only one will be selected, which one - depends on parsing order in this function.
TGLPlotOption_t parsedOption = {kGLDefaultPlot, kGLCartesian, kFALSE, kFALSE, gPad->GetLogx(),
gPad->GetLogy(), gPad->GetLogz()};
//Check coordinate system type.
if (option.Index("pol") != kNPOS)
parsedOption.fCoordType = kGLPolar;
if (option.Index("cyl") != kNPOS)
parsedOption.fCoordType = kGLCylindrical;
if (option.Index("sph") != kNPOS)
parsedOption.fCoordType = kGLSpherical;
//Define plot type
if (option.Index("lego") != kNPOS)
fStack ? parsedOption.fPlotType = kGLStackPlot : parsedOption.fPlotType = kGLLegoPlot;
if (option.Index("surf") != kNPOS)
parsedOption.fPlotType = kGLSurfacePlot;
if (option.Index("tf3") != kNPOS)
parsedOption.fPlotType = kGLTF3Plot;
if (option.Index("box") != kNPOS)
parsedOption.fPlotType = kGLBoxPlot;
return parsedOption;
}
//______________________________________________________________________________
void TGLPadHistPainter::CreatePainter(const TGLPlotOption_t &option, const TString &addOption)
{
// Create painter.
if (option.fPlotType != fPlotType)
fGLPainter.reset(0);
if (option.fPlotType == kGLLegoPlot) {
if (!fGLPainter.get())
fGLPainter.reset(new TGLLegoPainter(fHist, &f2DAxisPainter));
f2DAxisPainter.SetPlotFrame(static_cast<TGLLegoPainter *>(fGLPainter.get()));
} else if (option.fPlotType == kGLSurfacePlot) {
// if (!fGLPainter.get())
// fGLPainter.reset(new TGLSurfacePainter(fHist));
} else if (option.fPlotType == kGLBoxPlot) {
// if (!fGLPainter.get())
// fGLPainter.reset(new TGLBoxPainter(fHist));
} else if (option.fPlotType == kGLTF3Plot) {
// if (!fGLPainter.get())
// fGLPainter.reset(new TGLTF3Painter(fHist));
}
if (fGLPainter.get()) {
fPlotType = option.fPlotType;
fGLPainter->SetLogX(gPad->GetLogx());
fGLPainter->SetLogY(gPad->GetLogy());
fGLPainter->SetLogZ(gPad->GetLogz());
fGLPainter->SetCoordType(option.fCoordType);
if (gPad->GetFrameFillColor() != kWhite)
fGLPainter->SetFrameColor(gROOT->GetColor(gPad->GetFrameFillColor()));
fGLPainter->SetPadColor(gROOT->GetColor(gPad->GetFillColor()));
fGLPainter->AddOption(addOption);
} else
fPlotType = kGLDefaultPlot;
}
//______________________________________________________________________________
void TGLPadHistPainter::SetShowProjection(const char *, Int_t)
{
// Set show projection.
}
This diff is collapsed.
// @(#)root/gl:$Name: $:$Id: TGLUtil.cxx,v 1.25 2006/02/21 16:39:49 brun Exp $
// @(#)root/gl:$Name: $:$Id: TGLUtil.cxx,v 1.26 2006/02/23 16:44:52 brun Exp $
// Author: Richard Maunder 25/05/2005
/*************************************************************************
......@@ -895,3 +895,78 @@ void TGLUtil::DrawRing(const TGLVertex3 & center, const TGLVector3 & normal,
glPopMatrix();
}
namespace RootGL {
//______________________________________________________________________________
TGLEnableGuard::TGLEnableGuard(Int_t cap)
: fCap(cap)
{
// TGLEnableGuard constructor.
glEnable(GLenum(fCap));
}
//______________________________________________________________________________
TGLEnableGuard::~TGLEnableGuard()
{
// TGLEnableGuard destructor.
glDisable(GLenum(fCap));
}
//______________________________________________________________________________
TGLDisableGuard::TGLDisableGuard(Int_t cap)
: fCap(cap)
{
// TGLDisableGuard constructor.
glDisable(GLenum(fCap));
}
//______________________________________________________________________________
TGLDisableGuard::~TGLDisableGuard()
{
// TGLDisableGuard destructor.
glEnable(GLenum(fCap));
}
}
ClassImp(TGLSelectionBuffer)
//______________________________________________________________________________
TGLSelectionBuffer::TGLSelectionBuffer()
: fWidth(0)
{
// TGLSelectionBuffer constructor.
}
//______________________________________________________________________________
TGLSelectionBuffer::~TGLSelectionBuffer()
{
// TGLSelectionBuffer destructor.
}
//______________________________________________________________________________
void TGLSelectionBuffer::ReadColorBuffer(Int_t w, Int_t h)
{
// Read color buffer.
fWidth = w;
fHeight = h;
fBuffer.resize(w * h * 4);
glPixelStorei(GL_PACK_ALIGNMENT, 1);
glReadPixels(0, 0, w, h, GL_RGBA, GL_UNSIGNED_BYTE, &fBuffer[0]);
}
//______________________________________________________________________________
const UChar_t *TGLSelectionBuffer::GetPixelColor(Int_t px, Int_t py)const
{
// Get pixel color.
if (px < 0)
px = 0;
if (py < 0)
py = 0;
if (px * fWidth * 4 + py * 4 > fBuffer.size())
return &fBuffer[0];
return &fBuffer[px * fWidth * 4 + py * 4];
}
// @(#)root/win32gdk:$Name: $:$Id: TGWin32GL.cxx,v 1.12 2006/03/09 11:18:31 brun Exp $
// @(#)root/win32gdk:$Name: $:$Id: TGWin32GL.cxx,v 1.13 2006/06/06 11:49:01 couet Exp $
// Author: Valeriy Onuchin(TGWin32GL)/ Timur Pocheptsov (TGWin32GLManager)
/*************************************************************************
......@@ -426,7 +426,7 @@ Bool_t TGWin32GLManager::CreateDIB(TGLContext &ctx)const
CDCGuard dcGuard(dibDC);
BITMAPINFOHEADER bmpHeader = {sizeof bmpHeader, ctx.fW, ctx.fH, 1, 24, BI_RGB};
BITMAPINFOHEADER bmpHeader = {sizeof bmpHeader, ctx.fW, ctx.fH, 1, 32, BI_RGB};
void *bmpCnt = 0;
HBITMAP hDIB = CreateDIBSection(dibDC, (BITMAPINFO*)&bmpHeader, DIB_RGB_COLORS, &bmpCnt, 0, 0);
......@@ -507,7 +507,7 @@ void TGWin32GLManager::ReadGLBuffer(Int_t ctxInd)
if (ctx.fPixmapIndex != -1) {
glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
glReadBuffer(GL_BACK);
glReadPixels(0, 0, ctx.fW, ctx.fH, GL_BGR_EXT, GL_UNSIGNED_BYTE, ctx.fDIBData);
glReadPixels(0, 0, ctx.fW, ctx.fH, GL_BGRA_EXT, GL_UNSIGNED_BYTE, ctx.fDIBData);
}
}
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment