18void SampleRange(
const double xmin,
const double ymin,
const double xmax,
19 const double ymax, TF2* f,
double& zmin,
double& zmax) {
20 const unsigned int n = 1000;
21 const double dx = xmax - xmin;
22 const double dy = ymax - ymin;
23 zmin = std::numeric_limits<double>::max();
25 for (
unsigned int i = 0; i < n; ++i) {
28 if (z < zmin) zmin =
z;
29 if (z > zmax) zmax =
z;
33void SampleRange(TF1* f,
double& ymin,
double& ymax) {
34 const unsigned int n = 1000;
35 ymin = std::numeric_limits<double>::max();
37 for (
unsigned int i = 0; i < n; ++i) {
39 if (y < ymin) ymin =
y;
40 if (y > ymax) ymax =
y;
52 if (m_f2d)
delete m_f2d;
53 if (m_f2dW)
delete m_f2dW;
54 if (m_fProfile)
delete m_fProfile;
55 if (m_fProfileW)
delete m_fProfileW;
60 std::cerr <<
m_className <<
"::SetSensor: Null pointer.\n";
65 m_component =
nullptr;
70 std::cerr <<
m_className <<
"::SetComponent: Null pointer.\n";
81 if (xmin == xmax || ymin == ymax) {
82 std::cerr <<
m_className <<
"::SetArea: Null area range is not permitted.\n"
83 <<
" " << xmin <<
" < x < " << xmax <<
"\n"
84 <<
" " << ymin <<
" < y < " << ymax <<
"\n";
87 m_xmin = std::min(xmin, xmax);
88 m_ymin = std::min(ymin, ymax);
89 m_xmax = std::max(xmin, xmax);
90 m_ymax = std::max(ymin, ymax);
95 m_vmin = std::min(vmin, vmax);
96 m_vmax = std::max(vmin, vmax);
97 m_useAutoRange =
false;
101 m_emin = std::min(emin, emax);
102 m_emax = std::max(emin, emax);
103 m_useAutoRange =
false;
107 m_wmin = std::min(wmin, wmax);
108 m_wmax = std::max(wmin, wmax);
109 m_useAutoRange =
false;
113 if (n <= m_nMaxContours) {
116 std::cerr <<
m_className <<
"::SetNumberOfContours:\n"
117 <<
" Max. number of contours is " << m_nMaxContours <<
".\n";
122 constexpr unsigned int nmin = 10;
123 constexpr unsigned int nmax = 100000;
124 if (n < nmin || n > nmax) {
125 std::cerr <<
m_className <<
"::SetNumberOfSamples1d:\n"
126 <<
" Number of points (" << n <<
") out of range.\n"
127 <<
" " << nmin <<
" <= n <= " << nmax <<
"\n";
135 const unsigned int ny) {
136 constexpr unsigned int nmin = 10;
137 constexpr unsigned int nmax = 10000;
138 if (nx < nmin || nx > nmax) {
139 std::cerr <<
m_className <<
"::SetNumberOfSamples2d:\n"
140 <<
" Number of x-points (" << nx <<
") out of range.\n"
141 <<
" " << nmin <<
" <= nx <= " << nmax <<
"\n";
146 if (ny < nmin || ny > nmax) {
147 std::cerr <<
m_className <<
"::SetNumberOfSamples2d:\n"
148 <<
" Number of y-points (" << ny <<
") out of range.\n"
149 <<
" " << nmin <<
" <= ny <= " << nmax <<
"\n";
157 if (!SetupFunction(option, m_f2d,
true,
false))
return;
158 m_f2d->Draw(
"CONT4Z");
159 gPad->SetRightMargin(0.15);
165 if (!SetupFunction(option, m_f2d,
false,
false))
return;
166 m_f2d->Draw(drawopt.c_str());
167 gPad->SetRightMargin(0.15);
172 const double x1,
const double y1,
const double z1,
173 const std::string& option) {
175 if (!SetupProfile(x0, y0, z0, x1, y1, z1, option, m_fProfile,
false))
return;
181 const std::string& option,
182 const std::string& drawopt) {
185 if (!SetupFunction(option, m_f2dW,
false,
true))
return;
186 m_f2dW->Draw(drawopt.c_str());
187 gPad->SetRightMargin(0.15);
192 const std::string& option) {
195 if (!SetupFunction(option, m_f2dW,
true,
true))
return;
196 m_f2dW->Draw(
"CONT4Z");
197 gPad->SetRightMargin(0.15);
202 const double x0,
const double y0,
203 const double z0,
const double x1,
204 const double y1,
const double z1,
205 const std::string& option) {
208 if (!SetupProfile(x0, y0, z0, x1, y1, z1, option, m_fProfileW,
true))
return;
237 if (!m_sensor && !m_component)
return 0.;
240 const double u = pos[0];
241 const double v = pos[1];
242 const double x = m_project[0][0] * u + m_project[1][0] * v + m_project[2][0];
243 const double y = m_project[0][1] * u + m_project[1][1] * v + m_project[2][1];
244 const double z = m_project[0][2] * u + m_project[1][2] * v + m_project[2][2];
247 const PlotType plotType =
static_cast<PlotType
>(int(fabs(par[0]) / 10.));
250 double ex = 0., ey = 0., ez = 0., volt = 0.;
256 m_component->
ElectricField(x, y, z, ex, ey, ez, volt, medium, status);
258 m_sensor->
ElectricField(x, y, z, ex, ey, ez, volt, medium, status);
263 if (plotType == Potential) {
269 if (plotType == Potential) {
279 <<
" At (u, v) = (" << u <<
", " << v <<
"), "
280 <<
" (x,y,z) = (" << x <<
"," << y <<
"," << z <<
")\n"
281 <<
" E = " << ex <<
", " << ey <<
", " << ez
282 <<
"), V = " << volt <<
", status = " << status <<
"\n";
284 if (m_useStatus && status != 0)
return m_vBkg;
291 return sqrt(ex * ex + ey * ey + ez * ez);
309 if (!m_sensor && !m_component)
return 0.;
312 const double x0 = par[0];
313 const double y0 = par[1];
314 const double z0 = par[2];
315 const double x1 = par[3];
316 const double y1 = par[4];
317 const double z1 = par[5];
319 const double dx = x1 - x0;
320 const double dy = y1 - y0;
321 const double dz = z1 - z0;
323 const double t = pos[0];
324 const double x = x0 + t * dx;
325 const double y = y0 + t * dy;
326 const double z = z0 + t * dz;
328 const PlotType plotType =
static_cast<PlotType
>(int(fabs(par[6]) / 10.));
331 double ex = 0., ey = 0., ez = 0., volt = 0.;
337 m_component->
ElectricField(x, y, z, ex, ey, ez, volt, medium, status);
339 m_sensor->
ElectricField(x, y, z, ex, ey, ez, volt, medium, status);
344 if (plotType == Potential) {
350 if (plotType == Potential) {
357 if (m_useStatus && status != 0) volt = m_vBkg;
364 return sqrt(ex * ex + ey * ey + ez * ez);
381void ViewField::Labels() {
383 strcpy(m_xLabel,
"\0");
386 const double tol = 1.e-4;
388 if (fabs(m_project[0][0] - 1) < tol) {
389 strcat(m_xLabel,
"x");
390 }
else if (fabs(m_project[0][0] + 1) < tol) {
391 strcat(m_xLabel,
"-x");
392 }
else if (m_project[0][0] > tol) {
393 sprintf(buf,
"%g x", m_project[0][0]);
394 strcat(m_xLabel, buf);
395 }
else if (m_project[0][0] < -tol) {
396 sprintf(buf,
"%g x", m_project[0][0]);
397 strcat(m_xLabel, buf);
401 if (strlen(m_xLabel) > 0) {
402 if (m_project[0][1] < -tol) {
403 strcat(m_xLabel,
" - ");
404 }
else if (m_project[0][1] > tol) {
405 strcat(m_xLabel,
" + ");
407 if (
fabs(m_project[0][1] - 1) < tol ||
fabs(m_project[0][1] + 1) < tol) {
408 strcat(m_xLabel,
"y");
409 }
else if (
fabs(m_project[0][1]) > tol) {
410 sprintf(buf,
"%g y",
fabs(m_project[0][1]));
411 strcat(m_xLabel, buf);
414 if (
fabs(m_project[0][1] - 1) < tol) {
415 strcat(m_xLabel,
"y");
416 }
else if (
fabs(m_project[0][1] + 1) < tol) {
417 strcat(m_xLabel,
"-y");
418 }
else if (m_project[0][1] > tol) {
419 sprintf(buf,
"%g y", m_project[0][1]);
420 strcat(m_xLabel, buf);
421 }
else if (m_project[0][1] < -tol) {
422 sprintf(buf,
"%g y", m_project[0][1]);
423 strcat(m_xLabel, buf);
428 if (strlen(m_xLabel) > 0) {
429 if (m_project[0][2] < -tol) {
430 strcat(m_xLabel,
" - ");
431 }
else if (m_project[0][2] > tol) {
432 strcat(m_xLabel,
" + ");
434 if (
fabs(m_project[0][2] - 1) < tol ||
fabs(m_project[0][2] + 1) < tol) {
435 strcat(m_xLabel,
"z");
436 }
else if (
fabs(m_project[0][2]) > tol) {
437 sprintf(buf,
"%g z",
fabs(m_project[0][2]));
438 strcat(m_xLabel, buf);
441 if (
fabs(m_project[0][2] - 1) < tol) {
442 strcat(m_xLabel,
"z");
443 }
else if (
fabs(m_project[0][2] + 1) < tol) {
444 strcat(m_xLabel,
"-z");
445 }
else if (m_project[0][2] > tol) {
446 sprintf(buf,
"%g z", m_project[0][2]);
447 strcat(m_xLabel, buf);
448 }
else if (m_project[0][2] < -tol) {
449 sprintf(buf,
"%g z", m_project[0][2]);
450 strcat(m_xLabel, buf);
455 strcat(m_xLabel,
" [cm]");
458 strcpy(m_yLabel,
"\0");
461 if (
fabs(m_project[1][0] - 1) < tol) {
462 strcat(m_yLabel,
"x");
463 }
else if (
fabs(m_project[1][0] + 1) < tol) {
464 strcat(m_yLabel,
"-x");
465 }
else if (m_project[1][0] > tol) {
466 sprintf(buf,
"%g x", m_project[1][0]);
467 strcat(m_yLabel, buf);
468 }
else if (m_project[1][0] < -tol) {
469 sprintf(buf,
"%g x", m_project[1][0]);
470 strcat(m_yLabel, buf);
474 if (strlen(m_yLabel) > 0) {
475 if (m_project[1][1] < -tol) {
476 strcat(m_yLabel,
" - ");
477 }
else if (m_project[1][1] > tol) {
478 strcat(m_yLabel,
" + ");
480 if (
fabs(m_project[1][1] - 1) < tol ||
fabs(m_project[1][1] + 1) < tol) {
481 strcat(m_yLabel,
"y");
482 }
else if (
fabs(m_project[1][1]) > tol) {
483 sprintf(buf,
"%g y",
fabs(m_project[1][1]));
484 strcat(m_yLabel, buf);
487 if (
fabs(m_project[1][1] - 1) < tol) {
488 strcat(m_yLabel,
"y");
489 }
else if (
fabs(m_project[1][1] + 1) < tol) {
490 strcat(m_yLabel,
"-y");
491 }
else if (m_project[1][1] > tol) {
492 sprintf(buf,
"%g y", m_project[1][1]);
493 strcat(m_yLabel, buf);
494 }
else if (m_project[1][1] < -tol) {
495 sprintf(buf,
"%g y", m_project[1][1]);
496 strcat(m_yLabel, buf);
501 if (strlen(m_yLabel) > 0) {
502 if (m_project[1][2] < -tol) {
503 strcat(m_yLabel,
" - ");
504 }
else if (m_project[1][2] > tol) {
505 strcat(m_yLabel,
" + ");
507 if (
fabs(m_project[1][2] - 1) < tol ||
fabs(m_project[1][2] + 1) < tol) {
508 strcat(m_yLabel,
"z");
509 }
else if (
fabs(m_project[1][2]) > tol) {
510 sprintf(buf,
"%g z",
fabs(m_project[1][2]));
511 strcat(m_yLabel, buf);
514 if (
fabs(m_project[1][2] - 1) < tol) {
515 strcat(m_yLabel,
"z");
516 }
else if (
fabs(m_project[1][2] + 1) < tol) {
517 strcat(m_yLabel,
"-z");
518 }
else if (m_project[1][2] > tol) {
519 sprintf(buf,
"%g z", m_project[1][2]);
520 strcat(m_yLabel, buf);
521 }
else if (m_project[1][2] < -tol) {
522 sprintf(buf,
"%g z", m_project[1][2]);
523 strcat(m_yLabel, buf);
528 strcat(m_yLabel,
" [cm]");
531 strcpy(m_description,
"\0");
534 if (
fabs(m_plane[0] - 1) < tol) {
535 strcat(m_description,
"x");
536 }
else if (
fabs(m_plane[0] + 1) < tol) {
537 strcat(m_description,
"-x");
538 }
else if (m_plane[0] > tol) {
539 sprintf(buf,
"%g x", m_plane[0]);
540 strcat(m_description, buf);
541 }
else if (m_plane[0] < -tol) {
542 sprintf(buf,
"%g x", m_plane[0]);
543 strcat(m_description, buf);
547 if (strlen(m_description) > 0) {
548 if (m_plane[1] < -tol) {
549 strcat(m_description,
" - ");
550 }
else if (m_plane[1] > tol) {
551 strcat(m_description,
" + ");
553 if (
fabs(m_plane[1] - 1) < tol ||
fabs(m_plane[1] + 1) < tol) {
554 strcat(m_description,
"y");
555 }
else if (
fabs(m_plane[1]) > tol) {
556 sprintf(buf,
"%g y",
fabs(m_plane[1]));
557 strcat(m_description, buf);
560 if (
fabs(m_plane[1] - 1) < tol) {
561 strcat(m_description,
"y");
562 }
else if (
fabs(m_plane[1] + 1) < tol) {
563 strcat(m_description,
"-y");
564 }
else if (m_plane[1] > tol) {
565 sprintf(buf,
"%g y", m_plane[1]);
566 strcat(m_description, buf);
567 }
else if (m_plane[1] < -tol) {
568 sprintf(buf,
"%g y", m_plane[1]);
569 strcat(m_description, buf);
574 if (strlen(m_description) > 0) {
575 if (m_plane[2] < -tol) {
576 strcat(m_description,
" - ");
577 }
else if (m_plane[2] > tol) {
578 strcat(m_description,
" + ");
580 if (
fabs(m_plane[2] - 1) < tol ||
fabs(m_plane[2] + 1) < tol) {
581 strcat(m_description,
"z");
582 }
else if (
fabs(m_plane[2]) > tol) {
583 sprintf(buf,
"%g z",
fabs(m_plane[2]));
584 strcat(m_description, buf);
587 if (
fabs(m_plane[2] - 1) < tol) {
588 strcat(m_description,
"z");
589 }
else if (
fabs(m_plane[2] + 1) < tol) {
590 strcat(m_description,
"-z");
591 }
else if (m_plane[2] > tol) {
592 sprintf(buf,
"%g z", m_plane[2]);
593 strcat(m_description, buf);
594 }
else if (m_plane[2] < -tol) {
595 sprintf(buf,
"%g z", m_plane[2]);
596 strcat(m_description, buf);
601 sprintf(buf,
" = %g", m_plane[3]);
602 strcat(m_description, buf);
606 <<
" x label: |" << m_xLabel <<
"|\n"
607 <<
" y label: |" << m_yLabel <<
"|\n"
608 <<
" plane: |" << m_description <<
"|\n";
613 const double x0,
const double y0,
const double z0) {
615 const double fnorm = sqrt(fx * fx + fy * fy + fz * fz);
616 if (fnorm > 0 && fx * fx + fz * fz > 0) {
617 const double fxz = sqrt(fx * fx + fz * fz);
618 m_project[0][0] = fz / fxz;
620 m_project[0][2] = -fx / fxz;
621 m_project[1][0] = -fx * fy / (fxz * fnorm);
622 m_project[1][1] = (fx * fx + fz * fz) / (fxz * fnorm);
623 m_project[1][2] = -fy * fz / (fxz * fnorm);
624 m_project[2][0] = x0;
625 m_project[2][1] = y0;
626 m_project[2][2] = z0;
627 }
else if (fnorm > 0 && fy * fy + fz * fz > 0) {
628 const double fyz = sqrt(fy * fy + fz * fz);
629 m_project[0][0] = (fy * fy + fz * fz) / (fyz * fnorm);
630 m_project[0][1] = -fx * fz / (fyz * fnorm);
631 m_project[0][2] = -fy * fz / (fyz * fnorm);
633 m_project[1][1] = fz / fyz;
634 m_project[1][2] = -fy / fyz;
635 m_project[2][0] = x0;
636 m_project[2][1] = y0;
637 m_project[2][2] = z0;
640 <<
" Normal vector has zero norm. No new projection set.\n";
647 m_plane[3] = fx * x0 + fy * y0 + fz * z0;
655 double auxu[3], auxv[3];
656 const double ctheta = cos(theta);
657 const double stheta = sin(theta);
658 for (
int i = 0; i < 3; ++i) {
659 auxu[i] = ctheta * m_project[0][i] - stheta * m_project[1][i];
660 auxv[i] = stheta * m_project[0][i] + ctheta * m_project[1][i];
662 for (
int i = 0; i < 3; ++i) {
663 m_project[0][i] = auxu[i];
664 m_project[1][i] = auxv[i];
671void ViewField::SetupCanvas() {
680ViewField::PlotType ViewField::GetPlotType(
const std::string& option,
681 std::string& title)
const {
682 if (option ==
"v" || option ==
"p" || option ==
"phi" || option ==
"volt" ||
683 option ==
"voltage" || option ==
"pot" || option ==
"potential") {
686 }
else if (option ==
"e" || option ==
"field") {
689 }
else if (option ==
"ex") {
690 title =
"field (x-component)";
692 }
else if (option ==
"ey") {
693 title =
"field (y-component)";
695 }
else if (option ==
"ez") {
696 title =
"field (z-component)";
699 std::cerr <<
m_className <<
"::GetPlotType:\n Unknown option (" << option
705bool ViewField::SetupFunction(
const std::string& option, TF2*& f,
706 const bool contour,
const bool wfield) {
707 if (!m_sensor && !m_component) {
709 <<
" Neither sensor nor component are defined.\n";
714 if (!m_hasUserArea) {
719 if (!m_sensor->
GetArea(bbmin[0], bbmin[1], bbmin[2], bbmax[0], bbmax[1],
722 <<
" Sensor area is not defined.\n"
723 <<
" Please set the plot range explicitly (SetArea).\n";
727 if (!m_component->
GetBoundingBox(bbmin[0], bbmin[1], bbmin[2], bbmax[0],
728 bbmax[1], bbmax[2])) {
730 <<
" Bounding box of the component is not defined.\n"
731 <<
" Please set the plot range explicitly (SetArea).\n";
735 const double tol = 1.e-4;
736 double umin[2] = {-std::numeric_limits<double>::max(),
737 -std::numeric_limits<double>::max()};
738 double umax[2] = {std::numeric_limits<double>::max(),
739 std::numeric_limits<double>::max()};
740 for (
unsigned int i = 0; i < 3; ++i) {
741 bbmin[i] -= m_project[2][i];
742 bbmax[i] -= m_project[2][i];
743 for (
unsigned int j = 0; j < 2; ++j) {
744 if (
fabs(m_project[j][i]) < tol)
continue;
745 const double t1 = bbmin[i] / m_project[j][i];
746 const double t2 = bbmax[i] / m_project[j][i];
747 const double tmin = std::min(t1, t2);
748 const double tmax = std::max(t1, t2);
749 if (tmin > umin[j] && tmin < umax[j]) umin[j] = tmin;
750 if (tmax < umax[j] && tmax > umin[j]) umax[j] =
tmax;
757 std::cout <<
m_className <<
"::SetupFunction:\n Setting plot range to "
758 << m_xmin <<
" < x < " << m_xmax <<
", " << m_ymin <<
" < y < "
764 m_ymin, m_ymax, 1,
"ViewField",
"Evaluate2D");
767 f->SetRange(m_xmin, m_ymin, m_xmax, m_ymax);
771 const PlotType plotType = GetPlotType(option, title);
772 const int parPlotType = 10 * int(plotType) + 1;
775 double zmin = m_vmin;
776 double zmax = m_vmax;
778 title =
"weighting " + title;
779 f->SetParameter(0, -parPlotType);
780 if (m_useAutoRange) {
781 SampleRange(m_xmin, m_ymin, m_xmax, m_ymax, f, zmin, zmax);
782 }
else if (plotType == Potential) {
790 f->SetParameter(0, parPlotType);
791 if (plotType == Potential) {
792 if (m_useAutoRange) {
795 SampleRange(m_xmin, m_ymin, m_xmax, m_ymax, f, zmin, zmax);
797 }
else if (m_sensor) {
799 SampleRange(m_xmin, m_ymin, m_xmax, m_ymax, f, zmin, zmax);
807 title =
"electric " + title;
808 if (m_useAutoRange) {
809 SampleRange(m_xmin, m_ymin, m_xmax, m_ymax, f, zmin, zmax);
821 title =
"Contours of the " + title;
822 double level[m_nMaxContours];
823 if (m_nContours > 1) {
824 const double step = (zmax - zmin) / (m_nContours - 1.);
825 for (
unsigned int i = 0; i < m_nContours; ++i) {
826 level[i] = zmin + i * step;
829 level[0] = 0.5 * (zmax + zmin);
833 <<
" Number of contours: " << m_nContours <<
"\n";
834 for (
unsigned int i = 0; i < m_nContours; ++i) {
835 std::cout <<
" Level " << i <<
" = " << level[i] <<
"\n";
838 f->SetContour(m_nContours, level);
842 f->SetNpx(m_nSamples2dX);
843 f->SetNpy(m_nSamples2dY);
846 f->GetXaxis()->SetTitle(m_xLabel);
847 f->GetYaxis()->SetTitle(m_yLabel);
848 f->SetTitle(title.c_str());
853bool ViewField::SetupProfile(
const double x0,
const double y0,
const double z0,
854 const double x1,
const double y1,
const double z1,
855 const std::string& option, TF1*& f,
857 if (!m_sensor && !m_component) {
859 <<
" Neither sensor nor component are defined.\n";
864 const double dx = x1 - x0;
865 const double dy = y1 - y0;
866 const double dz = z1 - z0;
867 if (dx * dx + dy * dy + dz * dz <= 0.) {
869 <<
" Start and end points coincide.\n";
876 "ViewField",
"EvaluateProfile");
878 f->SetParameter(0, x0);
879 f->SetParameter(1, y0);
880 f->SetParameter(2, z0);
881 f->SetParameter(3, x1);
882 f->SetParameter(4, y1);
883 f->SetParameter(5, z1);
887 const PlotType plotType = GetPlotType(option, title);
888 const int parPlotType = 10 * int(plotType) + 1;
890 double fmin = m_vmin;
891 double fmax = m_vmax;
893 f->SetParameter(6, -parPlotType);
894 title =
"weighting " + title;
895 if (plotType == Potential) {
899 if (m_useAutoRange) {
900 SampleRange(f, fmin, fmax);
907 f->SetParameter(6, parPlotType);
908 if (plotType == Potential) {
909 if (m_useAutoRange) {
912 SampleRange(f, fmin, fmax);
914 }
else if (m_sensor) {
916 SampleRange(f, fmin, fmax);
924 title =
"electric " + title;
925 if (m_useAutoRange) {
926 SampleRange(f, fmin, fmax);
937 <<
" Plotting " << title <<
" along\n ("
938 << f->GetParameter(0) <<
", " << f->GetParameter(1) <<
", "
939 << f->GetParameter(2) <<
") - (" << f->GetParameter(3) <<
", "
940 << f->GetParameter(4) <<
", " << f->GetParameter(5) <<
")\n";
943 title =
"Profile plot of the " + title;
944 f->SetTitle(title.c_str());
945 f->GetXaxis()->SetTitle(
"normalised distance");
946 if (plotType == Potential) {
947 f->GetYaxis()->SetTitle(
"potential [V]");
949 f->GetYaxis()->SetTitle(
"field [V/cm]");
951 f->SetNpx(m_nSamples1d);
Abstract base class for components.
virtual void ElectricField(const double x, const double y, const double z, double &ex, double &ey, double &ez, Medium *&m, int &status)=0
virtual double WeightingPotential(const double x, const double y, const double z, const std::string &label)
virtual bool GetBoundingBox(double &xmin, double &ymin, double &zmin, double &xmax, double &ymax, double &zmax)
Get the bounding box coordinates.
virtual void WeightingField(const double x, const double y, const double z, double &wx, double &wy, double &wz, const std::string &label)
virtual bool GetVoltageRange(double &vmin, double &vmax)=0
Calculate the voltage range [V].
Abstract base class for media.
bool GetVoltageRange(double &vmin, double &vmax)
Return the voltage range.
void WeightingField(const double x, const double y, const double z, double &wx, double &wy, double &wz, const std::string &label)
Get the weighting field at (x, y, z).
void ElectricField(const double x, const double y, const double z, double &ex, double &ey, double &ez, double &v, Medium *&medium, int &status)
Get the drift field and potential at (x, y, z).
double WeightingPotential(const double x, const double y, const double z, const std::string &label)
Get the weighting potential at (x, y, z).
bool GetArea(double &xmin, double &ymin, double &zmin, double &xmax, double &ymax, double &zmax)
Return the current user area.
Base class for visualization classes.
std::string FindUnusedFunctionName(const std::string &s) const
void SetPlane(const double fx, const double fy, const double fz, const double x0, const double y0, const double z0)
void SetElectricFieldRange(const double emin, const double emax)
Set the plot limits for the electric field.
double Evaluate2D(double *pos, double *par)
void PlotWeightingField(const std::string &label, const std::string &option, const std::string &drawopt)
void PlotProfileWeightingField(const std::string &label, const double x0, const double y0, const double z0, const double x1, const double y1, const double z1, const std::string &option="v")
void SetNumberOfSamples2d(const unsigned int nx, const unsigned int ny)
Set the number of points used for drawing 2D functions.
void Rotate(const double angle)
Rotate the viewing plane (angle in radian).
void SetArea()
Set the viewing area based on the bounding box of the sensor/component.
void SetComponent(ComponentBase *c)
Set the component from which to retrieve the field.
void SetNumberOfSamples1d(const unsigned int n)
Set the number of points used for drawing 1D functions.
void SetVoltageRange(const double vmin, const double vmax)
Set the plot limits for the potential.
void PlotContour(const std::string &option="v")
void Plot(const std::string &option="v", const std::string &drawopt="arr")
void SetNumberOfContours(const unsigned int n)
Set the number of contour levels (at most 50).
void SetWeightingFieldRange(const double wmin, const double wmax)
Set the plot limits for the weighting field.
void SetSensor(Sensor *s)
Set the sensor from which to retrieve the field.
void SetDefaultProjection()
Set the default viewing plane ( - at ).
double EvaluateProfile(double *pos, double *par)
void PlotContourWeightingField(const std::string &label, const std::string &option)
void PlotProfile(const double x0, const double y0, const double z0, const double x1, const double y1, const double z1, const std::string &option="v")
double RndmUniform()
Draw a random number uniformly distributed in the range [0, 1).
DoubleAc fabs(const DoubleAc &f)