All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
Classes | Functions
analysis Namespace Reference

Classes

class  CalorimetryAnalysis
 

Functions

void TrkDirectionAtXYZ (const recob::Track trk, const double x, const double y, const double z, float out[3])
 
void True2RecoMappingXYZ (float t, float x, float y, float z, float out[3])
 
float XYZtoPlanecoordinate (const float x, const float y, const float z, const int plane)
 
float distance3d (const float &x1, const float &y1, const float &z1, const float &x2, const float &y2, const float &z2)
 
float ContainedLength (const TVector3 &v0, const TVector3 &v1, const std::vector< geoalgo::AABox > &boxes)
 
void FillHits (const detinfo::DetectorClocksData &clockData, const std::vector< art::Ptr< recob::Hit >> &hits, std::vector< float > &charge_u, std::vector< float > &charge_v, std::vector< float > &charge_y, std::vector< unsigned > &wire_u, std::vector< unsigned > &wire_v, std::vector< unsigned > &wire_y, std::vector< unsigned > &channel_u, std::vector< unsigned > &channel_v, std::vector< unsigned > &channel_y, std::vector< int > &multiplicity_u, std::vector< int > &multiplicity_v, std::vector< int > &multiplicity_y, std::vector< float > &width_u, std::vector< float > &width_v, std::vector< float > &width_y, std::vector< float > &time_u, std::vector< float > &time_v, std::vector< float > &time_y, std::vector< unsigned > &nhit_u, std::vector< unsigned > &nhit_v, std::vector< unsigned > &nhit_y, bool use_integral=true)
 
std::vector< unsigned > FinddEdxHits (const anab::Calorimetry &calo, const std::vector< art::Ptr< recob::Hit >> &hits)
 
float calcPitch (const geo::GeometryCore *geo, const geo::PlaneID &plane, TVector3 location, TVector3 direction, const spacecharge::SpaceCharge *SCEService=NULL)
 

Function Documentation

float analysis::calcPitch ( const geo::GeometryCore geo,
const geo::PlaneID plane,
TVector3  location,
TVector3  direction,
const spacecharge::SpaceCharge SCEService = NULL 
)

Definition at line 1543 of file CalorimetryAnalysis_module.cc.

1543  {
1544  float angletovert = geo->WireAngleToVertical(geo->View(plane), plane) - 0.5*::util::pi<>();
1545 
1546  // apply space charge change to dir
1547  if (SCEService) {
1548  geo::Point_t location_p(location);
1549  geo::Vector_t offset_v = SCEService->GetPosOffsets(location_p);
1550  TVector3 offset = TVector3(offset_v.X(), offset_v.Y(), offset_v.Z());
1551  // fix the x-sign
1552  if (location.X() < 0.) offset.SetX(-offset.X());
1553 
1554  // location a ~wire's distance along the track
1555  TVector3 location_dx = location + geo->WirePitch(plane) * direction;
1556 
1557  // Apply space charge to the offset location
1558  geo::Point_t location_dx_p(location_dx);
1559  geo::Vector_t offset_dx_v = SCEService->GetPosOffsets(location_dx_p);
1560  TVector3 offset_dx(offset_dx_v.X(), offset_dx_v.Y(), offset_dx_v.Z());
1561  // fix the x-sign
1562  if (location_dx.X() < 0.) offset_dx.SetX(-offset_dx.X());
1563 
1564  // this is the actual direction
1565  direction = (offset_dx + location_dx - offset - location).Unit();
1566  }
1567 
1568  // get the pitch
1569  float cosgamma = abs(cos(angletovert) * direction.Z() + sin(angletovert) * direction.Y());
1570  float pitch = geo->WirePitch(plane) / cosgamma;
1571 
1572  // map pitch back onto particle trajectory
1573  if (SCEService) {
1574  geo::Point_t location_p(location);
1575  geo::Vector_t offset_v = SCEService->GetPosOffsets(location_p);
1576  TVector3 offset(offset_v.X(), offset_v.Y(), offset_v.Z());
1577  // fix the x-sign
1578  if (location.X() < 0.) offset.SetX(-offset.X());
1579 
1580  TVector3 location_sce = location + offset;
1581 
1582  TVector3 location_sce_dx = location_sce + direction * pitch;
1583 
1584  // map this back onto the particle trajectory
1585  geo::Point_t location_sce_dx_p(location_sce_dx);
1586  geo::Vector_t back_v = SCEService->GetCalPosOffsets(location_sce_dx_p, plane.TPC);
1587  TVector3 back(back_v.X(), back_v.Y(), back_v.Z());
1588  TVector3 location_dx = location_sce_dx + back;
1589 
1590  pitch = (location - location_dx).Mag();
1591  }
1592 
1593  return pitch;
1594 }
ROOT::Math::DisplacementVector3D< ROOT::Math::Cartesian3D< double >, ROOT::Math::GlobalCoordinateSystemTag > Vector_t
Type for representation of momenta in 3D space.
Definition: geo_vectors.h:164
virtual geo::Vector_t GetCalPosOffsets(geo::Point_t const &point, int const &TPCid) const =0
BEGIN_PROLOG TPC Trig offset(g4 rise time) ProjectToHeight
Definition: CORSIKAGen.fcl:7
geo::Length_t WirePitch(geo::PlaneID const &planeid) const
Returns the distance between two consecutive wires.
T abs(T value)
View_t View(geo::PlaneID const &pid) const
Returns the view (wire orientation) on the channels of specified TPC plane.
virtual geo::Vector_t GetPosOffsets(geo::Point_t const &point) const =0
TPCID_t TPC
Index of the TPC within its cryostat.
Definition: geo_types.h:406
ROOT::Math::PositionVector3D< ROOT::Math::Cartesian3D< double >, ROOT::Math::GlobalCoordinateSystemTag > Point_t
Type for representation of position in physical 3D space.
Definition: geo_vectors.h:184
double WireAngleToVertical(geo::View_t view, geo::TPCID const &tpcid) const
Returns the angle of the wires in the specified view from vertical.
float analysis::ContainedLength ( const TVector3 &  v0,
const TVector3 &  v1,
const std::vector< geoalgo::AABox > &  boxes 
)

Definition at line 2509 of file CalorimetryAnalysis_module.cc.

2510  {
2511  static const geoalgo::GeoAlgo algo;
2512 
2513  // if points are the same, return 0
2514  if ((v0 - v1).Mag() < 1e-6) return 0;
2515 
2516  // construct individual points
2517  geoalgo::Point_t p0(v0);
2518  geoalgo::Point_t p1(v1);
2519 
2520  // construct line segment
2521  geoalgo::LineSegment line(p0, p1);
2522 
2523  double length = 0;
2524 
2525  // total contained length is sum of lengths in all boxes
2526  // assuming they are non-overlapping
2527  for (auto const &box: boxes) {
2528  int n_contained = box.Contain(p0) + box.Contain(p1);
2529  // both points contained -- length is total length (also can break out of loop)
2530  if (n_contained == 2) {
2531  length = (v1 - v0).Mag();
2532  break;
2533  }
2534  // one contained -- have to find intersection point (which must exist)
2535  if (n_contained == 1) {
2536  auto intersections = algo.Intersection(line, box);
2537  // Because of floating point errors, it can sometimes happen
2538  // that there is 1 contained point but no "Intersections"
2539  // if one of the points is right on the edge
2540  if (intersections.size() == 0) {
2541  // determine which point is on the edge
2542  double tol = 1e-5;
2543  bool p0_edge = algo.SqDist(p0, box) < tol;
2544  bool p1_edge = algo.SqDist(p1, box) < tol;
2545  assert(p0_edge || p1_edge);
2546  // contained one is on edge -- can treat both as not contained
2547  //
2548  // In this case, no length
2549  if ((p0_edge && box.Contain(p0)) || (box.Contain(p1) && p1_edge))
2550  continue;
2551  // un-contaned one is on edge -- treat both as contained
2552  else if ((p0_edge && box.Contain(p1)) || (box.Contain(p0) && p1_edge)) {
2553  length = (v1 - v0).Mag();
2554  break;
2555  }
2556  else {
2557  assert(false); // bad
2558  }
2559  }
2560  // floating point errors can also falsely cause 2 intersection points
2561  //
2562  // in this case, one of the intersections must be very close to the
2563  // "contained" point, so the total contained length will be about
2564  // the same as the distance between the two intersection points
2565  else if (intersections.size() == 2) {
2566  length += (intersections.at(0).ToTLorentzVector().Vect() - intersections.at(1).ToTLorentzVector().Vect()).Mag();
2567  continue;
2568  }
2569  // "Correct"/ideal case -- 1 intersection point
2570  else if (intersections.size() == 1) {
2571  // get TVector at intersection point
2572  TVector3 int_tv(intersections.at(0).ToTLorentzVector().Vect());
2573  length += ( box.Contain(p0) ? (v0 - int_tv).Mag() : (v1 - int_tv).Mag() );
2574  }
2575  else assert(false); // bad
2576  }
2577  // none contained -- either must have zero or two intersections
2578  if (n_contained == 0) {
2579  auto intersections = algo.Intersection(line, box);
2580  if (!(intersections.size() == 0 || intersections.size() == 2)) {
2581  // more floating point error fixes...
2582  //
2583  // figure out which points are near the edge
2584  double tol = 1e-5;
2585  bool p0_edge = algo.SqDist(p0, box) < tol;
2586  bool p1_edge = algo.SqDist(p1, box) < tol;
2587  // and which points are near the intersection
2588  TVector3 vint = intersections.at(0).ToTLorentzVector().Vect();
2589 
2590  bool p0_int = (v0 - vint).Mag() < tol;
2591  bool p1_int = (v1 - vint).Mag() < tol;
2592  // exactly one of them should produce the intersection
2593  assert((p0_int && p0_edge) != (p1_int && p1_edge));
2594  // void variables when assert-ions are turned off
2595  (void) p0_int; (void) p1_int;
2596 
2597  // both close to edge -- full length is contained
2598  if (p0_edge && p1_edge) {
2599  length += (v0 - v1).Mag();
2600  }
2601  // otherwise -- one of them is not on an edge, no length is contained
2602  else {}
2603  }
2604  // assert(intersections.size() == 0 || intersections.size() == 2);
2605  else if (intersections.size() == 2) {
2606  TVector3 start(intersections.at(0).ToTLorentzVector().Vect());
2607  TVector3 end(intersections.at(1).ToTLorentzVector().Vect());
2608  length += (start - end).Mag();
2609  }
2610  }
2611  }
2612 
2613  return length;
2614 }//ContainedLength
Algorithm to compute various geometrical relation among geometrical objects. In particular functions ...
auto const tol
Definition: SurfXYZTest.cc:16
double SqDist(const Line_t &line, const Point_t &pt) const
Representation of a simple 3D line segment Defines a finite 3D straight line by having the start and ...
auto end(FixedBins< T, C > const &) noexcept
Definition: FixedBins.h:585
j template void())
Definition: json.hpp:3108
do i e
std::vector< Point_t > Intersection(const AABox_t &box, const HalfLine_t &line, bool back=false) const
Intersection between a HalfLine and an AABox.
physics associatedGroupsWithLeft p1
float analysis::distance3d ( const float &  x1,
const float &  y1,
const float &  z1,
const float &  x2,
const float &  y2,
const float &  z2 
)

Definition at line 2500 of file CalorimetryAnalysis_module.cc.

2502  {
2503  return sqrt((x1-x2)*(x1-x2) +
2504  (y1-y2)*(y1-y2) +
2505  (z1-z2)*(z1-z2));
2506 
2507  }
void analysis::FillHits ( const detinfo::DetectorClocksData clockData,
const std::vector< art::Ptr< recob::Hit >> &  hits,
std::vector< float > &  charge_u,
std::vector< float > &  charge_v,
std::vector< float > &  charge_y,
std::vector< unsigned > &  wire_u,
std::vector< unsigned > &  wire_v,
std::vector< unsigned > &  wire_y,
std::vector< unsigned > &  channel_u,
std::vector< unsigned > &  channel_v,
std::vector< unsigned > &  channel_y,
std::vector< int > &  multiplicity_u,
std::vector< int > &  multiplicity_v,
std::vector< int > &  multiplicity_y,
std::vector< float > &  width_u,
std::vector< float > &  width_v,
std::vector< float > &  width_y,
std::vector< float > &  time_u,
std::vector< float > &  time_v,
std::vector< float > &  time_y,
std::vector< unsigned > &  nhit_u,
std::vector< unsigned > &  nhit_v,
std::vector< unsigned > &  nhit_y,
bool  use_integral = true 
)

Definition at line 2364 of file CalorimetryAnalysis_module.cc.

2387  {
2388 
2389  struct HitInfo {
2390  float charge;
2391  int multiplicity;
2392  float width;
2393  int start;
2394  int end;
2395  float time;
2396  int nhit;
2397  int wire;
2398  HitInfo(): charge(0), multiplicity(0), width(0), start(0), end(0), time(0.), nhit(0) {}
2399  };
2400 
2401  std::map<unsigned, HitInfo> hit_map_u;
2402  std::map<unsigned, HitInfo> hit_map_v;
2403  std::map<unsigned, HitInfo> hit_map_y;
2404 
2405  for (const art::Ptr<recob::Hit> hit: hits) {
2406  if (hit->WireID().Plane == 0) {
2407  // if using summed ADC method to count charge, don't double-count hits in the same snippet
2408  if (!use_integral && hit_map_u[hit->Channel()].start == hit->StartTick() && hit_map_u[hit->Channel()].end == hit->EndTick()) {
2409  continue;
2410  }
2411  hit_map_u[hit->Channel()].charge += (use_integral) ? hit->Integral() : hit->SummedADC();
2412  hit_map_u[hit->Channel()].multiplicity = std::max(hit_map_u[hit->Channel()].multiplicity, (int) hit->Multiplicity());
2413  hit_map_u[hit->Channel()].start = hit_map_u[hit->Channel()].nhit ? std::min(hit_map_u[hit->Channel()].start, hit->StartTick()) : hit->StartTick();
2414  hit_map_u[hit->Channel()].end = hit_map_u[hit->Channel()].nhit ? std::max(hit_map_u[hit->Channel()].end, hit->EndTick()) : hit->EndTick();
2415  hit_map_u[hit->Channel()].width = (hit_map_u[hit->Channel()].end - hit_map_u[hit->Channel()].start);
2416  hit_map_u[hit->Channel()].time = (hit->PeakTime() + hit_map_u[hit->Channel()].time * hit_map_u[hit->Channel()].nhit) / (hit_map_u[hit->Channel()].nhit + 1);
2417  hit_map_u[hit->Channel()].nhit ++;
2418  hit_map_u[hit->Channel()].wire = hit->WireID().Wire;
2419  }
2420  else if (hit->WireID().Plane == 1) {
2421  // if using summed ADC method to count charge, don't double-count hits in the same snippet
2422  if (!use_integral && hit_map_v[hit->Channel()].start == hit->StartTick() && hit_map_v[hit->Channel()].end == hit->EndTick()) {
2423  continue;
2424  }
2425  hit_map_v[hit->Channel()].charge += (use_integral) ? hit->Integral() : hit->SummedADC();
2426  hit_map_v[hit->Channel()].multiplicity = std::max(hit_map_v[hit->Channel()].multiplicity, (int) hit->Multiplicity());
2427  hit_map_v[hit->Channel()].start = hit_map_v[hit->Channel()].nhit ? std::min(hit_map_v[hit->Channel()].start, hit->StartTick()) : hit->StartTick();
2428  hit_map_v[hit->Channel()].end = hit_map_v[hit->Channel()].nhit ? std::max(hit_map_v[hit->Channel()].end, hit->EndTick()) : hit->EndTick();
2429  hit_map_v[hit->Channel()].width = (hit_map_v[hit->Channel()].end - hit_map_v[hit->Channel()].start);
2430  hit_map_v[hit->Channel()].time = (hit->PeakTime() + hit_map_v[hit->Channel()].time * hit_map_v[hit->Channel()].nhit) / (hit_map_v[hit->Channel()].nhit + 1);
2431  hit_map_v[hit->Channel()].nhit ++;
2432  hit_map_v[hit->Channel()].wire = hit->WireID().Wire;
2433  }
2434  else {
2435  // if using summed ADC method to count charge, don't double-count hits in the same snippet
2436  if (!use_integral && hit_map_y[hit->Channel()].start == hit->StartTick() && hit_map_y[hit->Channel()].end == hit->EndTick()) {
2437  continue;
2438  }
2439  hit_map_y[hit->Channel()].charge += (use_integral) ? hit->Integral() : hit->SummedADC();
2440  hit_map_y[hit->Channel()].multiplicity = std::max(hit_map_y[hit->Channel()].multiplicity, (int) hit->Multiplicity());
2441  hit_map_y[hit->Channel()].start = hit_map_y[hit->Channel()].nhit ? std::min(hit_map_y[hit->Channel()].start, hit->StartTick()) : hit->StartTick();
2442  hit_map_y[hit->Channel()].end = hit_map_y[hit->Channel()].nhit ? std::max(hit_map_y[hit->Channel()].end, hit->EndTick()) : hit->EndTick();
2443  hit_map_y[hit->Channel()].width = (hit_map_y[hit->Channel()].end - hit_map_y[hit->Channel()].start);
2444  hit_map_y[hit->Channel()].time = (hit->PeakTime() + hit_map_y[hit->Channel()].time * hit_map_y[hit->Channel()].nhit) / (hit_map_y[hit->Channel()].nhit + 1);
2445  hit_map_y[hit->Channel()].nhit ++;
2446  hit_map_y[hit->Channel()].wire = hit->WireID().Wire;
2447  }
2448  }
2449 
2450  for (auto const &pair: hit_map_u) {
2451  channel_u.push_back(pair.first);
2452  charge_u.push_back(pair.second.charge);
2453  multiplicity_u.push_back(pair.second.multiplicity);
2454  width_u.push_back(pair.second.width);
2455  time_u.push_back(pair.second.time);
2456  nhit_u.push_back(pair.second.nhit);
2457  wire_u.push_back(pair.second.wire);
2458  }
2459  for (auto const &pair: hit_map_v) {
2460  channel_v.push_back(pair.first);
2461  charge_v.push_back(pair.second.charge);
2462  multiplicity_v.push_back(pair.second.multiplicity);
2463  width_v.push_back(pair.second.width);
2464  time_v.push_back(pair.second.time);
2465  nhit_v.push_back(pair.second.nhit);
2466  wire_v.push_back(pair.second.wire);
2467  }
2468  for (auto const &pair: hit_map_y) {
2469  channel_y.push_back(pair.first);
2470  charge_y.push_back(pair.second.charge);
2471  multiplicity_y.push_back(pair.second.multiplicity);
2472  width_y.push_back(pair.second.width);
2473  time_y.push_back(pair.second.time);
2474  nhit_y.push_back(pair.second.nhit);
2475  wire_y.push_back(pair.second.wire);
2476  }
2477 
2478 }
process_name hit
Definition: cheaterreco.fcl:51
auto end(FixedBins< T, C > const &) noexcept
Definition: FixedBins.h:585
std::vector<unsigned> analysis::FinddEdxHits ( const anab::Calorimetry calo,
const std::vector< art::Ptr< recob::Hit >> &  hits 
)

Definition at line 1522 of file CalorimetryAnalysis_module.cc.

1522  {
1523  std::vector<unsigned> ret;
1524 
1525  // NOTE: TpIndices are __actually__ the art::Ptr keys of the Hit's
1526  // Don't ask me why
1527  for (size_t ind: calo.TpIndices()) {
1528  bool found = false;
1529  for (const art::Ptr<recob::Hit> &hit: hits) {
1530  if (hit.key() == ind) {
1531  ret.push_back(hit->Channel());
1532  found = true;
1533  break;
1534  }
1535  }
1536  if (!found) {
1537  throw cet::exception("dEdx w/out Hit!");
1538  }
1539  }
1540  return ret;
1541 }
process_name hit
Definition: cheaterreco.fcl:51
const std::vector< size_t > & TpIndices() const
Definition: Calorimetry.h:115
void analysis::TrkDirectionAtXYZ ( const recob::Track  trk,
const double  x,
const double  y,
const double  z,
float  out[3] 
)

Definition at line 2327 of file CalorimetryAnalysis_module.cc.

2328  {
2329  float min_dist = 1000;
2330  size_t i_min = -1;
2331  for(size_t i=0; i < trk.NumberTrajectoryPoints(); i++)
2332  {
2333  if (trk.HasValidPoint(i))
2334  { // check this point is valid
2335  auto point_i = trk.LocationAtPoint(i);
2336  float distance = distance3d((double)point_i.X(), (double)point_i.Y(), (double)point_i.Z(),
2337  x, y, z);
2338  if (distance < min_dist)
2339  {
2340  min_dist = distance;
2341  i_min = i;
2342  }
2343  }// if point is valid
2344  }// for all track points
2345 
2346  if (i_min == (size_t)-1) return;
2347 
2348  auto direction = trk.DirectionAtPoint(i_min);
2349  out[0] = (float)direction.X();
2350  out[1] = (float)direction.Y();
2351  out[2] = (float)direction.Z();
2352 
2353  float norm;
2354  norm = out[0]*out[0] + out[1]*out[1] + out[2]*out[2];
2355  if (fabs(norm -1) > 0.001)
2356  {
2357  std::cout << "i_min = " << i_min << std::endl;
2358  std::cout << "minimum distance = " << min_dist << std::endl;
2359  std::cout << "out[0], out[1], out[2] = " << out[0] << " , " << out[1] << " , " << out[2] << std::endl;
2360  std::cout << "norm = " << norm << std::endl;
2361  }
2362  }
process_name opflash particleana ie ie ie z
process_name opflash particleana ie x
Point_t const & LocationAtPoint(size_t i) const
bool HasValidPoint(size_t i) const
size_t NumberTrajectoryPoints() const
Various functions related to the presence and the number of (valid) points.
float distance3d(const float &x1, const float &y1, const float &z1, const float &x2, const float &y2, const float &z2)
process_name opflash particleana ie ie y
double distance(geo::Point_t const &point, CathodeDesc_t const &cathode)
Returns the distance of a point from the cathode.
auto norm(Vector const &v)
Return norm of the specified vector.
Vector_t DirectionAtPoint(size_t i) const
BEGIN_PROLOG could also be cout
void analysis::True2RecoMappingXYZ ( float  t,
float  x,
float  y,
float  z,
float  out[3] 
)

Definition at line 2481 of file CalorimetryAnalysis_module.cc.

2481  {
2482  (void) t;
2483  out[0] = x;
2484  out[1] = y;
2485  out[2] = z;
2486 }
process_name opflash particleana ie ie ie z
process_name opflash particleana ie x
process_name opflash particleana ie ie y
j template void())
Definition: json.hpp:3108
float analysis::XYZtoPlanecoordinate ( const float  x,
const float  y,
const float  z,
const int  plane 
)

Definition at line 2488 of file CalorimetryAnalysis_module.cc.

2489  {
2490  auto const* geom = ::lar::providerFrom<geo::Geometry>();
2491  geo::Point_t p(x,y,z);
2492  geo::TPCID tpc = geom->FindTPCAtPosition(p);
2493  if (!tpc) return -1e6;
2494  geo::PlaneID planeID(tpc, plane);
2495  double _wire2cm = geom->WirePitch(planeID);
2496 
2497  return geom->WireCoordinate(p, planeID) * _wire2cm;
2498  }
process_name opflash particleana ie ie ie z
process_name opflash particleana ie x
pdgs p
Definition: selectors.fcl:22
The data type to uniquely identify a Plane.
Definition: geo_types.h:472
process_name opflash particleana ie ie y
The data type to uniquely identify a TPC.
Definition: geo_types.h:386
ROOT::Math::PositionVector3D< ROOT::Math::Cartesian3D< double >, ROOT::Math::GlobalCoordinateSystemTag > Point_t
Type for representation of position in physical 3D space.
Definition: geo_vectors.h:184