Geant4  10.01
UVoxelizer.hh
Go to the documentation of this file.
1 //
2 // ********************************************************************
3 // * This Software is part of the AIDA Unified Solids Library package *
4 // * See: https://aidasoft.web.cern.ch/USolids *
5 // ********************************************************************
6 //
7 // $Id:$
8 //
9 // --------------------------------------------------------------------
10 //
11 // UVoxelizer
12 //
13 // Class description:
14 //
15 // Voxelizer used for UPolycone, UPolyhedra, UTessellatedSolid
16 // and UMultiUnion.
17 //
18 // 19.10.12 Marek Gayer
19 // Created from original implementation in ROOT
20 // --------------------------------------------------------------------
21 
22 #ifndef UVoxelizer_HH
23 #define UVoxelizer_HH
24 
25 #include <vector>
26 #include <string>
27 #include <map>
28 
29 #include "UBits.hh"
30 #include "UBox.hh"
31 #include "VUFacet.hh"
32 #include "VUSolid.hh"
33 #include "UUtils.hh"
34 #include "UTransform3D.hh"
35 
36 struct UVoxelBox
37 {
38  UVector3 hlen; // half length of the box
39  UVector3 pos; // position of the box
40 };
41 
42 struct UVoxelInfo
43 {
44  int count;
45  int previous;
46  int next;
47 };
48 
50 {
51 // friend class UVoxelCandidatesIterator;
52 
53  public:
54 
55  // Binary search
56  template <typename T>
57  static inline int BinarySearch(const std::vector<T>& vec, T value)
58  {
59  // Binary search in an array of doubles. If match is found, function returns
60  // position of element. If no match found, function gives nearest
61  // element smaller than value.
62  typename std::vector<T>::const_iterator begin = vec.begin(), end = vec.end();
63  int res = std::upper_bound(begin, end, value) - begin - 1;
64  return res;
65  }
66 
67 #ifdef USOLIDSONLY
68  void Voxelize(std::vector<VUSolid*>& solids, std::vector<UTransform3D>& transforms);
69 #endif // USOLIDSONLY
70 
71  void Voxelize(std::vector<VUFacet*>& facets);
72 
73  void DisplayVoxelLimits();
74  void DisplayBoundaries();
75  void DisplayListNodes();
76 
77  UVoxelizer();
78  ~UVoxelizer();
79 
80  // Method displaying the nodes located in a voxel characterized by its three indexes:
81  void GetCandidatesVoxel(std::vector<int>& voxels);
82  // Method returning in a vector container the nodes located in a voxel characterized by its three indexes:
83  int GetCandidatesVoxelArray(const UVector3& point, std::vector<int>& list, UBits* crossed = NULL) const;
84 
85  int GetCandidatesVoxelArray(const std::vector<int>& voxels, const UBits bitmasks[], std::vector<int>& list, UBits* crossed = NULL) const;
86 
87  int GetCandidatesVoxelArray(const std::vector<int>& voxels, std::vector<int>& list, UBits* crossed = NULL)const;
88 
89  // Method returning the pointer to the array containing the characteristics of each box:
90  inline const std::vector<UVoxelBox>& GetBoxes() const
91  {
92  return fBoxes;
93  }
94  inline const std::vector<double>& GetBoundary(int index) const
95  {
96  return fBoundaries[index];
97  }
98 
99  bool UpdateCurrentVoxel(const UVector3& point, const UVector3& direction, std::vector<int>& curVoxel) const;
100 
101  inline void GetVoxel(std::vector<int>& curVoxel, const UVector3& point) const
102  {
103  for (int i = 0; i <= 2; ++i)
104  {
105  const std::vector<double>& boundary = GetBoundary(i);
106  int n = BinarySearch(boundary, point[i]);
107  if (n == -1) n = 0;
108  else if (n == (int) boundary.size() - 1) n--;
109  curVoxel[i] = n;
110  }
111  }
112 
113  inline int GetBitsPerSlice() const
114  {
115  return fNPerSlice * 8 * sizeof(unsigned int);
116  }
117 
118  bool Contains(const UVector3& point) const;
119 
120  double DistanceToNext(const UVector3& point, const UVector3& direction, std::vector<int>& curVoxel) const;
121 
122  double DistanceToFirst(const UVector3& point, const UVector3& direction) const;
123 
124  double SafetyToBoundingBox(const UVector3& point) const;
125 
126  inline int GetVoxelsIndex(int x, int y, int z) const
127  {
128  if (x < 0 || y < 0 || z < 0) return -1;
129  int maxX = fBoundaries[0].size();
130  int maxY = fBoundaries[1].size();
131  int index = x + y * maxX + z * maxX * maxY;
132  return index;
133  }
134 
135  inline int GetVoxelsIndex(const std::vector<int>& voxels) const
136  {
137  return GetVoxelsIndex(voxels[0], voxels[1], voxels[2]);
138  }
139 
140  inline bool GetPointVoxel(const UVector3& p, std::vector<int>& voxels) const
141  {
142  for (int i = 0; i <= 2; ++i)
143  if (p[i] < *fBoundaries[i].begin() || p[i] > *fBoundaries[i].end()) return false;
144 
145  for (int i = 0; i <= 2; ++i)
146  voxels[i] = BinarySearch(fBoundaries[i], p[i]);
147 
148  return true;
149  }
150 
151  inline int GetPointIndex(const UVector3& p) const
152  {
153  int maxX = fBoundaries[0].size();
154  int maxY = fBoundaries[1].size();
155  int x = BinarySearch(fBoundaries[0], p[0]);
156  int y = BinarySearch(fBoundaries[1], p[1]);
157  int z = BinarySearch(fBoundaries[2], p[2]);
158  int index = x + y * maxX + z * maxX * maxY;
159  return index;
160  }
161 
162  inline const UBits& Empty() const
163  {
164  return fEmpty;
165  }
166 
167  inline bool IsEmpty(int index) const
168  {
169  return fEmpty[index];
170  }
171 
172  void SetMaxVoxels(int max);
173 
174  void SetMaxVoxels(const UVector3& reductionRatio);
175 
176  inline int GetMaxVoxels(UVector3& ratioOfReduction)
177  {
178  ratioOfReduction = fReductionRatio;
179  return fMaxVoxels;
180  }
181 
182  int AllocatedMemory();
183 
184  inline long long GetCountOfVoxels() const
185  {
186  return fCountOfVoxels;
187  }
188 
189  inline long long CountVoxels(std::vector<double> boundaries[]) const
190  {
191  long long sx = boundaries[0].size() - 1;
192  long long sy = boundaries[1].size() - 1;
193  long long sz = boundaries[2].size() - 1;
194  return sx * sy * sz;
195  }
196 
197  inline const std::vector<int>& GetCandidates(std::vector<int>& curVoxel) const
198  {
199  int voxelsIndex = GetVoxelsIndex(curVoxel);
200  if (voxelsIndex >= 0 && !fEmpty[voxelsIndex])
201  {
202  return fCandidates[voxelsIndex];
203  }
204  return fNoCandidates;
205  }
206 
207  inline int GetVoxelBoxesSize() const
208  {
209  return fVoxelBoxes.size();
210  }
211 
212  inline const UVoxelBox& GetVoxelBox(int i) const
213  {
214  return fVoxelBoxes[i];
215  }
216 
217  inline const std::vector<int>& GetVoxelBoxCandidates(int i) const
218  {
219  return fVoxelBoxesCandidates[i];
220  }
221 
222  inline int GetTotalCandidates() const
223  {
224  return fTotalCandidates;
225  }
226 
227  static double MinDistanceToBox(const UVector3& aPoint, const UVector3& f);
228 
229  static void SetDefaultVoxelsCount(int count);
230 
231  static int GetDefaultVoxelsCount();
232 
233  void BuildBoundingBox();
234 
235  void BuildBoundingBox(UVector3& amin, UVector3& amax, double tolerance = 0);
236 
237  static void FindComponentsFastest(unsigned int mask,
238  std::vector<int> &list, int i);
239  private:
240 
242 
243  std::vector<UVoxelBox> fVoxelBoxes;
244 
245  std::vector<std::vector<int> > fVoxelBoxesCandidates;
246 
247  mutable std::map<int, std::vector<int> > fCandidates;
248 
249  const std::vector<int> fNoCandidates;
250 
251  long long fCountOfVoxels;
252 
253  void BuildEmpty();
254 
255  std::string GetCandidatesAsString(const UBits& bits);
256 
257  void CreateSortedBoundary(std::vector<double>& boundaryRaw, int axis);
258 
259  void BuildBoundaries();
260 
261  void BuildReduceVoxels(std::vector<double> fBoundaries[], UVector3 reductionRatio);
262 
263  void BuildReduceVoxels2(std::vector<double> fBoundaries[], UVector3 reductionRatio);
264 
265 #ifdef USOLIDSONLY
266  void BuildVoxelLimits(std::vector<VUSolid*>& solids, std::vector<UTransform3D>& transforms);
267 #endif // USOLIDSONLY
268 
269  void BuildVoxelLimits(std::vector<VUFacet*>& facets);
270 
271  void DisplayBoundaries(std::vector<double>& fBoundaries);
272 
273  void BuildBitmasks(std::vector<double> fBoundaries[], UBits bitmasks[]);
274 
275  void SetReductionRatio(int maxVoxels, UVector3& reductionRatio);
276 
277  void CreateMiniVoxels(std::vector<double> fBoundaries[], UBits bitmasks[]);
278 
280 
281  std::vector<UVoxelBox> fBoxes; // Array of box limits on the 3 cartesian axis
282 
283  std::vector<double> fBoundaries[3]; // Sorted and if need skimmed fBoundaries along X,Y,Z axis
284 
285  std::vector<int> fCandidatesCounts[3];
286 
288 
290 
294 
296 
298 
299  double fTolerance;
300 
302 };
303 
304 #endif
void BuildVoxelLimits(std::vector< VUSolid * > &solids, std::vector< UTransform3D > &transforms)
int GetVoxelsIndex(const std::vector< int > &voxels) const
Definition: UVoxelizer.hh:135
static int fDefaultVoxelsCount
Definition: UVoxelizer.hh:241
UVector3 hlen
Definition: UVoxelizer.hh:38
void DisplayBoundaries()
Definition: UVoxelizer.cc:270
const std::vector< double > & GetBoundary(int index) const
Definition: UVoxelizer.hh:94
int GetVoxelsIndex(int x, int y, int z) const
Definition: UVoxelizer.hh:126
double DistanceToNext(const UVector3 &point, const UVector3 &direction, std::vector< int > &curVoxel) const
Definition: UVoxelizer.cc:1057
static void FindComponentsFastest(unsigned int mask, std::vector< int > &list, int i)
Definition: UVoxelizer.cc:848
static ush mask[]
Definition: csz_inflate.cc:332
G4double z
Definition: TRTMaterials.hh:39
int GetTotalCandidates() const
Definition: UVoxelizer.hh:222
void CreateMiniVoxels(std::vector< double > fBoundaries[], UBits bitmasks[])
Definition: UVoxelizer.cc:647
void Voxelize(std::vector< VUSolid * > &solids, std::vector< UTransform3D > &transforms)
void SetMaxVoxels(int max)
Definition: UVoxelizer.cc:1125
void BuildEmpty()
Definition: UVoxelizer.cc:46
static const G4double tolerance
int fMaxVoxels
Definition: UVoxelizer.hh:297
bool UpdateCurrentVoxel(const UVector3 &point, const UVector3 &direction, std::vector< int > &curVoxel) const
void GetVoxel(std::vector< int > &curVoxel, const UVector3 &point) const
Definition: UVoxelizer.hh:101
bool Contains(const UVector3 &point) const
Definition: UVoxelizer.cc:998
Definition: UBox.hh:33
long long GetCountOfVoxels() const
Definition: UVoxelizer.hh:184
std::vector< UVoxelBox > fBoxes
Definition: UVoxelizer.hh:281
int fTotalCandidates
Definition: UVoxelizer.hh:287
int GetMaxVoxels(UVector3 &ratioOfReduction)
Definition: UVoxelizer.hh:176
double DistanceToFirst(const UVector3 &point, const UVector3 &direction) const
Definition: UVoxelizer.cc:1008
std::vector< double > fBoundaries[3]
Definition: UVoxelizer.hh:283
static int BinarySearch(const std::vector< T > &vec, T value)
Definition: UVoxelizer.hh:57
int GetVoxelBoxesSize() const
Definition: UVoxelizer.hh:207
void BuildReduceVoxels2(std::vector< double > fBoundaries[], UVector3 reductionRatio)
Definition: UVoxelizer.cc:584
void BuildBoundaries()
Definition: UVoxelizer.cc:207
static double MinDistanceToBox(const UVector3 &aPoint, const UVector3 &f)
Definition: UVoxelizer.cc:1022
void BuildBoundingBox()
Definition: UVoxelizer.cc:424
std::vector< std::vector< int > > fVoxelBoxesCandidates
Definition: UVoxelizer.hh:245
const std::vector< int > fNoCandidates
Definition: UVoxelizer.hh:249
UVector3 pos
Definition: UVoxelizer.hh:39
int GetCandidatesVoxelArray(const UVector3 &point, std::vector< int > &list, UBits *crossed=NULL) const
Definition: UVoxelizer.cc:868
void BuildBitmasks(std::vector< double > fBoundaries[], UBits bitmasks[])
Definition: UVoxelizer.cc:298
const G4int n
long long CountVoxels(std::vector< double > boundaries[]) const
Definition: UVoxelizer.hh:189
const UVoxelBox & GetVoxelBox(int i) const
Definition: UVoxelizer.hh:212
bool GetPointVoxel(const UVector3 &p, std::vector< int > &voxels) const
Definition: UVoxelizer.hh:140
int previous
Definition: UVoxelizer.hh:45
UVector3 fReductionRatio
Definition: UVoxelizer.hh:295
int fNPerSlice
Definition: UVoxelizer.hh:279
std::string GetCandidatesAsString(const UBits &bits)
Definition: UVoxelizer.cc:389
UBits fBitmasks[3]
Definition: UVoxelizer.hh:289
const std::vector< int > & GetCandidates(std::vector< int > &curVoxel) const
Definition: UVoxelizer.hh:197
T max(const T t1, const T t2)
brief Return the largest of the two arguments
UBox fBoundingBox
Definition: UVoxelizer.hh:292
const std::vector< int > & GetVoxelBoxCandidates(int i) const
Definition: UVoxelizer.hh:217
void GetCandidatesVoxel(std::vector< int > &voxels)
Definition: UVoxelizer.cc:778
static int GetDefaultVoxelsCount()
Definition: UVoxelizer.cc:1157
int GetPointIndex(const UVector3 &p) const
Definition: UVoxelizer.hh:151
std::vector< UVoxelBox > fVoxelBoxes
Definition: UVoxelizer.hh:243
double fTolerance
Definition: UVoxelizer.hh:299
long long fCountOfVoxels
Definition: UVoxelizer.hh:251
int GetBitsPerSlice() const
Definition: UVoxelizer.hh:113
void BuildReduceVoxels(std::vector< double > fBoundaries[], UVector3 reductionRatio)
Definition: UVoxelizer.cc:490
std::vector< int > fCandidatesCounts[3]
Definition: UVoxelizer.hh:285
void CreateSortedBoundary(std::vector< double > &boundaryRaw, int axis)
Definition: UVoxelizer.cc:189
void DisplayListNodes()
Definition: UVoxelizer.cc:403
void DisplayVoxelLimits()
Definition: UVoxelizer.cc:173
std::map< int, std::vector< int > > fCandidates
Definition: UVoxelizer.hh:247
const std::vector< UVoxelBox > & GetBoxes() const
Definition: UVoxelizer.hh:90
void SetReductionRatio(int maxVoxels, UVector3 &reductionRatio)
Definition: UVoxelizer.cc:477
double SafetyToBoundingBox(const UVector3 &point) const
Definition: UVoxelizer.cc:1015
int AllocatedMemory()
Definition: UVoxelizer.cc:1137
const UBits & Empty() const
Definition: UVoxelizer.hh:162
static void SetDefaultVoxelsCount(int count)
Definition: UVoxelizer.cc:1152
UVector3 fBoundingBoxSize
Definition: UVoxelizer.hh:293
UBits fEmpty
Definition: UVoxelizer.hh:301
Definition: UBits.hh:38
bool IsEmpty(int index) const
Definition: UVoxelizer.hh:167
UVector3 fBoundingBoxCenter
Definition: UVoxelizer.hh:291