aimsalgo  5.1.2
Neuroimaging image processing
projection.h
Go to the documentation of this file.
1 /* This software and supporting documentation are distributed by
2  * Institut Federatif de Recherche 49
3  * CEA/NeuroSpin, Batiment 145,
4  * 91191 Gif-sur-Yvette cedex
5  * France
6  *
7  * This software is governed by the CeCILL-B license under
8  * French law and abiding by the rules of distribution of free software.
9  * You can use, modify and/or redistribute the software under the
10  * terms of the CeCILL-B license as circulated by CEA, CNRS
11  * and INRIA at the following URL "http://www.cecill.info".
12  *
13  * As a counterpart to the access to the source code and rights to copy,
14  * modify and redistribute granted by the license, users are provided only
15  * with a limited warranty and the software's author, the holder of the
16  * economic rights, and the successive licensors have only limited
17  * liability.
18  *
19  * In this respect, the user's attention is drawn to the risks associated
20  * with loading, using, modifying and/or developing or reproducing the
21  * software by the user in light of its specific status of free software,
22  * that may mean that it is complicated to manipulate, and that also
23  * therefore means that it is reserved for developers and experienced
24  * professionals having in-depth computer knowledge. Users are therefore
25  * encouraged to load and test the software's suitability as regards their
26  * requirements in conditions enabling the security of their systems and/or
27  * data to be ensured and, more generally, to use and operate it in the
28  * same conditions as regards security.
29  *
30  * The fact that you are presently reading this means that you have had
31  * knowledge of the CeCILL-B license and that you accept its terms.
32  */
33 
34 
35 #ifndef AIMS_DISTANCEMAP_PROJECTION_H
36 #define AIMS_DISTANCEMAP_PROJECTION_H
37 
38 #include <cstdlib>
39 #include <aims/mesh/texture.h>
40 #include <aims/mesh/surface.h>
44 #include <aims/math/gausslu.h>
45 #include <aims/math/eigen.h>
46 #include <set>
47 #include <list>
48 #include <map>
49 #include <float.h>
50 
51 
52 class Graph;
53 namespace aims
54 {
55  namespace meshdistance
56  {
57 
58 
66  const Texture<float> & curvtex,
67  const carto::rc_ptr<carto::Volume<short> > & bottom_vol,
68  const carto::rc_ptr<carto::Volume<short> > & surface_vol,
69  float alpha, float dmin,
70  int MINCC,
71  const std::map <short,std::string> & trans,
72  const std::set<std::string> & labels,
73  float maxdil,float maxdil_mesh,float alpha_reg,
74  bool connexity,
75  const std::vector<std::list<unsigned> > & neigho);
79  const carto::rc_ptr<carto::Volume<short> > & bottom_vol,
80  const carto::rc_ptr<carto::Volume<short> > & surface_vol,
81  const Point3df & CA,
82  float demin,float dpmin,
83  int MINCC,
84  const std::map <short,std::string> & trans,
85  const std::set<std::string> & labels,
86  float maxdil,float maxdil_mesh,float alpha_reg,
87  bool connexity,
88  const std::vector<std::list<unsigned> > & neigho);
89 
90 
93  const carto::rc_ptr<carto::Volume<short> > &ccvol,
94  const carto::rc_ptr<carto::Volume<short> > &sulcvol,
95  const AimsSurface<3,Void> & mesh,
96  std::set<short> &cc_sulci_labels,
97  std::map<short,short > &tri_sulci,
98  std::map<unsigned, Point3dfSet > &cc_sulci_coord,
99  std::map<Point3df, Point3df,
100  Point3dfCompare > &initend,
101  const Texture<float> &curvtex,
102  float alpha,float dmin);
103 
106  ( const carto::rc_ptr<carto::Volume<short> > &ccvol,
107  const carto::rc_ptr<carto::Volume<short> > &sulcvol,
108  const AimsSurface<3,Void> & mesh,
109  std::set<short> &cc_sulci_labels,
110  std::map<short,short > &tri_sulci,
111  const std::map<Point3df, Point3dfSet,
112  Point3dfCompare > &neigh,
113  std::map<unsigned, Point3dfSet > &cc_sulci_coord,
114  std::map<Point3df, Point3df, Point3dfCompare > &initend,
115  float demin, float dpmin,
116  short label_insula_left,short label_insula_right,
117  const Point3df & CA );
118 
119  void
121  const AimsSurface<3,Void> & mesh,
122  const std::map<Point3df, Point3df, Point3dfCompare >
123  &initend,
124  const Point3dfSet &setpointi,
125  short label,
126  float dmin,float alpha_reg );
127 
129  const carto::rc_ptr<carto::Volume<short> > &initVol,
130  const Texture<short> &tex,
131  const AimsSurface<3,Void> & mesh,
132  short val_domain,
133  short back);
134 
137  const carto::rc_ptr<carto::Volume<short> > &initVol,
138  const AimsSurface<3,Void> & mesh,
139  short back);
140 
143  void
144  NeighbourInCC( std::map<Point3df, Point3dfSet, Point3dfCompare > &neigh,
145  const carto::rc_ptr<carto::Volume<short> > & bvol,
146  const carto::rc_ptr<carto::Volume<short> > & svol,
147  Connectivity::Type connectivity,
148  short label, const unsigned size_neigh,
149  unsigned max_points = 50);
150 
151 
152 
153  //inline functions
154 
155  //first : barycenter of the input pt
156  //second : normal vector
157 
158  inline std::pair<Point3df,Point3df> NormalFromPoints( const Point3dfSet & init_point )
159  {
160  std::pair<Point3df,Point3df> output;
161  unsigned inc = 0, i=0,j=0,n = init_point.size();
162  Point3df mean = Point3df(0,0,0),temp;
163  Point3dfSet norm_point;
164  carto::VolumeRef<float> cov( 3, 3, 1, 1,
165  carto::AllocatorContext::fast() );
166  Point3dfSet::const_iterator is,es;
167 
168  for (is = init_point.begin(), es = init_point.end(); is != es; ++is)
169  mean += *is;
170 
171  mean = mean / (float)n;
172 
173  for (is = init_point.begin(), es = init_point.end(); is != es; ++is,
174  ++inc)
175  norm_point.insert(*is - mean);
176 
177  cov = 0;
178  for (is = norm_point.begin(), es = norm_point.end(); is != es; ++is,
179  ++inc)
180  {
181  temp = *is;
182  for (i=0; i<3; ++i)
183  for (j=0; j<3; ++j)
184  cov(i,j) += temp[i] * temp[j];
185  }
186  AimsEigen< float > eigen;
187  carto::VolumeRef< float > value = eigen.doit( cov );
188 
189  eigen.sort(cov,value);
190 
191  temp[0] = cov(0,2);
192  temp[1] = cov(1,2);
193  temp[2] = cov(2,2);
194 
195  temp.normalize();
196  output.second = temp;
197  output.first = mean;
198 
199  return(output);
200  }
201 
202  //Point3df : normal vector to the plane passing through pt
203  inline Point3df NormalFromPoints( const Point3df & pt,
204  const Point3dfSet & init_point )
205  {
206  unsigned inc = 0, i=0,j=0;
207  Point3df temp;
208  Point3dfSet norm_point;
209  carto::VolumeRef<float> cov( 3, 3, 1, 1,
210  carto::AllocatorContext::fast() );
211  Point3dfSet::const_iterator is,es;
212 
213  for( is = init_point.begin(), es = init_point.end(); is != es;
214  ++is, ++inc)
215  norm_point.insert(*is - pt);
216 
217  cov = 0;
218  for( is = norm_point.begin(), es = norm_point.end(); is != es;
219  ++is, ++inc)
220  {
221  temp = *is;
222  for (i=0; i<3; ++i)
223  for (j=0; j<3; ++j)
224  cov(i,j) += temp[i] * temp[j];
225  }
226  AimsEigen< float > eigen;
227  carto::VolumeRef< float > value = eigen.doit( cov );
228 
229  eigen.sort(cov,value);
230 
231  temp[0] = cov(0,2);
232  temp[1] = cov(1,2);
233  temp[2] = cov(2,2);
234 
235  temp.normalize();
236 
237 
238  return(temp);
239  }
240 
241  inline Point3df cross(const Point3df &A, const Point3df &B)
242  {
243  Point3df C;
244  C[0] = A[1] * B[2] - A[2] * B[1];
245  C[1] = A[2] * B[0] - A[0] * B[2];
246  C[2] = A[0] * B[1] - A[1] * B[0];
247  return (C);
248 
249  }
250 
251 
252  //Give the point of intersection
253  //between a line
254  //(defined by a point 'pt'
255  //and a direction 'direction_line' )
256  // and a plane
257  //(defined by 3 points s1, s2, s3)
259  const Point3df &s1,const Point3df &s2, const Point3df &s3,
260  const Point3df & direction_line, const Point3df & pt )
261  {
262  float a0, b0, c0;
263  float xb,yb,zb;
264  float a,b,c;
265  float xm,ym,zm;
266  Point3df pt_intersection, normal_tri;
267 
268 
269  ASSERT(direction_line != Point3df(0,0,0));
270  normal_tri = cross(s1 - s2,s1 - s3);
271  normal_tri.normalize();
272 
273  //mesh triangle normal
274  a0 = normal_tri[0];
275  b0 = normal_tri[1];
276  c0 = normal_tri[2];
277 
278  //one node of the triangle
279  xb = s1[0];
280  yb = s1[1];
281  zb = s1[2];
282 
283  //direction of the line
284  a = direction_line[0];
285  b = direction_line[1];
286  c = direction_line[2];
287 
288  //coord of the pt defining the line
289  xm = pt[0];
290  ym = pt[1];
291  zm = pt[2];
292 
293  pt_intersection[0] = (c * c0 * xm +
294  a * c0 * zb -
295  a * b0 * ym +
296  a * a0 * xb +
297  a * b0 * yb +
298  b0 * b * xm -
299  c0 * a * zm) /
300  ( c * c0 + a * a0 + b0 * b);
301 
302 
303  pt_intersection[1] = ( b * c0 * zb +
304  b * a0 * xb +
305  b * b0 * yb -
306  b * xm * a0 +
307  c * ym * c0 +
308  ym * a * a0 -
309  b * zm * c0 ) /
310  (c * c0 + a * a0 + b0 * b);
311 
312  pt_intersection[2] = ( c * c0 * zb
313  - b0 * c * ym
314  + c * a0 * xb
315  + c * b0 * yb
316  + a * zm * a0
317  + b0 * b * zm
318  - c * xm * a0 ) /
319  (c * c0 + a * a0 + b0 * b);
320 
321  return (pt_intersection);
322  }
323 
324 
325  /* Distance from a point (A) to the plane defined by
326  one of its point : bipoint.first
327  its normal (norm = 1): bipoint.second */
328  inline float DistancePointToPlane(const Point3df &A, const std::pair<Point3df,Point3df> &plane )
329  {
330 
331  float d;
332  Point3df temp = plane.first - A;
333  d = fabs( temp.dot(plane.second) );
334 
335  return(d);
336  }
337 
338 
339  /* Distance from a point (A) to a line defined by
340  one of its point : bipoint.first
341  its direction vector (norm = 1): bipoint.second */
342  inline float DistancePointToLine(const Point3df &A, const std::pair<Point3df,Point3df> &line )
343  {
344 
345  float d;
346  Point3df temp = A - line.first;
347  d = cross(temp,line.second).norm();
348 
349  return(d);
350  }
351 
352  //Compute the mean normal n0 of the cc
353  // n1 fix the sens of each normal
354  // Only pt with a least MIN_NEIGH neighbours are taken into account
355  // It avoid considering extremal points whose normal estimation is bad
356  // The normal of these pt can be seen as outliers
357  inline Point3df meanNormalofCC(const std::vector<Point3df> &cc,
358  const Point3dfNeigh & neigh,
359  unsigned MIN_NEIGH)
360  {
361  Point3df PtR,n0 = Point3df(0,0,0),n1= Point3df(0,0,0),normal_plan;
362  Point3dfNeigh::const_iterator is,es = neigh.end();
363  std::vector<Point3df>::const_iterator icc,ecc = cc.end();
364  bool ok1 = false;
365  //Fix an arbitrary orientation (n1) for the normals of each pt of the cc
366  icc = cc.begin();
367  while (!ok1 && icc != ecc)
368  {
369  PtR = *icc;
370  is = neigh.find(PtR);
371  if (is != es)
372  {
373  if (is->second.size() > MIN_NEIGH)
374  {
375  ok1 = false;
376  normal_plan = NormalFromPoints(is->first,is->second);
377  }
378  }
379  else
380  std::cerr << "Pb1: cannot find the neighbours of the point "
381  << PtR <<"\n";
382  ++icc;
383  }
384  n1 = normal_plan;
385 
386  for(icc = cc.begin(); icc != ecc; ++icc)
387  {
388  PtR = *icc;
389  is = neigh.find(PtR);
390  if (is != es)
391  {
392  if (is->second.size() > MIN_NEIGH)
393  normal_plan = NormalFromPoints(is->first,is->second);
394  }
395  else
396  std::cerr << "Pb2: cannot find the neighbours of the point "
397  << PtR <<"\n";
398  normal_plan *= normal_plan.dot(n1);
399  normal_plan.normalize();
400  n0 += normal_plan ;
401  }
402 
403  n0.normalize();
404  std::cout << "CC mean normal : "<< n0 << std::endl;
405 
406  return (n0);
407  }
408 
409 
410 
412  extern const short MESHDISTANCE_FORBIDDEN;
413  extern const short MESHDISTANCE_UNREACHED;
414 
415  }
416 }
417 
418 
419 #endif
#define ASSERT(EX)
void sort(carto::VolumeRef< T > eigenvectors, carto::VolumeRef< T > eigenvalues, carto::VolumeRef< T > *wi=NULL)
Sort the eigenvectors and eigenvalues in decreasing order.
carto::VolumeRef< T > doit(carto::VolumeRef< T >, carto::VolumeRef< T > *wi=NULL)
Eigen system resolution function.
AimsVector< T, D > & normalize()
T dot(const AimsVector< T, D > &other) const
float norm() const
iterator end()
float DistancePointToLine(const Point3df &A, const std::pair< Point3df, Point3df > &line)
Definition: projection.h:342
Texture< short > VolumeParcellation2MeshParcellation(const carto::rc_ptr< carto::Volume< short > > &initVol, const AimsSurface< 3, Void > &mesh, short back)
const short MESHDISTANCE_UNREACHED
Definition: meshvoronoi.h:85
std::pair< Point3df, Point3df > NormalFromPoints(const Point3dfSet &init_point)
Definition: projection.h:158
carto::VolumeRef< short > MeshParcellation2Volume(const carto::rc_ptr< carto::Volume< short > > &initVol, const Texture< short > &tex, const AimsSurface< 3, Void > &mesh, short val_domain, short back)
Texture< short > FirstSulciProjectionWithCurvatureMap(const carto::rc_ptr< carto::Volume< short > > &ccvol, const carto::rc_ptr< carto::Volume< short > > &sulcvol, const AimsSurface< 3, Void > &mesh, std::set< short > &cc_sulci_labels, std::map< short, short > &tri_sulci, std::map< unsigned, Point3dfSet > &cc_sulci_coord, std::map< Point3df, Point3df, Point3dfCompare > &initend, const Texture< float > &curvtex, float alpha, float dmin)
Point3df IntersectionPointOfPlanAndLine(const Point3df &s1, const Point3df &s2, const Point3df &s3, const Point3df &direction_line, const Point3df &pt)
Definition: projection.h:258
void NeighbourInCC(std::map< Point3df, Point3dfSet, Point3dfCompare > &neigh, const carto::rc_ptr< carto::Volume< short > > &bvol, const carto::rc_ptr< carto::Volume< short > > &svol, Connectivity::Type connectivity, short label, const unsigned size_neigh, unsigned max_points=50)
Give the neighbours of a point The neighbours have the same label as the point.
Point3df cross(const Point3df &A, const Point3df &B)
Definition: projection.h:241
TimeTexture< short > SulcusVolume2Texture(const AimsSurface< 3, Void > &mesh, const Texture< float > &curvtex, const carto::rc_ptr< carto::Volume< short > > &bottom_vol, const carto::rc_ptr< carto::Volume< short > > &surface_vol, float alpha, float dmin, int MINCC, const std::map< short, std::string > &trans, const std::set< std::string > &labels, float maxdil, float maxdil_mesh, float alpha_reg, bool connexity, const std::vector< std::list< unsigned > > &neigho)
Projection of the voxels relative to the bottom of the sulci to the edges of a triangulation.
void AffinePointProjection(Texture< short > &tex, const AimsSurface< 3, Void > &mesh, const std::map< Point3df, Point3df, Point3dfCompare > &initend, const Point3dfSet &setpointi, short label, float dmin, float alpha_reg)
Texture< short > FirstSulciProjectionWithInterpolationPlane(const carto::rc_ptr< carto::Volume< short > > &ccvol, const carto::rc_ptr< carto::Volume< short > > &sulcvol, const AimsSurface< 3, Void > &mesh, std::set< short > &cc_sulci_labels, std::map< short, short > &tri_sulci, const std::map< Point3df, Point3dfSet, Point3dfCompare > &neigh, std::map< unsigned, Point3dfSet > &cc_sulci_coord, std::map< Point3df, Point3df, Point3dfCompare > &initend, float demin, float dpmin, short label_insula_left, short label_insula_right, const Point3df &CA)
float DistancePointToPlane(const Point3df &A, const std::pair< Point3df, Point3df > &plane)
Definition: projection.h:328
const short MESHDISTANCE_FORBIDDEN
global variable...
Definition: meshvoronoi.h:84
Point3df meanNormalofCC(const std::vector< Point3df > &cc, const Point3dfNeigh &neigh, unsigned MIN_NEIGH)
Definition: projection.h:357
std::set< Point3df, Point3dfCompare > Point3dfSet
Definition: stlsort.h:118
std::map< Point3df, Point3dfSet, Point3dfCompare > Point3dfNeigh
Definition: stlsort.h:119