17 : m_className(
"ViewCell"),
19 m_useWireMarker(true),
20 m_label(
"Cell Layout"),
22 m_hasExternalCanvas(false),
38 if (!m_hasExternalCanvas && m_canvas != NULL)
delete m_canvas;
46 std::cerr << m_className <<
"::SetComponent:\n";
47 std::cerr <<
" Component pointer is null.\n";
56 if (c == NULL)
return;
57 if (!m_hasExternalCanvas && m_canvas != NULL) {
62 m_hasExternalCanvas =
true;
67 const double& xmax,
const double& ymax,
71 if (xmin == xmax || ymin == ymax || zmin == zmax) {
72 std::cout << m_className <<
"::SetArea:\n";
73 std::cout <<
" Null area range not permitted.\n";
76 m_xMin = std::min(xmin, xmax);
77 m_yMin = std::min(ymin, ymax);
78 m_zMin = std::min(zmin, zmax);
79 m_xMax = std::max(xmin, xmax);
80 m_yMax = std::max(ymin, ymax);
81 m_zMax = std::max(zmin, zmax);
90 std::cerr << m_className <<
"::Plot2d:\n";
91 std::cerr <<
" Error creating 2d plot.\n";
98 std::cerr << m_className <<
"::Plot3d:\n";
99 std::cerr <<
" Error creating 3d plot.\n";
103bool ViewCell::Plot(
const bool use3d) {
105 if (m_component == NULL) {
106 std::cerr << m_className <<
"::Plot:\n";
107 std::cerr <<
" Component is not defined.\n";
111 double pmin = 0., pmax = 0.;
113 std::cerr << m_className <<
"::Plot:\n";
114 std::cerr <<
" Component is not ready.\n";
119 double x0 = m_xMin, y0 = m_yMin, z0 = m_zMin;
120 double x1 = m_xMax, y1 = m_yMax, z1 = m_zMax;
121 if (!m_hasUserArea) {
123 std::cerr << m_className <<
"::Plot:\n";
124 std::cerr <<
" Bounding box cannot be determined.\n";
125 std::cerr <<
" Call SetArea first.\n";
130 const double dx = std::max(
fabs(x0),
fabs(x1));
131 const double dy = std::max(
fabs(y0),
fabs(y1));
132 const double dz = std::max(
fabs(z0),
fabs(z1));
134 if (m_canvas == NULL) {
135 m_canvas =
new TCanvas();
136 if (!use3d) m_canvas->SetTitle(m_label.c_str());
137 if (m_hasExternalCanvas) m_hasExternalCanvas =
false;
140 m_canvas->Range(x0 - 0.1 * (x1 - x0), y0 - 0.1 * (y1 - y0),
141 x1 + 0.1 * (x1 - x0), y1 + 0.1 * (y1 - y0));
146 const std::string cellType = m_component->
GetCellType();
149 double sx = 0., sy = 0.;
153 int nMaxX = 0, nMinX = 0;
154 int nMaxY = 0, nMinY = 0;
156 nMinX = int(x0 / sx) - 1;
157 nMaxX = int(x1 / sx) + 1;
160 nMinY = int(y0 / sy) - 1;
161 nMaxY = int(y1 / sy) + 1;
166 m_geoManager =
new TGeoManager(
"ViewCellGeoManager", m_label.c_str());
167 TGeoMaterial* matVacuum =
new TGeoMaterial(
"Vacuum", 0., 0., 0.);
168 TGeoMaterial* matMetal =
new TGeoMaterial(
"Metal", 63.546, 29., 8.92);
169 TGeoMedium* medVacuum =
new TGeoMedium(
"Vacuum", 1, matVacuum);
170 TGeoMedium* medMetal =
new TGeoMedium(
"Metal", 1, matMetal);
171 m_media.push_back(medVacuum);
172 m_media.push_back(medMetal);
173 TGeoVolume* world = m_geoManager->MakeBox(
"World", medVacuum,
174 1.05 * dx, 1.05 * dy, 1.05 * dz);
175 m_geoManager->SetTopVolume(world);
176 m_volumes.push_back(world);
181 std::vector<std::string> wireTypes;
184 for (
int i = nWires; i--;) {
185 double xw = 0., yw = 0., dw = 0., vw = 0., lw = 0., qw = 0.;
189 m_component->
GetWire(i, xw, yw, dw, vw, lbl, lw, qw, nTrap);
191 if (nWireTypes == 0) {
192 wireTypes.push_back(lbl);
196 for (
int j = nWireTypes; j--;) {
197 if (lbl == wireTypes[j]) {
203 wireTypes.push_back(lbl);
208 for (
int nx = nMinX; nx <= nMaxX; ++nx) {
209 for (
int ny = nMinY; ny <= nMaxY; ++ny) {
210 const double x = xw + nx * sx;
211 const double y = yw + ny * sy;
212 if (x + 0.5 * dw <= x0 || x - 0.5 * dw >= x1 || y + 0.5 * dw <= y0 ||
213 y - 0.5 * dw >= y1) {
217 TGeoVolume* wire = m_geoManager->MakeTube(
"Wire", m_media[1],
219 std::min(0.5 * lw, dz));
222 wire->SetLineColor(kBlue);
225 wire->SetLineColor(kRed + 2);
228 wire->SetLineColor(kPink + 3);
231 wire->SetLineColor(kCyan + 3);
234 wire->SetLineColor(kBlue + type);
237 m_volumes.push_back(wire);
238 m_geoManager->GetTopVolume()->AddNode(wire, 1,
239 new TGeoTranslation(x, y, 0.));
241 PlotWire(x, y, dw, type);
249 for (
int i = nPlanesX; i--;) {
250 double xp = 0., vp = 0.;
253 for (
int nx = nMinX; nx <= nMaxX; ++nx) {
254 const double x = xp + nx * sx;
255 if (x < x0 || x > x1)
continue;
257 const double width = 0.01;
258 TGeoVolume* plane = m_geoManager->MakeBox(
"PlaneX", m_media[1],
260 plane->SetLineColor(kGreen + 2);
261 m_volumes.push_back(plane);
262 m_geoManager->GetTopVolume()->AddNode(plane, 1,
263 new TGeoTranslation(x, 0., 0.));
265 PlotLine(x, y0, x, y1);
272 for (
int i = nPlanesY; i--;) {
273 double yp = 0., vp = 0.;
276 for (
int ny = nMinY; ny <= nMaxY; ++ny) {
277 const double y = yp + ny * sy;
278 if (y < y0 || y > y1)
continue;
280 const double width = 0.01;
281 TGeoVolume* plane = m_geoManager->MakeBox(
"PlaneY", m_media[1],
283 plane->SetLineColor(kGreen + 2);
284 m_volumes.push_back(plane);
285 m_geoManager->GetTopVolume()->AddNode(plane, 1,
286 new TGeoTranslation(0., y, 0.));
288 PlotLine(x0, y, x1, y);
293 double rt = 0., vt = 0.;
296 if (m_component->
GetTube(rt, vt, nt, lbl)) {
300 TGeoVolume* tube = m_geoManager->MakeTube(
"Tube", m_media[1],
301 0.98 * rt, 1.02 * rt, dz);
302 tube->SetLineColor(kGreen + 2);
303 m_volumes.push_back(tube);
304 m_geoManager->GetTopVolume()->AddNode(tube, 1,
305 new TGeoTranslation(0., 0., 0.));
307 TGeoVolume* tube = m_geoManager->MakePgon(
"Tube", m_media[1],
309 TGeoPgon* pgon =
dynamic_cast<TGeoPgon*
>(tube->GetShape());
310 pgon->DefineSection(0, -dz, 0.98 * rt, 1.02 * rt);
311 pgon->DefineSection(1, +dz, 0.98 * rt, 1.02 * rt);
312 tube->SetLineColor(kGreen + 2);
313 m_volumes.push_back(tube);
314 m_geoManager->GetTopVolume()->AddNode(tube, 1,
315 new TGeoTranslation(0., 0., 0.));
318 PlotTube(0., 0., rt, nt);
323 m_geoManager->CloseGeometry();
324 m_geoManager->GetTopNode()->Draw(
"ogl");
332void ViewCell::PlotWire(
const double& x,
const double& y,
const double& d,
335 if (m_useWireMarker) {
338 markerStyle = kFullCircle;
339 }
else if (type == 1) {
340 markerStyle = kOpenCircle;
341 }
else if (type == 2) {
342 markerStyle = kFullSquare;
343 }
else if (type == 3) {
344 markerStyle = kOpenSquare;
346 markerStyle = 26 + type;
348 TMarker* marker =
new TMarker(x, y, markerStyle);
353 TEllipse* circle =
new TEllipse(x, y, 0.5 * d);
357void ViewCell::PlotLine(
const double& x0,
const double& y0,
358 const double& x1,
const double& y1) {
360 TLine* line =
new TLine(x0, y0, x1, y1);
364void ViewCell::PlotTube(
const double& x0,
const double& y0,
const double& r,
368 TEllipse* circle =
new TEllipse(x0, y0, r);
369 circle->SetFillStyle(0);
374 TPolyLine* pline =
new TPolyLine(n + 1);
375 for (
int i = 0; i <= n; ++i) {
376 const double x = x0 + r *
cos(i * TwoPi /
double(n));
377 const double y = y0 + r *
sin(i * TwoPi /
double(n));
378 pline->SetPoint(i, x, y);
383void ViewCell::Reset() {
385 for (std::vector<TGeoVolume*>::iterator it = m_volumes.begin();
386 it != m_volumes.end(); ++it) {
388 TGeoShape* shape = (*it)->GetShape();
389 if (shape)
delete shape;
394 for (std::vector<TGeoMedium*>::iterator it = m_media.begin();
395 it != m_media.end(); ++it) {
397 TGeoMaterial* material = (*it)->GetMaterial();
398 if (material)
delete material;
DoubleAc cos(const DoubleAc &f)
DoubleAc sin(const DoubleAc &f)
DoubleAc fabs(const DoubleAc &f)
bool GetVoltageRange(double &pmin, double &pmax)
bool GetPeriodicityY(double &s)
std::string GetCellType()
bool GetPlaneX(const int i, double &x, double &voltage, std::string &label)
bool GetPeriodicityX(double &s)
bool GetBoundingBox(double &x0, double &y0, double &z0, double &x1, double &y1, double &z1)
bool GetWire(const int i, double &x, double &y, double &diameter, double &voltage, std::string &label, double &length, double &charge, int &ntrap)
bool GetPlaneY(const int i, double &y, double &voltage, std::string &label)
bool GetTube(double &r, double &voltage, int &nEdges, std::string &label)
void SetCanvas(TCanvas *c)
void SetComponent(ComponentAnalyticField *comp)
PlottingEngineRoot plottingEngine