OpenVDB 11.0.0
Loading...
Searching...
No Matches
Primitives.h
Go to the documentation of this file.
1// Copyright Contributors to the OpenVDB Project
2// SPDX-License-Identifier: MPL-2.0
3
4/*!
5 \file Primitives.h
6
7 \author Ken Museth
8
9 \date June 26, 2020
10
11 \brief Generates volumetric primitives, e.g. sphere, torus etc, as NanoVDB grid.
12
13 \note This has no dependency on openvdb.
14*/
15
16#ifndef NANOVDB_PRIMITIVES_H_HAS_BEEN_INCLUDED
17#define NANOVDB_PRIMITIVES_H_HAS_BEEN_INCLUDED
18
19#define NANOVDB_PARALLEL_PRIMITIVES
20
21#include <nanovdb/NanoVDB.h>
22#include "CreateNanoGrid.h"
24
25namespace nanovdb {
26
27/// @brief Returns a handle to a narrow-band level set of a sphere
28///
29/// @param radius Radius of sphere in world units
30/// @param center Center of sphere in world units
31/// @param voxelSize Size of a voxel in world units
32/// @param halfWidth Half-width of narrow band in voxel units
33/// @param origin Origin of grid in world units
34/// @param name Name of the grid
35/// @param sMode Mode of computation for the statistics.
36/// @param cMode Mode of computation for the checksum.
37/// @param tolerance Global error tolerance use when VoxelT = FpN
38/// @param ditherOn If true dithering will be applied when VoxelT = {Fp4,Fp8,Fp16,FpN}
39/// @param buffer Buffer used for memory allocation by the handle
40///
41/// @details The @c BuildT template parameter must be one of the following:
42/// float (default), double, Fp4, Fp8, Fp16 or FpN. The @c tolerance
43/// argument is only used when BuildT is set to FpN.
44template<typename BuildT = float, typename BufferT = HostBuffer>
45typename enable_if<is_same<float, BuildT>::value ||
46 is_same<double, BuildT>::value, GridHandle<BufferT>>::type
47createLevelSetSphere(double radius = 100.0,
48 const Vec3d& center = Vec3d(0),
49 double voxelSize = 1.0,
50 double halfWidth = 3.0,
51 const Vec3d& origin = Vec3d(0),
52 const std::string& name = "sphere_ls",
55 const BufferT& buffer = BufferT());
56
57template<typename BuildT, typename BufferT = HostBuffer>
58typename enable_if<is_same<Fp4, BuildT>::value ||
60 is_same<Fp16, BuildT>::value, GridHandle<BufferT>>::type
61createLevelSetSphere(double radius = 100.0,
62 const Vec3d& center = Vec3d(0),
63 double voxelSize = 1.0,
64 double halfWidth = 3.0,
65 const Vec3d& origin = Vec3d(0),
66 const std::string& name = "sphere_ls",
69 bool ditherOn = false,
70 const BufferT& buffer = BufferT());
71
72template<typename BuildT, typename BufferT = HostBuffer>
73typename enable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
74createLevelSetSphere(double radius = 100.0,
75 const Vec3d& center = Vec3d(0),
76 double voxelSize = 1.0,
77 double halfWidth = 3.0,
78 const Vec3d& origin = Vec3d(0),
79 const std::string& name = "sphere_ls_FpN",
82 float tolerance = -1.0f,
83 bool ditherOn = false,
84 const BufferT& buffer = BufferT());
85
86//================================================================================================
87
88/// @brief Returns a handle to a sparse fog volume of a sphere such
89/// that the exterior is 0 and inactive, the interior is active
90/// with values varying smoothly from 0 at the surface of the
91/// sphere to 1 at the halfWidth and interior of the sphere.
92///
93/// @param radius Radius of sphere in world units
94/// @param center Center of sphere in world units
95/// @param voxelSize Size of a voxel in world units
96/// @param halfWidth Half-width of narrow band in voxel units
97/// @param origin Origin of grid in world units
98/// @param name Name of the grid
99/// @param sMode Mode of computation for the statistics.
100/// @param cMode Mode of computation for the checksum.
101/// @param tolerance Global error tolerance use when VoxelT = FpN
102/// @param ditherOn If true dithering will be applied when BuildT = {Fp4,Fp8,Fp16,FpN}
103/// @param buffer Buffer used for memory allocation by the handle
104///
105/// @details The @c BuildT template parameter must be one of the following:
106/// float (default), double, Fp4, Fp8, Fp16 or FpN. The @c tolerance
107/// argument is only used when BuildT is set to FpN.
108template<typename BuildT = float, typename BufferT = HostBuffer>
109typename disable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
110createFogVolumeSphere(double radius = 100.0,
111 const Vec3d& center = Vec3d(0.0),
112 double voxelSize = 1.0,
113 double halfWidth = 3.0,
114 const Vec3d& origin = Vec3d(0.0),
115 const std::string& name = "sphere_fog",
118 const BufferT& buffer = BufferT());
119
120template<typename BuildT, typename BufferT = HostBuffer>
121typename enable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
122createFogVolumeSphere(double radius = 100.0,
123 const Vec3d& center = Vec3d(0.0),
124 double voxelSize = 1.0,
125 double halfWidth = 3.0,
126 const Vec3d& origin = Vec3d(0.0),
127 const std::string& name = "sphere_fog",
130 float tolerance = -1.0f,
131 bool ditherOn = false,
132 const BufferT& buffer = BufferT());
133
134//================================================================================================
135
136/// @brief Returns a handle to a PointDataGrid containing points scattered
137/// on the surface of a sphere.
138///
139/// @param pointsPerVoxel Number of point per voxel on on the surface
140/// @param radius Radius of sphere in world units
141/// @param center Center of sphere in world units
142/// @param voxelSize Size of a voxel in world units
143/// @param origin Origin of grid in world units
144/// @param name Name of the grid
145/// @param mode Mode of computation for the checksum.
146/// @param buffer Buffer used for memory allocation by the handle
147///
148/// @details The @c BuildT template parameter must be float (default) or double.
149template<typename BuildT = float, typename BufferT = HostBuffer>
150typename disable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
151createPointSphere(int pointsPerVoxel = 1,
152 double radius = 100.0,
153 const Vec3d& center = Vec3d(0.0),
154 double voxelSize = 1.0,
155 const Vec3d& origin = Vec3d(0.0),
156 const std::string& name = "sphere_points",
158 const BufferT& buffer = BufferT());
159
160//================================================================================================
161
162/// @brief Returns a handle to a narrow-band level set of a torus in the xz-plane
163///
164/// @param majorRadius Major radius of torus in world units
165/// @param minorRadius Minor radius of torus in world units
166/// @param center Center of torus in world units
167/// @param voxelSize Size of a voxel in world units
168/// @param halfWidth Half-width of narrow band in voxel units
169/// @param origin Origin of grid in world units
170/// @param name Name of the grid
171/// @param sMode Mode of computation for the statistics.
172/// @param cMode Mode of computation for the checksum.
173/// @param tolerance Global error tolerance use when VoxelT = FpN
174/// @param ditherOn If true dithering will be applied when VoxelT = {Fp4,Fp8,Fp16,FpN}
175/// @param buffer Buffer used for memory allocation by the handle
176///
177/// @details The @c BuildT template parameter must be one of the following:
178/// float (default), double, Fp4, Fp8, Fp16 or FpN. The @c tolerance
179/// argument is only used when BuildT is set to FpN.
180template<typename BuildT = float, typename BufferT = HostBuffer>
181typename disable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
182createLevelSetTorus(double majorRadius = 100.0,
183 double minorRadius = 50.0,
184 const Vec3d& center = Vec3d(0.0),
185 double voxelSize = 1.0,
186 double halfWidth = 3.0,
187 const Vec3d& origin = Vec3d(0.0),
188 const std::string& name = "torus_ls",
191 const BufferT& buffer = BufferT());
192
193template<typename BuildT, typename BufferT = HostBuffer>
194typename enable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
195createLevelSetTorus(double majorRadius = 100.0,
196 double minorRadius = 50.0,
197 const Vec3d& center = Vec3d(0.0),
198 double voxelSize = 1.0,
199 double halfWidth = 3.0,
200 const Vec3d& origin = Vec3d(0.0),
201 const std::string& name = "torus_ls",
204 float tolerance = -1.0f,
205 bool ditherOn = false,
206 const BufferT& buffer = BufferT());
207
208//================================================================================================
209
210/// @brief Returns a handle to a sparse fog volume of a torus in the xz-plane such
211/// that the exterior is 0 and inactive, the interior is active
212/// with values varying smoothly from 0 at the surface of the
213/// torus to 1 at the halfWidth and interior of the torus.
214///
215/// @param majorRadius Major radius of torus in world units
216/// @param minorRadius Minor radius of torus in world units
217/// @param center Center of torus in world units
218/// @param voxelSize Size of a voxel in world units
219/// @param halfWidth Half-width of narrow band in voxel units
220/// @param origin Origin of grid in world units
221/// @param name Name of the grid
222/// @param sMode Mode of computation for the statistics.
223/// @param cMode Mode of computation for the checksum.
224/// @param tolerance Global error tolerance use when VoxelT = FpN
225/// @param ditherOn If true dithering will be applied when VoxelT = {Fp4,Fp8,Fp16,FpN}
226/// @param buffer Buffer used for memory allocation by the handle
227///
228/// @details The @c BuildT template parameter must be one of the following:
229/// float (default), double, Fp4, Fp8, Fp16 or FpN. The @c tolerance
230/// argument is only used when BuildT is set to FpN.
231template<typename BuildT = float, typename BufferT = HostBuffer>
232typename disable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
233createFogVolumeTorus(double majorRadius = 100.0,
234 double minorRadius = 50.0,
235 const Vec3d& center = Vec3d(0.0),
236 double voxelSize = 1.0,
237 double halfWidth = 3.0,
238 const Vec3d& origin = Vec3d(0.0),
239 const std::string& name = "torus_fog",
242 const BufferT& buffer = BufferT());
243
244template<typename BuildT, typename BufferT = HostBuffer>
245typename enable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
246createFogVolumeTorus(double majorRadius = 100.0,
247 double minorRadius = 50.0,
248 const Vec3d& center = Vec3d(0.0),
249 double voxelSize = 1.0,
250 double halfWidth = 3.0,
251 const Vec3d& origin = Vec3d(0.0),
252 const std::string& name = "torus_fog_FpN",
255 float tolerance = -1.0f,
256 bool ditherOn = false,
257 const BufferT& buffer = BufferT());
258
259//================================================================================================
260
261/// @brief Returns a handle to a PointDataGrid containing points scattered
262/// on the surface of a torus.
263///
264/// @param pointsPerVoxel Number of point per voxel on on the surface
265/// @param majorRadius Major radius of torus in world units
266/// @param minorRadius Minor radius of torus in world units
267/// @param center Center of torus in world units
268/// @param voxelSize Size of a voxel in world units
269/// @param origin Origin of grid in world units
270/// @param name Name of the grid
271/// @param cMode Mode of computation for the checksum.
272/// @param buffer Buffer used for memory allocation by the handle
273//
274/// @details The @c BuildT template parameter must be float (default) or double.
275template<typename BuildT = float, typename BufferT = HostBuffer>
276typename disable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
277createPointTorus(int pointsPerVoxel = 1, // half-width of narrow band in voxel units
278 double majorRadius = 100.0, // major radius of torus in world units
279 double minorRadius = 50.0, // minor radius of torus in world units
280 const Vec3d& center = Vec3d(0.0), // center of torus in world units
281 double voxelSize = 1.0, // size of a voxel in world units
282 const Vec3d& origin = Vec3d(0.0f), // origin of grid in world units
283 const std::string& name = "torus_points", // name of grid
285 const BufferT& buffer = BufferT());
286
287//================================================================================================
288
289/// @brief Returns a handle to a narrow-band level set of a box
290///
291/// @param width Width of box in world units
292/// @param height Height of box in world units
293/// @param depth Depth of box in world units
294/// @param center Center of box in world units
295/// @param voxelSize Size of a voxel in world units
296/// @param halfWidth Half-width of narrow band in voxel units
297/// @param origin Origin of grid in world units
298/// @param name Name of the grid
299/// @param sMode Mode of computation for the statistics.
300/// @param cMode Mode of computation for the checksum.
301/// @param tolerance Global error tolerance use when VoxelT = FpN
302/// @param ditherOn If true dithering will be applied when VoxelT = {Fp4,Fp8,Fp16,FpN}
303/// @param buffer Buffer used for memory allocation by the handle
304///
305/// @details The @c BuildT template parameter must be one of the following:
306/// float (default), double, Fp4, Fp8, Fp16 or FpN. The @c tolerance
307/// argument is only used when BuildT is set to FpN.
308template<typename BuildT = float, typename BufferT = HostBuffer>
309typename disable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
310createLevelSetBox(double width = 40.0,
311 double height = 60.0,
312 double depth = 100.0,
313 const Vec3d& center = Vec3d(0.0),
314 double voxelSize = 1.0,
315 double halfWidth = 3.0,
316 const Vec3d& origin = Vec3d(0.0),
317 const std::string& name = "box_ls",
320 const BufferT& buffer = BufferT());
321
322template<typename BuildT, typename BufferT = HostBuffer>
323typename enable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
324createLevelSetBox(double width = 40.0,
325 double height = 60.0,
326 double depth = 100.0,
327 const Vec3d& center = Vec3d(0.0),
328 double voxelSize = 1.0,
329 double halfWidth = 3.0,
330 const Vec3d& origin = Vec3d(0.0),
331 const std::string& name = "box_ls_FpN",
334 float tolerance = -1.0f,
335 bool ditherOn = false,
336 const BufferT& buffer = BufferT());
337
338//================================================================================================
339
340/// @brief Returns a handle to a sparse fog volume of a box such
341/// that the exterior is 0 and inactive, the interior is active
342/// with values varying smoothly from 0 at the surface of the
343/// box to 1 at the halfWidth and interior of the box.
344///
345/// @param width Width of box in world units
346/// @param height Height of box in world units
347/// @param depth Depth of box in world units
348/// @param center Center of box in world units
349/// @param voxelSize Size of a voxel in world units
350/// @param halfWidth Half-width of narrow band in voxel units
351/// @param origin Origin of grid in world units
352/// @param name Name of the grid
353/// @param sMode Mode of computation for the statistics.
354/// @param cMode Mode of computation for the checksum.
355/// @param tolerance Global error tolerance use when VoxelT = FpN
356/// @param ditherOn If true dithering will be applied when VoxelT = {Fp4,Fp8,Fp16,FpN}
357/// @param buffer Buffer used for memory allocation by the handle
358///
359/// @details The @c BuildT template parameter must be one of the following:
360/// float (default), double, Fp4, Fp8, Fp16 or FpN. The @c tolerance
361/// argument is only used when BuildT is set to FpN.
362template<typename BuildT = float, typename BufferT = HostBuffer>
363typename disable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
364createFogVolumeBox(double width = 40.0,
365 double height = 60.0,
366 double depth = 100.0,
367 const Vec3d& center = Vec3d(0.0),
368 double voxelSize = 1.0,
369 double halfWidth = 3.0,
370 const Vec3d& origin = Vec3d(0.0),
371 const std::string& name = "box_fog",
374 const BufferT& buffer = BufferT());
375
376template<typename BuildT, typename BufferT = HostBuffer>
377typename enable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
378createFogVolumeBox(double width = 40.0,
379 double height = 60.0,
380 double depth = 100.0,
381 const Vec3d& center = Vec3d(0.0),
382 double voxelSize = 1.0,
383 double halfWidth = 3.0,
384 const Vec3d& origin = Vec3d(0.0),
385 const std::string& name = "box_fog_FpN",
388 float tolerance = -1.0f,
389 bool ditherOn = false,
390 const BufferT& buffer = BufferT());
391
392//================================================================================================
393
394/// @brief Returns a handle to a narrow-band level set of a octahedron
395///
396/// @param scale Scale of octahedron in world units
397/// @param center Center of octahedron in world units
398/// @param voxelSize Size of a voxel in world units
399/// @param halfWidth Half-width of narrow band in voxel units
400/// @param origin Origin of grid in world units
401/// @param name Name of the grid
402/// @param sMode Mode of computation for the statistics.
403/// @param cMode Mode of computation for the checksum.
404/// @param tolerance Global error tolerance use when VoxelT = FpN
405/// @param ditherOn If true dithering will be applied when VoxelT = {Fp4,Fp8,Fp16,FpN}
406/// @param buffer Buffer used for memory allocation by the handle
407///
408/// @details The @c BuildT template parameter must be one of the following:
409/// float (default), double, Fp4, Fp8, Fp16 or FpN. The @c tolerance
410/// argument is only used when BuildT is set to FpN.
411template<typename BuildT = float, typename BufferT = HostBuffer>
412typename disable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
413createLevelSetOctahedron(double scale = 100.0,
414 const Vec3d& center = Vec3d(0.0),
415 double voxelSize = 1.0,
416 double halfWidth = 3.0,
417 const Vec3d& origin = Vec3d(0.0),
418 const std::string& name = "octadedron_ls",
421 const BufferT& buffer = BufferT());
422
423template<typename BuildT, typename BufferT = HostBuffer>
424typename enable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
425createLevelSetOctahedron(double scale = 100.0,
426 const Vec3d& center = Vec3d(0.0),
427 double voxelSize = 1.0,
428 double halfWidth = 3.0,
429 const Vec3d& origin = Vec3d(0.0),
430 const std::string& name = "octadedron_ls_FpN",
433 float tolerance = -1.0f,
434 bool ditherOn = false,
435 const BufferT& buffer = BufferT());
436
437//================================================================================================
438
439/// @brief Returns a handle to a sparse fog volume of an octahedron such
440/// that the exterior is 0 and inactive, the interior is active
441/// with values varying smoothly from 0 at the surface of the
442/// octahedron to 1 at the halfWidth and interior of the octahedron.
443///
444/// @param scale Scale of octahedron in world units
445/// @param center Center of box in world units
446/// @param voxelSize Size of a voxel in world units
447/// @param halfWidth Half-width of narrow band in voxel units
448/// @param origin Origin of grid in world units
449/// @param name Name of the grid
450/// @param sMode Mode of computation for the statistics.
451/// @param cMode Mode of computation for the checksum.
452/// @param tolerance Global error tolerance use when VoxelT = FpN
453/// @param ditherOn If true dithering will be applied when VoxelT = {Fp4,Fp8,Fp16,FpN}
454/// @param buffer Buffer used for memory allocation by the handle
455///
456/// @details The @c BuildT template parameter must be one of the following:
457/// float (default), double, Fp4, Fp8, Fp16 or FpN. The @c tolerance
458/// argument is only used when BuildT is set to FpN.
459template<typename BuildT = float, typename BufferT = HostBuffer>
460typename disable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
461createFogVolumeOctahedron(double scale = 100.0,
462 const Vec3d& center = Vec3d(0.0),
463 double voxelSize = 1.0,
464 double halfWidth = 3.0,
465 const Vec3d& origin = Vec3d(0.0),
466 const std::string& name = "octadedron_fog",
469 const BufferT& buffer = BufferT());
470
471template<typename BuildT, typename BufferT = HostBuffer>
472typename enable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
473createFogVolumeOctahedron(double scale = 100.0,
474 const Vec3d& center = Vec3d(0.0),
475 double voxelSize = 1.0,
476 double halfWidth = 3.0,
477 const Vec3d& origin = Vec3d(0.0),
478 const std::string& name = "octadedron_fog_FpN",
481 float tolerance = -1.0f,
482 bool ditherOn = false,
483 const BufferT& buffer = BufferT());
484
485//================================================================================================
486
487/// @brief Returns a handle to a narrow-band level set of a bounding-box (= wireframe of a box)
488///
489/// @param width Width of box in world units
490/// @param height Height of box in world units
491/// @param depth Depth of box in world units
492/// @param thickness Thickness of the wire in world units
493/// @param center Center of bbox in world units
494/// @param voxelSize Size of a voxel in world units
495/// @param halfWidth Half-width of narrow band in voxel units
496/// @param origin Origin of grid in world units
497/// @param name Name of the grid
498/// @param sMode Mode of computation for the statistics.
499/// @param cMode Mode of computation for the checksum.
500/// @param tolerance Global error tolerance use when VoxelT = FpN
501/// @param ditherOn If true dithering will be applied when VoxelT = {Fp4,Fp8,Fp16,FpN}
502/// @param buffer Buffer used for memory allocation by the handle
503///
504/// @details The @c BuildT template parameter must be one of the following:
505/// float (default), double, Fp4, Fp8, Fp16 or FpN. The @c tolerance
506/// argument is only used when BuildT is set to FpN.
507template<typename BuildT = float, typename BufferT = HostBuffer>
508typename disable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
509createLevelSetBBox(double width = 40.0,
510 double height = 60.0,
511 double depth = 100.0,
512 double thickness = 10.0,
513 const Vec3d& center = Vec3d(0.0),
514 double voxelSize = 1.0,
515 double halfWidth = 3.0,
516 const Vec3d& origin = Vec3d(0.0),
517 const std::string& name = "bbox_ls",
520 const BufferT& buffer = BufferT());
521
522template<typename BuildT, typename BufferT = HostBuffer>
523typename enable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
524createLevelSetBBox(double width = 40.0,
525 double height = 60.0,
526 double depth = 100.0,
527 double thickness = 10.0,
528 const Vec3d& center = Vec3d(0.0),
529 double voxelSize = 1.0,
530 double halfWidth = 3.0,
531 const Vec3d& origin = Vec3d(0.0),
532 const std::string& name = "bbox_ls_FpN",
535 float tolerance = -1.0f,
536 bool ditherOn = false,
537 const BufferT& buffer = BufferT());
538
539
540//================================================================================================
541
542/// @brief Returns a handle to a PointDataGrid containing points scattered
543/// on the surface of a box.
544///
545/// @param pointsPerVoxel Number of point per voxel on on the surface
546/// @param width Width of box in world units
547/// @param height Height of box in world units
548/// @param depth Depth of box in world units
549/// @param center Center of box in world units
550/// @param voxelSize Size of a voxel in world units
551/// @param origin Origin of grid in world units
552/// @param name Name of the grid
553/// @param mode Mode of computation for the checksum.
554/// @param buffer Buffer used for memory allocation by the handle
555template<typename BuildT = float, typename BufferT = HostBuffer>
556typename disable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
557createPointBox(int pointsPerVoxel = 1, // half-width of narrow band in voxel units
558 double width = 40.0, // width of box in world units
559 double height = 60.0, // height of box in world units
560 double depth = 100.0, // depth of box in world units
561 const Vec3d& center = Vec3d(0.0), // center of box in world units
562 double voxelSize = 1.0, // size of a voxel in world units
563 const Vec3d& origin = Vec3d(0.0), // origin of grid in world units
564 const std::string& name = "box_points", // name of grid
566 const BufferT& buffer = BufferT());
567
568//================================================================================================
569
570/// @brief Given an input NanoVDB voxel grid this methods returns a GridHandle to another NanoVDB
571/// PointDataGrid with points scattered in the active leaf voxels of in input grid. Note, the
572/// coordinates of the points are encoded as blind data in world-space.
573///
574/// @param srcGrid Const input grid used to determine the active voxels to scatter points into
575/// @param pointsPerVoxel Number of point per voxel on on the surface
576/// @param name Name of the grid
577/// @param mode Mode of computation for the checksum.
578/// @param buffer Buffer used for memory allocation by the handle
579template<typename SrcBuildT = float, typename BufferT = HostBuffer>
580inline GridHandle<BufferT>
581createPointScatter(const NanoGrid<SrcBuildT>& srcGrid, // source grid used to scatter points into
582 int pointsPerVoxel = 1, // half-width of narrow band in voxel units
583 const std::string& name = "point_scatter", // name of grid
585 const BufferT& buffer = BufferT());
586
587//================================================================================================
588
589namespace {
590
591/// @brief Returns a shared pointer to a build::Grid containing a narrow-band SDF values for a sphere
592///
593/// @brief Note, this is not (yet) a valid level set SDF field since values inside sphere (and outside
594/// the narrow band) are still undefined. Call builder::sdfToLevelSet() to set those
595/// values or alternatively call builder::levelSetToFog to generate a FOG volume.
596///
597/// @details The @c BuildT template parameter must be one of the following:
598/// float (default), double, Fp4, Fp8, Fp16 or FpN.
599template<typename BuildT>
600std::shared_ptr<build::Grid<BuildT>>
601initSphere(double radius, // radius of sphere in world units
602 const Vec3d& center, // center of sphere in world units
603 double voxelSize, // size of a voxel in world units
604 double halfWidth, // half-width of narrow band in voxel units
605 const Vec3d& origin) // origin of grid in world units
606{
607 using GridT = build::Grid<BuildT>;
608 using ValueT = typename BuildToValueMap<BuildT>::type;
609 static_assert(is_floating_point<ValueT>::value, "initSphere: expect floating point");
610 if (!(radius > 0))
611 throw std::runtime_error("Sphere: radius must be positive!");
612 if (!(voxelSize > 0))
613 throw std::runtime_error("Sphere: voxelSize must be positive!");
614 if (!(halfWidth > 0))
615 throw std::runtime_error("Sphere: halfWidth must be positive!");
616
617 auto grid = std::make_shared<GridT>(ValueT(halfWidth * voxelSize));
618 grid->setTransform(voxelSize, origin);
619
620 // Define radius of sphere with narrow-band in voxel units
621 const ValueT r0 = radius / ValueT(voxelSize), rmax = r0 + ValueT(halfWidth);
622
623 // Radius below the Nyquist frequency
624 if (r0 < ValueT(1.5f)) return grid;
625
626 // Define center of sphere in voxel units
627 const Vec3<ValueT> c(ValueT(center[0] - origin[0]) / ValueT(voxelSize),
628 ValueT(center[1] - origin[1]) / ValueT(voxelSize),
629 ValueT(center[2] - origin[2]) / ValueT(voxelSize));
630
631 // Define bounds of the voxel coordinates
632 const int imin = Floor(c[0] - rmax), imax = Ceil(c[0] + rmax);
633 const int jmin = Floor(c[1] - rmax), jmax = Ceil(c[1] + rmax);
634 const int kmin = Floor(c[2] - rmax), kmax = Ceil(c[2] + rmax);
635
636 const Range<1,int> range(imin, imax+1, 32);
637
638 auto kernel = [&](const Range<1,int> &r) {
639 auto acc = grid->getWriteAccessor();
640 Coord ijk;
641 int &i = ijk[0], &j = ijk[1], &k = ijk[2], m = 1;
642 // Compute signed distances to sphere using leapfrogging in k
643 for (i = r.begin(); i < r.end(); ++i) {
644 const auto x2 = Pow2(ValueT(i) - c[0]);
645 for (j = jmin; j <= jmax; ++j) {
646 const auto x2y2 = Pow2(ValueT(j) - c[1]) + x2;
647 for (k = kmin; k <= kmax; k += m) {
648 m = 1;
649 const auto v = Sqrt(x2y2 + Pow2(ValueT(k) - c[2])) - r0; // Distance in voxel units
650 const auto d = v < 0 ? -v : v;
651 if (d < halfWidth) { // inside narrow band
652 acc.setValue(ijk, ValueT(voxelSize) * v); // distance in world units
653 } else { // outside narrow band
654 m += Floor(d - halfWidth); // leapfrog
655 }
656 } //end leapfrog over k
657 } //end loop over j
658 } //end loop over i
659 };// kernel
660#ifdef NANOVDB_PARALLEL_PRIMITIVES
661 forEach(range, kernel);
662#else
663 kernel(range);
664#endif
665 return grid;
666} // initSphere
667
668template<typename BuildT>
669std::shared_ptr<build::Grid<BuildT>>
670initTorus(double radius1, // major radius of torus in world units
671 double radius2, // minor radius of torus in world units
672 const Vec3d& center, // center of torus in world units
673 double voxelSize, // size of a voxel in world units
674 double halfWidth, // half-width of narrow band in voxel units
675 const Vec3d& origin) // origin of grid in world units
676{
677 using GridT = build::Grid<BuildT>;
678 using ValueT = typename BuildToValueMap<BuildT>::type;
679 static_assert(is_floating_point<ValueT>::value, "initTorus: expect floating point");
680 if (!(radius2 > 0))
681 throw std::runtime_error("Torus: radius2 must be positive!");
682 if (!(radius1 > radius2))
683 throw std::runtime_error("Torus: radius1 must be larger than radius2!");
684 if (!(voxelSize > 0))
685 throw std::runtime_error("Torus: voxelSize must be positive!");
686 if (!(halfWidth > 0))
687 throw std::runtime_error("Torus: halfWidth must be positive!");
688
689 auto grid = std::make_shared<GridT>(ValueT(halfWidth * voxelSize));
690 grid->setTransform(voxelSize, origin);
691
692 // Define size of torus with narrow-band in voxel units
693 const ValueT r1 = radius1 / ValueT(voxelSize), r2 = radius2 / ValueT(voxelSize), rmax1 = r1 + r2 + ValueT(halfWidth), rmax2 = r2 + ValueT(halfWidth);
694
695 // Radius below the Nyquist frequency
696 if (r2 < ValueT(1.5)) return grid;
697
698 // Define center of torus in voxel units
699 const Vec3<ValueT> c(ValueT(center[0] - origin[0]) / ValueT(voxelSize),
700 ValueT(center[1] - origin[1]) / ValueT(voxelSize),
701 ValueT(center[2] - origin[2]) / ValueT(voxelSize));
702
703 // Define bounds of the voxel coordinates
704 const int imin = Floor(c[0] - rmax1), imax = Ceil(c[0] + rmax1);
705 const int jmin = Floor(c[1] - rmax2), jmax = Ceil(c[1] + rmax2);
706 const int kmin = Floor(c[2] - rmax1), kmax = Ceil(c[2] + rmax1);
707
708 const Range<1,int> range(imin, imax+1, 32);
709 auto kernel = [&](const Range<1,int> &r) {
710 auto acc = grid->getWriteAccessor();
711 Coord ijk;
712 int &i = ijk[0], &j = ijk[1], &k = ijk[2], m = 1;
713 // Compute signed distances to torus using leapfrogging in k
714 for (i = r.begin(); i < r.end(); ++i) {
715 const auto x2 = Pow2(ValueT(i) - c[0]);
716 for (k = kmin; k <= kmax; ++k) {
717 const auto x2z2 = Pow2(Sqrt(Pow2(ValueT(k) - c[2]) + x2) - r1);
718 for (j = jmin; j <= jmax; j += m) {
719 m = 1;
720 const auto v = Sqrt(x2z2 + Pow2(ValueT(j) - c[1])) - r2; // Distance in voxel units
721 const auto d = v < 0 ? -v : v;
722 if (d < halfWidth) { // inside narrow band
723 acc.setValue(ijk, ValueT(voxelSize) * v); // distance in world units
724 } else { // outside narrow band
725 m += Floor(d - halfWidth); // leapfrog
726 }
727 } //end leapfrog over k
728 } //end loop over j
729 } //end loop over i
730 }; // kernel
731
732#ifdef NANOVDB_PARALLEL_PRIMITIVES
733 forEach(range, kernel);
734#else
735 kernel(range);
736#endif
737
738 return grid;
739} // initTorus
740
741template<typename BuildT>
742std::shared_ptr<build::Grid<BuildT>>
743initBox(double width, // major radius of torus in world units
744 double height, // minor radius of torus in world units
745 double depth,
746 const Vec3d& center, // center of box in world units
747 double voxelSize, // size of a voxel in world units
748 double halfWidth, // half-width of narrow band in voxel units
749 const Vec3d& origin) // origin of grid in world units
750{
751 using GridT = build::Grid<BuildT>;
752 using ValueT = typename BuildToValueMap<BuildT>::type;
753 static_assert(is_floating_point<ValueT>::value, "initBox: expect floating point");
754 using Vec3T = Vec3<ValueT>;
755 if (!(width > 0))
756 throw std::runtime_error("Box: width must be positive!");
757 if (!(height > 0))
758 throw std::runtime_error("Box: height must be positive!");
759 if (!(depth > 0))
760 throw std::runtime_error("Box: depth must be positive!");
761
762 if (!(voxelSize > 0))
763 throw std::runtime_error("Box: voxelSize must be positive!");
764 if (!(halfWidth > 0))
765 throw std::runtime_error("Box: halfWidth must be positive!");
766
767 auto grid = std::make_shared<GridT>(ValueT(halfWidth * voxelSize));
768 grid->setTransform(voxelSize, origin);
769
770 // Define size of box with narrow-band in voxel units
771 const Vec3T r(width / (2 * ValueT(voxelSize)),
772 height / (2 * ValueT(voxelSize)),
773 depth / (2 * ValueT(voxelSize)));
774
775 // Below the Nyquist frequency
776 if (r.min() < ValueT(1.5)) return grid;
777
778 // Define center of box in voxel units
779 const Vec3T c(ValueT(center[0] - origin[0]) / ValueT(voxelSize),
780 ValueT(center[1] - origin[1]) / ValueT(voxelSize),
781 ValueT(center[2] - origin[2]) / ValueT(voxelSize));
782
783 // Define utility functions
784 auto Pos = [](ValueT x) { return x > 0 ? x : 0; };
785 auto Neg = [](ValueT x) { return x < 0 ? x : 0; };
786
787 // Define bounds of the voxel coordinates
788 const BBox<Vec3T> b(c - r - Vec3T(ValueT(halfWidth)), c + r + Vec3T(ValueT(halfWidth)));
789 const CoordBBox bbox(Coord(Floor(b[0][0]), Floor(b[0][1]), Floor(b[0][2])),
790 Coord( Ceil(b[1][0]), Ceil(b[1][1]), Ceil(b[1][2])));
791 const Range<1,int> range(bbox[0][0], bbox[1][0]+1, 32);
792
793 // Compute signed distances to box using leapfrogging in k
794 auto kernel = [&](const Range<1,int> &ra) {
795 auto acc = grid->getWriteAccessor();
796 int m = 1;
797 for (Coord p(ra.begin(),bbox[0][1],bbox[0][2]); p[0] < ra.end(); ++p[0]) {
798 const auto q1 = Abs(ValueT(p[0]) - c[0]) - r[0];
799 const auto x2 = Pow2(Pos(q1));
800 for (p[1] = bbox[0][1]; p[1] <= bbox[1][1]; ++p[1]) {
801 const auto q2 = Abs(ValueT(p[1]) - c[1]) - r[1];
802 const auto q0 = Max(q1, q2);
803 const auto x2y2 = x2 + Pow2(Pos(q2));
804 for (p[2] = bbox[0][2]; p[2] <= bbox[1][2]; p[2] += m) {
805 m = 1;
806 const auto q3 = Abs(ValueT(p[2]) - c[2]) - r[2];
807 const auto v = Sqrt(x2y2 + Pow2(Pos(q3))) + Neg(Max(q0, q3)); // Distance in voxel units
808 const auto d = Abs(v);
809 if (d < halfWidth) { // inside narrow band
810 acc.setValue(p, ValueT(voxelSize) * v); // distance in world units
811 } else { // outside narrow band
812 m += Floor(d - halfWidth); // leapfrog
813 }
814 } //end leapfrog over k
815 } //end loop over j
816 } //end loop over i
817 }; // kernel
818#ifdef NANOVDB_PARALLEL_PRIMITIVES
819 forEach(range, kernel);
820#else
821 kernel(range);
822#endif
823 return grid;
824} // initBox
825
826template<typename BuildT>
827std::shared_ptr<build::Grid<BuildT>>
828initBBox(double width, // width of the bbox in world units
829 double height, // height of the bbox in world units
830 double depth, // depth of the bbox in world units
831 double thickness, // thickness of the wire in world units
832 const Vec3d& center, // center of bbox in world units
833 double voxelSize, // size of a voxel in world units
834 double halfWidth, // half-width of narrow band in voxel units
835 const Vec3d& origin) // origin of grid in world units
836{
837 using GridT = build::Grid<BuildT>;
838 using ValueT = typename BuildToValueMap<BuildT>::type;
839 static_assert(is_floating_point<ValueT>::value, "initBBox: expect floating point");
840 using Vec3T = Vec3<ValueT>;
841 if (!(width > 0))
842 throw std::runtime_error("BBox: width must be positive!");
843 if (!(height > 0))
844 throw std::runtime_error("BBox: height must be positive!");
845 if (!(depth > 0))
846 throw std::runtime_error("BBox: depth must be positive!");
847 if (!(thickness > 0))
848 throw std::runtime_error("BBox: thickness must be positive!");
849 if (!(voxelSize > 0.0))
850 throw std::runtime_error("BBox: voxelSize must be positive!");
851
852
853 auto grid = std::make_shared<GridT>(ValueT(halfWidth * voxelSize));
854 grid->setTransform(voxelSize, origin);
855
856 // Define size of bbox with narrow-band in voxel units
857 const Vec3T r(width / (2 * ValueT(voxelSize)),
858 height / (2 * ValueT(voxelSize)),
859 depth / (2 * ValueT(voxelSize)));
860 const ValueT e = thickness / ValueT(voxelSize);
861
862 // Below the Nyquist frequency
863 if (r.min() < ValueT(1.5) || e < ValueT(1.5)) return grid;
864
865 // Define center of bbox in voxel units
866 const Vec3T c(ValueT(center[0] - origin[0]) / ValueT(voxelSize),
867 ValueT(center[1] - origin[1]) / ValueT(voxelSize),
868 ValueT(center[2] - origin[2]) / ValueT(voxelSize));
869
870 // Define utility functions
871 auto Pos = [](ValueT x) { return x > 0 ? x : 0; };
872 auto Neg = [](ValueT x) { return x < 0 ? x : 0; };
873
874 // Define bounds of the voxel coordinates
875 const BBox<Vec3T> b(c - r - Vec3T(e + ValueT(halfWidth)), c + r + Vec3T(e + ValueT(halfWidth)));
876 const CoordBBox bbox(Coord(Floor(b[0][0]), Floor(b[0][1]), Floor(b[0][2])),
877 Coord( Ceil(b[1][0]), Ceil(b[1][1]), Ceil(b[1][2])));
878 const Range<1,int> range(bbox[0][0], bbox[1][0]+1, 32);
879
880 // Compute signed distances to bbox using leapfrogging in k
881 auto kernel = [&](const Range<1,int> &ra) {
882 auto acc = grid->getWriteAccessor();
883 int m = 1;
884 for (Coord p(ra.begin(),bbox[0][1],bbox[0][2]); p[0] < ra.end(); ++p[0]) {
885 const ValueT px = Abs(ValueT(p[0]) - c[0]) - r[0];
886 const ValueT qx = Abs(ValueT(px) + e) - e;
887 const ValueT px2 = Pow2(Pos(px));
888 const ValueT qx2 = Pow2(Pos(qx));
889 for (p[1] = bbox[0][1]; p[1] <= bbox[1][1]; ++p[1]) {
890 const ValueT py = Abs(ValueT(p[1]) - c[1]) - r[1];
891 const ValueT qy = Abs(ValueT(py) + e) - e;
892 const ValueT qy2 = Pow2(Pos(qy));
893 const ValueT px2qy2 = px2 + qy2;
894 const ValueT qx2py2 = qx2 + Pow2(Pos(py));
895 const ValueT qx2qy2 = qx2 + qy2;
896 const ValueT a[3] = {Max(px, qy), Max(qx, py), Max(qx, qy)};
897 for (p[2] = bbox[0][2]; p[2] <= bbox[1][2]; p[2] += m) {
898 m = 1;
899 const ValueT pz = Abs(ValueT(p[2]) - c[2]) - r[2];
900 const ValueT qz = Abs(ValueT(pz) + e) - e;
901 const ValueT qz2 = Pow2(Pos(qz));
902 const ValueT s1 = Sqrt(px2qy2 + qz2) + Neg(Max(a[0], qz));
903 const ValueT s2 = Sqrt(qx2py2 + qz2) + Neg(Max(a[1], qz));
904 const ValueT s3 = Sqrt(qx2qy2 + Pow2(Pos(pz))) + Neg(Max(a[2], pz));
905 const ValueT v = Min(s1, Min(s2, s3)); // Distance in voxel units
906 const ValueT d = Abs(v);
907 if (d < halfWidth) { // inside narrow band
908 acc.setValue(p, ValueT(voxelSize) * v); // distance in world units
909 } else { // outside narrow band
910 m += Floor(d - halfWidth); // leapfrog
911 }
912 } //end leapfrog over k
913 } //end loop over j
914 } //end loop over i
915 }; //kernel
916#ifdef NANOVDB_PARALLEL_PRIMITIVES
917 forEach(range, kernel);
918#else
919 kernel(range);
920#endif
921
922 return grid;
923} // initBBox
924
925template<typename BuildT>
926std::shared_ptr<build::Grid<BuildT>>
927initOctahedron(double scale, // scale of the octahedron in world units
928 const Vec3d& center, // center of octahedron in world units
929 double voxelSize, // size of a voxel in world units
930 double halfWidth, // half-width of narrow band in voxel units
931 const Vec3d& origin) // origin of grid in world units
932{
933 using GridT = build::Grid<BuildT>;
934 using ValueT = typename BuildToValueMap<BuildT>::type;
935 using Vec3T = Vec3<ValueT>;
936 static_assert(is_floating_point<ValueT>::value, "initOctahedron: expect floating point");
937
938 if (!(scale > 0)) throw std::runtime_error("Octahedron: width must be positive!");
939 if (!(voxelSize > 0)) throw std::runtime_error("Octahedron: voxelSize must be positive!");
940
941 auto grid = std::make_shared<GridT>(ValueT(halfWidth * voxelSize));
942 grid->setTransform(voxelSize, origin);
943
944 // Define size of octahedron with narrow-band in voxel units
945 const ValueT s = scale / (2 * ValueT(voxelSize));
946
947 // Below the Nyquist frequency
948 if ( s < ValueT(1.5) ) return grid;
949
950 // Define center of octahedron in voxel units
951 const Vec3T c(ValueT(center[0] - origin[0]) / ValueT(voxelSize),
952 ValueT(center[1] - origin[1]) / ValueT(voxelSize),
953 ValueT(center[2] - origin[2]) / ValueT(voxelSize));
954
955 // Define utility functions
956 auto sdf = [&s](ValueT x, ValueT y, ValueT z) {
957 const ValueT d = ValueT(0.5)*(z - y + s);
958 if (d < ValueT(0)) {
959 return Vec3T(x, y - s, z).length();
960 } else if (d > s) {
961 return Vec3T(x, y, z - s).length();
962 }
963 return Vec3T(x, y - s + d, z - d).length();
964 };
965
966 // Define bounds of the voxel coordinates
967 const BBox<Vec3T> b(c - Vec3T(s + ValueT(halfWidth)), c + Vec3T(s + ValueT(halfWidth)));
968 const CoordBBox bbox(Coord(Floor(b[0][0]), Floor(b[0][1]), Floor(b[0][2])),
969 Coord( Ceil(b[1][0]), Ceil(b[1][1]), Ceil(b[1][2])));
970 const Range<1,int> range(bbox[0][0], bbox[1][0]+1, 32);
971
972 // Compute signed distances to octahedron using leapfrogging in k
973 auto kernel = [&](const Range<1,int> &ra) {
974 auto acc = grid->getWriteAccessor();
975 int m = 1;
976 static const ValueT a = Sqrt(ValueT(1)/ValueT(3));
977 for (Coord p(ra.begin(),bbox[0][1],bbox[0][2]); p[0] < ra.end(); ++p[0]) {
978 const ValueT px = Abs(ValueT(p[0]) - c[0]);
979 for (p[1] = bbox[0][1]; p[1] <= bbox[1][1]; ++p[1]) {
980 const ValueT py = Abs(ValueT(p[1]) - c[1]);
981 for (p[2] = bbox[0][2]; p[2] <= bbox[1][2]; p[2] += m) {
982 m = 1;
983 const ValueT pz = Abs(ValueT(p[2]) - c[2]);
984 ValueT d = px + py + pz - s;
985 ValueT v;
986 if (ValueT(3)*px < d) {
987 v = sdf(px, py, pz);
988 } else if (ValueT(3)*py < d) {
989 v = sdf(py, pz, px);
990 } else if (ValueT(3)*pz < d) {
991 v = sdf(pz, px, py);
992 } else {
993 v = a * d;
994 }
995 d = Abs(v);
996 if (d < halfWidth) { // inside narrow band
997 acc.setValue(p, ValueT(voxelSize) * v); // distance in world units
998 } else { // outside narrow band
999 m += Floor(d - halfWidth); // leapfrog
1000 }
1001 } //end leapfrog over k
1002 } //end loop over j
1003 } //end loop over i
1004 };// kernel
1005#ifdef NANOVDB_PARALLEL_PRIMITIVES
1006 forEach(range, kernel);
1007#else
1008 kernel(range);
1009#endif
1010 return grid;
1011} // initOctahedron
1012
1013} // unnamed namespace
1014
1015//================================================================================================
1016
1017template<typename BuildT, typename BufferT>
1018typename enable_if<is_same<float, BuildT>::value ||
1019 is_same<double, BuildT>::value, GridHandle<BufferT>>::type
1020createLevelSetSphere(double radius, // radius of sphere in world units
1021 const Vec3d& center, // center of sphere in world units
1022 double voxelSize, // size of a voxel in world units
1023 double halfWidth, // half-width of narrow band in voxel units
1024 const Vec3d& origin, // origin of grid in world units
1025 const std::string& name, // name of grid
1026 StatsMode sMode, // mode of computation for the statistics
1027 ChecksumMode cMode, // mode of computation for the checksum
1028 const BufferT& buffer)
1029{
1030 using GridT = build::Grid<BuildT>;
1031 auto grid = initSphere<BuildT>(radius, center, voxelSize, halfWidth, origin);
1032 grid->mName = name;
1033 build::NodeManager<GridT> mgr(*grid);
1035 CreateNanoGrid<GridT> converter(*grid);
1036 converter.setStats(sMode);
1037 converter.setChecksum(cMode);
1038 auto handle = converter.template getHandle<BuildT, BufferT>(buffer);
1039 assert(handle);
1040 return handle;
1041} // createLevelSetSphere<T>
1042
1043//================================================================================================
1044
1045template<typename BuildT, typename BufferT>
1046typename enable_if<is_same<Fp4, BuildT>::value ||
1048 is_same<Fp16, BuildT>::value, GridHandle<BufferT>>::type
1049createLevelSetSphere(double radius, // radius of sphere in world units
1050 const Vec3d& center, // center of sphere in world units
1051 double voxelSize, // size of a voxel in world units
1052 double halfWidth, // half-width of narrow band in voxel units
1053 const Vec3d& origin, // origin of grid in world units
1054 const std::string& name, // name of grid
1055 StatsMode sMode, // mode of computation for the statistics
1056 ChecksumMode cMode, // mode of computation for the checksum
1057 bool ditherOn,
1058 const BufferT& buffer)
1059{
1060 using GridT = build::Grid<BuildT>;
1061 auto grid = initSphere<BuildT>(radius, center, voxelSize, halfWidth, origin);
1062 grid->mName = name;
1063 build::NodeManager<GridT> mgr(*grid);
1065 CreateNanoGrid<GridT> converter(*grid);
1066 converter.setStats(sMode);
1067 converter.setChecksum(cMode);
1068 converter.enableDithering(ditherOn);
1069 auto handle = converter.template getHandle<BuildT, BufferT>(buffer);
1070 assert(handle);
1071 return handle;
1072} // createLevelSetSphere<Fp4 or Fp8 or Fp16>
1073
1074//================================================================================================
1075
1076template<typename BuildT, typename BufferT>
1077typename enable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
1078createLevelSetSphere(double radius, // radius of sphere in world units
1079 const Vec3d& center, // center of sphere in world units
1080 double voxelSize, // size of a voxel in world units
1081 double halfWidth, // half-width of narrow band in voxel units
1082 const Vec3d& origin, // origin of grid in world units
1083 const std::string& name, // name of grid
1084 StatsMode sMode, // mode of computation for the statistics
1085 ChecksumMode cMode, // mode of computation for the checksum
1086 float tolerance,// only used if VoxelT = FpN
1087 bool ditherOn,
1088 const BufferT& buffer)
1089{
1090 using GridT = build::Grid<BuildT>;
1091 auto grid = initSphere<BuildT>(radius, center, voxelSize, halfWidth, origin);
1092 grid->mName = name;
1093 build::NodeManager<GridT> mgr(*grid);
1095 CreateNanoGrid<GridT> converter(*grid);
1096 converter.setStats(sMode);
1097 converter.setChecksum(cMode);
1098 converter.enableDithering(ditherOn);
1099 AbsDiff oracle(tolerance);
1100 auto handle = converter.template getHandle<BuildT, AbsDiff, BufferT>(oracle, buffer);
1101 assert(handle);
1102 return handle;
1103} // createLevelSetSphere<FpN>
1104
1105//================================================================================================
1106
1107template<typename BuildT, typename BufferT>
1108typename disable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
1109createFogVolumeSphere(double radius, // radius of sphere in world units
1110 const Vec3d& center, // center of sphere in world units
1111 double voxelSize, // size of a voxel in world units
1112 double halfWidth, // half-width of narrow band in voxel units
1113 const Vec3d& origin, // origin of grid in world units
1114 const std::string& name, // name of grid
1115 StatsMode sMode, // mode of computation for the statistics
1116 ChecksumMode cMode, // mode of computation for the checksum
1117 const BufferT& buffer)
1118{
1119 using GridT = build::Grid<BuildT>;
1120 auto grid = initSphere<BuildT>(radius, center, voxelSize, halfWidth, origin);
1121 grid->mName = name;
1122 build::NodeManager<GridT> mgr(*grid);
1124 build::levelSetToFog(mgr, false);
1125 CreateNanoGrid<GridT> converter(*grid);
1126 converter.setStats(sMode);
1127 converter.setChecksum(cMode);
1128 auto handle = converter.template getHandle<BuildT, BufferT>(buffer);
1129 assert(handle);
1130 return handle;
1131} // createFogVolumeSphere<T>
1132
1133//================================================================================================
1134
1135template<typename BuildT, typename BufferT>
1136typename enable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
1137createFogVolumeSphere(double radius, // radius of sphere in world units
1138 const Vec3d& center, // center of sphere in world units
1139 double voxelSize, // size of a voxel in world units
1140 double halfWidth, // half-width of narrow band in voxel units
1141 const Vec3d& origin, // origin of grid in world units
1142 const std::string& name, // name of grid
1143 StatsMode sMode, // mode of computation for the statistics
1144 ChecksumMode cMode, // mode of computation for the checksum
1145 float tolerance,// only used if VoxelT = FpN
1146 bool ditherOn,
1147 const BufferT& buffer)
1148{
1149 using GridT = build::Grid<BuildT>;
1150 auto grid = initSphere<BuildT>(radius, center, voxelSize, halfWidth, origin);
1151 grid->mName = name;
1152 build::NodeManager<GridT> mgr(*grid);
1154 build::levelSetToFog(mgr, false);
1155 CreateNanoGrid<GridT> converter(*grid);
1156 converter.setStats(sMode);
1157 converter.setChecksum(cMode);
1158 converter.enableDithering(ditherOn);
1159 AbsDiff oracle(tolerance);
1160 auto handle = converter.template getHandle<BuildT, AbsDiff, BufferT>(oracle, buffer);
1161 assert(handle);
1162 return handle;
1163} // createFogVolumeSphere<FpN>
1164
1165//================================================================================================
1166
1167template<typename BuildT, typename BufferT>
1168typename disable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
1169createPointSphere(int pointsPerVoxel, // number of points to be scattered in each active voxel
1170 double radius, // radius of sphere in world units
1171 const Vec3d& center, // center of sphere in world units
1172 double voxelSize, // size of a voxel in world units
1173 const Vec3d& origin, // origin of grid in world units
1174 const std::string& name, // name of grid
1175 ChecksumMode cMode, // mode of computation for the checksum
1176 const BufferT& buffer)
1177{
1178 auto sphereHandle = createLevelSetSphere(radius, center, voxelSize, 0.5, origin, "dummy",
1180 assert(sphereHandle);
1181 auto* sphereGrid = sphereHandle.template grid<BuildT>();
1182 assert(sphereGrid);
1183 auto pointHandle = createPointScatter(*sphereGrid, pointsPerVoxel, name, cMode, buffer);
1184 assert(pointHandle);
1185 return pointHandle;
1186} // createPointSphere
1187
1188//================================================================================================
1189
1190template<typename BuildT, typename BufferT>
1191typename disable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
1192createLevelSetTorus(double majorRadius, // major radius of torus in world units
1193 double minorRadius, // minor radius of torus in world units
1194 const Vec3d& center, // center of torus in world units
1195 double voxelSize, // size of a voxel in world units
1196 double halfWidth, // half-width of narrow band in voxel units
1197 const Vec3d& origin, // origin of grid in world units
1198 const std::string& name, // name of grid
1199 StatsMode sMode, // mode of computation for the statistics
1200 ChecksumMode cMode, // mode of computation for the checksum
1201 const BufferT& buffer)
1202{
1203 using GridT = build::Grid<BuildT>;
1204 auto grid = initTorus<BuildT>(majorRadius, minorRadius, center, voxelSize, halfWidth, origin);
1205 grid->mName = name;
1206 build::NodeManager<GridT> mgr(*grid);
1208 CreateNanoGrid<GridT> converter(*grid);
1209 converter.setStats(sMode);
1210 converter.setChecksum(cMode);
1211 auto handle = converter.template getHandle<BuildT, BufferT>(buffer);
1212 assert(handle);
1213 return handle;
1214} // createLevelSetTorus<T>
1215
1216//================================================================================================
1217
1218template<typename BuildT, typename BufferT>
1219typename enable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
1220createLevelSetTorus(double majorRadius, // major radius of torus in world units
1221 double minorRadius, // minor radius of torus in world units
1222 const Vec3d& center, // center of torus in world units
1223 double voxelSize, // size of a voxel in world units
1224 double halfWidth, // half-width of narrow band in voxel units
1225 const Vec3d& origin, // origin of grid in world units
1226 const std::string& name, // name of grid
1227 StatsMode sMode, // mode of computation for the statistics
1228 ChecksumMode cMode, // mode of computation for the checksum
1229 float tolerance,
1230 bool ditherOn,
1231 const BufferT& buffer)
1232{
1233 using GridT = build::Grid<BuildT>;
1234 auto grid = initTorus<BuildT>(majorRadius, minorRadius, center, voxelSize, halfWidth, origin);
1235 grid->mName = name;
1236 build::NodeManager<GridT> mgr(*grid);
1238 CreateNanoGrid<GridT> converter(*grid);
1239 converter.setStats(sMode);
1240 converter.setChecksum(cMode);
1241 converter.enableDithering(ditherOn);
1242 AbsDiff oracle(tolerance);
1243 auto handle = converter.template getHandle<BuildT, AbsDiff, BufferT>(oracle, buffer);
1244 assert(handle);
1245 return handle;
1246} // createLevelSetTorus<FpN>
1247
1248//================================================================================================
1249
1250template<typename BuildT, typename BufferT>
1251typename disable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
1252createFogVolumeTorus(double majorRadius, // major radius of torus in world units
1253 double minorRadius, // minor radius of torus in world units
1254 const Vec3d& center, // center of torus in world units
1255 double voxelSize, // size of a voxel in world units
1256 double halfWidth, // half-width of narrow band in voxel units
1257 const Vec3d& origin, // origin of grid in world units
1258 const std::string& name, // name of grid
1259 StatsMode sMode, // mode of computation for the statistics
1260 ChecksumMode cMode, // mode of computation for the checksum
1261 const BufferT& buffer)
1262{
1263 using GridT = build::Grid<BuildT>;
1264 auto grid = initTorus<BuildT>(majorRadius, minorRadius, center, voxelSize, halfWidth, origin);
1265 grid->mName = name;
1266 build::NodeManager<GridT> mgr(*grid);
1268 build::levelSetToFog(mgr, false);
1269 CreateNanoGrid<GridT> converter(*grid);
1270 converter.setStats(sMode);
1271 converter.setChecksum(cMode);
1272 auto handle = converter.template getHandle<BuildT, BufferT>(buffer);
1273 assert(handle);
1274 return handle;
1275} // createFogVolumeTorus<T>
1276
1277//================================================================================================
1278
1279template<typename BuildT, typename BufferT>
1280typename enable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
1281createFogVolumeTorus(double majorRadius, // major radius of torus in world units
1282 double minorRadius, // minor radius of torus in world units
1283 const Vec3d& center, // center of torus in world units
1284 double voxelSize, // size of a voxel in world units
1285 double halfWidth, // half-width of narrow band in voxel units
1286 const Vec3d& origin, // origin of grid in world units
1287 const std::string& name, // name of grid
1288 StatsMode sMode, // mode of computation for the statistics
1289 ChecksumMode cMode, // mode of computation for the checksum
1290 float tolerance,
1291 bool ditherOn,
1292 const BufferT& buffer)
1293{
1294 using GridT = build::Grid<BuildT>;
1295 auto grid = initTorus<BuildT>(majorRadius, minorRadius, center, voxelSize, halfWidth, origin);
1296 grid->mName = name;
1297 build::NodeManager<GridT> mgr(*grid);
1299 build::levelSetToFog(mgr, false);
1300 CreateNanoGrid<GridT> converter(*grid);
1301 converter.setStats(sMode);
1302 converter.setChecksum(cMode);
1303 converter.enableDithering(ditherOn);
1304 AbsDiff oracle(tolerance);
1305 auto handle = converter.template getHandle<BuildT, AbsDiff, BufferT>(oracle, buffer);
1306 assert(handle);
1307 return handle;
1308} // createFogVolumeTorus<FpN>
1309
1310//================================================================================================
1311
1312template<typename BuildT, typename BufferT>
1313typename disable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
1314createPointTorus(int pointsPerVoxel, // number of points to be scattered in each active voxel
1315 double majorRadius, // major radius of torus in world units
1316 double minorRadius, // minor radius of torus in world units
1317 const Vec3d& center, // center of torus in world units
1318 double voxelSize, // size of a voxel in world units
1319 const Vec3d& origin, // origin of grid in world units
1320 const std::string& name, // name of grid
1321 ChecksumMode cMode, // mode of computation for the checksum
1322 const BufferT& buffer)
1323{
1324 auto torusHandle = createLevelSetTorus(majorRadius, minorRadius, center, voxelSize, 0.5f, origin,
1325 "dummy", StatsMode::BBox, ChecksumMode::Disable, buffer);
1326 assert(torusHandle);
1327 auto* torusGrid = torusHandle.template grid<BuildT>();
1328 assert(torusGrid);
1329 auto pointHandle = createPointScatter(*torusGrid, pointsPerVoxel, name, cMode, buffer);
1330 assert(pointHandle);
1331 return pointHandle;
1332} // createPointTorus<T>
1333
1334//================================================================================================
1335
1336template<typename BuildT, typename BufferT>
1337typename disable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
1338createLevelSetBox(double width, // width of box in world units
1339 double height, // height of box in world units
1340 double depth, // depth of box in world units
1341 const Vec3d& center, // center of box in world units
1342 double voxelSize, // size of a voxel in world units
1343 double halfWidth, // half-width of narrow band in voxel units
1344 const Vec3d& origin, // origin of grid in world units
1345 const std::string& name, // name of grid
1346 StatsMode sMode, // mode of computation for the statistics
1347 ChecksumMode cMode, // mode of computation for the checksum
1348 const BufferT& buffer)
1349{
1350 using GridT = build::Grid<BuildT>;
1351 auto grid = initBox<BuildT>(width, height, depth, center, voxelSize, halfWidth, origin);
1352 grid->mName = name;
1353 build::NodeManager<GridT> mgr(*grid);
1355 CreateNanoGrid<GridT> converter(*grid);
1356 converter.setStats(sMode);
1357 converter.setChecksum(cMode);
1358 auto handle = converter.template getHandle<BuildT, BufferT>(buffer);
1359 assert(handle);
1360 return handle;
1361} // createLevelSetBox<T>
1362
1363//================================================================================================
1364
1365template<typename BuildT, typename BufferT>
1366typename enable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
1367createLevelSetBox(double width, // width of box in world units
1368 double height, // height of box in world units
1369 double depth, // depth of box in world units
1370 const Vec3d& center, // center of box in world units
1371 double voxelSize, // size of a voxel in world units
1372 double halfWidth, // half-width of narrow band in voxel units
1373 const Vec3d& origin, // origin of grid in world units
1374 const std::string& name, // name of grid
1375 StatsMode sMode, // mode of computation for the statistics
1376 ChecksumMode cMode, // mode of computation for the checksum
1377 float tolerance,
1378 bool ditherOn,
1379 const BufferT& buffer)
1380{
1381 using GridT = build::Grid<BuildT>;
1382 auto grid = initBox<BuildT>(width, height, depth, center, voxelSize, halfWidth, origin);
1383 grid->mName = name;
1384 build::NodeManager<GridT> mgr(*grid);
1386 CreateNanoGrid<GridT> converter(*grid);
1387 converter.setStats(sMode);
1388 converter.setChecksum(cMode);
1389 converter.enableDithering(ditherOn);
1390 AbsDiff oracle(tolerance);
1391 auto handle = converter.template getHandle<BuildT, AbsDiff, BufferT>(oracle, buffer);
1392 assert(handle);
1393 return handle;
1394} // createLevelSetBox<FpN>
1395
1396//================================================================================================
1397
1398template<typename BuildT, typename BufferT>
1399typename disable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
1400createLevelSetOctahedron(double scale, // scale of the octahedron in world units
1401 const Vec3d& center, // center of box in world units
1402 double voxelSize, // size of a voxel in world units
1403 double halfWidth, // half-width of narrow band in voxel units
1404 const Vec3d& origin, // origin of grid in world units
1405 const std::string& name, // name of grid
1406 StatsMode sMode, // mode of computation for the statistics
1407 ChecksumMode cMode, // mode of computation for the checksum
1408 const BufferT& buffer)
1409{
1410 using GridT = build::Grid<BuildT>;
1411 auto grid = initOctahedron<BuildT>(scale, center, voxelSize, halfWidth, origin);
1412 grid->mName = name;
1413 build::NodeManager<GridT> mgr(*grid);
1415 CreateNanoGrid<GridT> converter(*grid);
1416 converter.setStats(sMode);
1417 converter.setChecksum(cMode);
1418 auto handle = converter.template getHandle<BuildT, BufferT>(buffer);
1419 assert(handle);
1420 return handle;
1421} // createLevelSetOctahedron<T>
1422
1423//================================================================================================
1424
1425template<typename BuildT, typename BufferT>
1426typename enable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
1427createLevelSetOctahedron(double scale, // scale of the octahedron in world units
1428 const Vec3d& center, // center of box in world units
1429 double voxelSize, // size of a voxel in world units
1430 double halfWidth, // half-width of narrow band in voxel units
1431 const Vec3d& origin, // origin of grid in world units
1432 const std::string& name, // name of grid
1433 StatsMode sMode, // mode of computation for the statistics
1434 ChecksumMode cMode, // mode of computation for the checksum
1435 float tolerance,
1436 bool ditherOn,
1437 const BufferT& buffer)
1438{
1439 using GridT = build::Grid<BuildT>;
1440 auto grid = initOctahedron<BuildT>(scale, center, voxelSize, halfWidth, origin);
1441 grid->mName = name;
1442 build::NodeManager<GridT> mgr(*grid);
1444 CreateNanoGrid<GridT> converter(*grid);
1445 converter.setStats(sMode);
1446 converter.setChecksum(cMode);
1447 converter.enableDithering(ditherOn);
1448 AbsDiff oracle(tolerance);
1449 auto handle = converter.template getHandle<BuildT, AbsDiff, BufferT>(oracle, buffer);
1450 assert(handle);
1451 return handle;
1452} // createLevelSetOctahedron<FpN>
1453
1454//================================================================================================
1455
1456template<typename BuildT, typename BufferT>
1457typename disable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
1458createLevelSetBBox(double width, // width of bbox in world units
1459 double height, // height of bbox in world units
1460 double depth, // depth of bbox in world units
1461 double thickness, // thickness of the wire in world units
1462 const Vec3d& center, // center of bbox in world units
1463 double voxelSize, // size of a voxel in world units
1464 double halfWidth, // half-width of narrow band in voxel units
1465 const Vec3d& origin, // origin of grid in world units
1466 const std::string& name, // name of grid
1467 StatsMode sMode, // mode of computation for the statistics
1468 ChecksumMode cMode, // mode of computation for the checksum
1469 const BufferT& buffer)
1470{
1471 using GridT = build::Grid<BuildT>;
1472 auto grid = initBBox<BuildT>(width, height, depth, thickness, center, voxelSize, halfWidth, origin);
1473 grid->mName = name;
1474 build::NodeManager<GridT> mgr(*grid);
1476 CreateNanoGrid<GridT> converter(*grid);
1477 converter.setStats(sMode);
1478 converter.setChecksum(cMode);
1479 auto handle = converter.template getHandle<BuildT, BufferT>(buffer);
1480 assert(handle);
1481 return handle;
1482} // createLevelSetBBox<T>
1483
1484//================================================================================================
1485
1486template<typename BuildT, typename BufferT>
1487typename enable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
1488createLevelSetBBox(double width, // width of bbox in world units
1489 double height, // height of bbox in world units
1490 double depth, // depth of bbox in world units
1491 double thickness, // thickness of the wire in world units
1492 const Vec3d& center, // center of bbox in world units
1493 double voxelSize, // size of a voxel in world units
1494 double halfWidth, // half-width of narrow band in voxel units
1495 const Vec3d& origin, // origin of grid in world units
1496 const std::string& name, // name of grid
1497 StatsMode sMode, // mode of computation for the statistics
1498 ChecksumMode cMode, // mode of computation for the checksum
1499 float tolerance,
1500 bool ditherOn,
1501 const BufferT& buffer)
1502{
1503 using GridT = build::Grid<BuildT>;
1504 auto grid = initBBox<BuildT>(width, height, depth, thickness, center, voxelSize, halfWidth, origin);
1505 grid->mName = name;
1506 build::NodeManager<GridT> mgr(*grid);
1508 CreateNanoGrid<GridT> converter(*grid);
1509 converter.setStats(sMode);
1510 converter.setChecksum(cMode);
1511 converter.enableDithering(ditherOn);
1512 AbsDiff oracle(tolerance);
1513 auto handle = converter.template getHandle<BuildT, AbsDiff, BufferT>(oracle, buffer);
1514 assert(handle);
1515 return handle;
1516} // createLevelSetBBox<FpN>
1517
1518//================================================================================================
1519
1520template<typename BuildT, typename BufferT>
1521typename disable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
1522createFogVolumeBox(double width, // width of box in world units
1523 double height, // height of box in world units
1524 double depth, // depth of box in world units
1525 const Vec3d& center, // center of box in world units
1526 double voxelSize, // size of a voxel in world units
1527 double halfWidth, // half-width of narrow band in voxel units
1528 const Vec3d& origin, // origin of grid in world units
1529 const std::string& name, // name of grid
1530 StatsMode sMode, // mode of computation for the statistics
1531 ChecksumMode cMode, // mode of computation for the checksum
1532 const BufferT& buffer)
1533{
1534 using GridT = build::Grid<BuildT>;
1535 auto grid = initBox<BuildT>(width, height, depth, center, voxelSize, halfWidth, origin);
1536 grid->mName = name;
1537 build::NodeManager<GridT> mgr(*grid);
1539 build::levelSetToFog(mgr, false);
1540 CreateNanoGrid<GridT> converter(*grid);
1541 converter.setStats(sMode);
1542 converter.setChecksum(cMode);
1543 auto handle = converter.template getHandle<BuildT, BufferT>(buffer);
1544 assert(handle);
1545 return handle;
1546} // createFogVolumeBox<T>
1547
1548//================================================================================================
1549
1550template<typename BuildT, typename BufferT>
1551typename enable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
1552createFogVolumeBox(double width, // width of box in world units
1553 double height, // height of box in world units
1554 double depth, // depth of box in world units
1555 const Vec3d& center, // center of box in world units
1556 double voxelSize, // size of a voxel in world units
1557 double halfWidth, // half-width of narrow band in voxel units
1558 const Vec3d& origin, // origin of grid in world units
1559 const std::string& name, // name of grid
1560 StatsMode sMode, // mode of computation for the statistics
1561 ChecksumMode cMode, // mode of computation for the checksum
1562 float tolerance,
1563 bool ditherOn,
1564 const BufferT& buffer)
1565{
1566 using GridT = build::Grid<BuildT>;
1567 auto grid = initBox<BuildT>(width, height, depth, center, voxelSize, halfWidth, origin);
1568 grid->mName = name;
1569 build::NodeManager<GridT> mgr(*grid);
1571 build::levelSetToFog(mgr, false);
1572 CreateNanoGrid<GridT> converter(*grid);
1573 converter.setStats(sMode);
1574 converter.setChecksum(cMode);
1575 converter.enableDithering(ditherOn);
1576 AbsDiff oracle(tolerance);
1577 auto handle = converter.template getHandle<BuildT, AbsDiff, BufferT>(oracle, buffer);
1578 assert(handle);
1579 return handle;
1580} // createFogVolumeBox<FpN>
1581
1582//================================================================================================
1583
1584template<typename BuildT, typename BufferT>
1585typename disable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
1586createFogVolumeOctahedron(double scale, // scale of octahedron in world units
1587 const Vec3d& center, // center of box in world units
1588 double voxelSize, // size of a voxel in world units
1589 double halfWidth, // half-width of narrow band in voxel units
1590 const Vec3d& origin, // origin of grid in world units
1591 const std::string& name, // name of grid
1592 StatsMode sMode, // mode of computation for the statistics
1593 ChecksumMode cMode, // mode of computation for the checksum
1594 const BufferT& buffer)
1595{
1596 using GridT = build::Grid<BuildT>;
1597 auto grid = initOctahedron<BuildT>(scale, center, voxelSize, halfWidth, origin);
1598 grid->mName = name;
1599 build::NodeManager<GridT> mgr(*grid);
1601 build::levelSetToFog(mgr, false);
1602 CreateNanoGrid<GridT> converter(*grid);
1603 converter.setStats(sMode);
1604 converter.setChecksum(cMode);
1605 auto handle = converter.template getHandle<BuildT, BufferT>(buffer);
1606 assert(handle);
1607 return handle;
1608} // createFogVolumeOctahedron<T>
1609
1610//================================================================================================
1611
1612template<typename BuildT, typename BufferT>
1613typename enable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
1614createFogVolumeOctahedron(double scale, // scale of octahedron in world units
1615 const Vec3d& center, // center of box in world units
1616 double voxelSize, // size of a voxel in world units
1617 double halfWidth, // half-width of narrow band in voxel units
1618 const Vec3d& origin, // origin of grid in world units
1619 const std::string& name, // name of grid
1620 StatsMode sMode, // mode of computation for the statistics
1621 ChecksumMode cMode, // mode of computation for the checksum
1622 float tolerance,
1623 bool ditherOn,
1624 const BufferT& buffer)
1625{
1626 using GridT = build::Grid<BuildT>;
1627 auto grid = initOctahedron<BuildT>(scale, center, voxelSize, halfWidth, origin);
1628 grid->mName = name;
1629 build::NodeManager<GridT> mgr(*grid);
1631 build::levelSetToFog(mgr, false);
1632 CreateNanoGrid<GridT> converter(*grid);
1633 converter.setStats(sMode);
1634 converter.setChecksum(cMode);
1635 converter.enableDithering(ditherOn);
1636 AbsDiff oracle(tolerance);
1637 auto handle = converter.template getHandle<BuildT, AbsDiff, BufferT>(oracle, buffer);
1638 assert(handle);
1639 return handle;
1640} // createFogVolumeOctahedron<FpN>
1641
1642//================================================================================================
1643
1644template<typename BuildT, typename BufferT>
1645typename disable_if<is_same<FpN, BuildT>::value, GridHandle<BufferT>>::type
1646createPointBox(int pointsPerVoxel, // number of points to be scattered in each active voxel
1647 double width, // width of box in world units
1648 double height, // height of box in world units
1649 double depth, // depth of box in world units
1650 const Vec3d& center, // center of box in world units
1651 double voxelSize, // size of a voxel in world units
1652 const Vec3d& origin, // origin of grid in world units
1653 const std::string& name, // name of grid
1654 ChecksumMode cMode, // mode of computation for the checksum
1655 const BufferT& buffer)
1656{
1657 auto boxHandle = createLevelSetBox(width, height, depth, center, voxelSize, 0.5, origin, "dummy",
1659 assert(boxHandle);
1660 auto* boxGrid = boxHandle.template grid<BuildT>();
1661 assert(boxGrid);
1662 auto pointHandle = createPointScatter(*boxGrid, pointsPerVoxel, name, cMode, buffer);
1663 assert(pointHandle);
1664 return pointHandle;
1665} // createPointBox<T>
1666
1667//================================================================================================
1668
1669template<typename SrcBuildT, typename BufferT>
1670inline GridHandle<BufferT>
1671createPointScatter(const NanoGrid<SrcBuildT>& srcGrid, // origin of grid in world units
1672 int pointsPerVoxel, // number of points to be scattered in each active voxel
1673 const std::string& name, // name of grid
1674 ChecksumMode cMode, // mode of computation for the checksum
1675 const BufferT& buffer)
1676{
1677 using ValueT = typename BuildToValueMap<SrcBuildT>::type;
1678 static_assert(is_floating_point<ValueT>::value, "createPointScatter: expect floating point");
1679 using Vec3T = Vec3<ValueT>;
1680 if (pointsPerVoxel < 1) {
1681 throw std::runtime_error("createPointScatter: Expected at least one point per voxel");
1682 }
1683 if (!srcGrid.isLevelSet()) {
1684 throw std::runtime_error("createPointScatter: Expected a level set grid");
1685 }
1686 if (!srcGrid.hasBBox()) {
1687 throw std::runtime_error("createPointScatter: ActiveVoxelCount is required");
1688 }
1689 const uint64_t pointCount = pointsPerVoxel * srcGrid.activeVoxelCount();
1690 if (pointCount == 0) {
1691 throw std::runtime_error("createPointScatter: No particles to scatter");
1692 }
1693 std::vector<Vec3T> xyz;
1694 xyz.reserve(pointCount);
1695 using DstGridT = build::Grid<uint32_t>;
1696 DstGridT dstGrid(std::numeric_limits<uint32_t>::max(), name, GridClass::PointData);
1697 dstGrid.mMap = srcGrid.map();
1698 auto dstAcc = dstGrid.getAccessor();
1699 std::srand(1234);
1700 const ValueT s = 1 / (1 + ValueT(RAND_MAX)); // scale so s*rand() is in ] 0, 1 [
1701 // return a point with random local voxel coordinates (-0.5 to +0.5)
1702 auto randomPoint = [&s](){return s * Vec3T(rand(), rand(), rand()) - Vec3T(0.5);};
1703 const auto& srcTree = srcGrid.tree();
1704 auto srcMgrHandle = createNodeManager(srcGrid);
1705 auto *srcMgr = srcMgrHandle.template mgr<SrcBuildT>();
1706 assert(srcMgr);
1707 for (uint32_t i = 0, end = srcTree.nodeCount(0); i < end; ++i) {
1708 auto& srcLeaf = srcMgr->leaf(i);
1709 auto* dstLeaf = dstAcc.setValue(srcLeaf.origin(), pointsPerVoxel); // allocates leaf node
1710 dstLeaf->mValueMask = srcLeaf.valueMask();
1711 for (uint32_t j = 0, m = 0; j < 512; ++j) {
1712 if (dstLeaf->mValueMask.isOn(j)) {
1713 const Vec3f ijk = dstLeaf->offsetToGlobalCoord(j).asVec3s();// floating-point representatrion of index coorindates
1714 for (int n = 0; n < pointsPerVoxel; ++n) xyz.push_back(srcGrid.indexToWorld(randomPoint() + ijk));
1715 m += pointsPerVoxel;
1716 }// active voxels
1717 dstLeaf->mValues[j] = m;
1718 }// loop over all voxels
1719 }// loop over leaf nodes
1720 assert(pointCount == xyz.size());
1721 CreateNanoGrid<DstGridT> converter(dstGrid);
1722 converter.setStats(StatsMode::MinMax);
1724
1725 converter.addBlindData(name,
1728 mapToGridType<Vec3T>(),
1729 pointCount,
1730 sizeof(Vec3T));
1731 auto handle = converter.template getHandle<uint32_t>(buffer);
1732 assert(handle);
1733
1734 auto* grid = handle.template grid<uint32_t>();
1735 assert(grid && grid->template isSequential<0>());
1736 auto &tree = grid->tree();
1737 if (tree.nodeCount(0) == 0) throw std::runtime_error("Expect leaf nodes!");
1738 auto *leafData = tree.getFirstLeaf()->data();
1739 leafData[0].mMinimum = 0; // start of prefix sum
1740 for (uint32_t i = 1, n = tree.nodeCount(0); i < n; ++i) {
1741 leafData[i].mMinimum = leafData[i - 1].mMinimum + leafData[i - 1].mMaximum;
1742 }
1743 if (Vec3T *blindData = grid->template getBlindData<Vec3T>(0)) {
1744 memcpy(blindData, xyz.data(), xyz.size() * sizeof(Vec3T));
1745 } else {
1746 throw std::runtime_error("Blind data pointer was NULL");
1747 }
1748 updateChecksum(*grid, cMode);
1749 return handle;
1750} // createPointScatter
1751
1752} // namespace nanovdb
1753
1754#endif // NANOVDB_PRIMITIVES_H_HAS_BEEN_INCLUDED
A unified wrapper for tbb::parallel_for and a naive std::thread fallback.
Implements a light-weight self-contained VDB data-structure in a single file! In other words,...
Compression oracle based on absolute difference.
Definition CreateNanoGrid.h:231
Creates any nanovdb Grid from any source grid (certain combinations are obviously not allowed)
Definition CreateNanoGrid.h:524
uint64_t addBlindData(const std::string &name, GridBlindDataSemantic dataSemantic, GridBlindDataClass dataClass, GridType dataType, size_t count, size_t size)
Add blind data to the destination grid.
Definition CreateNanoGrid.h:607
void setStats(StatsMode mode=StatsMode::Default)
Set the mode used for computing statistics of the destination grid.
Definition CreateNanoGrid.h:554
void setChecksum(ChecksumMode mode=ChecksumMode::Default)
Set the mode used for computing checksums of the destination grid.
Definition CreateNanoGrid.h:558
void enableDithering(bool on=true)
Enable or disable dithering, i.e. randomization of the quantization error.
Definition CreateNanoGrid.h:550
Highest level of the data structure. Contains a tree and a world->index transform (that currently onl...
Definition NanoVDB.h:3699
Vec3T indexToWorld(const Vec3T &xyz) const
index to world space transformation
Definition NanoVDB.h:3773
uint64_t activeVoxelCount() const
Computes a AABB of active values in world space.
Definition NanoVDB.h:3823
const TreeT & tree() const
Return a const reference to the tree.
Definition NanoVDB.h:3753
const Map & map() const
Return a const reference to the Map for this grid.
Definition NanoVDB.h:3765
bool hasBBox() const
Definition NanoVDB.h:3838
bool isLevelSet() const
Definition NanoVDB.h:3829
Definition GridBuilder.h:2055
enable_if< is_floating_point< typenameNodeManagerT::ValueType >::value >::type sdfToLevelSet(NodeManagerT &mgr)
Definition GridBuilder.h:2149
void levelSetToFog(NodeManagerT &mgr, bool rebuild=true)
Definition GridBuilder.h:2167
Convert a base-pointer to an openvdb grid, denoted srcGrid, to a nanovdb grid of the same type,...
Definition NanoVDB.h:247
disable_if< is_same< FpN, BuildT >::value, GridHandle< BufferT > >::type createPointBox(int pointsPerVoxel=1, double width=40.0, double height=60.0, double depth=100.0, const Vec3d &center=Vec3d(0.0), double voxelSize=1.0, const Vec3d &origin=Vec3d(0.0), const std::string &name="box_points", ChecksumMode mode=ChecksumMode::Default, const BufferT &buffer=BufferT())
Returns a handle to a PointDataGrid containing points scattered on the surface of a box.
Definition Primitives.h:1646
disable_if< is_same< FpN, BuildT >::value, GridHandle< BufferT > >::type createFogVolumeSphere(double radius=100.0, const Vec3d &center=Vec3d(0.0), double voxelSize=1.0, double halfWidth=3.0, const Vec3d &origin=Vec3d(0.0), const std::string &name="sphere_fog", StatsMode sMode=StatsMode::Default, ChecksumMode cMode=ChecksumMode::Default, const BufferT &buffer=BufferT())
Returns a handle to a sparse fog volume of a sphere such that the exterior is 0 and inactive,...
Definition Primitives.h:1109
GridHandle< BufferT > createPointScatter(const NanoGrid< SrcBuildT > &srcGrid, int pointsPerVoxel=1, const std::string &name="point_scatter", ChecksumMode mode=ChecksumMode::Default, const BufferT &buffer=BufferT())
Given an input NanoVDB voxel grid this methods returns a GridHandle to another NanoVDB PointDataGrid ...
Definition Primitives.h:1671
disable_if< is_same< FpN, BuildT >::value, GridHandle< BufferT > >::type createLevelSetOctahedron(double scale=100.0, const Vec3d &center=Vec3d(0.0), double voxelSize=1.0, double halfWidth=3.0, const Vec3d &origin=Vec3d(0.0), const std::string &name="octadedron_ls", StatsMode sMode=StatsMode::Default, ChecksumMode cMode=ChecksumMode::Default, const BufferT &buffer=BufferT())
Returns a handle to a narrow-band level set of a octahedron.
Definition Primitives.h:1400
T Abs(T x)
Definition NanoVDB.h:1185
Type Min(Type a, Type b)
Definition NanoVDB.h:1089
float Sqrt(float x)
Return the square root of a floating-point value.
Definition NanoVDB.h:1233
disable_if< is_same< FpN, BuildT >::value, GridHandle< BufferT > >::type createFogVolumeTorus(double majorRadius=100.0, double minorRadius=50.0, const Vec3d &center=Vec3d(0.0), double voxelSize=1.0, double halfWidth=3.0, const Vec3d &origin=Vec3d(0.0), const std::string &name="torus_fog", StatsMode sMode=StatsMode::Default, ChecksumMode cMode=ChecksumMode::Default, const BufferT &buffer=BufferT())
Returns a handle to a sparse fog volume of a torus in the xz-plane such that the exterior is 0 and in...
Definition Primitives.h:1252
disable_if< is_same< FpN, BuildT >::value, GridHandle< BufferT > >::type createLevelSetBBox(double width=40.0, double height=60.0, double depth=100.0, double thickness=10.0, const Vec3d &center=Vec3d(0.0), double voxelSize=1.0, double halfWidth=3.0, const Vec3d &origin=Vec3d(0.0), const std::string &name="bbox_ls", StatsMode sMode=StatsMode::Default, ChecksumMode cMode=ChecksumMode::Default, const BufferT &buffer=BufferT())
Returns a handle to a narrow-band level set of a bounding-box (= wireframe of a box)
Definition Primitives.h:1458
int32_t Ceil(float x)
Definition NanoVDB.h:1158
int32_t Floor(float x)
Definition NanoVDB.h:1149
disable_if< is_same< FpN, BuildT >::value, GridHandle< BufferT > >::type createLevelSetBox(double width=40.0, double height=60.0, double depth=100.0, const Vec3d &center=Vec3d(0.0), double voxelSize=1.0, double halfWidth=3.0, const Vec3d &origin=Vec3d(0.0), const std::string &name="box_ls", StatsMode sMode=StatsMode::Default, ChecksumMode cMode=ChecksumMode::Default, const BufferT &buffer=BufferT())
Returns a handle to a narrow-band level set of a box.
Definition Primitives.h:1338
BBox< Coord > CoordBBox
Definition NanoVDB.h:2535
StatsMode
Grid flags which indicate what extra information is present in the grid buffer.
Definition GridStats.h:38
Vec3< double > Vec3d
Definition NanoVDB.h:1704
disable_if< is_same< FpN, BuildT >::value, GridHandle< BufferT > >::type createPointTorus(int pointsPerVoxel=1, double majorRadius=100.0, double minorRadius=50.0, const Vec3d &center=Vec3d(0.0), double voxelSize=1.0, const Vec3d &origin=Vec3d(0.0f), const std::string &name="torus_points", ChecksumMode cMode=ChecksumMode::Default, const BufferT &buffer=BufferT())
Returns a handle to a PointDataGrid containing points scattered on the surface of a torus.
Definition Primitives.h:1314
ChecksumMode
List of different modes for computing for a checksum.
Definition GridChecksum.h:38
disable_if< is_same< FpN, BuildT >::value, GridHandle< BufferT > >::type createLevelSetTorus(double majorRadius=100.0, double minorRadius=50.0, const Vec3d &center=Vec3d(0.0), double voxelSize=1.0, double halfWidth=3.0, const Vec3d &origin=Vec3d(0.0), const std::string &name="torus_ls", StatsMode sMode=StatsMode::Default, ChecksumMode cMode=ChecksumMode::Default, const BufferT &buffer=BufferT())
Returns a handle to a narrow-band level set of a torus in the xz-plane.
Definition Primitives.h:1192
T Pow2(T x)
Definition NanoVDB.h:1168
disable_if< is_same< FpN, BuildT >::value, GridHandle< BufferT > >::type createFogVolumeBox(double width=40.0, double height=60.0, double depth=100.0, const Vec3d &center=Vec3d(0.0), double voxelSize=1.0, double halfWidth=3.0, const Vec3d &origin=Vec3d(0.0), const std::string &name="box_fog", StatsMode sMode=StatsMode::Default, ChecksumMode cMode=ChecksumMode::Default, const BufferT &buffer=BufferT())
Returns a handle to a sparse fog volume of a box such that the exterior is 0 and inactive,...
Definition Primitives.h:1522
Type Max(Type a, Type b)
Definition NanoVDB.h:1110
void updateChecksum(NanoGrid< BuildT > &grid, ChecksumMode mode=ChecksumMode::Default)
Updates the checksum of a grid.
enable_if< is_same< float, BuildT >::value||is_same< double, BuildT >::value, GridHandle< BufferT > >::type createLevelSetSphere(double radius=100.0, const Vec3d &center=Vec3d(0), double voxelSize=1.0, double halfWidth=3.0, const Vec3d &origin=Vec3d(0), const std::string &name="sphere_ls", StatsMode sMode=StatsMode::Default, ChecksumMode cMode=ChecksumMode::Default, const BufferT &buffer=BufferT())
Returns a handle to a narrow-band level set of a sphere.
Definition Primitives.h:1020
disable_if< is_same< FpN, BuildT >::value, GridHandle< BufferT > >::type createFogVolumeOctahedron(double scale=100.0, const Vec3d &center=Vec3d(0.0), double voxelSize=1.0, double halfWidth=3.0, const Vec3d &origin=Vec3d(0.0), const std::string &name="octadedron_fog", StatsMode sMode=StatsMode::Default, ChecksumMode cMode=ChecksumMode::Default, const BufferT &buffer=BufferT())
Returns a handle to a sparse fog volume of an octahedron such that the exterior is 0 and inactive,...
Definition Primitives.h:1586
void forEach(RangeT range, const FuncT &func)
simple wrapper for tbb::parallel_for with a naive std fallback
Definition ForEach.h:40
NodeManagerHandle< BufferT > createNodeManager(const NanoGrid< BuildT > &grid, const BufferT &buffer=BufferT())
brief Construct a NodeManager and return its handle
Definition NodeManager.h:284
disable_if< is_same< FpN, BuildT >::value, GridHandle< BufferT > >::type createPointSphere(int pointsPerVoxel=1, double radius=100.0, const Vec3d &center=Vec3d(0.0), double voxelSize=1.0, const Vec3d &origin=Vec3d(0.0), const std::string &name="sphere_points", ChecksumMode mode=ChecksumMode::Default, const BufferT &buffer=BufferT())
Returns a handle to a PointDataGrid containing points scattered on the surface of a sphere.
Definition Primitives.h:1169
T type
Definition NanoVDB.h:654
Definition GridBuilder.h:1882
C++11 implementation of std::is_floating_point.
Definition NanoVDB.h:463
static constexpr bool value
Definition NanoVDB.h:464
static constexpr bool value
Definition NanoVDB.h:443