13#ifndef IGL_WINDINGNUMBERAABB_H 
   14#define IGL_WINDINGNUMBERAABB_H 
   48        const Eigen::MatrixBase<DerivedV> & 
V,
 
   49        const Eigen::MatrixBase<DerivedF> & 
F);
 
   52        const Eigen::MatrixBase<DerivedF> & 
F);
 
   58        const Eigen::MatrixBase<DerivedV> & 
V,
 
   59        const Eigen::MatrixBase<DerivedF> & 
F);
 
   61      inline bool inside(
const Point & p) 
const;
 
   62      inline virtual void grow();
 
 
   85#ifndef WindingNumberAABB_MIN_F 
   86#  define WindingNumberAABB_MIN_F 100 
   89template <
typename Po
int, 
typename DerivedV, 
typename DerivedF>
 
   91    const Eigen::MatrixBase<DerivedV> & V,
 
   92    const Eigen::MatrixBase<DerivedF> & F)
 
 
   98template <
typename Po
int, 
typename DerivedV, 
typename DerivedF>
 
  101  using namespace Eigen;
 
  102  assert(max_corner.size() == 3);
 
  103  assert(min_corner.size() == 3);
 
  104  compute_min_max_corners();
 
  105  Eigen::Matrix<typename DerivedV::Scalar,Eigen::Dynamic,1> dblA;
 
  107  total_positive_area = dblA.sum()/2.0;
 
 
  110template <
typename Po
int, 
typename DerivedV, 
typename DerivedF>
 
  112  const Eigen::MatrixBase<DerivedV> & V,
 
  113  const Eigen::MatrixBase<DerivedF> & F):
 
  118    std::numeric_limits<typename DerivedV::Scalar>::infinity()),
 
  119  split_method(MEDIAN_ON_LONGEST_AXIS)
 
 
  124template <
typename Po
int, 
typename DerivedV, 
typename DerivedF>
 
  127  const Eigen::MatrixBase<DerivedF> & F):
 
  132    std::numeric_limits<typename DerivedV::Scalar>::infinity()),
 
  133  split_method(MEDIAN_ON_LONGEST_AXIS)
 
 
  138template <
typename Po
int, 
typename DerivedV, 
typename DerivedF>
 
  142  using namespace Eigen;
 
  144  this->delete_children();
 
  151    this->getF().rows() <= (WindingNumberAABB_MIN_F>0?WindingNumberAABB_MIN_F:0) ||
 
  152    (this->getcap().rows() - 2) >= this->getF().rows())
 
  160  typename DerivedV::Scalar max_len = 
 
  161    -numeric_limits<typename DerivedV::Scalar>::infinity();
 
  162  for(
int d = 0;d<min_corner.size();d++)
 
  164    if( (max_corner[d] - min_corner[d]) > max_len )
 
  166      max_len = (max_corner[d] - min_corner[d]);
 
  171  Eigen::Matrix<typename DerivedV::Scalar,Eigen::Dynamic,Eigen::Dynamic> BC;
 
  177  typename DerivedV::Scalar split_value;
 
  181    case MEDIAN_ON_LONGEST_AXIS:
 
  183      median(BC.col(max_d),split_value);
 
  187    case CENTER_ON_LONGEST_AXIS:
 
  188      split_value = 0.5*(max_corner[max_d] + min_corner[max_d]);
 
  194  vector<int> id( this->getF().rows());
 
  195  for(
int i = 0;i<this->getF().rows();i++)
 
  197    if(BC(i,max_d) <= split_value)
 
  206  const int lefts = (int) 
count(
id.begin(),
id.end(),0);
 
  207  const int rights = (int) 
count(
id.begin(),
id.end(),1);
 
  208  if(lefts == 0 || rights == 0)
 
  213  assert(lefts+rights == this->getF().rows());
 
  214  DerivedF leftF(lefts,  this->getF().cols());
 
  215  DerivedF rightF(rights,this->getF().cols());
 
  218  for(
int i = 0;i<this->getF().rows();i++)
 
  222      leftF.row(left_i++) = this->getF().row(i);
 
  225      rightF.row(right_i++) = this->getF().row(i);
 
  231  assert(right_i == rightF.rows());
 
  232  assert(left_i == leftF.rows());
 
  236  leftWindingNumberAABB->
grow();
 
  237  this->children.push_back(leftWindingNumberAABB);
 
  240  rightWindingNumberAABB->
grow();
 
  241  this->children.push_back(rightWindingNumberAABB);
 
 
  244template <
typename Po
int, 
typename DerivedV, 
typename DerivedF>
 
  247  assert(p.size() == max_corner.size());
 
  248  assert(p.size() == min_corner.size());
 
  249  for(
int i = 0;i<p.size();i++)
 
  254    if( p(i) < min_corner(i) || p(i) > max_corner(i))
 
 
  262template <
typename Po
int, 
typename DerivedV, 
typename DerivedF>
 
  267  for(
int d = 0;d<min_corner.size();d++)
 
  269    min_corner[d] =  numeric_limits<typename Point::Scalar>::infinity();
 
  270    max_corner[d] = -numeric_limits<typename Point::Scalar>::infinity();
 
  273  this->center = Point(0,0,0);
 
  275  for(
int i = 0;i<this->getF().rows();i++)
 
  277    for(
int j = 0;j<this->getF().cols();j++)
 
  279      for(
int d = 0;d<min_corner.size();d++)
 
  282          this->getV()(this->getF()(i,j),d) < min_corner[d] ?  
 
  283            this->getV()(this->getF()(i,j),d) : min_corner[d];
 
  285          this->getV()(this->getF()(i,j),d) > max_corner[d] ?  
 
  286            this->getV()(this->getF()(i,j),d) : max_corner[d];
 
  290      this->center += this->getV().row(this->getF()(i,j));
 
  294  this->center.array() /= this->getF().size();
 
  302  this->radius = (max_corner-min_corner).norm()/2.0;
 
 
  305template <
typename Po
int, 
typename DerivedV, 
typename DerivedF>
 
  306inline typename DerivedV::Scalar
 
  313    return numeric_limits<typename DerivedV::Scalar>::infinity();
 
  317  return numeric_limits<typename DerivedV::Scalar>::infinity();
 
 
  320template <
typename Po
int, 
typename DerivedV, 
typename DerivedF>
 
  321inline typename DerivedV::Scalar 
 
  323  const Point & p)
 const 
  326  using namespace Eigen;
 
  330    return numeric_limits<typename DerivedV::Scalar>::infinity();
 
  338    Eigen::Matrix<typename DerivedV::Scalar,Eigen::Dynamic,Eigen::Dynamic>
 
  341    Eigen::Matrix<typename DerivedF::Scalar,Eigen::Dynamic,Eigen::Dynamic>
 
  345    min_corner[0],min_corner[1],min_corner[2],
 
  346    min_corner[0],min_corner[1],max_corner[2],
 
  347    min_corner[0],max_corner[1],min_corner[2],
 
  348    min_corner[0],max_corner[1],max_corner[2],
 
  349    max_corner[0],min_corner[1],min_corner[2],
 
  350    max_corner[0],min_corner[1],max_corner[2],
 
  351    max_corner[0],max_corner[1],min_corner[2],
 
  352    max_corner[0],max_corner[1],max_corner[2];
 
  374  Point p2c = 0.5*(min_corner+max_corner)-p;
 
  375  for(
int i = 0;i<BFN.rows();i++)
 
  377    if(p2c.dot(BFN.row(i)) > 0)
 
  379      PBF.row(pbfi++) = BF.row(i);
 
  382  PBF.conservativeResize(pbfi,PBF.cols());
 
 
  392  template <> 
inline igl::WindingNumberAABB<Eigen::Matrix<double, 1, 3, 1, 1, 3>,Eigen::Matrix<double, -1, 2, 0, -1, 2>,Eigen::Matrix<int, -1, 2, 0, -1, 2>>::WindingNumberAABB(
const Eigen::MatrixBase<Eigen::Matrix<double, -1, 2, 0, -1, 2>> & , 
const Eigen::MatrixBase<Eigen::Matrix<int, -1, 2, 0, -1, 2>> & ){};
 
  393  template <> 
inline void igl::WindingNumberAABB<Eigen::Matrix<double, 1, 3, 1, 1, 3>,Eigen::Matrix<double, -1, 2, 0, -1, 2>,Eigen::Matrix<int, -1, 2, 0, -1, 2>>::grow(){};
 
  394  template <> 
inline void igl::WindingNumberAABB<Eigen::Matrix<double, 1, 3, 1, 1, 3>,Eigen::Matrix<double, -1, 2, 0, -1, 2>,Eigen::Matrix<int, -1, 2, 0, -1, 2>>::init(){};
 
Class for building an AABB tree to implement the divide and conquer algorithm described in [Jacobson ...
Definition WindingNumberAABB.h:26
 
virtual void grow()
Definition WindingNumberAABB.h:139
 
Point min_corner
Definition WindingNumberAABB.h:28
 
DerivedV::Scalar total_positive_area
Definition WindingNumberAABB.h:30
 
void set_mesh(const Eigen::MatrixBase< DerivedV > &V, const Eigen::MatrixBase< DerivedF > &F)
Initialize the hierarchy to a given mesh.
Definition WindingNumberAABB.h:90
 
WindingNumberAABB()
Definition WindingNumberAABB.h:39
 
SplitMethod
Definition WindingNumberAABB.h:33
 
@ CENTER_ON_LONGEST_AXIS
Definition WindingNumberAABB.h:34
 
@ MEDIAN_ON_LONGEST_AXIS
Definition WindingNumberAABB.h:35
 
@ NUM_SPLIT_METHODS
Definition WindingNumberAABB.h:36
 
DerivedV::Scalar max_simple_abs_winding_number(const Point &p) const
Definition WindingNumberAABB.h:322
 
Point max_corner
Definition WindingNumberAABB.h:29
 
enum igl::WindingNumberAABB::SplitMethod split_method
 
bool inside(const Point &p) const
Definition WindingNumberAABB.h:245
 
void init()
Definition WindingNumberAABB.h:99
 
DerivedV::Scalar max_abs_winding_number(const Point &p) const
Definition WindingNumberAABB.h:307
 
void compute_min_max_corners()
Definition WindingNumberAABB.h:263
 
Space partitioning tree for computing winding number hierarchically.
Definition WindingNumberTree.h:25
 
Eigen::Matrix< typename DerivedF::Scalar, Eigen::Dynamic, Eigen::Dynamic > MatrixXF
Definition WindingNumberTree.h:45
 
const WindingNumberTree * parent
Definition WindingNumberTree.h:38
 
DerivedV & V
Definition WindingNumberTree.h:49
 
virtual void set_mesh(const Eigen::MatrixBase< DerivedV > &V, const Eigen::MatrixBase< DerivedF > &F)
Definition WindingNumberTree.h:189
 
Eigen::Matrix< typename DerivedV::Scalar, Eigen::Dynamic, Eigen::Dynamic > MatrixXS
Definition WindingNumberTree.h:42
 
MatrixXF F
Definition WindingNumberTree.h:53
 
void per_face_normals(const Eigen::MatrixBase< DerivedV > &V, const Eigen::MatrixBase< DerivedF > &F, const Eigen::MatrixBase< DerivedZ > &Z, Eigen::PlainObjectBase< DerivedN > &N)
Compute face normals via vertex position list, face list.
 
void winding_number(const Eigen::MatrixBase< DerivedV > &V, const Eigen::MatrixBase< DerivedF > &F, const Eigen::MatrixBase< DerivedO > &O, Eigen::PlainObjectBase< DerivedW > &W)
Computes the generalized winding number at each dim-dimensional query point in O with respect to the ...
 
void doublearea(const Eigen::MatrixBase< DerivedV > &V, const Eigen::MatrixBase< DerivedF > &F, Eigen::PlainObjectBase< DeriveddblA > &dblA)
Computes twice the area for each input triangle or quad.
 
void count(const Eigen::SparseMatrix< XType > &X, const int dim, Eigen::SparseVector< SType > &S)
Count the number of non-zeros in the columns or rows of a sparse matrix.
 
void barycenter(const Eigen::MatrixBase< DerivedV > &V, const Eigen::MatrixBase< DerivedF > &F, Eigen::PlainObjectBase< DerivedBC > &BC)
Computes the barycenter of every simplex.
 
bool median(const Eigen::MatrixBase< DerivedV > &V, mType &m)
Compute the median of an eigen vector.