ViewVC Help
View File | Revision Log | Show Annotations | View Changeset | Root Listing
root/REPOS_ERICCA/magic/lib/mailleur/src/mailleur2d_optimisation.cpp
Revision: 1189
Committed: Tue Feb 4 17:26:49 2025 UTC (3 months ago) by francois
File size: 21141 byte(s)
Log Message:
Version 5.0 de MAGIC. Integration de ALGLIB pour faire de l'optimisation. ALGLIB se download automatiquement en executant un script dans le repertoire config update_magic.bash


File Contents

# User Rev Content
1 francois 1158 //####//------------------------------------------------------------
2     //####//------------------------------------------------------------
3     //####// MAGiC
4     //####// Jean Christophe Cuilliere et Vincent FRANCOIS
5     //####// Departement de Genie Mecanique - UQTR
6     //####//------------------------------------------------------------
7     //####// MAGIC est un projet de recherche de l equipe ERICCA
8     //####// du departement de genie mecanique de l Universite du Quebec a Trois Rivieres
9     //####// http://www.uqtr.ca/ericca
10     //####// http://www.uqtr.ca/
11     //####//------------------------------------------------------------
12     //####//------------------------------------------------------------
13     //####//
14     //####// mailleur2d_optimisation.cpp
15     //####//
16     //####//------------------------------------------------------------
17     //####//------------------------------------------------------------
18     //####// COPYRIGHT 2000-2024
19     //####// jeu 13 jun 2024 11:58:55 EDT
20     //####//------------------------------------------------------------
21     //####//------------------------------------------------------------
22 francois 447 #include "mailleur2d_optimisation.h"
23     #include "m3d_triangle.h"
24     #include "mg_gestionnaire.h"
25     #include "ot_decalage_parametre.h"
26     #include <math.h>
27 francois 696 #include <string.h>
28 francois 447
29    
30 francois 494 MAILLEUR2D_OPTIMISATION::MAILLEUR2D_OPTIMISATION(MG_MAILLAGE* mgmai,int niv):MAILLEUR(false),mg_maillage(mgmai),niveau_optimisation(niv)
31 francois 447 {
32     }
33    
34     MAILLEUR2D_OPTIMISATION::~MAILLEUR2D_OPTIMISATION()
35     {
36     }
37    
38     void MAILLEUR2D_OPTIMISATION::change_niveau_optimisation(int num)
39     {
40     niveau_optimisation=num;
41     }
42    
43     int MAILLEUR2D_OPTIMISATION::get_niveau_optimisation(void)
44     {
45     return niveau_optimisation;
46     }
47    
48 francois 448 void MAILLEUR2D_OPTIMISATION::optimise(MG_VOLUME* mgvolume)
49     {
50     LISTE_MG_TRIANGLE::iterator ittr;
51     TPL_MAP_ENTITE<M3D_TRIANGLE*> lsttrim3d;
52     for (MG_TRIANGLE* tri=mg_maillage->get_premier_triangle(ittr);tri!=NULL;tri=mg_maillage->get_suivant_triangle(ittr))
53     {
54     M3D_TRIANGLE* nvtri=new M3D_TRIANGLE(tri->get_id(),tri->get_lien_topologie(),tri->get_noeud1(),tri->get_noeud2(),tri->get_noeud3(),tri->get_segment1(),tri->get_segment2(),tri->get_segment3(),tri->get_origine());
55     lsttrim3d.ajouter(nvtri);
56     }
57 francois 447
58 francois 448 TPL_MAP_ENTITE<M3D_TRIANGLE*>::ITERATEUR it2;
59 francois 454 TPL_MAP_ENTITE<MG_NOEUD*> liste_noeud;
60 francois 448
61 francois 454
62 francois 448 for (M3D_TRIANGLE* tri=lsttrim3d.get_premier(it2);tri!=NULL;tri=lsttrim3d.get_suivant(it2))
63     {
64     mg_maillage->supprimer_mg_triangleid(tri->get_id());
65 francois 454 mg_maillage->ajouter_mg_triangle(tri);
66     liste_noeud.ajouter(tri->get_noeud1());
67     liste_noeud.ajouter(tri->get_noeud2());
68     liste_noeud.ajouter(tri->get_noeud3());
69 francois 448 }
70    
71     int nbcoquille=mgvolume->get_nb_mg_coquille();
72     for (int i=0;i<nbcoquille;i++)
73     {
74     MG_COQUILLE* coq=mgvolume->get_mg_coquille(i);
75     int nbface=coq->get_nb_mg_coface();
76     for (int j=0;j<nbface;j++)
77     {
78     MG_FACE* face=coq->get_mg_coface(j)->get_face();
79 francois 454 optimise_avec_calcul_uv(face);
80 francois 448 }
81     }
82    
83     }
84    
85 francois 573
86     void MAILLEUR2D_OPTIMISATION::optimise(MG_COQUE* mgcoque)
87     {
88     LISTE_MG_TRIANGLE::iterator ittr;
89     TPL_MAP_ENTITE<M3D_TRIANGLE*> lsttrim3d;
90     for (MG_TRIANGLE* tri=mg_maillage->get_premier_triangle(ittr);tri!=NULL;tri=mg_maillage->get_suivant_triangle(ittr))
91     {
92     M3D_TRIANGLE* nvtri=new M3D_TRIANGLE(tri->get_id(),tri->get_lien_topologie(),tri->get_noeud1(),tri->get_noeud2(),tri->get_noeud3(),tri->get_segment1(),tri->get_segment2(),tri->get_segment3(),tri->get_origine());
93     lsttrim3d.ajouter(nvtri);
94     }
95    
96     TPL_MAP_ENTITE<M3D_TRIANGLE*>::ITERATEUR it2;
97     TPL_MAP_ENTITE<MG_NOEUD*> liste_noeud;
98    
99    
100     for (M3D_TRIANGLE* tri=lsttrim3d.get_premier(it2);tri!=NULL;tri=lsttrim3d.get_suivant(it2))
101     {
102     mg_maillage->supprimer_mg_triangleid(tri->get_id());
103     mg_maillage->ajouter_mg_triangle(tri);
104     liste_noeud.ajouter(tri->get_noeud1());
105     liste_noeud.ajouter(tri->get_noeud2());
106     liste_noeud.ajouter(tri->get_noeud3());
107     }
108    
109     int nbcoquille=mgcoque->get_nb_mg_coquille();
110     for (int i=0;i<nbcoquille;i++)
111     {
112     MG_COQUILLE* coq=mgcoque->get_mg_coquille(i);
113     int nbface=coq->get_nb_mg_coface();
114     for (int j=0;j<nbface;j++)
115     {
116     MG_FACE* face=coq->get_mg_coface(j)->get_face();
117     optimise_avec_calcul_uv(face);
118     }
119     }
120    
121     }
122 francois 454 void MAILLEUR2D_OPTIMISATION::optimise_avec_calcul_uv(MG_FACE* mgface)
123     {
124     TPL_MAP_ENTITE<MG_NOEUD*> liste_noeud;
125     TPL_SET<MG_ELEMENT_MAILLAGE*>::ITERATEUR it;
126     for (MG_TRIANGLE *mgtri=(MG_TRIANGLE*)mgface->get_lien_maillage()->get_premier(it);mgtri!=NULL;mgtri=(MG_TRIANGLE*)mgface->get_lien_maillage()->get_suivant(it))
127     {
128     if (mg_maillage->get_mg_triangleid(mgtri->get_id())!=mgtri) continue;
129     liste_noeud.ajouter(mgtri->get_noeud1());
130     liste_noeud.ajouter(mgtri->get_noeud2());
131     liste_noeud.ajouter(mgtri->get_noeud3());
132     }
133     TPL_MAP_ENTITE<MG_NOEUD*>::ITERATEUR it2;
134     for (MG_NOEUD* no=liste_noeud.get_premier(it2);no!=NULL;no=liste_noeud.get_suivant(it2))
135     {
136     double uv[2];
137     double *xyz=no->get_coord();
138     mgface->inverser(uv,xyz);
139     no->change_u(uv[0]);
140     no->change_v(uv[1]);
141     }
142 sattarpa 644 reinit();
143     optimise(mgface);
144 francois 454 }
145    
146    
147    
148 sattarpa 644 void MAILLEUR2D_OPTIMISATION::reinit(void)
149     {
150 francois 696 lst_tri[0].clear();
151     lst_tri[1].clear();
152     lst_triid[0].clear();
153     lst_triid[1].clear();
154 sattarpa 644 }
155 francois 454
156    
157 francois 696 void MAILLEUR2D_OPTIMISATION::ajouter_ordre_tri(M3D_TRIANGLE* tri,int num)
158     {
159     double val;
160     if (num==0) val=tri->get_qualite();
161     if (num==1) val=1./tri->get_qualite();
162     std::pair<double,M3D_TRIANGLE*> tmp(val,tri);
163     ORDRE_TRIANGLE::iterator p=lst_tri[num].insert(tmp);
164     lst_triid[num][tri->get_id()]=p;
165     }
166 francois 454
167    
168 francois 696 void MAILLEUR2D_OPTIMISATION::supprimer_ordre_tri(M3D_TRIANGLE* tri)
169     {
170     int num=0;
171     ORDRE_TRIANGLE_PARID::iterator it=lst_triid[num].find(tri->get_id());
172     if (it==lst_triid[num].end())
173     {
174     num=1;
175     it=lst_triid[num].find(tri->get_id());
176     }
177     if (it==lst_triid[num].end()) return;
178     lst_tri[num].erase(it->second);
179     lst_triid[num].erase(it);
180     }
181    
182    
183 francois 447 void MAILLEUR2D_OPTIMISATION::optimise(MG_FACE* mgface)
184     {
185 francois 696 periode_u=mgface->get_surface()->get_periode_u();
186     periode_v=mgface->get_surface()->get_periode_v();
187     decalage=new OT_DECALAGE_PARAMETRE(periode_u,periode_v);
188     std::vector<int> strategie;
189     char* code=(char*)param.get_nom("Optimisation_2D").c_str();
190     for (int i=0;i<strlen(code);i++)
191     {
192     if (code[i]=='1') strategie.push_back(1);
193     if (code[i]=='2') strategie.push_back(2);
194     if (code[i]=='3') strategie.push_back(3);
195     if (code[i]=='4') strategie.push_back(4);
196     }
197    
198     int nb_level=strategie.size();
199     std::string info=" stratégie d'optimisation ";
200     for (int level=0;level<nb_level;level++)
201     {
202     char chaine[10];
203     sprintf(chaine,"%d",strategie[level]);
204     info = info + chaine;
205     reinit();
206 francois 447 TPL_SET<MG_ELEMENT_MAILLAGE*>::ITERATEUR it;
207     for (MG_TRIANGLE *mgtri=(MG_TRIANGLE*)mgface->get_lien_maillage()->get_premier(it);mgtri!=NULL;mgtri=(MG_TRIANGLE*)mgface->get_lien_maillage()->get_suivant(it))
208     {
209 francois 448 if (mg_maillage->get_mg_triangleid(mgtri->get_id())!=mgtri) continue;
210 francois 447 M3D_TRIANGLE* mtri=(M3D_TRIANGLE*)mgtri;
211     double qual=OPERATEUR::qualite_triangle(mtri->get_noeud1()->get_coord(),mtri->get_noeud2()->get_coord(),mtri->get_noeud3()->get_coord());
212     mtri->change_qualite(qual);
213     if (mtri->get_qualite()<0.1*niveau_optimisation)
214 francois 696 ajouter_ordre_tri(mtri,0);
215 francois 447 }
216 francois 696
217 francois 447 for (int phase=0;phase<2;phase++)
218     {
219     int ok=0;
220     do
221     {
222 francois 696 ORDRE_TRIANGLE::iterator i=lst_tri[phase].begin();
223     if (i==lst_tri[phase].end())
224 francois 447 {
225     ok=1;
226     continue;
227     }
228     M3D_TRIANGLE* tri=(*i).second;
229 francois 696 supprimer_ordre_tri(tri);
230     switch (strategie[level])
231     {
232     case 1: operateur_bouge_de_point(phase,mgface,tri);
233     break;
234     case 2: operateur_inverse_diagonale(phase,mgface,&tri);
235     break;
236     case 3: operateur_bouge_de_point(phase,mgface,tri);
237     operateur_inverse_diagonale(phase,mgface,&tri);
238     break;
239     case 4: operateur_inverse_diagonale(phase,mgface,&tri);
240     if (tri!=NULL) operateur_bouge_de_point(phase,mgface,tri);
241     break;
242     }
243     if (tri!=NULL)
244 francois 447 if ((tri->get_qualite()<0.1*niveau_optimisation) && (phase==0))
245 francois 696 ajouter_ordre_tri(tri,1);
246 francois 447 }
247     while (ok==0);
248     }
249 francois 696 }
250     affiche((char*)info.c_str());
251 francois 447 delete decalage;
252     }
253    
254 francois 696 int MAILLEUR2D_OPTIMISATION::inverse_diagonale(MG_FACE* face,int num,M3D_TRIANGLE* tri,M3D_TRIANGLE** autretri,double &crit,MG_NOEUD** tabnoeudres)
255     {
256     MG_SEGMENT* seg;
257     MG_NOEUD* no1;
258     MG_NOEUD* no2;
259     MG_NOEUD* no3;
260 francois 791 if (tri->get_origine()==MAGIC::ORIGINE::IMPOSE) return 0;
261 francois 696 if (num==0)
262     {
263     seg=tri->get_segment1();
264     no1=tri->get_noeud1();
265     no2=tri->get_noeud2();
266     no3=tri->get_noeud3();
267     }
268     else if (num==1)
269     {
270     seg=tri->get_segment2();
271     no1=tri->get_noeud2();
272     no2=tri->get_noeud3();
273     no3=tri->get_noeud1();
274     }
275     else if (num==2)
276     {
277     seg=tri->get_segment3();
278     no1=tri->get_noeud3();
279     no2=tri->get_noeud1();
280     no3=tri->get_noeud2();
281     }
282     else return 0;
283     if (seg->get_lien_topologie()!=face) return 0;
284 francois 447
285    
286 francois 696 *autretri=NULL;
287     for (int i=0;i<no1->get_lien_triangle()->get_nb();i++)
288     for (int j=0;j<no2->get_lien_triangle()->get_nb();j++)
289     {
290     MG_TRIANGLE* tri1=no1->get_lien_triangle()->get(i);
291     MG_TRIANGLE* tri2=no2->get_lien_triangle()->get(j);
292     if (tri1==tri2)
293     if (tri1!=tri) *autretri=(M3D_TRIANGLE*)tri1;
294     }
295     if ((*autretri)==NULL) return 0;
296 francois 791 if ((*autretri)->get_origine()==MAGIC::ORIGINE::IMPOSE) return 0;
297 francois 696 MG_NOEUD* no4;
298     if (((*autretri)->get_noeud1()!=no1) && ((*autretri)->get_noeud1()!=no2)) no4=(*autretri)->get_noeud1();
299     if (((*autretri)->get_noeud2()!=no1) && ((*autretri)->get_noeud2()!=no2)) no4=(*autretri)->get_noeud2();
300     if (((*autretri)->get_noeud3()!=no1) && ((*autretri)->get_noeud3()!=no2)) no4=(*autretri)->get_noeud3();
301     double qual1=tri->get_qualite();
302     double qual2=(*autretri)->get_qualite();
303     double qualmin=std::min(qual1,qual2);
304     double nqual1=OPERATEUR::qualite_triangle(no1->get_coord(),no4->get_coord(),no3->get_coord());
305     double nqual2=OPERATEUR::qualite_triangle(no2->get_coord(),no3->get_coord(),no4->get_coord());
306     OT_VECTEUR_3D n1n3(no1->get_coord(),no3->get_coord());
307     OT_VECTEUR_3D n1n4(no1->get_coord(),no4->get_coord());
308     double xyznormal[3];
309     double uv[2]={no1->get_u(),no1->get_v()};
310     face->calcul_normale_unitaire(uv,xyznormal);
311     OT_VECTEUR_3D normalface(xyznormal);
312     OT_VECTEUR_3D normal=normalface&n1n3;
313     normal.norme();
314     n1n4.norme();
315     if (normal*n1n4<0.0001) nqual1=0.;
316     OT_VECTEUR_3D n2n4(no2->get_coord(),no4->get_coord());
317     OT_VECTEUR_3D n2n3(no2->get_coord(),no3->get_coord());
318     double uv2[2]={no2->get_u(),no2->get_v()};
319     face->calcul_normale_unitaire(uv2,xyznormal);
320     OT_VECTEUR_3D normalface2(xyznormal);
321     OT_VECTEUR_3D normal2=normalface&n2n4;
322     normal2.norme();
323     n2n3.norme();
324     if (normal2*n2n3<0.0001) nqual2=0.;
325     double nqualmin=std::min(nqual1,nqual2);
326     if (nqualmin>qualmin)
327     {
328     crit=nqualmin;
329     tabnoeudres[0]=no1;
330     tabnoeudres[1]=no4;
331     tabnoeudres[2]=no3;
332     tabnoeudres[3]=no2;
333     tabnoeudres[4]=no3;
334     tabnoeudres[5]=no4;
335     return 1;
336     }
337     return 0;
338     }
339    
340 francois 447 int MAILLEUR2D_OPTIMISATION::bouge_point(MG_FACE* mgface,MG_NOEUD* mg_noeud,double& crit,double &u,double& v,double& x,double& y, double& z)
341     {
342     if (mg_noeud->get_lien_topologie()!=mgface) return 0;
343 francois 791 if (mg_noeud->get_origine()==MAGIC::ORIGINE::IMPOSE) return 0;
344 francois 447 double du=decalage->calcul_decalage_parametre_u(mg_noeud->get_u());
345     double dv=decalage->calcul_decalage_parametre_v(mg_noeud->get_v());
346     double u1=decalage->decalage_parametre_u(mg_noeud->get_u(),du);
347     double v1=decalage->decalage_parametre_v(mg_noeud->get_v(),dv);
348     double uopt=0.;
349     double vopt=0.;
350     double qual_dep=1.;
351     int nb_tri=mg_noeud->get_lien_triangle()->get_nb();
352     for (int i=0;i<nb_tri;i++)
353     {
354     M3D_TRIANGLE* tri=(M3D_TRIANGLE*)mg_noeud->get_lien_triangle()->get(i);
355     qual_dep=std::min(qual_dep,tri->get_qualite());
356     MG_NOEUD* no1=tri->get_noeud1();
357     MG_NOEUD* no2=tri->get_noeud2();
358     MG_NOEUD* no3=tri->get_noeud3();
359     MG_NOEUD *noeud1,*noeud2;
360     if (no1==mg_noeud)
361     {
362     noeud1=no2;
363     noeud2=no3;
364     }
365     if (no2==mg_noeud)
366     {
367     noeud1=no1;
368     noeud2=no3;
369     }
370     if (no3==mg_noeud)
371     {
372     noeud1=no1;
373     noeud2=no2;
374     }
375     double u2=noeud1->get_u()+du;
376     double v2=noeud1->get_v()+dv;
377     uopt=uopt+u2;
378     vopt=vopt+v2;
379     u2=noeud2->get_u()+du;
380     v2=noeud2->get_v()+dv;
381     uopt=uopt+u2;
382     vopt=vopt+v2;
383     }
384     uopt=uopt/2./nb_tri;
385     vopt=vopt/2./nb_tri;
386    
387     double ddeb=sqrt((u1-uopt)*(u1-uopt)+(v1-vopt)*(v1-vopt));
388     double alpha=0.5;
389     double d=alpha*ddeb;
390     double qual=qual_dep;
391     double testu[8]={1.,-1.,0.,0.,0.707106781,-0.707106781,-0.707106781,0.707106781};
392     double testv[8]={0.,0.,1.,-1.,0.707106781,0.707106781,-0.707106781,-0.707106781};
393     double uu=u1;
394     double vv=v1;
395     while (alpha>0.09)
396     {
397     double qualcoq=0.;
398     for (int nb_essai=0;nb_essai<8;nb_essai++)
399     {
400     double uv[2];
401     double xyz[3];
402     uv[0]=uu+d*testu[nb_essai]-du;
403     uv[1]=vv+d*testv[nb_essai]-dv;
404     int valide1=mgface->valide_parametre_u(uv[0]);
405     int valide2=mgface->valide_parametre_v(uv[1]);
406     if (!((valide1) && (valide2) )) break;
407     mgface->evaluer(uv,xyz);
408     double qual1=1.;
409     for (int i=0;i<nb_tri;i++)
410     {
411     M3D_TRIANGLE* tri=(M3D_TRIANGLE*)mg_noeud->get_lien_triangle()->get(i);
412     MG_NOEUD* no1=tri->get_noeud1();
413     MG_NOEUD* no2=tri->get_noeud2();
414     MG_NOEUD* no3=tri->get_noeud3();
415     double *xyz1=no1->get_coord();
416     double *xyz2=no2->get_coord();
417     double *xyz3=no3->get_coord();
418     if (no1==mg_noeud) xyz1=xyz;
419     if (no2==mg_noeud) xyz2=xyz;
420     if (no3==mg_noeud) xyz3=xyz;
421     double qualtmp=OPERATEUR::qualite_triangle(xyz1,xyz2,xyz3);
422     OT_VECTEUR_3D n1n3(xyz1,xyz3);
423     OT_VECTEUR_3D n1n2(xyz1,xyz2);
424     double xyznormal[3];
425     mgface->calcul_normale_unitaire(uv,xyznormal);
426     OT_VECTEUR_3D normalface(xyznormal);
427     OT_VECTEUR_3D normal=normalface&n1n3;
428     normal.norme();
429     n1n2.norme();
430     if (normal*n1n2<0.0001) qualtmp=0.;
431     if (qualtmp<qual1) qual1=qualtmp;
432     }
433     if (qual1>qualcoq)
434     {
435     qualcoq=qual1;
436     crit=qualcoq;
437     u=uv[0]+du;
438     v=uv[1]+dv;
439     }
440     }
441    
442     if (qualcoq<qual+0.0001) alpha=alpha-0.1;
443     else
444     {
445     qual=qualcoq;
446     uu=u;
447     vv=v;
448     }
449     d=ddeb*alpha;
450    
451     }
452     if (qual>qual_dep)
453     {
454     u=decalage->decalage_parametre_u(u,-du);
455     v=decalage->decalage_parametre_v(v,-dv);
456     double uv[2];
457     uv[0]=u;
458     uv[1]=v;
459     double xyz[3];
460     mgface->evaluer(uv,xyz);
461     x=xyz[0];
462     y=xyz[1];
463     z=xyz[2];
464     return 1;
465     }
466     return 0;
467     }
468 francois 696
469     class M3D_TRIANGLE* MAILLEUR2D_OPTIMISATION::insere_triangle(class MG_FACE* mgface,MG_NOEUD* noeud1,MG_NOEUD* noeud2,MG_NOEUD* noeud3,int origine)
470     {
471     MG_SEGMENT* segment1=mg_maillage->get_mg_segment(noeud1->get_id(),noeud2->get_id());
472 francois 700 MG_SEGMENT* segment2=mg_maillage->get_mg_segment(noeud2->get_id(),noeud3->get_id());
473     MG_SEGMENT* segment3=mg_maillage->get_mg_segment(noeud3->get_id(),noeud1->get_id());
474 francois 696 if (segment1==NULL) segment1=cree_segment(mgface,noeud1,noeud2,origine);
475 francois 700 if (segment2==NULL) segment2=cree_segment(mgface,noeud2,noeud3,origine);
476     if (segment3==NULL) segment3=cree_segment(mgface,noeud3,noeud1,origine);
477 francois 696 M3D_TRIANGLE* tri=cree_triangle(mgface,noeud1,noeud2,noeud3,segment1,segment2,segment3,origine);
478     double qual=OPERATEUR::qualite_triangle(noeud1->get_coord(),noeud2->get_coord(),noeud3->get_coord());
479     tri->change_qualite(qual);
480     return tri;
481     }
482    
483    
484    
485    
486     void MAILLEUR2D_OPTIMISATION::operateur_bouge_de_point(int phase,MG_FACE* mgface,M3D_TRIANGLE* tri)
487     {
488     if (tri->get_qualite()<0.1*niveau_optimisation)
489     {
490     MG_NOEUD* no[3];
491     no[0]=tri->get_noeud1();
492     no[1]=tri->get_noeud2();
493     no[2]=tri->get_noeud3();
494     double crit[3],u[3],v[3],x[3],y[3],z[3];
495     int ierr=bouge_point(mgface,no[0],crit[0],u[0],v[0],x[0],y[0],z[0]);
496     if (ierr==0) crit[0]=0.;
497     ierr=bouge_point(mgface,no[1],crit[1],u[1],v[1],x[1],y[1],z[1]);
498     if (ierr==0) crit[1]=0.;
499     ierr=bouge_point(mgface,no[2],crit[2],u[2],v[2],x[2],y[2],z[2]);
500     if (ierr==0) crit[2]=0.;
501     double critopt=std::max(crit[0],crit[1]);
502     critopt=std::max(critopt,crit[2]);
503     int num=-1;
504     if (critopt>tri->get_qualite())
505     {
506     if (critopt==crit[0]) num=0;
507     if (critopt==crit[1]) num=1;
508     if (critopt==crit[2]) num=2;
509     }
510     if (num!=-1)
511     {
512     no[num]->change_u(u[num]);
513     no[num]->change_v(v[num]);
514     no[num]->change_x(x[num]);
515     no[num]->change_y(y[num]);
516     no[num]->change_z(z[num]);
517     int nb_tri=no[num]->get_lien_triangle()->get_nb();
518     for (int i=0;i<nb_tri;i++)
519     {
520     M3D_TRIANGLE* mtri=(M3D_TRIANGLE*)no[num]->get_lien_triangle()->get(i);
521     double qual=OPERATEUR::qualite_triangle(mtri->get_noeud1()->get_coord(),mtri->get_noeud2()->get_coord(),mtri->get_noeud3()->get_coord());
522     mtri->change_qualite(qual);
523     if (mtri!=tri)
524     {
525     supprimer_ordre_tri(mtri);
526     if (mtri->get_qualite()<0.1*niveau_optimisation) ajouter_ordre_tri(mtri,phase);
527     }
528    
529     }
530     }
531     }
532     }
533    
534    
535     void MAILLEUR2D_OPTIMISATION::operateur_inverse_diagonale(int phase,MG_FACE* mgface,M3D_TRIANGLE** tri)
536     {
537     if ((*tri)->get_qualite()<0.1*niveau_optimisation)
538     {
539     MG_NOEUD* tab1[6];
540     MG_NOEUD* tab2[6];
541     MG_NOEUD* tab3[6];
542     double crit1,crit2,crit3;
543     M3D_TRIANGLE* autretri1;
544     M3D_TRIANGLE* autretri2;
545     M3D_TRIANGLE* autretri3;
546     int ierr1=inverse_diagonale(mgface,0,*tri,&autretri1,crit1,tab1);
547     int ierr2=inverse_diagonale(mgface,1,*tri,&autretri2,crit2,tab2);
548     int ierr3=inverse_diagonale(mgface,2,*tri,&autretri3,crit3,tab3);
549     double maxcrit=std::max(ierr1*crit1,ierr2*crit2);
550     maxcrit=std::max(maxcrit,ierr3*crit3);
551     MG_NOEUD** tab;
552     M3D_TRIANGLE *autretri;
553     if (maxcrit>(*tri)->get_qualite())
554     {
555     if (maxcrit==ierr1*crit1) {tab=tab1;autretri=autretri1;}
556     if (maxcrit==ierr2*crit2) {tab=tab2;autretri=autretri2;}
557     if (maxcrit==ierr3*crit3) {tab=tab3;autretri=autretri3;}
558 francois 791 M3D_TRIANGLE* nvtri1=insere_triangle(mgface,tab[0],tab[1],tab[2],MAGIC::ORIGINE::MAILLEUR_AUTO);
559     M3D_TRIANGLE* nvtri2=insere_triangle(mgface,tab[3],tab[4],tab[5],MAGIC::ORIGINE::MAILLEUR_AUTO);
560 francois 696 if (nvtri1->get_qualite()<0.1*niveau_optimisation) ajouter_ordre_tri(nvtri1,phase);
561     if (nvtri2->get_qualite()<0.1*niveau_optimisation) ajouter_ordre_tri(nvtri2,phase);
562     supprimer_ordre_tri(autretri);
563     mg_maillage->supprimer_mg_triangleid((*tri)->get_id());(*tri)=NULL;
564     mg_maillage->supprimer_mg_triangleid(autretri->get_id());
565     }
566     }
567     }
568     M3D_TRIANGLE* MAILLEUR2D_OPTIMISATION::cree_triangle(class MG_FACE* mgface,MG_NOEUD* noeud1,MG_NOEUD* noeud2,MG_NOEUD* noeud3,MG_SEGMENT* segment1,MG_SEGMENT* segment2,MG_SEGMENT* segment3,int origine)
569     {
570     M3D_TRIANGLE* tri=new M3D_TRIANGLE(mgface,noeud1,noeud2,noeud3,segment1,segment2,segment3,origine);
571     mg_maillage->ajouter_mg_triangle(tri);
572     return tri;
573     }
574    
575    
576    
577     MG_SEGMENT* MAILLEUR2D_OPTIMISATION::cree_segment(class MG_FACE* mgface,MG_NOEUD* noeud1,MG_NOEUD* noeud2,int origine)
578     {
579     MG_SEGMENT* seg=mg_maillage->ajouter_mg_segment(mgface,noeud1,noeud2,origine);
580     seg->change_dimension_topo_null(3);
581     return seg;
582     }