58 fCurrentPixelsPerBin(0),
88 fM = SetModelDynCast<TEveCaloLego>(obj);
161 glNormal3f(0, 0, -1);
162 glVertex3f(x2, y2, z1);
163 glVertex3f(x2, y1, z1);
164 glVertex3f(x1, y1, z1);
165 glVertex3f(x1, y2, z1);
168 glVertex3f(x2, y2, z2);
169 glVertex3f(x1, y2, z2);
170 glVertex3f(x1, y1, z2);
171 glVertex3f(x2, y1, z2);
175 glVertex3f(x2, y2, z1);
176 glVertex3f(x2, y2, z2);
177 glVertex3f(x2, y1, z2);
178 glVertex3f(x2, y1, z1);
180 glNormal3f(-1, 0, 0);
181 glVertex3f(x1, y2, z1);
182 glVertex3f(x1, y1, z1);
183 glVertex3f(x1, y1, z2);
184 glVertex3f(x1, y2, z2);
188 glVertex3f(x2, y2, z1);
189 glVertex3f(x1, y2, z1);
190 glVertex3f(x1, y2, z2);
191 glVertex3f(x2, y2, z2);
193 glNormal3f(0, -1, 0);
194 glVertex3f(x2, y1, z1);
195 glVertex3f(x2, y1, z2);
196 glVertex3f(x1, y1, z2);
197 glVertex3f(x1, y1, z1);
214 for (
Int_t s = 0; s < nSlices; ++s)
216 if (dlMap.empty() || dlMap[s] == 0)
217 dlMap[s] = glGenLists(1);
219 glNewList(dlMap[s], GL_COMPILE);
221 for (
UInt_t i = 0; i < cellList.size(); ++i)
223 if (cellList[i].fSlice > s)
continue;
224 if (cellList[i].fTower != prevTower) {
226 prevTower = cellList[i].fTower;
230 if (s == cellList[i].fSlice)
232 if (selection) glLoadName(i);
255 for (
Int_t s = 0; s < nSlices; ++s)
257 if (dlMap.empty() || dlMap[s] == 0)
258 dlMap[s] = glGenLists(1);
260 glNewList(dlMap[s], GL_COMPILE);
272 for (
Int_t t = 0; t < s; ++t)
279 if (selection) glLoadName(bin);
298 glGetDoublev(GL_MODELVIEW_MATRIX, mm);
299 glGetIntegerv(GL_VIEWPORT, vp);
300 GLdouble projX[4], projY[4], projZ[4];
304 cornerX[0] = x0; cornerY[0] = y0;
305 cornerX[1] =
x1; cornerY[1] = y0;
306 cornerX[2] =
x1; cornerY[2] = y1;
307 cornerX[3] = x0; cornerY[3] = y1;
309 gluProject(cornerX[0], cornerY[0], 0, mm, pm, vp, &projX[0], &projY[0], &projZ[0]);
310 gluProject(cornerX[1], cornerY[1], 0, mm, pm, vp, &projX[1], &projY[1], &projZ[1]);
311 gluProject(cornerX[2], cornerY[2], 0, mm, pm, vp, &projX[2], &projY[2], &projZ[2]);
312 gluProject(cornerX[3], cornerY[3], 0, mm, pm, vp, &projX[3], &projY[3], &projZ[3]);
319 for (
Int_t i = 1; i < 4; ++i) {
333 for (
Int_t i = 0; i < 4; ++i) {
338 if (projZ[i] > zMin) zMin = projZ[i];
342 Int_t xyIdx = idxFront;
343 if (zMin - zt < 1
e-2) xyIdx = 0;
388 for (
Int_t i = 0; i < 4; ++i)
390 if (projZ[i] < zm && projZ[i] >= zt && i != idxFront )
396 if (idxFront == idxLeft) idxFront =idxDepthT;
430 glGetDoublev(GL_MODELVIEW_MATRIX, mm.
Arr());
431 glGetDoublev(GL_PROJECTION_MATRIX, pm);
438 + (up[1] - dn[1]) * (up[1] - dn[1])
439 + (up[2] - dn[2]) * (up[2] - dn[2]));
489 glPushAttrib(GL_ENABLE_BIT | GL_LINE_BIT);
516 glEnable(GL_LINE_STIPPLE);
517 glLineStipple(1, 0x5555);
520 for (
Int_t i = 1; i <= ondiv; ++i, hz += bw1) {
587 Double_t unit = ((eM -
em) < (pM - pm)) ? (eM - em) : (pM - pm);
628 glGetDoublev(GL_MODELVIEW_MATRIX, mm.
Arr());
629 glGetDoublev(GL_PROJECTION_MATRIX, pm);
630 glGetIntegerv(GL_VIEWPORT, vp);
637 + (up[1] - dn[1]) * (up[1] - dn[1])
638 + (up[2] - dn[2]) * (up[2] - dn[2]));
692 GLint vp[4]; glGetIntegerv(GL_VIEWPORT, vp);
693 Float_t viewportD =
TMath::Sqrt((vp[1] - vp[0]) * (vp[1] - vp[0]) + (vp[3] - vp[1]) * (vp[3] - vp[1]));
694 Float_t deltaToViewport = viewportD/frustD;
697 GLdouble
em, eM, pm, pM;
706 Float_t ppb = deltaToViewport*averageBinWidth;
715 if (ngroup > maxGroup) ngroup = maxGroup;
731 if (bc > center) --idx0;
735 std::vector<Double_t> bins(nbR + 1);
736 for (
Int_t i = 0; i <= nbR; ++i)
740 curr->
Set(nbR, &bins[0]);
758 glVertex2f(eta0, phi0);
759 glVertex2f(eta0, phi1);
760 glVertex2f(eta1, phi0);
761 glVertex2f(eta1, phi1);
763 glVertex2f(eta0, phi0);
764 glVertex2f(eta1, phi0);
765 glVertex2f(eta0, phi1);
766 glVertex2f(eta1, phi1);
771 for (
Int_t i = 0; i<= neb; i++)
774 if (val > eta0 && val < eta1 )
776 glVertex2f(val, phi0);
777 glVertex2f(val, phi1);
783 for (
Int_t i = 1; i <= npb; i++) {
785 if (val > phi0 && val < phi1)
787 glVertex2f(eta0, val);
788 glVertex2f(eta1, val);
796 glPushAttrib(GL_ENABLE_BIT | GL_LINE_BIT | GL_POLYGON_BIT);
819 glLoadName(i->first);
821 glCallList(i->second);
828 glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
829 glDisable(GL_POLYGON_OFFSET_FILL);
832 glCallList(i->second);
842 Int_t max_energy_slice, cellID=0;
845 TEveCaloData::vCellId_t::iterator currentCell = cellList.begin();
846 TEveCaloData::vCellId_t::iterator nextCell = currentCell;
856 max_energy_slice = currentCell->fSlice;
857 while (nextCell != cellList.end() && currentCell->fTower == nextCell->fTower)
862 if (energy > max_energy)
865 max_energy_slice = nextCell->fSlice;
872 cells2D.push_back(
Cell2D_t(cellID, sum, max_energy_slice));
873 cells2D.back().SetGeom(currentCellData.
fEtaMin, currentCellData.
fEtaMax,
876 if (nextCell == cellList.end())
879 currentCell = nextCell;
892 std::vector<Float_t> vec;
893 vec.assign((nEta + 2)*(nPhi + 2), 0.
f);
894 std::vector<Float_t> max_e;
895 std::vector<Int_t> max_e_slice;
896 max_e.assign((nEta + 2) * (nPhi + 2), 0.
f);
897 max_e_slice.assign((nEta + 2) * (nPhi + 2), -1);
901 if (rebinData.
fBinData[bin] != -1) {
905 if (val[s] > max_e[bin]) {
907 max_e_slice[bin] = s;
924 const Int_t bin = j * (nEta + 2) + i;
925 if (vec[bin] > threshold && rebinData.
fBinData[bin] != -1) {
926 cells2D.push_back(
Cell2D_t(bin, vec[bin], max_e_slice[bin]));
949 for (
vCell2D_i i = cells2D.begin(); i != cells2D.end(); ++i)
957 glVertex3f(i->fX0, i->fY0, z);
958 glVertex3f(i->fX1, i->fY0, z);
959 glVertex3f(i->fX1, i->fY1, z);
960 glVertex3f(i->fX0, i->fY1, z);
970 if (i->MinSize() < bws) bws = i->MinSize();
971 if (i->fSumVal > maxv) maxv = i->fSumVal;
981 for (
vCell2D_i i = cells2D.begin(); i != cells2D.end(); ++i)
983 glLoadName(i->fMaxSlice);
988 glVertex3f(i->fX0, i->fY0, z);
989 glVertex3f(i->fX1, i->fY0, z);
990 glVertex3f(i->fX1, i->fY1, z);
991 glVertex3f(i->fX0, i->fY1, z);
1004 for (
vCell2D_i i = cells2D.begin(); i != cells2D.end(); ++i)
1008 glVertex3f(i->X(), i->Y() ,
z);
1014 for (
vCell2D_i i = cells2D.begin(); i != cells2D.end(); ++i)
1021 glVertex3f(x - bw, y - bw, z);
1022 glVertex3f(x + bw, y - bw, z);
1023 glVertex3f(x + bw, y + bw, z);
1024 glVertex3f(x - bw, y + bw, z);
1030 glPushAttrib(GL_ENABLE_BIT | GL_POLYGON_BIT);
1034 for (
vCell2D_i i = cells2D.begin(); i != cells2D.end(); ++i) {
1039 glVertex3f(i->fX0, i->fY0, z);
1040 glVertex3f(i->fX1, i->fY0, z);
1041 glVertex3f(i->fX1, i->fY1, z);
1042 glVertex3f(i->fX0, i->fY1, z);
1046 glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
1048 for (
vCell2D_i i = cells2D.begin(); i != cells2D.end(); ++i) {
1052 glVertex3f(i->fX0, i->fY0, z);
1053 glVertex3f(i->fX1, i->fY0, z);
1054 glVertex3f(i->fX1, i->fY1, z);
1055 glVertex3f(i->fX0, i->fY1, z);
1071 for (
vCell2D_i i = cells2D.begin(); i != cells2D.end(); ++i) {
1077 txt =
Form(
"%.1f", val);
1078 else if (val > 0.01 )
1102 glScalef(sx, sy, sz);
1107 glPushAttrib(GL_ENABLE_BIT | GL_LINE_BIT | GL_POLYGON_BIT);
1108 glDisable(GL_LIGHTING);
1109 glDisable(GL_CULL_FACE);
1110 glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
1148 cellsSelected.push_back(*i);
1158 for (std::vector<Float_t>::iterator it = rebinDataSelected.
fSliceData.begin(); it != rebinDataSelected.
fSliceData.end(); it++)
1172 Int_t orig_slice = j->fSlice;
1173 for (
Int_t s = 0; s < orig_slice; ++s)
1179 j->fSlice = orig_slice;
1198 if (rebinDataSelected.
fBinData[bin] !=-1)
1203 for (
Int_t s = 0; s < nSlices; ++s)
1213 offset += valsRef[s];
1228 std::set<Int_t> towers;
1231 towers.insert(j->fTower);
1238 if (towers.find(cell.
fTower) != towers.end())
1240 cells2DSelected.push_back(*i);
1316 glScalef(sx, sy, sz);
1326 if (fFontColor < 0) {
1340 glPushAttrib(GL_ENABLE_BIT | GL_LINE_BIT | GL_POLYGON_BIT);
1343 glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
1357 glEnable(GL_NORMALIZE);
1358 glEnable(GL_POLYGON_OFFSET_FILL);
1359 glPolygonOffset(0.8, 1);
1365 glDisable(GL_LIGHTING);
1382 glPushAttrib(GL_ENABLE_BIT | GL_LINE_BIT | GL_POLYGON_BIT);
1383 glDisable(GL_LIGHTING);
1386 glBlendFunc(GL_ONE, GL_ONE_MINUS_SRC_ALPHA);
1387 glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
1388 glDisable(GL_CULL_FACE);
1391 glBegin(GL_POLYGON);
1418 while (cell > 0 && tower ==
fM->
fCellList[cell].fTower)
1431 Int_t etaBin = cell - phiBin*(nEta+2);
1440 if ((*it).fSlice == slice ) sel.push_back(*it);
1442 if ((*it).fSlice <= slice ) sel.push_back(*it);
TEveRGBAPalette * AssertPalette()
Make sure the TEveRGBAPalette pointer is not null.
virtual void DLCacheDrop()
Drop all entries for all LODs for this drawable from the display list cache, WITHOUT returning the re...
void DrawSelectedCells(TGLRnrCtx &rnrCtx, TEveCaloData::vCellId_t cells) const
Draw selected cells in highlight mode.
virtual Float_t GetTickLength() const
vCellId_t & GetCellsSelected()
TEveCaloData * GetData() const
Float_t GetMaxTowerH() const
void Make3DDisplayListRebin(TEveCaloData::RebinData_t &rebinData, SliceDLMap_t &map, Bool_t select) const
Create display-list that draws histogram bars for rebinned data.
The TGLRnrCtx class aggregates data for a given redering context as needed by various parts of the RO...
static long int sum(long int i)
Bool_t SecSelection() const
virtual TAxis * GetEtaBins() const
Abstract base camera class - concrete classes for orthographic and perspective cameras derive from it...
static void Color(const TGLColor &color)
Set color from TGLColor.
std::vector< CellId_t >::iterator vCellId_i
virtual void SetLimits(Double_t xmin, Double_t xmax)
static void ColorTransparency(Color_t color_index, Char_t transparency=0)
Set color from color_index and ROOT-style transparency (default 0).
void Set(const Float_t *v)
virtual ~TEveCaloLegoGL()
Destructor.
virtual Float_t GetLabelOffset() const
void SetTitlePixelFontSize(Int_t fs)
bool GetHasFixedHeightIn2DMode() const
void PrepareCell2DDataRebin(TEveCaloData::RebinData_t &rebinData, vCell2D_t &cells2D) const
Prepare cells 2D rebinned data for drawing.
virtual Double_t GetBinLowEdge(Int_t bin) const
Return low edge of bin.
virtual void DLCachePurge()
Unregister all display-lists.
OpenGL renderer class for TEveCaloLego.
void MakeQuad(Float_t x, Float_t y, Float_t z, Float_t xw, Float_t yw, Float_t zh) const
Draw an axis-aligned box using quads.
16 component (4x4) transform matrix - column MAJOR as per GL.
std::vector< Int_t > fBinData
virtual void SetLabelColor(Color_t color=1, Float_t alpha=1.)
Set color of labels.
void DrawCells3D(TGLRnrCtx &rnrCtx) const
Render the calo lego-plot with OpenGL.
virtual void SetNdivisions(Int_t n=510, Bool_t optim=kTRUE)
Set the number of divisions for this axis.
Float_t GetPhiMax() const
static void Optimize(Double_t A1, Double_t A2, Int_t nold, Double_t &BinLow, Double_t &BinHigh, Int_t &nbins, Double_t &BWID, Option_t *option="")
static function to compute reasonable axis limits
void SetFontMode(TGLFont::EMode m)
TEveCaloLegoGL()
Constructor.
void SetAxisAlignedBBox(Float_t xmin, Float_t xmax, Float_t ymin, Float_t ymax, Float_t zmin, Float_t zmax)
Set axis-aligned bounding-box.
virtual void SetTitleFont(Style_t font=62)
Set the title font.
Short_t Min(Short_t a, Short_t b)
Char_t GetSliceTransparency(Int_t slice) const
Get transparency for given slice.
std::vector< Cell2D_t >::iterator vCell2D_i
void RegisterFontNoScale(Int_t size, Int_t file, Int_t mode, TGLFont &out)
Get font in the GL rendering context.
Int_t FloorNint(Double_t x)
virtual Float_t GetLabelSize() const
TGLAxisPainter fAxisPainter
Char_t fPlaneTransparency
void Set(Double_t x, Double_t y, Double_t z)
virtual void SetLabelOffset(Float_t offset=0.005)
Set distance between the axis and the labels The distance is expressed in per cent of the pad width...
Float_t GetEtaRng() const
void DrawHistBase(TGLRnrCtx &rnrCtx) const
Draw basic histogram components: x-y grid.
virtual Double_t GetBinUpEdge(Int_t bin) const
Return up edge of bin.
Concrete physical shape - a GL drawable.
Float_t GetEtaMin() const
TGLVector3 & RefTMOff(Int_t i)
virtual Style_t GetTitleFont() const
void PrepareCell2DData(TEveCaloData::vCellId_t &cellList, vCell2D_t &cells2D) const
Prepare cells 2D data non-rebinned for drawing.
void Make3DDisplayList(TEveCaloData::vCellId_t &cellList, SliceDLMap_t &map, Bool_t select) const
Create display-list that draws histogram bars for non-rebinned data.
Bool_t IsDrawPassFilled() const
Returns true if current render-pass uses filled polygon style.
virtual void GetCellList(Float_t etaMin, Float_t etaMax, Float_t phi, Float_t phiRng, vCellId_t &out) const =0
static const double x2[5]
void RebinAxis(TAxis *orig, TAxis *curr) const
Rebin eta, phi axis.
float GetFixedHeightValIn2DMode() const
you should not use this method at all Int_t Int_t Double_t Double_t em
3 component (x/y/z) vertex class.
Int_t fCurrentPixelsPerBin
const UChar_t * CArr() const
Double_t Log10(Double_t x)
Float_t GetPhiMin() const
virtual Double_t GetBinCenter(Int_t bin) const
Return center of bin.
TEveVector fXAxisTitlePos
void DrawCells2D(TGLRnrCtx &rnrCtx, vCell2D_t &cells2D) const
Draw cells in top view.
void DrawAxis2D(TGLRnrCtx &rnrCtx) const
Draw XY axis.
Base-class for direct OpenGL renderers.
TEveVector fYAxisTitlePos
TGLVector3 & RefTitlePos()
3 component (x/y/z) vector class.
std::vector< CellId_t > vCellId_t
const TGLMatrix & GetCamBase() const
const UChar_t * ColorFromValue(Int_t val) const
virtual void GetPhiLimits(Double_t &min, Double_t &max) const =0
static UInt_t LockColor()
Prevent further color changes.
static UInt_t UnlockColor()
Allow color changes.
void GetScaleForMatrix(Float_t &sx, Float_t &sy, Float_t &sz) const
Get scale for matrix.
TEveCaloData::RebinData_t fRebinData
virtual void DLCachePurge()
Purge all entries for all LODs for this drawable from the display list cache, returning the reserved ...
TObject * fExternalObj
first replica
TEveVector fBackPlaneYConst[2]
void DrawAxis3D(TGLRnrCtx &rnrCtx) const
Draw z-axis and z-box at the appropriate grid corner-point including tick-marks and labels...
void SetAxis3DTitlePos(TGLRnrCtx &rnrCtx, Float_t x0, Float_t x1, Float_t y0, Float_t y1) const
Set the axis 3D title position.
virtual Int_t GetNdivisions() const
TGLVector3 ViewportDeltaToWorld(const TGLVertex3 &worldRef, Double_t viewportXDelta, Double_t viewportYDelta, TGLMatrix *modviewMat=0) const
Apply a 2D viewport delta (shift) to the projection of worldRef onto viewport, returning the resultan...
void PaintAxis(TGLRnrCtx &ctx, TAxis *ax)
GL render TAxis.
virtual void DLCacheDrop()
Drop all display-list definitions.
const char * GetTitle() const
Returns title of object.
Class to manage histogram axis.
Short_t SceneStyle() const
void ProcessSelection(vCellId_t &sel_cells, TGLSelectRecord &rec)
Process newly selected cells with given select-record.
Standard selection record including information about containing scene and details ob out selected ob...
Int_t GetLabelPixelFontSize() const
void WrapTwoPi(Float_t &min, Float_t &max) const
const Double_t * CArr() const
char * Form(const char *fmt,...)
std::map< Int_t, UInt_t > SliceDLMap_t
TEveCaloData::vCellId_t fCellList
virtual void GetCellData(const CellId_t &id, CellData_t &data) const =0
static Int_t GetColor(const char *hexcolor)
Static method returning color number for color specified by hex color string of form: "#rrggbb"...
virtual void DrawHighlight(TGLRnrCtx &rnrCtx, const TGLPhysicalShape *ps, Int_t lvl=-1) const
Draw highligted cells.
Int_t fDrawNumberCellPixels
EProjection_e fProjection
virtual void SetAxisColor(Color_t color=1, Float_t alpha=1.)
Set color of the line axis and tick marks.
void SetLabelAlign(TGLFont::ETextAlignH_e, TGLFont::ETextAlignV_e)
Set label align.
vCellId_t & GetCellsHighlighted()
virtual void SetBBox()
Set bounding box.
Float_t GetDataSliceThreshold(Int_t slice) const
Get threshold for given slice.
virtual void SetTitleColor(Color_t color=1)
Set color of axis title.
virtual void SetTitleSize(Float_t size=0.04)
Set size of axis title The size is expressed in per cent of the pad width.
Int_t Diagonal() const
Return the diagonal of the rectangle.
virtual Bool_t IsOrthographic() const
std::vector< Cell2D_t > vCell2D_t
virtual Int_t FindBin(Double_t x)
Find bin number corresponding to abscissa x.
Visualization of calorimeter data as eta/phi histogram.
static const double x1[5]
Float_t GetEtaMax() const
UInt_t GetItem(Int_t i) const
Color_t GetSliceColor(Int_t slice) const
Get color for given slice.
Color_t GetColorIndex() const
Returns color-index representing the color.
you should not use this method at all Int_t Int_t Double_t Double_t Double_t e
The color creation and management class.
Bool_t CellInEtaPhiRng(TEveCaloData::CellData_t &) const
Returns true if given cell is in the ceta phi range.
virtual TAxis * GetPhiBins() const
virtual Float_t GetTitleSize() const
Double_t Hypot(Double_t x, Double_t y)
std::map< Int_t, UInt_t >::iterator SliceDLMap_i
Bool_t AssertCellIdCache() const
Assert cell id cache is ok.
Mother of all ROOT objects.
virtual Bool_t SetModel(TObject *obj, const Option_t *opt=0)
Set model object.
you should not use this method at all Int_t Int_t z
std::vector< Float_t > fSliceData
virtual void GetEtaLimits(Double_t &min, Double_t &max) const =0
TGLColor & Selection(Int_t i)
virtual void ProcessSelection(TGLRnrCtx &rnrCtx, TGLSelectRecord &rec)
Processes tower selection from TGLViewer.
Float_t GetMaxVal() const
virtual Double_t GetBinWidth(Int_t bin) const
Return bin width.
double f2(const double *x)
Short_t Max(Short_t a, Short_t b)
Int_t GetGridStep(TGLRnrCtx &rnrCtx) const
Calculate view-dependent grid density.
const TGLPlane & FrustumPlane(EFrustumPlane plane) const
Float_t GetPhiRng() const
void SetLabelPixelFontSize(Int_t fs)
you should not use this method at all Int_t Int_t Double_t Double_t Double_t Int_t Double_t Double_t Double_t Double_t b
virtual void SetTickLength(Float_t length=0.03)
Set tick mark length The length is expressed in per cent of the pad width.
void PurgeDLRange(UInt_t base, Int_t size) const
External object is a fake.
TEveVector fBackPlaneXConst[2]
Cell data inner structure.
Color_t GetDataSliceColor(Int_t slice) const
Get slice color from data.
static Float_t LineWidth()
Get the line-width, taking the global scaling into account.
Bool_t fDLCache
display-list validity bit-field
A wrapper class for FTFont.
virtual void DirectDraw(TGLRnrCtx &rnrCtx) const
Draw the object.
TEveRGBAPalette * fPalette
Double_t Sqrt(Double_t x)
TGLColorSet & ColorSet()
Return reference to current color-set (top of the stack).
TEveVector fZAxisTitlePos
Float_t Value(Bool_t) const
Return energy value associated with the cell, usually Et.
virtual void Set(Int_t nbins, Double_t xmin, Double_t xmax)
Initialize axis with fix bins.
virtual void SetTitle(const char *title="")
Set the title of the TNamed.
TGLMatrix & RefLastNoPickProjM() const
virtual void Rebin(TAxis *ax, TAxis *ay, vCellId_t &in, Bool_t et, RebinData_t &out) const =0
static void Color4ubv(const UChar_t *rgba)
Wrapper for glColor4ubv.
Float_t * GetSliceVals(Int_t bin)
TGLVector3 GetBaseVec(Int_t b) const
void SetAttAxis(TAttAxis *a)
const Int_t * CArr() const