ViewVC Help
View File | Revision Log | Show Annotations | View Changeset | Root Listing
root/REPOS_ERICCA/magic/lib/mailleur/src/mailleur_stl.cpp
Revision: 1082
Committed: Thu Dec 23 21:17:26 2021 UTC (3 years, 4 months ago) by francois
Original Path: magic/lib/mailleur_auto/src/mailleur_stl.cpp
File size: 24246 byte(s)
Log Message:
correction de bug dans le generateur de particule RSA et DCR
+ ajout mailleur_stl (a ameliorer)

File Contents

# User Rev Content
1 francois 1082 #include "mailleur_stl.h"
2     #include "mg_maillage.h"
3     #include "tpl_fonctions_generiques.h"
4     #include "fct_taille.h"
5     #include <tpl_map_entite.h>
6     #include <mg_maillage_outils.h>
7     #include <fct_taille_fem_solution_generateur_gradient.h>
8    
9    
10    
11     MAILLEUR_STL::MAILLEUR_STL(MG_MAILLAGE* maiori, MG_GESTIONNAIRE* gt, FCT_TAILLE* carte,double limite,double angle1,double angle2):MAILLEUR(false),maiin(maiori),gest(gt),metrique(carte),limite_discretisation(limite),angle_arete(angle1),angle_limite(angle2),pas(4),nx(25),ny(25),nz(25),qualmaxaopt(0.5),nbcoucheopt(1)
12     {
13     }
14    
15     MAILLEUR_STL::MAILLEUR_STL(MAILLEUR_STL& mdd):MAILLEUR(mdd),maiin(mdd.maiin),mai(mdd.mai),metrique(mdd.metrique),pas(mdd.pas),angle_arete(mdd.angle_arete),angle_limite(mdd.angle_limite),limite_discretisation(mdd.limite_discretisation),nx(mdd.nx),ny(mdd.ny),nz(mdd.nz),qualmaxaopt(mdd.qualmaxaopt),nbcoucheopt(mdd.nbcoucheopt)
16     {
17     }
18    
19    
20    
21     MAILLEUR_STL::~MAILLEUR_STL()
22     {
23     delete gesttmp;
24     }
25    
26    
27    
28    
29     int MAILLEUR_STL::maille(class MG_GROUPE_TOPOLOGIQUE* mggt)
30     {
31    
32     affiche((char*)" Parametre du mailleur");
33     char mess[255];
34     sprintf(mess,(char*)" Ratio limite de discrétisation = %f",limite_discretisation);
35     affiche(mess);
36     sprintf(mess,(char*)" Ratio limite angle arete = %f",angle_arete);
37     affiche(mess);
38     sprintf(mess,(char*)" Ratio limite angle de la cavité de Delaunay = %f",angle_limite);
39     affiche(mess);
40     affiche((char*)" Duplication du maillage original");
41     //mai=maiin->dupliquer(gest);
42     mai=maiin->detacher(gest);
43     affiche((char*)" Adaptation de la carte de taille");
44     adapte_carte();
45     affiche((char*)" Prepartion de la projection");
46     prepare_projection();
47     affiche((char*)" Determination des arêtes");
48     determine_arete();
49     affiche((char*)" Maillage");
50     cree_maillage();
51     affiche((char*)" Optimisation de maillage");
52     int oldnb=mai->get_nb_mg_triangle();
53     for (int i=0;i<nbcoucheopt;i++)
54     {
55     sprintf(mess," Passe numero %d",i+1);
56     affiche(mess);
57     int nb=optimise_maillage();
58     if ((nb==1)||(nb==oldnb)) i=nbcoucheopt;
59     oldnb=nb;
60     }
61     return OK;
62     }
63    
64     int MAILLEUR_STL::optimise_maillage(void)
65     {
66     std::multimap<double,MG_TRIANGLE*> lsttriaopt;
67     LISTE_MG_TRIANGLE::iterator it;
68     for (MG_TRIANGLE* tri=mai->get_premier_triangle(it);tri!=NULL;tri=mai->get_suivant_triangle(it))
69     {
70     double val=OPERATEUR::qualite_triangle(tri->get_noeud1()->get_coord(),tri->get_noeud2()->get_coord(),tri->get_noeud3()->get_coord());
71     lsttriaopt.insert(std::pair<double,MG_TRIANGLE*>(val,tri));
72     tri->change_solution(val);
73     }
74     int ok=0;
75     int compteur_iter=0;
76     do
77     {
78     compteur_iter++;
79     if (lsttriaopt.begin()->first<qualmaxaopt)
80     {
81     MG_TRIANGLE *tri=lsttriaopt.begin()->second;
82     double crit1,crit2,crit3;
83     double x1,y1,z1;
84     double x2,y2,z2;
85     double x3,y3,z3;
86     int res1=bouge_point(tri->get_noeud1(),crit1,x1,y1,z1);
87     int res2=bouge_point(tri->get_noeud2(),crit2,x2,y2,z2);
88     int res3=bouge_point(tri->get_noeud3(),crit3,x3,y3,z3);
89     double critmax=0;
90     double nvx,nvy,nvz;
91     MG_NOEUD* nno;
92     if (res1==1)
93     if (crit1>critmax)
94     {critmax=crit1;nvx=x1;nvy=y1;nvz=z1;nno=tri->get_noeud1();}
95     if (res2==1)
96     if (crit2>critmax)
97     {critmax=crit2;nvx=x2;nvy=y2;nvz=z2;nno=tri->get_noeud2();}
98     if (res3==1)
99     if (crit3>critmax)
100     {critmax=crit3;nvx=x3;nvy=y3;nvz=z3;nno=tri->get_noeud3();}
101     if (critmax>lsttriaopt.begin()->first)
102     {
103     projete_point_sur_triangulation(nvx,nvy,nvz,nvx,nvy,nvz);
104     nno->change_x(nvx);
105     nno->change_y(nvy);
106     nno->change_z(nvz);
107     for (int i=0;i<nno->get_lien_triangle()->get_nb();i++)
108     {
109     MG_TRIANGLE* tri=nno->get_lien_triangle()->get(i);
110     double *xyz1=tri->get_noeud1()->get_coord();
111     double *xyz2=tri->get_noeud2()->get_coord();
112     double *xyz3=tri->get_noeud3()->get_coord();
113     double val=OPERATEUR::qualite_triangle(xyz1,xyz2,xyz3);
114     std::multimap<double,MG_TRIANGLE*>:: iterator it=lsttriaopt.lower_bound(tri->get_solution());
115     int trouve=0;
116     while (trouve==0)
117     if (it->first>tri->get_solution()) trouve=-1;
118     else if (it->second==tri) trouve=1;
119     else it++;
120     if (trouve==1) lsttriaopt.erase(it);
121     //lsttriaopt.insert(std::pair<double,MG_TRIANGLE*>(val,tri));
122     //tri->change_solution(val);
123     }
124    
125     }
126     else lsttriaopt.erase(lsttriaopt.begin());
127    
128    
129     }
130     else
131     ok=1;
132     }
133     while (ok==0);
134     char chaine[500];
135     sprintf(chaine," %d iterations effectuées",compteur_iter);
136     affiche(chaine);
137     return(compteur_iter);
138     }
139    
140    
141     void MAILLEUR_STL::adapte_carte(void)
142     {
143     LISTE_MG_SEGMENT::iterator it;
144     std::vector<double> lstraf;
145     for (MG_SEGMENT* seg=mai->get_premier_segment(it);seg!=NULL;seg=mai->get_suivant_segment(it))
146     {
147     double val=metrique->calcul_distance_metrique(seg,pas);
148     if (val<1.)
149     {
150     double l=seg->get_longueur()/limite_discretisation/1.01;
151     double *xyz=seg->get_noeud1()->get_coord();
152     lstraf.push_back(xyz[0]);
153     lstraf.push_back(xyz[1]);
154     lstraf.push_back(xyz[2]);
155     lstraf.push_back(l);
156     xyz=seg->get_noeud2()->get_coord();
157     lstraf.push_back(xyz[0]);
158     lstraf.push_back(xyz[1]);
159     lstraf.push_back(xyz[2]);
160     lstraf.push_back(l);
161     }
162     }
163     gesttmp=new MG_GESTIONNAIRE();
164     FCT_TAILLE_FEM_SOLUTION_GENERATEUR_GRADIENT* metriquetmp=new FCT_TAILLE_FEM_SOLUTION_GENERATEUR_GRADIENT(gesttmp,mai,metrique,2,nx,ny,nz,(char*)"carteadapte.sol",lstraf);
165     metriquetmp->construit();
166     metrique2=metrique;
167     metrique=metriquetmp;
168     }
169    
170    
171    
172     void MAILLEUR_STL::prepare_projection()
173     {
174     LISTE_MG_NOEUD::iterator it;
175     MG_NOEUD* no=maiin->get_premier_noeud(it);
176     BOITE_3D boite(no->get_boite_3D());
177     TPL_LISTE_ENTITE<MG_NOEUD*> lstini;
178     for (MG_NOEUD* no=maiin->get_premier_noeud(it);no!=NULL;no=maiin->get_suivant_noeud(it))
179     {
180     boite=no->get_boite_3D()+boite;
181     lstini.ajouter(no);
182     }
183     boite.change_grosseur(1.2);
184     octree.initialiser(&lstini,1,boite.get_xmin(),boite.get_ymin(),boite.get_zmin(),boite.get_xmax(),boite.get_ymax(),boite.get_zmax());
185     LISTE_MG_TRIANGLE::iterator itt;
186     for (MG_TRIANGLE* tri=maiin->get_premier_triangle(itt);tri!=NULL;tri=maiin->get_suivant_triangle(itt))
187     octree.inserer(tri);
188     }
189    
190    
191    
192     void MAILLEUR_STL::determine_arete(void)
193     {
194     LISTE_MG_SEGMENT::iterator it;
195     int nbsegmentarete=0;
196     for (MG_SEGMENT* seg=mai->get_premier_segment(it);seg!=NULL;seg=mai->get_suivant_segment(it))
197     {
198     int nbtri=seg->get_lien_triangle()->get_nb();
199     if (nbtri!=2)
200     {
201     char chaine[500];
202     sprintf(chaine," Maillage STL invalide : segment à %d voisin : noeud 1 %lu noeud 2 %lu ",nbtri,seg->get_noeud1()->get_id(),seg->get_noeud2()->get_id());
203     affiche(chaine);
204     }
205     if (nbtri==2)
206     {
207     MG_TRIANGLE *tri1=seg->get_lien_triangle()->get(0);
208     MG_TRIANGLE *tri2=seg->get_lien_triangle()->get(1);
209     double angle=get_angle_par_noeud<MG_NOEUD*>(tri1->get_noeud1(),tri1->get_noeud2(),tri1->get_noeud3(),tri2->get_noeud1(),tri2->get_noeud2(),tri2->get_noeud3());
210     if ((angle<M_PI-angle_arete) || (angle > M_PI+angle_arete))
211     {
212     seg->change_origine(MAGIC::ORIGINE::TRIANGULATION_ARETEORIGINE);
213     seg->get_noeud1()->change_origine(MAGIC::ORIGINE::TRIANGULATION_ARETEORIGINE);
214     seg->get_noeud2()->change_origine(MAGIC::ORIGINE::TRIANGULATION_ARETEORIGINE);
215     nbsegmentarete++;
216     }
217     ajouter_seg_a_discretiser(seg);
218     }
219     }
220     char mess[255];
221     sprintf(mess,(char*)" Nombre de segments aretes = %d",nbsegmentarete);
222     affiche(mess);
223     }
224    
225    
226     void MAILLEUR_STL::calcul_nouveau_noeud_et_etoile(MG_SEGMENT* seg,double& x, double& y, double& z,OT_VECTEUR_3D &normale, TPL_LISTE_ENTITE<MG_TRIANGLE*> &listuniquetri,std::map<unsigned long,std::pair<MG_SEGMENT*,int> > &lstsegment)
227     {
228     MG_TRIANGLE *tri1=seg->get_lien_triangle()->get(0);
229     MG_TRIANGLE *tri2=seg->get_lien_triangle()->get(1);
230     double xyz1[3],xyz2[3];
231     tri1->normal(xyz1);
232     tri2->normal(xyz2);
233     OT_VECTEUR_3D nor1(xyz1);
234     OT_VECTEUR_3D nor2(xyz2);
235     normale=0.5*nor1+0.5*nor2;
236     MG_NOEUD* no1=seg->get_noeud1();
237     MG_NOEUD* no2=seg->get_noeud2();
238     x=0.5*(no1->get_x()+no2->get_x());
239     y=0.5*(no1->get_y()+no2->get_y());
240     z=0.5*(no1->get_z()+no2->get_z());
241     listuniquetri.ajouter(tri1);
242     listuniquetri.ajouter(tri2);
243     for (int i=0;i<listuniquetri.get_nb();i++)
244     {
245     MG_TRIANGLE* tri=listuniquetri.get(i);
246     for (int cote=1;cote<4;cote++)
247     {
248     MG_TRIANGLE* triv=get_voisin(tri,cote);
249     if (!(listuniquetri.est_dans_la_liste(triv)))
250     if (triv!=NULL)
251     {
252     double xyzv[3];
253     triv->normal(xyzv);
254     OT_VECTEUR_3D norv(xyzv);
255     if (norv*normale>cos(angle_limite))
256     {
257     bool res=respecte_delaunay(x,y,z,triv);
258     if (!res)
259     listuniquetri.ajouter(triv);
260     }
261     }
262     }
263    
264    
265    
266     }
267     for (int i=0;i<listuniquetri.get_nb();i++)
268     {
269     MG_TRIANGLE* tri=listuniquetri.get(i);
270     std::map<unsigned long,std::pair<MG_SEGMENT*,int> >::iterator ptmp;
271     MG_SEGMENT* seg=tri->get_segment1();
272     ptmp=lstsegment.find(seg->get_id());
273     if (ptmp==lstsegment.end()) lstsegment[seg->get_id()]=std::pair<MG_SEGMENT*,int>(seg,1);
274     else ptmp->second.second=ptmp->second.second+1;
275     seg=tri->get_segment2();
276     ptmp=lstsegment.find(seg->get_id());
277     if (ptmp==lstsegment.end()) lstsegment[seg->get_id()]=std::pair<MG_SEGMENT*,int>(seg,1);
278     else ptmp->second.second=ptmp->second.second+1;
279     seg=tri->get_segment3();
280     ptmp=lstsegment.find(seg->get_id());
281     if (ptmp==lstsegment.end()) lstsegment[seg->get_id()]=std::pair<MG_SEGMENT*,int>(seg,1);
282     else ptmp->second.second=ptmp->second.second+1;
283     }
284    
285    
286    
287     projete_point_sur_triangulation(x,y,z,x,y,z);
288    
289    
290     bool convergecoquille;
291    
292     do
293     {
294     convergecoquille=true;
295     TPL_LISTE_ENTITE<MG_SEGMENT*> contour;
296     for (std::map<unsigned long,std::pair<MG_SEGMENT*,int> >::iterator ptmp=lstsegment.begin();ptmp!=lstsegment.end();ptmp++)
297     if (ptmp->second.second==1)
298     {
299     MG_SEGMENT* seg=ptmp->second.first;
300     contour.ajouter(seg);
301     }
302    
303     for (int i=0;i<contour.get_nb();i++)
304     {
305     MG_SEGMENT* seg=contour.get(i);
306     MG_TRIANGLE *triin,*triext;
307     if (listuniquetri.est_dans_la_liste(seg->get_lien_triangle()->get(0)))
308     {
309     triin=seg->get_lien_triangle()->get(0);
310     triext=seg->get_lien_triangle()->get(1);
311     }
312     else
313     {
314     triin=seg->get_lien_triangle()->get(1);
315     triext=seg->get_lien_triangle()->get(0);
316     }
317     MG_NOEUD* no1=seg->get_noeud1();
318     MG_NOEUD* no2=seg->get_noeud2();
319     int sens=-1;
320     if ((triin->get_noeud1()==no1) && (triin->get_noeud2()==no2)) sens=1;
321     if ((triin->get_noeud2()==no1) && (triin->get_noeud3()==no2)) sens=1;
322     if ((triin->get_noeud3()==no1) && (triin->get_noeud1()==no2)) sens=1;
323     double *xyz1,*xyz2;
324     if (sens==-1)
325     {
326     xyz1=no2->get_coord();
327     xyz2=no1->get_coord();
328     }
329     else
330     {
331     xyz1=no1->get_coord();
332     xyz2=no2->get_coord();
333     }
334     double xyz3[3]={x,y,z};
335     OT_VECTEUR_3D vec1(xyz1,xyz2);
336     OT_VECTEUR_3D vec2(xyz1,xyz3);
337     OT_VECTEUR_3D nor=vec1&vec2;
338     nor.norme();
339     double xyzin[3];
340     triin->normal(xyzin);
341     OT_VECTEUR_3D norin(xyzin);
342     if (nor*norin<0.)
343     {
344     affiche("etoile non conforme");
345     listuniquetri.ajouter(triext);
346     std::map<unsigned long,std::pair<MG_SEGMENT*,int> >::iterator ptmp;
347     MG_SEGMENT* seg=triext->get_segment1();
348     ptmp=lstsegment.find(seg->get_id());
349     ptmp=lstsegment.find(seg->get_id());
350     if (ptmp==lstsegment.end()) lstsegment[seg->get_id()]=std::pair<MG_SEGMENT*,int>(seg,1);
351     else ptmp->second.second=ptmp->second.second+1;
352     seg=triext->get_segment2();
353     ptmp=lstsegment.find(seg->get_id());
354     if (ptmp==lstsegment.end()) lstsegment[seg->get_id()]=std::pair<MG_SEGMENT*,int>(seg,1);
355     else ptmp->second.second=ptmp->second.second+1;
356     seg=triext->get_segment3();
357     ptmp=lstsegment.find(seg->get_id());
358     if (ptmp==lstsegment.end()) lstsegment[seg->get_id()]=std::pair<MG_SEGMENT*,int>(seg,1);
359     else ptmp->second.second=ptmp->second.second+1;
360     convergecoquille=false;
361     }
362     }
363     }
364     while (convergecoquille==false);
365    
366     /*
367     MG_SEGMENT* segcourant=contour.get(0);
368     MG_NOEUD* n1=segcourant->get_noeud1();
369     MG_NOEUD* n2=segcourant->get_noeud2();
370     MG_NOEUD* ns;
371     MG_NOEUD* premier=n2;
372    
373     do
374     {
375     MG_SEGMENT* segsuivant=NULL;
376     int i=0;
377     while (segsuivant==NULL)
378     {
379     if (contour.get(i)!=segcourant)
380     if ((contour.get(i)->get_noeud1()==n2) || ((contour.get(i)->get_noeud2()==n2)))
381     {
382     segsuivant=contour.get(i);
383     if (segsuivant->get_noeud1()==n2) ns=segsuivant->get_noeud2(); else ns=segsuivant->get_noeud1();
384     }
385     i++;
386     }
387     OT_VECTEUR_3D vecbase(n1->get_coord(),n2->get_coord());
388     OT_VECTEUR_3D vecsuiv(n2->get_coord(),ns->get_coord());
389     OT_VECTEUR_3D vecori(n1->get_coord(),ns->get_coord());
390     OT_VECTEUR_3D sens(x-0.5*(n1->get_x()+n2->get_x()),y-0.5*(n1->get_y()+n2->get_y()),z-0.5*(n1->get_z()+n2->get_z()));
391     vecbase.norme();
392     vecsuiv.norme();
393     vecori.norme();
394     sens.norme();
395     OT_VECTEUR_3D norm=vecbase&sens;
396     sens=norm&vecbase;
397     double angle=acos((-vecbase)*vecsuiv);
398     double signe=vecori*sens;
399     if (signe<0.) angle=2*M_PI-angle;
400     if (angle>M_PI)
401     affiche("etoile concave");
402     segcourant=segsuivant;
403     n1=n2;
404     n2=ns;
405     }
406     while (n2!=premier);
407     */
408     }
409    
410     int MAILLEUR_STL::bouge_point(MG_NOEUD* mg_noeud,double& crit,double& x,double& y, double& z)
411     {
412     if (mg_noeud->get_origine()==MAGIC::ORIGINE::TRIANGULATION_ARETEORIGINE)
413     return 0;
414     TPL_MAP_ENTITE<MG_NOEUD*> lstnoeud;
415     double critdep=1.;
416     for (int i=0;i<mg_noeud->get_lien_triangle()->get_nb();i++)
417     {
418     MG_TRIANGLE* tri=mg_noeud->get_lien_triangle()->get(i);
419     double val=OPERATEUR::qualite_triangle(tri->get_noeud1()->get_coord(),tri->get_noeud2()->get_coord(),tri->get_noeud3()->get_coord());
420     if (val<critdep) critdep=val;
421     if (tri->get_noeud1()!=mg_noeud) lstnoeud.ajouter(tri->get_noeud1());
422     if (tri->get_noeud2()!=mg_noeud) lstnoeud.ajouter(tri->get_noeud2());
423     if (tri->get_noeud3()!=mg_noeud) lstnoeud.ajouter(tri->get_noeud3());
424     }
425     TPL_MAP_ENTITE<MG_NOEUD*>::ITERATEUR it;
426     double xi=0.;
427     double yi=0.;
428     double zi=0.;
429     for (MG_NOEUD* no=lstnoeud.get_premier(it);no!=NULL;no=lstnoeud.get_suivant(it))
430     {
431     xi=xi+no->get_x();
432     yi=yi+no->get_y();
433     zi=zi+no->get_z();
434     }
435     xi=xi/lstnoeud.get_nb();
436     yi=yi/lstnoeud.get_nb();
437     zi=zi/lstnoeud.get_nb();
438     OT_VECTEUR_3D dir(xi-mg_noeud->get_x(),yi-mg_noeud->get_y(),zi-mg_noeud->get_z());
439     if (dir.get_longueur()<1e-10) return 0;
440     double alpha=0.1;
441     bool converge=false;
442     double critencours=critdep;
443     int passe=0;
444     while (converge==false)
445     {
446     double xyz[3];
447     xyz[0]=mg_noeud->get_x()+alpha*dir.get_x();
448     xyz[1]=mg_noeud->get_y()+alpha*dir.get_y();
449     xyz[2]=mg_noeud->get_z()+alpha*dir.get_z();
450     double critcourant=1.;
451     for (int i=0;i<mg_noeud->get_lien_triangle()->get_nb();i++)
452     {
453     MG_TRIANGLE* tri=mg_noeud->get_lien_triangle()->get(i);
454     double *xyz1=tri->get_noeud1()->get_coord();
455     double *xyz2=tri->get_noeud2()->get_coord();
456     double *xyz3=tri->get_noeud3()->get_coord();
457     if (tri->get_noeud1()==mg_noeud) xyz1=xyz;
458     if (tri->get_noeud2()==mg_noeud) xyz2=xyz;
459     if (tri->get_noeud3()==mg_noeud) xyz3=xyz;
460     double val=OPERATEUR::qualite_triangle(xyz1,xyz2,xyz3);
461     if (val<critcourant) critcourant=val;
462     }
463     if (critencours>critcourant)
464     {
465     converge=true;
466     return passe;
467     }
468     else
469     {
470     alpha=alpha+0.1;
471     x=xyz[0];
472     y=xyz[1];
473     z=xyz[2];
474     critencours=critcourant;
475     crit=critencours;
476     passe=1;
477     }
478    
479     }
480     return 0;
481     }
482    
483     void MAILLEUR_STL::maillage_et_segadiscretiser_update(MG_SEGMENT* segbase,double x, double y, double z, OT_VECTEUR_3D normale,TPL_LISTE_ENTITE<MG_TRIANGLE *>& listuniquetri, std::map<unsigned long, std::pair<MG_SEGMENT *, int> >& lstsegment)
484     {
485     projete_point_sur_triangulation(x,y,z,x,y,z);
486     MG_NOEUD *no=mai->ajouter_mg_noeud(NULL,x,y,z,segbase->get_origine());
487     MG_NOEUD* nobase1=NULL;
488     MG_NOEUD* nobase2=NULL;
489     if (segbase->get_origine()==MAGIC::ORIGINE::TRIANGULATION_ARETEORIGINE)
490     {
491     nobase1=segbase->get_noeud1();
492     nobase2=segbase->get_noeud2();
493     }
494     for (std::map<unsigned long,std::pair<MG_SEGMENT*,int> >::iterator ptmp=lstsegment.begin();ptmp!=lstsegment.end();ptmp++)
495     if (ptmp->second.second==2)
496     supprimer_seg_a_discretiser(ptmp->second.first);
497     for (int i=0;i<listuniquetri.get_nb();i++)
498     {
499     MG_TRIANGLE* tri=listuniquetri.get(i);
500     mai->supprimer_mg_triangleid(tri->get_id());
501     }
502     for (std::map<unsigned long,std::pair<MG_SEGMENT*,int> >::iterator ptmp=lstsegment.begin();ptmp!=lstsegment.end();ptmp++)
503     if (ptmp->second.second==1)
504     {
505     MG_SEGMENT* seg=ptmp->second.first;
506     MG_SEGMENT* mgsegment1=mai->get_mg_segment(seg->get_noeud1()->get_id(),seg->get_noeud2()->get_id());
507     MG_SEGMENT* mgsegment2=mai->get_mg_segment(seg->get_noeud2()->get_id(),no->get_id());
508     MG_SEGMENT* mgsegment3=mai->get_mg_segment(no->get_id(),seg->get_noeud1()->get_id());
509     if (mgsegment1==NULL)
510     {
511     mgsegment1=mai->ajouter_mg_segment(NULL,seg->get_noeud1(),seg->get_noeud2(),MAGIC::ORIGINE::TRIANGULATION);
512     ajouter_seg_a_discretiser(mgsegment1);
513     }
514     if (mgsegment2==NULL)
515     {
516     int origine=MAGIC::ORIGINE::TRIANGULATION;
517     if ((seg->get_noeud2()==nobase1)|| (seg->get_noeud2()==nobase2))
518     origine=MAGIC::ORIGINE::TRIANGULATION_ARETEORIGINE;
519     mgsegment2=mai->ajouter_mg_segment(NULL,seg->get_noeud2(),no,origine);
520     ajouter_seg_a_discretiser(mgsegment2);
521     }
522     if (mgsegment3==NULL)
523     {
524     int origine=MAGIC::ORIGINE::TRIANGULATION;
525     if ((seg->get_noeud1()==nobase1)|| (seg->get_noeud1()==nobase2))
526     origine=MAGIC::ORIGINE::TRIANGULATION_ARETEORIGINE;
527     mgsegment3=mai->ajouter_mg_segment(NULL,no,seg->get_noeud1(),origine);
528     ajouter_seg_a_discretiser(mgsegment3);
529     }
530     MG_TRIANGLE* nvtri=new MG_TRIANGLE(NULL,seg->get_noeud1(),seg->get_noeud2(),no,mgsegment1,mgsegment2,mgsegment3,MAGIC::ORIGINE::TRIANGULATION);
531     mai->ajouter_mg_triangle(nvtri);
532     double xyz[3];
533     nvtri->normal(xyz);
534     OT_VECTEUR_3D nvnor(xyz);
535     if (nvnor*normale<0)
536     nvtri->inverse_sens();
537    
538     MG_TRIANGLE* tri1=get_voisin(nvtri,1);
539     MG_TRIANGLE* tri2=get_voisin(nvtri,2);
540     MG_TRIANGLE* tri3=get_voisin(nvtri,3);
541     double nor[3],nor1[3],nor2[3],nor3[3];
542     nvtri->normal(nor);
543     OT_VECTEUR_3D vnor(nor);
544     if (tri1!=NULL)
545     {
546     tri1->normal(nor1);
547     OT_VECTEUR_3D vnor1(nor1);
548     if (vnor*vnor1<0.)
549    
550     affiche("Triangle retourne v1");
551    
552     }
553     if (tri2!=NULL)
554     {
555     tri2->normal(nor2);
556     OT_VECTEUR_3D vnor2(nor2);
557     if (vnor*vnor2<0.)
558     affiche("Triangle retourne v2");
559     }
560     if (tri3!=NULL)
561     {
562     tri3->normal(nor3);
563     OT_VECTEUR_3D vnor3(nor3);
564     if (vnor*vnor3<0.)
565     affiche("Triangle retourne v3");
566     }
567     }
568     }
569    
570    
571     void MAILLEUR_STL::cree_maillage()
572     {
573     int ok=0;
574     int compteur_iter=0;
575     do
576     {
577     compteur_iter++;
578     if (lstsegadiscretiser.begin()->first>limite_discretisation)
579     {
580     MG_SEGMENT* seg=lstsegadiscretiser.begin()->second;
581     double x,y,z;
582     OT_VECTEUR_3D normale;
583     TPL_LISTE_ENTITE<MG_TRIANGLE*> listtrietoile;
584     std::map<unsigned long,std::pair<MG_SEGMENT*,int> > lstsegmentetoile;
585     calcul_nouveau_noeud_et_etoile(seg,x,y,z,normale,listtrietoile,lstsegmentetoile);
586     maillage_et_segadiscretiser_update(seg,x,y,z,normale,listtrietoile,lstsegmentetoile);
587     }
588     else
589     ok=1;
590     }
591     while (ok==0);
592     char chaine[500];
593     sprintf(chaine," %d iterations effectuées",compteur_iter);
594     affiche(chaine);
595     }
596    
597    
598    
599    
600     bool MAILLEUR_STL::respecte_delaunay(double x, double y, double z, MG_TRIANGLE* tri)
601     {
602     OT_VECTEUR_3D vec1(tri->get_noeud1()->get_coord(),tri->get_noeud2()->get_coord());
603     OT_VECTEUR_3D vec2(tri->get_noeud1()->get_coord(),tri->get_noeud3()->get_coord());
604     OT_VECTEUR_3D vec3=vec1&vec2;
605     vec1.norme();
606     vec3.norme();
607     vec2=vec3&vec1;
608     OT_MATRICE_3D base(vec1,vec2,vec3);
609     OT_MATRICE_3D baset=base.transpose();;
610     OT_VECTEUR_3D pt1(tri->get_noeud1()->get_coord());
611     OT_VECTEUR_3D pt2(tri->get_noeud1()->get_coord(),tri->get_noeud2()->get_coord());
612     OT_VECTEUR_3D pt3(tri->get_noeud1()->get_coord(),tri->get_noeud3()->get_coord());
613     OT_VECTEUR_3D pt1l(0.,0.,0.);
614     OT_VECTEUR_3D pt2l=baset*pt2;
615     OT_VECTEUR_3D pt3l=baset*pt3;
616    
617     OT_VECTEUR_3D colx(pt1l.get_x(),pt2l.get_x(),pt3l.get_x());
618     OT_VECTEUR_3D coly(pt1l.get_y(),pt2l.get_y(),pt3l.get_y());
619     OT_VECTEUR_3D colz(1.,1.,1.);
620     OT_VECTEUR_3D colx2y2(pt1l.get_x()*pt1l.get_x()+pt1l.get_y()*pt1l.get_y(),pt2l.get_x()*pt2l.get_x()+pt2l.get_y()*pt2l.get_y(),pt3l.get_x()*pt3l.get_x()+pt3l.get_y()*pt3l.get_y());
621     OT_MATRICE_3D sys1(colx,coly,colz);
622     double det=2.*sys1.get_determinant();
623     OT_MATRICE_3D sys2(colx2y2,coly,colz);
624     double xcl=sys2.get_determinant()/det;
625     OT_MATRICE_3D sys3(colx2y2,colx,colz);
626     double ycl=-sys3.get_determinant()/det;
627     OT_VECTEUR_3D centrel(xcl,ycl,0.);
628     OT_VECTEUR_3D centre=pt1+base*centrel;
629    
630     OT_VECTEUR_3D r1(centre.get_xyz(),tri->get_noeud1()->get_coord());
631     double rayon=r1.get_longueur();
632     OT_VECTEUR_3D dist(x,y,z);
633     dist=dist-centre;
634     bool rep=true;
635     if (dist.get_longueur()<rayon)
636     rep=false;
637     return rep;
638     }
639    
640    
641    
642     void MAILLEUR_STL::projete_point_sur_triangulation(double x, double y, double z, double& nvx, double& nvy, double& nvz)
643     {
644     double mat[9];
645     double xyz[3]={x,y,z};
646     metrique->evaluer(xyz,mat);
647     double dref=1./sqrt(mat[0]);
648     TPL_MAP_ENTITE<MG_TRIANGLE*> lst;
649     while (lst.get_nb()==0)
650     {
651     octree.rechercher(x,y,z,dref,lst);
652     dref=dref*1.05;
653     }
654     MG_MAILLAGE_OUTILS ot;
655     TPL_MAP_ENTITE<MG_TRIANGLE*>::ITERATEUR it;
656     double dis=1e308;
657     for (MG_TRIANGLE* tri=lst.get_premier(it);tri!=NULL;tri=lst.get_suivant(it))
658     {
659     double xt,yt,zt;
660     ot.projetedansletriangle(tri,x,y,z,xt,yt,zt);
661     OT_VECTEUR_3D vec(x-xt,y-yt,z-zt);
662     double l=vec.get_longueur();
663     if (l<dis)
664     {
665     dis=l;
666     nvx=xt;
667     nvy=yt;
668     nvz=zt;
669     }
670     }
671     }
672    
673    
674    
675     void MAILLEUR_STL::change_angle_arete(double val)
676     {
677     angle_arete=val;
678     }
679    
680    
681     double MAILLEUR_STL::get_angle_arete()
682     {
683     return angle_arete;
684     }
685    
686     MG_TRIANGLE * MAILLEUR_STL::get_voisin(MG_TRIANGLE* tri, int cote)
687     {
688     MG_SEGMENT* seg;
689     if (cote==1) seg=tri->get_segment1();
690     if (cote==2) seg=tri->get_segment2();
691     if (cote==3) seg=tri->get_segment3();
692     if (seg->get_origine()==MAGIC::ORIGINE::TRIANGULATION_ARETEORIGINE) return NULL;
693     if (seg->get_lien_triangle()->get_nb()!=2) return NULL;
694     MG_TRIANGLE* tri1=seg->get_lien_triangle()->get(0);
695     MG_TRIANGLE* tri2=seg->get_lien_triangle()->get(1);
696     if (tri1==tri) return tri2;
697     return tri1;
698     }
699    
700     void MAILLEUR_STL::ajouter_seg_a_discretiser(MG_SEGMENT* seg)
701     {
702     double l=metrique->calcul_distance_metrique(seg,pas);
703     seg->change_distance_metrique(l);
704     lstsegadiscretiser.insert(std::pair<double,MG_SEGMENT*>(l,seg));
705     }
706    
707     void MAILLEUR_STL::supprimer_seg_a_discretiser(MG_SEGMENT* seg)
708     {
709     double l;
710     seg->get_distance_metrique(&l);
711     std::multimap<double,MG_SEGMENT*,std::greater<double > >:: iterator it=lstsegadiscretiser.lower_bound(l);
712     while (it->second!=seg)
713     it++;
714     lstsegadiscretiser.erase(it);
715     }
716    
717     void MAILLEUR_STL::change_pas(int val)
718     {
719     pas=val;
720     }
721    
722     void MAILLEUR_STL::change_nbpasseoptimisation(int nb)
723     {
724     nbcoucheopt=nb;
725     }
726    
727    
728     void MAILLEUR_STL::change_nx(int val)
729     {
730     nx=val;
731     }
732    
733    
734     void MAILLEUR_STL::change_ny(int val)
735     {
736     ny=val;
737     }
738    
739    
740     void MAILLEUR_STL::change_nz(int val)
741     {
742     nz=val;
743     }
744    
745     void MAILLEUR_STL::change_nxnynz(int nvx, int nvy, int nvz)
746     {
747     nx=nvx;
748     ny=nvy;
749     nz=nvz;
750     }
751    
752    
753     void MAILLEUR_STL::change_qualmaxaoptimiser(double val)
754     {
755     qualmaxaopt=val;
756     }