]> Creatis software - creaMaracasVisu.git/blob - bbtk/src/bbcreaMaracasVisuShowNPoints_Tools.cxx
Clean Code MacOs
[creaMaracasVisu.git] / bbtk / src / bbcreaMaracasVisuShowNPoints_Tools.cxx
1 //===== 
2 // Before editing this file, make sure it's a file of your own (i.e.: it wasn't generated from xml description; if so : your modifications will be lost)
3 //===== 
4 #include "bbcreaMaracasVisuShowNPoints_Tools.h"
5 #include "bbcreaMaracasVisuPackage.h"
6
7 #include <vtkPointData.h>
8 #include <vtkDataArray.h>
9 #include <vtkMath.h>
10
11
12 namespace bbcreaMaracasVisu
13 {
14
15 BBTK_ADD_BLACK_BOX_TO_PACKAGE(creaMaracasVisu,ShowNPoints_Tools)
16 BBTK_BLACK_BOX_IMPLEMENTATION(ShowNPoints_Tools,bbtk::AtomicBlackBox);
17
18
19
20 void ShowNPoints_Tools::NearestPointToMesh( vtkPoints *points,vtkStaticPointLocator *pointLocator,double *spc,double *p,double *pM)
21 {
22     p[0]  = p[0] * spc[0];
23     p[1]  = p[1] * spc[1];
24     p[2]  = p[2] * spc[2];
25     points->GetPoint( pointLocator->FindClosestPoint(p) , pM );
26     pM[0] = pM[0] / spc[0];
27     pM[1] = pM[1] / spc[1];
28     pM[2] = pM[2] / spc[2];
29 }
30
31 void ShowNPoints_Tools::CreatePatch_3points()
32 {
33         printf("PG ShowNPoints_Tools::CreatePatch_3points  Entered patch 3 points !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\n");
34         WidgetShowNPoints* wsp = bbGetInputWidgetShowNPoints();
35         wsp->StopAutoAddPoints();
36     wsp->StopTrackPoint();
37         if ( (wsp->GetLstModelShowNPointsSize()==1) &&
38          (wsp->GetModelShowNPoints()->GetLstPointsSize()==3) &&
39          (bbGetInputMesh()!=NULL ) )
40     {
41                 std::vector<int> lstX = wsp->GetModelShowNPoints()->GetLstPointsX();
42                 std::vector<int> lstY = wsp->GetModelShowNPoints()->GetLstPointsY();
43                 std::vector<int> lstZ = wsp->GetModelShowNPoints()->GetLstPointsZ();
44                 
45 //        double pA[3] = {lstX[0],lstY[0],lstZ[0]};
46         //        double pB[3] = {lstX[1],lstY[1],lstZ[1]};
47         //        double pC[3] = {lstX[2],lstY[2],lstZ[2]};
48                 double pA[3];
49         pA[0] = lstX[0];
50         pA[1] = lstY[0];
51         pA[2] = lstZ[0];
52         double pB[3];
53         pB[0] = lstX[1];
54         pB[1] = lstY[1];
55         pB[2] = lstZ[1];
56         double pC[3];
57         pC[0] = lstX[2];
58         pC[1] = lstY[2];
59         pC[2] = lstZ[2];
60
61                 double v[3];
62                 double u[3];
63                 vtkMath::Subtract(pC,pA,v);
64                 vtkMath::Subtract(pB,pA,u);
65                 
66                 /**point in AC closest to B.
67                 *formula t=(V)dot(U)/(V)dot(V)
68                 */
69                 double t = vtkMath::Dot(v,u)/vtkMath::Dot(v,v);
70                 /**nP found point
71                 *formula A+t(C-A) -> A+tV
72                 */
73                 vtkMath::MultiplyScalar(v, t);
74                 double nP[3];
75                 vtkMath::Add(pA, v, nP);
76                 
77                 //calculate direction vector from found point to B
78                 double dirVector[3];
79                 vtkMath::Subtract(pB, nP, dirVector);
80                 
81                 double pointAdd[3];
82                 double pointSub[3];
83                 
84                 //Add and subtract direction vector to A and C to find the 4 points to create the patch,
85                 
86                 std::vector<int> resListX;
87                 std::vector<int> resListY;
88                 std::vector<int> resListZ;
89                 
90                 vtkMath::Add(pA, dirVector, pointAdd);
91                 vtkMath::Subtract(pA, dirVector, pointSub);
92                 
93                 resListX.push_back(pointSub[0]);
94                 resListY.push_back(pointSub[1]);
95                 resListZ.push_back(pointSub[2]);
96
97                 resListX.push_back(pointAdd[0]);
98                 resListY.push_back(pointAdd[1]);
99                 resListZ.push_back(pointAdd[2]);
100                 
101                 
102                 vtkMath::Add(pC, dirVector, pointAdd);
103                 vtkMath::Subtract(pC, dirVector, pointSub);
104                 
105                 resListX.push_back(pointAdd[0]);
106                 resListY.push_back(pointAdd[1]);
107                 resListZ.push_back(pointAdd[2]);
108                 
109                 resListX.push_back(pointSub[0]);
110                 resListY.push_back(pointSub[1]);
111                 resListZ.push_back(pointSub[2]);
112                 printf("PG ShowNPoints_Tools::CreatePatch_3points  Calls CreatePatch_Points !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\n");
113                 //Create patch given the previously calculated points (4 points)
114                 CreatePatch_Points(resListX, resListY, resListZ);
115         }else{
116                 printf("PG ShowNPoints_Tools::CreatePatch_3points  Warning patch not apply. Need only one group of 3 points\n");
117         }
118 }
119
120 void ShowNPoints_Tools::CreatePatch_4points()
121 {
122         WidgetShowNPoints* wsp = bbGetInputWidgetShowNPoints();
123         wsp->StopAutoAddPoints();
124     wsp->StopTrackPoint();
125         if ( (wsp->GetLstModelShowNPointsSize()==1) &&
126          (wsp->GetModelShowNPoints()->GetLstPointsSize()==4) &&
127          (bbGetInputMesh()!=NULL ) )
128     {                
129                 std::vector<int> lstX = wsp->GetModelShowNPoints()->GetLstPointsX();
130                 std::vector<int> lstY = wsp->GetModelShowNPoints()->GetLstPointsY();
131                 std::vector<int> lstZ = wsp->GetModelShowNPoints()->GetLstPointsZ();
132                 CreatePatch_Points(lstX, lstY, lstZ);
133     }else{
134                 printf("PG ShowNPoints_Tools::CreatePatch_4points  Warning patch not apply. Need only one group of 4 points\n");
135         }
136 }
137
138 void ShowNPoints_Tools::CreatePatch_Points(std::vector<int> lstX, std::vector<int> lstY, std::vector<int> lstZ)
139 {
140     WidgetShowNPoints* wsp = bbGetInputWidgetShowNPoints();
141     std::vector<long int>   lstIdNormalSurface;
142     double                  spc[3];
143                             spc[0]          = bbGetInputSpacing()[0];
144                             spc[1]          = bbGetInputSpacing()[1];
145                             spc[2]          = bbGetInputSpacing()[2];
146     vtkPoints               *points         = bbGetInputMesh()->GetPoints();
147     vtkStaticPointLocator   *pointLocator   = vtkStaticPointLocator::New();
148     pointLocator->SetDataSet( bbGetInputMesh() );
149     pointLocator->BuildLocator();
150     wsp->StopTrackPoint();
151     double p[3],pM[3];
152     double dx,dy,dz;
153     
154     wsp->DeleteAllPoints_();
155     //wsp->ErasePoint( 0 );
156     //wsp->ErasePoint( 0 );
157     //wsp->ErasePoint( 0 );
158     //wsp->ErasePoint( 0 );
159     // --- Group 0 ---
160     dx = lstX[1]-lstX[0];
161     dy = lstY[1]-lstY[0];
162     dz = lstZ[1]-lstZ[0];
163     //
164     //
165     double part = 0.25;
166     for(int sect = 0; sect < 5; sect++)
167     {
168         p[0] = lstX[0] + dx*(sect*part);
169                 p[1] = lstY[0] + dy*(sect*part);
170                 p[2] = lstZ[0] + dz*(sect*part);
171                 if(sect == 4){
172                         p[0] = p[0] + 0.5*(((lstX[1]+lstX[2])/2)-p[0]);
173                         p[1] = p[1] + 0.5*(((lstY[1]+lstY[2])/2)-p[1]);
174                         p[2] = p[2] + 0.5*(((lstZ[1]+lstZ[2])/2)-p[2]);
175                 }
176                 if(sect == 0){
177                         p[0] = p[0] + 0.5*(((lstX[0]+lstX[3])/2)-p[0]);
178                         p[1] = p[1] + 0.5*(((lstY[0]+lstY[3])/2)-p[1]);
179                         p[2] = p[2] + 0.5*(((lstZ[0]+lstZ[3])/2)-p[2]);
180                 }
181                 NearestPointToMesh(points, pointLocator, spc, p,pM);
182                 wsp->InsertPoint(pM[0] ,pM[1], pM[2],"");
183                 
184                 if(sect == 0 || sect == 4) lstIdNormalSurface.push_back( pointLocator->FindClosestPoint(pM) );
185     }
186         
187     // --- Group 1 ---
188     wsp->InsertCollectionAfter_();
189       p[0] = (lstX[0]+lstX[3])/2;
190       p[1] = (lstY[0]+lstY[3])/2;
191       p[2] = (lstZ[0]+lstZ[3])/2;
192       NearestPointToMesh(points, pointLocator, spc, p,pM);
193       wsp->InsertPoint(pM[0] ,pM[1], pM[2],"");
194       p[0] = (lstX[1]+lstX[2])/2;
195       p[1] = (lstY[1]+lstY[2])/2;
196       p[2] = (lstZ[1]+lstZ[2])/2;
197       NearestPointToMesh(points, pointLocator, spc, p,pM);
198       wsp->InsertPoint(pM[0] ,pM[1], pM[2],"");
199       p[0] = (lstX[0]+lstX[1]+lstX[2]+lstX[3])/4;          p[1] = (lstY[0]+lstY[1]+lstY[2]+lstY[3])/4;          p[2] = (lstZ[0]+lstZ[1]+lstZ[2]+lstZ[3])/4;
200       wsp->InsertPoint(p[0] ,p[1], p[2],"");
201         
202     // --- Group 2 ---
203     
204     wsp->InsertCollectionAfter_();
205
206     dx = lstX[2]-lstX[3];
207     dy = lstY[2]-lstY[3];
208     dz = lstZ[2]-lstZ[3];  
209     for(int sect = 0; sect < 5; sect++)
210     {
211         p[0] = lstX[3] + dx*(sect*part);
212                 p[1] = lstY[3] + dy*(sect*part);
213                 p[2] = lstZ[3] + dz*(sect*part);
214                 if(sect == 4){
215                         p[0] = p[0] + 0.5*(((lstX[1]+lstX[2])/2)-p[0]);
216                         p[1] = p[1] + 0.5*(((lstY[1]+lstY[2])/2)-p[1]);
217                         p[2] = p[2] + 0.5*(((lstZ[1]+lstZ[2])/2)-p[2]);
218                 }
219                 if(sect == 0){
220                         p[0] = p[0] + 0.5*(((lstX[0]+lstX[3])/2)-p[0]);
221                         p[1] = p[1] + 0.5*(((lstY[0]+lstY[3])/2)-p[1]);
222                         p[2] = p[2] + 0.5*(((lstZ[0]+lstZ[3])/2)-p[2]);
223                 }
224                 NearestPointToMesh(points, pointLocator, spc, p,pM);
225                 wsp->InsertPoint(pM[0] ,pM[1], pM[2],"");
226                 
227                 if(sect == 0 || sect == 4) lstIdNormalSurface.push_back( pointLocator->FindClosestPoint(pM) );
228     }
229
230      pointLocator->Delete();
231     
232     // Check normals
233 //        1. Recorrer las normales de lstIdNormals y calcular el promedio  -> V1
234     double          *nValue;
235         double                  n1[3];
236     vtkPointData    *pointdata  =  bbGetInputMesh()->GetPointData();
237     vtkDataArray    *dataarray  = pointdata->GetNormals();
238         int i,size = lstIdNormalSurface.size();
239         n1[0]=0;
240         n1[1]=0;
241         n1[2]=0;
242         for (i=0; i<size; i++)
243         {
244             nValue        = dataarray->GetTuple3( lstIdNormalSurface[i] );
245                 n1[0] = n1[0] + nValue[0];
246                 n1[1] = n1[1] + nValue[1];
247                 n1[2] = n1[2] + nValue[2];
248         } // for i
249         n1[0] = n1[0]/size;
250         n1[1] = n1[1]/size;
251         n1[2] = n1[2]/size;
252
253 //        2. Calcular el promedio de 4 normales de la nueva superficie     -> V2
254     double pC[3];
255     double pM1[3];
256     double pM2[3];
257     double n2[3];
258     n2[0] = 0;
259     n2[1] = 0;
260     n2[2] = 0;
261     // Collection 0 with 4 points
262     // Collection 1 with 3 points
263     // Collection 2 with 4 points
264     wsp->GetCollectionPoint(1,1, pC);
265     
266     wsp->GetCollectionPoint(0,0, pM);
267     vtkMath::Subtract(pM,pC,pM1);
268     wsp->GetCollectionPoint(0,3, pM);
269     vtkMath::Subtract(pM,pC,pM2);
270     vtkMath::Cross(pM1,pM2,pM);
271     n2[0] = pM[0];
272     n2[1] = pM[1];
273     n2[2] = pM[2];
274
275     wsp->GetCollectionPoint(0,3, pM);
276     vtkMath::Subtract(pM,pC,pM1);
277     wsp->GetCollectionPoint(2,3, pM);
278     vtkMath::Subtract(pM,pC,pM2);
279     vtkMath::Cross(pM1,pM2,pM);
280     n2[0] = n2[0] + pM[0];
281     n2[1] = n2[1] + pM[1];
282     n2[2] = n2[2] + pM[2];
283
284     wsp->GetCollectionPoint(2,3, pM);
285     vtkMath::Subtract(pM,pC,pM1);
286     wsp->GetCollectionPoint(2,0, pM);
287     vtkMath::Subtract(pM,pC,pM2);
288     vtkMath::Cross(pM1,pM2,pM);
289     n2[0] = n2[0] + pM[0];
290     n2[1] = n2[1] + pM[1];
291     n2[2] = n2[2] + pM[2];
292     
293     wsp->GetCollectionPoint(2,0, pM);
294     vtkMath::Subtract(pM,pC,pM1);
295     wsp->GetCollectionPoint(0,0, pM);
296     vtkMath::Subtract(pM,pC,pM2);
297     vtkMath::Cross(pM1,pM2,pM);
298     n2[0] = n2[0] + pM[0];
299     n2[1] = n2[1] + pM[1];
300     n2[2] = n2[2] + pM[2];
301     
302     n2[0] = n2[0] / 4;
303     n2[1] = n2[1] / 4;
304     n2[2] = n2[2] / 4;
305     
306 //        3. Calcular el angulo entre V1 y V2
307     double angle = vtkMath::AngleBetweenVectors(n1,n2) * 180 / vtkMath::Pi();
308 //        4. Si el angulo es major de 90 Invertir las normales de la superficie actual
309     if (angle<90)
310     {
311         wsp->InvertLstPoints_();
312     } // if angle
313     
314     // --- Finish ---
315     wsp->SetOutputBox();
316     wsp->UndoRedo_SaveCollection();
317 }
318
319
320
321 //=====
322 // Before editing this file, make sure it's a file of your own (i.e.: it wasn't generated from xml description; if so : your modifications will be lost)
323 //===== 
324 void ShowNPoints_Tools::Process()
325 {
326
327 // THE MAIN PROCESSING METHOD BODY
328 //   Here we simply set the input 'In' value to the output 'Out'
329 //   And print out the output value
330 // INPUT/OUTPUT ACCESSORS ARE OF THE FORM :
331 //    void bbSet{Input|Output}NAME(const TYPE&)
332 //    const TYPE& bbGet{Input|Output}NAME() const 
333 //    Where :
334 //    * NAME is the name of the input/output
335 //      (the one provided in the attribute 'name' of the tag 'input')
336 //    * TYPE is the C++ type of the input/output
337 //      (the one provided in the attribute 'type' of the tag 'input')
338
339 //    bbSetOutputOut( bbGetInputIn() );
340 //    std::cout << "Output value = " <<bbGetOutputOut() << std::endl;
341
342     if (bbGetInputWidgetShowNPoints()!=NULL)
343     {
344         if (bbGetInputType()==1)
345         {
346             bbGetInputWidgetShowNPoints()->OnAutoAddPoints_tool();
347         } // if Type
348
349         if (bbGetInputType()==5)
350         {
351             bbGetInputWidgetShowNPoints()->OnAddPoint_();
352         } // if Type
353         if (bbGetInputType()==10)
354         {
355             bbGetInputWidgetShowNPoints()->OnInsertPoint_();
356         } // if Type
357         if (bbGetInputType()==20)
358         {
359             bbGetInputWidgetShowNPoints()->OnTrackPoint_tool();
360         } // if Type
361         if (bbGetInputType()==30)
362         {
363             bbGetInputWidgetShowNPoints()->OnSetPoint_();
364         } // if Type
365         if (bbGetInputType()==40)
366         {
367             bbGetInputWidgetShowNPoints()->OnErasePoint_();
368         } // if Type
369         if (bbGetInputType()==50)
370         {
371             bbGetInputWidgetShowNPoints()->OnDeleteAllPoints_();
372         } // if Type
373         if (bbGetInputType()==100)
374         {
375             bbGetInputWidgetShowNPoints()->OnInsertCollectionAfter_();
376         } // if Type
377         if (bbGetInputType()==110)
378         {
379             bbGetInputWidgetShowNPoints()->OnDeleteCollection_();
380         } // if Type
381         if (bbGetInputType()==120)
382         {
383             bbGetInputWidgetShowNPoints()->OnResetCollections_();
384         } // if Type
385         if (bbGetInputType()==190)
386         {
387             CreatePatch_3points();
388         } // if Type
389         if (bbGetInputType()==200)
390         {
391             CreatePatch_4points();
392         } // if Type
393         if (bbGetInputType()==210)
394         {
395             bbGetInputWidgetShowNPoints()->OnInvertLstPoints_();
396         } // if Type
397     } // if bbGetInputWidgetShowNPoints
398 }
399 //===== 
400 // Before editing this file, make sure it's a file of your own (i.e.: it wasn't generated from xml description; if so : your modifications will be lost)
401 //===== 
402 void ShowNPoints_Tools::bbUserSetDefaultValues()
403 {
404 //  SET HERE THE DEFAULT INPUT/OUTPUT VALUES OF YOUR BOX 
405 //    Here we initialize the input 'In' to 0
406    bbSetInputType(0);
407    bbSetInputMesh(NULL);
408    bbSetInputWidgetShowNPoints(NULL);
409     
410     std::vector<double> spc;
411     spc.push_back(1);
412     spc.push_back(1);
413     spc.push_back(1);
414     bbSetInputSpacing(spc);
415 }
416 //===== 
417 // Before editing this file, make sure it's a file of your own (i.e.: it wasn't generated from xml description; if so : your modifications will be lost)
418 //===== 
419 void ShowNPoints_Tools::bbUserInitializeProcessing()
420 {
421 //  THE INITIALIZATION METHOD BODY :
422 //    Here does nothing 
423 //    but this is where you should allocate the internal/output pointers 
424 //    if any
425 }
426 //===== 
427 // Before editing this file, make sure it's a file of your own (i.e.: it wasn't generated from xml description; if so : your modifications will be lost)
428 //===== 
429 void ShowNPoints_Tools::bbUserFinalizeProcessing()
430 {
431 //  THE FINALIZATION METHOD BODY :
432 //    Here does nothing 
433 //    but this is where you should desallocate the internal/output pointers 
434 //    if any
435 }
436
437 } // EO namespace bbcreaMaracasVisu
438
439