1 #ifndef PROXIMITY_DOMAIN_3_H 
    2 #define PROXIMITY_DOMAIN_3_H 
    4 #include "mesher_cgal.h" 
    6 #include <vtkImageData.h> 
    7 #include <vtkXMLImageDataWriter.h> 
    8 #include <CGAL/AABB_tree.h> 
    9 #include <CGAL/AABB_traits.h> 
   10 #include <CGAL/AABB_face_graph_triangle_primitive.h> 
   12 typedef K::Iso_cuboid_3 Iso_cuboid;
 
   14 typedef CGAL::AABB_face_graph_triangle_primitive<Polyhedron> Primitive;
 
   15 typedef CGAL::AABB_traits<K, Primitive> Traits;
 
   16 typedef CGAL::AABB_tree<Traits> Tree;
 
   19     template <
typename Gt, 
typename Index_>
 
   23       typedef typename Gt::FT         FT;
 
   24       typedef typename Gt::Point_3    Point_3;
 
   29       int minx, miny, minz, nx, ny, nz;
 
   36       Proximity_domain_field_3(Tree* tree, 
double near_cl, 
double far_cl, std::vector< std::unique_ptr<Zone> >& zones, 
float zone_radius, 
float centre_radius,
 
   37                     const Point* centre, Tree* needle_tree, 
float granularity, 
const Iso_cuboid& bbox, 
bool solid_zones) :
 
   38                             max_(
CGAL::Max<FT>()), min_(
CGAL::Min<FT>()),
 
   39                             tree_(tree), near_cl_(near_cl), far_cl_(far_cl), zones_(zones), zone_radius_(zone_radius),
 
   40                             centre_radius_(centre_radius),
 
   41                             centre_(centre), needle_tree_(needle_tree), granularity_(granularity),
 
   42                             bbox_(bbox), checks_(0), total_checks_(0), values_size_(0), solid_zones_(solid_zones)
 
   44             max_dist[0] = 0.; max_dist[1] = 0.; max_dist[2] = 0.;
 
   46             minx = (int)(bbox.xmin()/granularity_); nx = 1 + (int)(bbox.xmax()/granularity_) - minx;
 
   47             miny = (int)(bbox.ymin()/granularity_); ny = 1 + (int)(bbox.ymax()/granularity_) - miny;
 
   48             minz = (int)(bbox.zmin()/granularity_); nz = 1 + (int)(bbox.zmax()/granularity_) - minz;
 
   49             length_scale = std::pow(bbox.volume(), 1./3);
 
   51             std::cout << 
"Bounding Box coordinates: " 
   52                 << 
"[" << bbox.xmin() << 
", " << bbox.ymin() << 
", " << bbox.zmin() << 
"] -> " 
   53                 << 
"[" << bbox.xmax() << 
", " << bbox.ymax() << 
", " << bbox.zmax() << 
"]" 
   55             std::cout << 
"Length scale: " << length_scale << std::endl;
 
   56             std::cout << 
"CL bitmap: " 
   57                 << 
"[" << minx << 
", " << miny << 
", " << minz << 
"] + " 
   58                 << 
"[" << nx << 
", " << ny << 
", " << nz << 
"]" 
   60             std::cout << 
"Array size: " << nx * ny * nz << std::endl;
 
   64             values_ = (FT*)calloc(
sizeof(FT), nx*ny*nz);
 
   65             dists_ = (FT*)calloc(
sizeof(FT), nx*ny*nz);
 
   71       void output_characteristic_lengths(std::string filename)
 
   73           vtkSmartPointer<vtkImageData> imageData = vtkSmartPointer<vtkImageData>::New();
 
   74           imageData->SetDimensions(nx, ny, nz);
 
   75           imageData->SetNumberOfScalarComponents(2);
 
   76           imageData->SetScalarTypeToDouble();
 
   77           imageData->SetSpacing(granularity_, granularity_, granularity_);
 
   78           imageData->SetOrigin(minx * granularity_, miny * granularity_, minz * granularity_);
 
   80           for (
int z = 0 ; z < nz ; z++)
 
   81               for (
int y = 0 ; y < ny ; y++)
 
   82                   for (
int x = 0 ; x < nx ; x++) {
 
   83                       double *pix = 
static_cast<double*
>(imageData->GetScalarPointer(x, y, z));
 
   84                       int ix = nx*(ny*z + y) + x;
 
   85                       pix[0] = values_[ix] > 1e-20 ? values_[ix] : -1.0;
 
   86                       pix[1] = dists_[ix] > 1e-20 ? dists_[ix] : -2.0;
 
   89           vtkSmartPointer<vtkXMLImageDataWriter> imageWriter = vtkSmartPointer<vtkXMLImageDataWriter>::New();
 
   90           imageWriter->SetInput(imageData);
 
   91           imageWriter->SetFileName(filename.c_str());
 
   92           imageWriter->Update();
 
   96       FT to_cl(FT closest_cl, FT dist)
 const 
  100           if (dist <= 4 * closest_cl * closest_cl + 1e-10)
 
  103               scaling *= pow((dist - closest_cl * closest_cl * 4)/(length_scale * length_scale * 0.25), 0.5);
 
  105           return (far_cl_ - (far_cl_-closest_cl)*(exp(-scaling) - exp(-1)) / (1 - exp(-1)));
 
  109       FT 
operator()(
const Point_3& q, 
const int , 
const Index& )
 const 
  112                   min_(max_(q.x(), bbox_.xmin()), bbox_.xmax()),
 
  113                   min_(max_(q.y(), bbox_.ymin()), bbox_.ymax()),
 
  114                   min_(max_(q.z(), bbox_.zmin()), bbox_.zmax())
 
  116           int x = (int)(p.x()/granularity_);
 
  117           int y = (int)(p.y()/granularity_);
 
  118           int z = (int)(p.z()/granularity_);
 
  120           int ix = nx*(ny*(z - minz) + y - miny) + x - minx;
 
  126           if ( checks_ % 10000 == 0 ) {
 
  127               total_checks_ += checks_;
 
  128               std::cout << 
"Cached " << values_size_
 
  129                   << 
" blocks (miss rate " << values_size_*100./total_checks_
 
  130                   << 
"%) - max. cl: " << max_cl_
 
  131                   << 
" - max. distances from key points/surfaces: " << max_dist[0]
 
  132                   << 
" " << max_dist[1] << 
" " << max_dist[2] << std::endl;
 
  154           FT scaling = 1., dist = -1.;
 
  155           FT closest_cl = near_cl_;
 
  158               FT tree_dist = tree_->squared_distance(p);
 
  159               if (dist < 0 || tree_dist < dist) {
 
  161                   closest_cl = near_cl_;
 
  167           if (needle_tree_ != NULL) {
 
  168               needle_dist = needle_tree_->squared_distance(p);
 
  170               if (dist < 0 || needle_dist < dist) {
 
  172                   closest_cl = near_cl_;
 
  177           for (
auto&& zone : zones_) {
 
  179               if (solid_zones_ && zone->is_container() && zone->contains(p)) {
 
  182               else if (zone->has_tree()) {
 
  183                   zone_dist = zone->squared_distance(p);
 
  184                   if (zone_dist > zone_radius_ * zone_radius_)
 
  185                       zone_dist = zone_dist + zone_radius_ * zone_radius_ - 2. * sqrt(zone_dist) * zone_radius_;
 
  187                   if (zone_dist < 0) zone_dist = 0.;
 
  190               if (zone_dist >= 0 && (dist < 0 || (to_cl(closest_cl, dist) > to_cl(zone->get_cl(), zone_dist)))) {
 
  192                   closest_cl = zone->get_cl();
 
  196           if (centre_ != NULL) {
 
  197               FT centre_dist = squared_distance(*centre_, p);
 
  198               if (centre_dist > centre_radius_ * centre_radius_)
 
  199                   centre_dist = centre_dist + centre_radius_ * centre_radius_ - 2. * sqrt(centre_dist) * centre_radius_;
 
  200               else centre_dist = 0.;
 
  201               if (centre_dist < 0) centre_dist = 0.;
 
  202               if (dist < 0 || to_cl(closest_cl, dist) > to_cl(near_cl_, centre_dist)) {
 
  204                   closest_cl = near_cl_;
 
  215               cl = CGAL::min(far_cl_, to_cl(closest_cl, dist));
 
  216               if (cl > max_cl_) max_cl_ = cl;
 
  247       mutable float max_cl_;
 
  252       FT near_cl_, far_cl_;
 
  253       std::vector< std::unique_ptr<Zone> >& zones_;
 
  254       FT zone_radius_, centre_radius_;
 
  255       const Point* centre_;
 
  258       const Iso_cuboid& bbox_;
 
  259       mutable int checks_, total_checks_, values_size_;
 
  260       mutable FT max_dist[3];
 
Definition: proximity_domain_3.h:20
 
Proximity_domain_field_3(Tree *tree, double near_cl, double far_cl, std::vector< std::unique_ptr< Zone > > &zones, float zone_radius, float centre_radius, const Point *centre, Tree *needle_tree, float granularity, const Iso_cuboid &bbox, bool solid_zones)
Constructor. 
Definition: proximity_domain_3.h:36
 
Definition: implicit_zone_function.h:17
 
Definition: write_c3t3_to_gmsh_file.h:50
 
FT operator()(const Point_3 &q, const int, const Index &) const 
Returns size. 
Definition: proximity_domain_3.h:109