Projet

Général

Profil

Perl script : viewing Herezh meshes in Gmsh » hz_visuMail.pl

version 1.03 (ajout option -disable_A : desactiver les listes de reference d'arêtes) - Julien Troufflard, 19/11/2020 14:22

 
1
#!/usr/bin/env perl
2
use strict;
3
use warnings;
4
use English;
5
use File::Spec::Functions qw(rel2abs);
6
use File::Basename;
7
my $NOM_PROG = basename $PROGRAM_NAME;
8

    
9

    
10
my $VERSION = '1.03';
11
#####################################################################################################
12
#  script pour visualiser un ou plusieurs maillages dans Gmsh                                       #
13
#  version 1.00 : version initiale                                                                  #
14
#                 (version testee sur : MacOSX Darwin, Linux Debian)                                #
15
#  version 1.01 : which du package File::Which n est plus utilise pour verifier l existence         #
16
#                 d une commande (pour eviter une erreur dans le cas ou ce package n est pas        #
17
#                 installe). A la place, on regarde la variable $PATH via la subroutine verif_cmd() #
18
#                 (version testee sur : MacOSX Darwin, Linux Debian, Linux Mint 16)                 #
19
#  version 1.02 : modification de la facon dont le calcul Herezh temporaire est lance de maniere    #
20
#                 a faciliter l arret du programme avec ctrl+c. Le signal ctrl+c est capture via    #
21
#                 $SIG{INT} et le calcul Herezh est lance dans un processus fils fork() pour        #
22
#                 permettre l application de la subroutine pointee par $SIG{INT}                    #
23
#                 ( cette modif permet de stopper l execution du programme dans le cas ou           #
24
#                   l utilisateur n a pas envie d attendre la fin d un calcul Herezh trop long )    #
25
#  version 1.021 : (((rien de special)))                                                            #
26
#                    1) il y a avait un "lectureCommandesVisu" inutile dans le calcul temporaire    #
27
#                       mais qui ne posait pas de souci. Il est supprime par securite               #
28
#                    2) ajout du pragma "use warnings;" et donc en consequence => legere modif de   #
29
#                       la subroutine lecture_mail_her() pour debugger quelques warnings            #
30
#  version 1.022 : ajout de ./ dans l appel system() d execution de Herezh via lien symbolique      #
31
#                  (car dans le cas ou le repertoire courant ne figure pas dans les PATH, ce lien   #
32
#                   symbolique qui est cree dans le repertoire courant n etait pas trouve et donc,  #
33
#                   Herezh n etait pas lance)                                                       #
34
#  version 1.023 : ajout de l option -quit (execution normale du script mais sans lancement de la   #
35
#                  visu gmsh). Typiquement, cette option est utilisee conjointement a -saveVisu, ce #
36
#                  qui permet de generer le fichier de visu, le sauvegarder et quitter              #
37
#  version 1.024 : ajout option -lis_[i] : ajout d un fichier .lis pour le maillage i               #
38
#                  exemple : -lis_2 toto.lis => ajoute les references de toto.lis pour le 2eme      #
39
#                                               maillage                                            #
40
#                  exemple : -lis_3 toto.lis -lis_3 titi.lis => ajoute les references de toto.lis   #
41
#                                                               et titi.lis pour le 3eme maillage   #
42
#  version 1.025 : ajout option -disable_F (desactivation des listes de reference de faces pour     #
43
#                    permettant de mieux voir les numeros d elements dans le cas des elements 2D)   #
44
#  version 1.026 : 1) ajout option -disable_lis_[i] (desactivation du fichier .lis du maillage i;   #
45
#                     ce qui n empeche d utiliser l option -lis_[i] pour activer d autres .lis)     #
46
#                  2) ajout option -wireframe (desactiver la vue des faces des elements 2D et 3D au #
47
#                     demarrage de gmsh)                                                            #
48
#  version 1.027 : ajout option -saveInfo (sauvegarde des fichiers de calcul herezh)                #
49
#  version 1.028 : correction d un bug graphique lie a gmsh en ajoutant 2 points de maniere a       #
50
#                  forcer gmsh a dezoomer au depart (ajout de 2 points Point() = {x,y,z,1} a la fin #
51
#                  du fichier .geo de visualisation)                                                #  
52
#  version 1.029 : modif de la maniere dont on repere les elements axisymetriques au moment du      #
53
#                  choix de la loi de comportement                                                  #
54
#                  changement de place du traitement de l option -saveInfo (deplace avant le        #
55
#                  lancement du calcul)                                                             #
56
#  version 1.03  : ajout option -disable_A (desactivation des listes de reference d aretes pour     #
57
#                    permettant de mieux voir les numeros d elements dans le cas des elements 1D)   #
58
#####################################################################################################
59

    
60

    
61

    
62

    
63
# # # # # # # # # # # # # # # # # # # # # # # # # # # # # # #
64
# VARIABLES QUE L UTILISATEUR PEUT ETRE AMENE A RENSEIGNER  #
65
# # # # # # # # # # # # # # # # # # # # # # # # # # # # # # #
66
#
67
# les variables $exeHZ et $exeGMSH servent a imposer le choix des executables Herezh et Gmsh
68
#   (rq : les alias shell ne fonctionneront pas)
69
#
70
#commande HZ++ definie par l utilisateur (modifiable egalement avec l option -exeHZ)
71
my $exeHZ; # = 'mon_executable_a_moi';
72
#commande gmsh definie par l utilisateur (modifiable egalement avec l option -exeGMSH)
73
my $exeGMSH; # = 'mon_executable_a_moi';
74

    
75

    
76
#commande Herezh par defaut selon la plateforme
77
#  rq : ces variables seront utilisees uniquement si la variable $exeHZ n a pas ete definie
78
my $EXE_HZ_Linux64bits = 'HZppfast64';#linux 64 bits
79
my $EXE_HZ_MacOSX = 'HZppfast_Vn-1';#MacOSX
80
my $EXE_HZ_autres = 'HZppfast';#tous les autres systemes
81
#commande gmsh par defaut (quelque soit la plateforme)
82
#  rq : cette variable sera utilisee uniquement si la variable $exeGMSH n a pas ete definie
83
my $exeGMSH_defaut = 'gmsh';
84

    
85
# # # # # # # # # # # # # # # # # # # # # # # # # # # # # # #
86
# FIN VARIABLES UTILISATEUR                                 #
87
# # # # # # # # # # # # # # # # # # # # # # # # # # # # # # #
88

    
89

    
90

    
91

    
92
sub affichage_aide {
93
  use Text::Wrap;
94
  #config du package Text::Wrap
95
  $Text::Wrap::columns = 81;#le nombre de caracteres maximum par ligne sera egal a ($Text::Wrap::columns - 1) dans le cas ou utilise wrap
96

    
97
  #indentation de longueur $NOM_PROG
98
  my $indent_NOM_PROG = ""; $indent_NOM_PROG .= " " for(1 .. length($NOM_PROG));
99

    
100
  print "----------------------------------------\n";
101
  print " script $NOM_PROG  (version $VERSION)\n";
102
  print "----------------------------------------\n";
103
  print "\n";
104
  print "But : visualiser des maillages Herezh avec Gmsh\n";
105
  print "\n";
106
  print "Usage 1 : mode interactif\n";
107
  print "          > $NOM_PROG\n";
108
  print "Usage 2 : lancement avec arguments\n";
109
  print wrap("          ","            $indent_NOM_PROG ", "> $NOM_PROG [-h|help] [-v] [-exeHZ path_HZ] [-exeGMSH path_GMSH] [-saveVisu] fher_1 [fher_2 .. fher_N]\n");
110
  print "\n";
111
  print "Arguments :\n";
112
  print "     o fic_1   : 1er maillage .her\n";
113
  print "     o [fher_2 .. fher_N] : maillages .her supplementaires eventuels\n";
114
  print "\n";
115
  print "Fonctionnement :\n";
116
  print wrap("      ", "    ", "$NOM_PROG lance un calcul herezh pour creer un fichier .msh ",
117
                               "qui est ensuite visualise dans Gmsh. La visualisation des references est ",
118
                               "desactivee a l ouverture (exceptee la derniere vue qui est specialement ",
119
                               "creee par ce script pour afficher les elements en vue solide) ",
120
                               "Le code couleur pour les references est :\n");
121
  print wrap("          ", "          ", "- reference de noeuds   => rouge\n",
122
                                      "- reference d  aretes   => jaune\n",
123
                                      "- reference de faces    => vert\n",
124
                                      "- reference d  elements => bleu\n",
125
                                      "- reference de points d integration => mauve\n");
126
  print wrap("      ", "    ", "Dans le cas de maillages avec beaucoup d elements, la preparation des fichiers ", 
127
  "peut prendre du temps. Il est alors conseille d utiliser l option -saveVisu pour ",
128
  "conserver les fichiers de visualisation pour pouvoir les reouvrir ulterieurment ",
129
  "sans avoir a reexecuter ce script.\n");
130
  print "\n";
131
  print "Options :\n";
132
  print "    -v : affichage du numero de version\n";
133
  print "\n";
134
  print wrap("    ", "                     ", "-exeHZ path_HZ : choisir l executable Herezh++. Le calcul Herezh se ",
135
                                                               "fera avec l executable path_HZ\n",
136
                                                               "par defaut : linux 64 bits   => path_HZ=HZppfast64\n", 
137
                                                               "             MacOSX (darwin) => path_HZ=HZppfast_Vn-1\n",
138
                                                               "             autres          => path_HZ=HZppfast\n",
139
                                                               "(a noter que les alias shell ne fonctionneront pas)\n",
140
                                                               "(a noter que cette option fonctionne aussi en mode interactif)\n");
141
  print "\n";
142
  print wrap("    ", "                         ", "-exeGMSH path_GMSH : choisir l executable Gmsh. La visualisation Gmsh se ",
143
                                                                       "fera avec l executable path_GMSH\n",
144
                                                                       "par defaut : path_GMSH=gmsh\n",
145
                                                                       "(a noter que les alias shell ne fonctionneront pas)\n",
146
                                                                       "(a noter que cette option fonctionne aussi en mode interactif)\n");
147
  print "\n";
148
  print wrap("    ", "                 ", "-saveVisu : sauvegarde des fichiers .geo et .msh de visu\n");
149
  print "\n";
150
  print wrap("    ", "                 ", "-saveInfo : sauvegarde des fichiers de calcul Herezh++ (.info et .CVisu)\n");
151
  print "\n";
152
  print wrap("    ", "            ", "-quit : executer le script sans lancer la visualisation Gmsh\n");
153
  print "\n";
154
  print wrap("    ", "                     ", "-lis_i fic.lis : ajout de fichiers de listes de reference pour le maillage f_her_i ",
155
                                                               "(cette option peut etre repetee autant de fois que necessaire)\n",
156
                                                               "exemple : $NOM_PROG -lis_1 mon_fic.lis maillage.her\n");
157
  print "\n";
158
  print wrap("    ", "                  ", "-disable_F  : desactiver l affichage des listes de reference de faces\n");
159
  print "\n";
160
  print wrap("    ", "                  ", "-disable_A  : desactiver l affichage des listes de reference d aretes\n");
161
  print "\n";
162
  print wrap("    ", "                  ", "-disable_lis_i  : desactiver le fichier .lis associe au maillage f_her_i \n",
163
                                                               "    exemple : $NOM_PROG -disable_lis_1 maillage.her\n",
164
                                                               "    **remarque : l option -lis_i reste disponible si besoin\n");
165
  print "\n";
166
  print wrap("    ", "                  ", "-wireframe  : desactiver la vue concernant l affichage des faces des elements 2D et 3D\n",
167
                                                               "**remarque : la vue reste disponible si besoin dans la visualition gmsh\n");
168
  print "\n";
169
  print "Exemples :\n";
170
  print wrap("    ", "      ", "o visualiser les maillages mail1.her et mail2.her :\n");
171
  print wrap("        ", "          $indent_NOM_PROG ", "> $NOM_PROG mail1.her mail2.her\n");
172
  print wrap("    ", "      ", "o visualiser le maillage mail1.her en choisissant l executable Herezh :\n");
173
  print wrap("        ", "          $indent_NOM_PROG ", "> $NOM_PROG -exeHZ HZpp_perso mail1.her\n");
174
  print wrap("    ", "      ", "o visualiser le maillage mail1.her et sauvegarder les fichiers de visu :\n");
175
  print wrap("        ", "          $indent_NOM_PROG ", "> $NOM_PROG -saveVisu  mail1.her\n");
176
  print wrap("    ", "      ", "o visualiser le maillage mail1.her en choisissant l executable Herezh et ",
177
                                 "l executable Gmsh (exemple dans le cas ou les executables se trouvent ",
178
                                 "quelque part dans le HOME) :\n");
179
  print wrap("        ", "          $indent_NOM_PROG ", "> $NOM_PROG -exeHZ ~/mon_rep_HZ/HZpp -exeGMSH ~/mon_rep_GMSH/gmsh  mail1.her\n");
180
  print wrap("    ", "      ", "o creer et sauvegarder les fichiers de visualisation sans lancer la visualisation :\n");
181
  print wrap("        ", "          $indent_NOM_PROG ", "> $NOM_PROG -saveVisu -quit  mail1.her\n");
182
  print wrap("    ", "      ", "o creer et sauvegarder les fichiers de calcul .info et .CVisu sans lancer la visualisation :\n");
183
  print wrap("        ", "          $indent_NOM_PROG ", "> $NOM_PROG -saveInfo -quit  mail1.her\n");
184
  print wrap("    ", "      ", "o visualiser 2 maillages en ajoutant 2 fichiers .lis supplementaires pour le 2eme maillage :\n");
185
  print wrap("        ", "          $indent_NOM_PROG ", "> $NOM_PROG -lis_2 ref_sup.lis -lis_2 autres_ref_sup.lis  mail1.her mail2.her\n");
186
  print wrap("    ", "      ", "o visualiser 1 maillage en ajoutant 1 fichier .lis supplementaire et en desactivant le .lis principal :\n");
187
  print wrap("        ", "          $indent_NOM_PROG ", "> $NOM_PROG -lis_1 ref_sup.lis -disable_lis_1 mail1.her\n");
188
  print "\n";
189
  print "Auteur :\n";
190
  print "   TROUFFLARD Julien\n";
191
  print "       julien.troufflard\@univ-ubs.fr\n";
192
  print "       julien.troufflard\@free.fr\n";
193
  print "----------------------------------------\n";
194
}
195

    
196

    
197

    
198
#------------------------------------
199
#option -h ou -help => affichage de l aide et arret
200
#------------------------------------
201
# rq : insensible a la casse
202
foreach my $arg (@ARGV) {
203
  if(($arg =~ /^-h$/i) or ($arg =~ /^-help$/i)) {
204
    affichage_aide();
205
    exit;
206
  }
207
}
208

    
209
#------------------------------------
210
#option -v => affichage de la version et arret
211
#------------------------------------
212
foreach my $arg (@ARGV) {
213
  if($arg eq '-v') {
214
    print "\n $NOM_PROG : version $VERSION\n\n";
215
    exit;
216
  }
217
}
218

    
219

    
220

    
221
#------------------------------------
222
#recuperation des arguments et options
223
#------------------------------------
224
my @liste_fher;#liste des maillages
225
my $is_opt_saveVisu = 0;#indicateur de l option -saveVisu (sauvegarde des fichiers .geo et _Gmsh.msh de visualisation)
226
my $is_opt_saveInfo = 0;#indicateur de l option -saveInfo (sauvegarde des fichiers de calcul Herezh++ (.info et .CVisu))
227
my $is_opt_quit = 0;#indicateur de l option -quit (execution normale du script excepte le fait que la visu Gmsh n est pas lancee)
228
my %FLIS_i;#table des .lis supplementaires indiques par une ou plusieurs options -lis_i
229
           #  fonctionnement de la variable :
230
           #             $FLIS_i{no maillage}{'IS_LIS_SUP'} = 1 ou non defini (sert d indicateur pour savoir si il y a des .lis supplementaires)
231
           #             @{ $FLIC_i{no maillage}{'LISTE'} } = (liste des fichiers .lis supplementaires)
232
my $is_opt_disable_F = 0;#indicateur de l option -disable_F (desactiver l affichage des listes de reference de faces)
233
my $is_opt_disable_A = 0;#indicateur de l option -disable_A (desactiver l affichage des listes de reference d aretes)
234
my @DISABLE_LIS_i;#liste des .lis a activer en fonction du numero du maillage (option -disable_lis_i)
235
my $is_opt_wireframe = 0;#indicateur de l option -wireframe (desactiver la vue des faces des elements 2D et 3D au demarrage de gmsh)
236

    
237

    
238
#on parcourt la liste des arguments (on traite les options connues et on stocke les autres dans @args)
239
my $opt;
240
my @args;
241
while($#ARGV != -1) {
242
  $opt = shift(@ARGV);
243

    
244
  #option -exeHZ
245
  if($opt eq '-exeHZ') {
246
    ($#ARGV >= 0) or die "\nErreur (prog:$NOM_PROG,opt:-exeHZ) : pas assez d arguments donnes pour cette option...\n\n";
247
    $exeHZ = shift(@ARGV);
248
  }
249
  #option -exeGMSH
250
  elsif($opt eq '-exeGMSH') {
251
    ($#ARGV >= 0) or die "\nErreur (prog:$NOM_PROG,opt:-exeGMSH) : pas assez d arguments donnes pour cette option...\n\n";
252
    $exeGMSH = shift(@ARGV);
253
  }
254
  #option -saveVisu
255
  elsif($opt eq '-saveVisu') {
256
    $is_opt_saveVisu = 1;
257
  }
258
  #option -saveInfo
259
  elsif($opt eq '-saveInfo') {
260
    $is_opt_saveInfo = 1;
261
  }
262
  #option -quit
263
  elsif($opt eq '-quit') {
264
    $is_opt_quit = 1;
265
  }
266
  #option -lis_i
267
  elsif($opt =~ /^-lis_(\d+)$/) {
268
    my $no_maillage = $1;
269
    ($#ARGV >= 0) or die "\nErreur (prog:$NOM_PROG,opt:-lis_$no_maillage) : pas assez d arguments donnes pour cette option...\n\n";
270
    my $flis_sup = shift(@ARGV);
271
    (-e $flis_sup) or die "\nErreur (prog:$NOM_PROG,opt:-lis_$no_maillage) : fichier $flis_sup introuvable...\n\n";
272
    #on retranche 1 au numero de maillage car plus loin dans le script, les numeros de maillage commence a 0 (liste de 0 a N-1 maillages)
273
    $no_maillage--;
274
    #indicateur de presence d au moins 1 fichier .lis supplementaire pour le maillage n? $no_maillage
275
    $FLIS_i{$no_maillage}{'IS_LIS_SUP'} = 1;
276
    #ajout du fichier dans la liste
277
    push(@{ $FLIS_i{$no_maillage}{'LISTE'} }, $flis_sup);
278
  }
279
  #option -disable_F
280
  elsif($opt eq '-disable_F') {
281
    $is_opt_disable_F = 1;
282
  }
283
  #option -disable_A
284
  elsif($opt eq '-disable_A') {
285
    $is_opt_disable_A = 1;
286
  }
287
  #option -disable_lis_i
288
  elsif($opt =~ /^-disable_lis_(\d+)$/) {
289
    my $no_maillage = $1;
290
    #on retranche 1 au numero de maillage car plus loin dans le script, les numeros de maillage commence a 0 (liste de 0 a N-1 maillages)
291
    $no_maillage--;
292
    $DISABLE_LIS_i[$no_maillage] = 1;
293
  }
294
  #option -wireframe
295
  elsif($opt eq '-wireframe') {
296
    $is_opt_wireframe = 1;
297
  }
298

    
299
  #cas d une option inconnue
300
  elsif($opt =~ /^-/) {
301
    warn "**Attention : option $opt inconnue (on ignore cette option)...\n";
302
  }
303

    
304
  #autres arguments
305
  else {
306
    push(@args,$opt);
307
  }
308
}#while($#ARGV != -1)
309

    
310

    
311
#---------------------
312
#verif de l executable Herezh
313
#---------------------
314
#si la variable $exeHZ n a pas ete renseigne au prealable => on selectionne l executable par defaut en fonction de la plateforme
315
if(not defined($exeHZ)) {
316
  #- - - - - -
317
  #type de plateforme
318
  #- - - - - -
319
  my $type_OS;
320
  #-avec uname
321
  if(verif_cmd('uname')) {
322
    $type_OS = qx(uname -a);
323
    chomp($type_OS);
324
  }
325
  #-sinon : warning (OS inconnue)
326
  else {warn "**Attention : impossible de saisir le type de systeme d exploitation avec uname -a ...\n";}
327

    
328
  #selection de l executable Herezh
329
  #-linux 64 bits
330
  if($type_OS =~ /linux/i and $type_OS =~ /x86_64/i) {$exeHZ = $EXE_HZ_Linux64bits;}
331
  #-MacOSX (darwin)
332
  elsif($type_OS =~ /darwin/i) {$exeHZ = $EXE_HZ_MacOSX;}
333
  #-tous les autres (y compris linux 32 bits)
334
  else{$exeHZ = $EXE_HZ_autres;}
335
}
336
#verif de l executable Herezh
337
verif_cmd($exeHZ) or die "\n**Erreur (prog:$NOM_PROG) : executable Herezh ($exeHZ) introuvable (pour eviter cette erreur : vous pouvez soit utiliser l option -exeHZ, soit renseigner directement la commande Herezh dans la variable \$exeHZ au debut du script)...\n\n";
338

    
339
#---------------------
340
#verif de l executable Gmsh
341
#---------------------
342
#si la variable $exeGMSH n a pas ete renseigne au prealable => on selectionne l executable par defaut
343
$exeGMSH = $exeGMSH_defaut if(not defined($exeGMSH));
344
#verif de l executable Gmsh
345
verif_cmd($exeGMSH) or die "\n**Erreur (prog:$NOM_PROG) : executable Gmsh ($exeGMSH) introuvable (pour eviter cette erreur : vous pouvez soit utiliser l option -exeGMSH, soit renseigner directement la commande Gmsh dans la variable \$exeGMSH au debut du script)...\n\n";
346

    
347

    
348

    
349

    
350

    
351
#---------------------
352
#liste des maillages (on en profite pour faire des verifs sur la validite du fichier)
353
#---------------------
354
#
355
# la liste @args va servir de liste temporaire pour la saisie des noms de fichier
356
#
357
#cas avec arguments
358
if($#args >= 0) {
359
  #rien a faire pour l instant (la liste @args a deja ete remplie par les arguments)
360
}
361
#cas en mode interactif (on remplit la liste @args avec un menu interactif)
362
else {
363
  print "\nChoix des maillages a visualiser :\n";
364
  print "    (taper liste pour afficher la liste actuelle)\n";
365
  my $choix = -1;
366
  while() {
367
    print "  Donner un nom de maillage (f pour finir) : ";
368
    $choix = <STDIN>; chomp($choix);
369
    next if($choix eq '');#cas ou l utilisateur a tape "Entree"
370

    
371
    #choix f => on arrete la saisie
372
    last if($choix eq 'f');
373

    
374
    if($choix eq 'liste') {
375
      print "  Liste actuelle :\n @args\n\n" if($choix eq 'liste');
376
      next;
377
    }
378

    
379
    push(@args, $choix);
380
  }
381
  print "\n";
382
}
383
#-verif de la validite des maillages
384
foreach my $arg (@args) {
385
  $arg .= '.her' if(not $arg =~ /\.her$/);#rajout de l extension .her si manquante
386
  #existence du fichier
387
  (-e $arg) or do {warn "**Attention : fichier $arg introuvable (on ignore ce fichier)...\n"; next;};
388
  #ouverture du fichier
389
  open(FIC, "<$arg") or do {warn "**Attention : impossible d ouvrir le fichier $arg (on ignore ce fichier)...\n"; next;};
390
  #est-ce un maillage Herezh ? (verif par la presence des mots noeuds et NOEUDS)
391
  my ($is_noeuds, $is_NOEUDS) = (0,0);
392
  while(<FIC>) {
393
    $is_noeuds = 1 if(/^\s*noeuds/o);
394
    $is_NOEUDS = 1 if(/^\s*\d+\s+NOEUDS/o);
395
    last if($is_NOEUDS);
396
  }
397
  close(FIC);
398
  $is_noeuds or do {warn "**Attention : le fichier $arg ne contient pas le mot \"noeuds\" (on ignore ce fichier)...\n"; next;};
399
  $is_NOEUDS or do {warn "**Attention : le fichier $arg ne contient pas le mot \"NOEUDS\" (on ignore ce fichier)...\n"; next;};
400

    
401
  #fichier ok => ajout a la liste
402
  push(@liste_fher, $arg);
403
}
404

    
405
#si a ce stade, la liste des maillages est vide => on arrete le programme
406
($#liste_fher > -1) or die "\nArret du programme car aucun maillage valide n a ete fourni...\n\n";
407

    
408

    
409

    
410
#---------------------
411
#verif des maillages (constitution de la liste des noms de maillage)
412
#---------------------
413
print "  verification des maillages...\n";
414
my @liste_nom_maillage;
415
#-verif 1 : si il y a un seul maillage et qu il n a pas de nom, on indique "premier_maillage" dans la liste des noms de maillages
416
if($#liste_fher == 0) {
417
  my $nom_maillage = '';
418
  open(FIC, "<$liste_fher[0]") or die "\n**Erreur (prog:$NOM_PROG) : impossible d ouvrir le fichier $liste_fher[0] ...\n\n";
419
  while(<FIC>) {
420
    last if(/^\s*noeuds/o);
421
    next if(not /^\s*nom_maillage\s+(\S+)/o);
422
    $nom_maillage = $1;
423
    last;
424
  }
425
  close(FIC);
426
  $nom_maillage = 'premier_maillage' if($nom_maillage eq '');
427
  push(@liste_nom_maillage, $nom_maillage);
428
}
429

    
430
#-verif 2 : si il y a plusieurs maillages, il faut qu il ait chacun un nom_maillage different (sinon arret du programme)
431
if($#liste_fher > 0) {
432
  my $is_maillage_ok = 1;
433
  foreach my $fher (@liste_fher) {
434
    my $nom_maillage = '';
435
    open(FIC, "<$fher") or die "\n**Erreur (prog:$NOM_PROG) : impossible d ouvrir le fichier $fher ...\n\n";;
436
    while(<FIC>) {
437
      next if(not /^\s*nom_maillage\s+(\S+)/o);
438
      $nom_maillage = $1;
439
      last;
440
    }
441
    close(FIC);
442
    push(@liste_nom_maillage, $nom_maillage);
443
  }
444

    
445
  my @maillages_deja_traites; for(my $i=0; $i<=$#liste_nom_maillage; $i++) {$maillages_deja_traites[$i] = 0;}
446
  for(my $i=0; $i<=$#liste_nom_maillage; $i++) {
447
    next if($maillages_deja_traites[$i]);
448

    
449
    #cas d un maillage sans nom
450
    if($liste_nom_maillage[$i] eq '') {
451
      warn "**Erreur (prog:$NOM_PROG) : le maillage $liste_fher[$i] n a pas de nom (nom_maillage non specifie)...\n";
452
      $is_maillage_ok = 0;
453
      next;
454
    }
455

    
456
    #cas d un maillage ayant le meme nom qu un ou plusieurs autres maillages
457
    my @liste_maillages_meme_nom = ();
458
    for(my $j=$i+1; $j<=$#liste_nom_maillage; $j++) {
459
      if($liste_nom_maillage[$i] eq $liste_nom_maillage[$j]) {
460
        $maillages_deja_traites[$j] = 1;
461
        push(@liste_maillages_meme_nom, $liste_fher[$j]);
462
      }
463
    }
464
    if($#liste_maillages_meme_nom > -1) {
465
      warn "**Erreur (prog:$NOM_PROG) : les maillages suivants ont le meme nom => $liste_fher[$i] @liste_maillages_meme_nom\n";
466
      $is_maillage_ok = 0;
467
    }
468
  }
469

    
470
  #arret du programme si on a trouve des maillages sans nom ou des noms utilises plusieurs fois
471
  $is_maillage_ok or die "\nArret du programme a cause d un probleme sur les noms de maillages...\n\n";
472
}
473

    
474

    
475
#---------------------
476
#listes des elements 1D, 2D et 3D (pour affecter des lois de type LOI_RIEN)
477
#  rq : modif version 1.028 => on en profite pour saisir les dimensions max parmi les maillages
478
#---------------------
479
print "  preparation du calcul Herezh...\n";
480
#-prefixes et suffixe pour la reconnaissance des elements 1D, 2D et axisymetriques
481
my @PREFIXE_1D = qw(POUT SEG);
482
my @PREFIXE_2D = qw(TRIA QUAD);
483
my @SUFFIXE_AXI = qw(_AXI);
484

    
485
#coordonnees mini et maxi parmi tous les maillages
486
my ($Xmin,$Xmax) = (1.e90, -1.e90);
487
my ($Ymin,$Ymax) = (1.e90, -1.e90);
488
my ($Zmin,$Zmax) = (1.e90, -1.e90);
489

    
490
#-table de hachage pour definir pour chaque maillage, la liste des elements 1D, 2D, 3D (rq : les elements AXI sont consideres comme 3D car il necessite une loi 3D)
491
my %TAB_DIM_LOI;#@{$TAB_DIM_LOI{indice maillage}{dim loi}} = (liste elements) (par exemple, pour le premier maillage => @{$TAB_DIM_LOI{0}{'3D'}} = (1,5,10)
492

    
493
#on boucle sur les maillages pour constituer les listes d elements par dimension de loi de comportement pour chaque maillage
494
# rq : on en profite pour reperer si il y a au moins 1 element 1D et au moins un element 2D (pour savoir si il faudra renseigner le mot-cle sections et epaisseurs)
495
my $is_elt_1D = 0;#indicateur de la presence d au moins 1 element 1D
496
my $is_elt_2D = 0;#indicateur de la presence d au moins 1 element 2D
497
my $nb_elts_tot = 0;
498
for(my $no_mail=0; $no_mail<=$#liste_fher; $no_mail++) {
499
  #saisie des elements
500
  my ($nb_noeuds, $ref_noeuds, $nb_elts, $ref_elements);
501
  ($_, $nb_noeuds, $ref_noeuds, $nb_elts, $ref_elements) = lecture_mail_her($liste_fher[$no_mail]);
502

    
503
  #dimension max
504
  for(my $i=1; $i<=$nb_noeuds; $i++) {
505
    $Xmin = $ref_noeuds->[$i][0] if($Xmin > $ref_noeuds->[$i][0]);
506
    $Ymin = $ref_noeuds->[$i][1] if($Ymin > $ref_noeuds->[$i][1]);
507
    $Zmin = $ref_noeuds->[$i][2] if($Zmin > $ref_noeuds->[$i][2]);
508
    $Xmax = $ref_noeuds->[$i][0] if($Xmax < $ref_noeuds->[$i][0]);
509
    $Ymax = $ref_noeuds->[$i][1] if($Ymax < $ref_noeuds->[$i][1]);
510
    $Zmax = $ref_noeuds->[$i][2] if($Zmax < $ref_noeuds->[$i][2]);
511
  }
512

    
513
  $nb_elts_tot += $nb_elts;
514
  my @ELEM_1D = ();
515
  my @ELEM_2D = ();
516
  my @ELEM_3D = ();
517
  ELEM:for(my $i=1; $i<=$nb_elts; $i++) {
518
    #verif si element 1D (=> loi LOI_RIEN1D ou LOI_RIEN2D_C si element axisymetrique)
519
    foreach my $prefixe (@PREFIXE_1D) {
520
      if($ref_elements->{$i}{'TYPE'} =~ /^\s*$prefixe/) {
521
        #cas element 1D axisymetrique
522
        foreach my $suffixe (@SUFFIXE_AXI) {
523
          @_ = split(/\s+/, $ref_elements->{$i}{'TYPE'});
524
          if($_[0] =~ /$suffixe\s*$/) {
525
            push(@ELEM_2D, $i);
526
            $is_elt_2D = 1;
527
            next ELEM;
528
          }
529
        }
530
        #cas element 1D classique
531
        push(@ELEM_1D, $i);
532
        $is_elt_1D = 1;
533
        next ELEM;
534
      }
535
    }
536
    #verif si element 2D (=> loi LOI_RIEN2D_C ou LOI_RIEN3D si element axisymetrique)
537
    foreach my $prefixe (@PREFIXE_2D) {
538
      if($ref_elements->{$i}{'TYPE'} =~ /^\s*$prefixe/) {
539
        #cas element 2D axisymetrique
540
        foreach my $suffixe (@SUFFIXE_AXI) {
541
          @_ = split(/\s+/, $ref_elements->{$i}{'TYPE'});
542
          if($_[0] =~ /$suffixe\s*$/) {
543
            push(@ELEM_3D, $i);
544
            next ELEM;
545
          }
546
        }
547
        #cas element 2D classique
548
        push(@ELEM_2D, $i);
549
        $is_elt_2D = 1;
550
        next ELEM;
551
      }
552
    }
553
    #sinon, c est un element 3D (=> loi LOI_RIEN3D )
554
    push(@ELEM_3D, $i);
555
  }#FIN BOUCLE SUR LES ELEMENTS DU MAILLAGE indice $no_mail
556

    
557
  #remplissage de la table pour ce maillage
558
  push(@{$TAB_DIM_LOI{$no_mail}{'1D'}}, @ELEM_1D);
559
  push(@{$TAB_DIM_LOI{$no_mail}{'2D'}}, @ELEM_2D);
560
  push(@{$TAB_DIM_LOI{$no_mail}{'3D'}}, @ELEM_3D);
561

    
562
}#FIN BOUCLE SUR LES MAILLAGES
563

    
564

    
565

    
566
#--------------------
567
#nom des fichiers .info, .CVisu, _Gmsh.msh et .geo temporaires (on s assure qu ils n existent pas deja)
568
#--------------------
569
my $racine_fic_tmp = $NOM_PROG; $racine_fic_tmp =~ s/\.\S+$//;
570
my $no = 0;
571
$racine_fic_tmp .= "_$no";
572
my $finfo = "$racine_fic_tmp.info";#fichier de calcul temporaire
573
my $fCVisu = "$racine_fic_tmp.CVisu";#.CVisu associe
574
my $fGmsh = "$racine_fic_tmp\_Gmsh.msh";#.msh qui va etre cree apres calcul
575
my $fgeo = "$racine_fic_tmp.geo";#.geo qui sera utilise pour lancer la visu
576

    
577
while(-e $finfo or -e $fCVisu or -e $fGmsh or -e $fgeo) {
578
  $no++;
579
  $racine_fic_tmp = $NOM_PROG; $racine_fic_tmp =~ s/\.\S+$//;
580
  $racine_fic_tmp .= "_$no";
581
  $finfo = "$racine_fic_tmp.info";
582
  $fCVisu = "$racine_fic_tmp.CVisu";
583
  $fGmsh = "$racine_fic_tmp\_Gmsh.msh";
584
  $fgeo = "$racine_fic_tmp.geo";
585
}
586
#-memorisation des eventuels fichiers deja existants qui commencent comme le fichier .info (pour ne pas les effacer a la fin du script)
587
my @liste_fic_a_ne_pas_effacer = glob("$racine_fic_tmp*");
588

    
589

    
590
#####################################################################
591
# a partir de maintenant, le signal ctrl+c est recupere et gere par une subroutine pour s assurer d effacer tous les fichiers
592
#   temporaires et de tuer l eventuel processus Herezh si l utilisateur fait un ctrl+c (typiquement pour arreter un calcul Herezh trop long)
593
#####################################################################
594

    
595
#-on reperera le processus Herezh via un nom de lien symbolique genere a partir du PID du processus de ce script Perl $PID (qui sera donc unique a priori)
596
my $HZ_symbolic_link = 'HZppfast_'.$PID.'_hz_visuMail';
597
my $absolute_path_cmd = absolute_path_cmd($exeHZ);
598
#-creation du lien symbolique
599
system("ln -s $absolute_path_cmd $HZ_symbolic_link");
600
#-capture du signal ctrl+c
601
$SIG{INT} = sub {
602
  #kill des processus Herezh (on les repere grace au nom du lien symbolique $HZ_symbolic_link
603
  foreach my $processus (qx(ps -U $ENV{USER} -o pid,%cpu,command | grep $HZ_symbolic_link | grep -v grep)) {
604
    next if(not $processus =~ /^\s*(\d+)/);
605
    kill("TERM", $1);
606
  }
607

    
608
  #destruction des fichiers temporaires
609
  efface_fic_temporaires();
610

    
611
  die "\nArret du programme a cause d un ctrl+c ...\n\n";
612
};
613

    
614

    
615

    
616

    
617
#---------------------
618
#ecriture du .info
619
#---------------------
620
open(FIC, ">$finfo");
621
print FIC "dimension 3\n\n";
622

    
623
print FIC "niveau_commentaire 1\n\n";
624

    
625
#on choisit de lancer le calcul en dynamique_explicite en prevision des maillages a grand nombre de noeuds (plus rapide que non_dynamique pour faire un increment)
626
print FIC "TYPE_DE_CALCUL\ndynamique_explicite\n";
627

    
628
#ecriture des maillages et de references d elements speciales
629
for(my $no_mail=0; $no_mail<=$#liste_fher; $no_mail++) {
630
  my $fher = $liste_fher[$no_mail];
631
  my $flis = $fher; $flis =~ s/.her$/.lis/;
632
  print FIC "\n< $fher\n";
633
  print FIC "< $flis\n" if(-e $flis and not defined $DISABLE_LIS_i[$no_mail]);#inclusion du .lis si il existe (et si l option -disable_lis_i n a pas ete utilisee pour ce maillage)
634
  #ajout de .lis supplementaire si l option -lis_i a ete utilisee
635
  if(defined $FLIS_i{$no_mail}{'IS_LIS_SUP'}) {
636
    print FIC "< $_\n" for @{ $FLIS_i{$no_mail}{'LISTE'} };
637
  }
638
  #set d elements speciaux en fonction de la dimension de la loi de comportement
639
  #  rq : on utilise une subroutine qui ecrit les references avec 15 elements max par ligne (sinon bug Herezh si il y a trop d elements par ligne)
640
  foreach my $dim ('1D', '2D', '3D') {
641
    next if($#{$TAB_DIM_LOI{$no_mail}{$dim}} == -1);#pas d ecriture si aucun element de dimension $dim
642
    ecrire_liste_N_E(*FIC, "E_tmp_visu_elem_$dim", @{$TAB_DIM_LOI{$no_mail}{$dim}});
643
  }
644
}
645

    
646
print FIC "\nchoix_materiaux\n";
647
for(my $no_mail=0; $no_mail<=$#liste_fher; $no_mail++) {
648
  #choix materiau par dimension de loi
649
  foreach my $dim ('1D', '2D', '3D') {
650
    next if($#{$TAB_DIM_LOI{$no_mail}{$dim}} == -1);#pas d ecriture si aucun element de dimension $dim
651
    print FIC "nom_mail= $liste_nom_maillage[$no_mail] E_tmp_visu_elem_$dim MAT$dim\n";
652
  }
653
}
654

    
655
print FIC "\nmateriaux\n";
656
print FIC "MAT1D LOI_RIEN1D\nMAT2D LOI_RIEN2D_C\nMAT3D LOI_RIEN3D\n\n";
657

    
658
print FIC "masse_volumique\n";
659
for(my $no_mail=0; $no_mail<=$#liste_fher; $no_mail++) {
660
  foreach my $dim ('1D', '2D', '3D') {
661
    next if($#{$TAB_DIM_LOI{$no_mail}{$dim}} == -1);#pas d ecriture si aucun element de dimension $dim
662
    print FIC "nom_mail= $liste_nom_maillage[$no_mail] E_tmp_visu_elem_$dim 1.\n";
663
  }
664
}
665

    
666
#sections pour les eventuels elements 1D
667
if($is_elt_1D) {
668
  print FIC "\nsections\n";
669
  for(my $no_mail=0; $no_mail<=$#liste_fher; $no_mail++) {
670
    next if($#{$TAB_DIM_LOI{$no_mail}{'1D'}} == -1);#pas d ecriture si aucun element de dimension $dim
671
    print FIC "nom_mail= $liste_nom_maillage[$no_mail] E_tmp_visu_elem_1D 1.\n";
672
  }
673
}
674

    
675
#epaisseurs pour les eventuels elements 2D
676
if($is_elt_2D) {
677
  print FIC "\nepaisseurs\n";
678
  for(my $no_mail=0; $no_mail<=$#liste_fher; $no_mail++) {
679
    next if($#{$TAB_DIM_LOI{$no_mail}{'2D'}} == -1);#pas d ecriture si aucun element de dimension $dim
680
    print FIC "nom_mail= $liste_nom_maillage[$no_mail] E_tmp_visu_elem_2D 1.\n";
681
  }
682
}
683

    
684
print FIC "\ncharges\n\n";
685
print FIC "blocages\n\n";
686

    
687
#controle => un seul increment
688
print FIC "controle\n";
689
print FIC "DELTAt 1.\n";
690
print FIC "TEMPSFIN 1.\n";
691
print FIC "SAUVEGARDE 0\n";
692
print FIC "MAXINCRE 1\n";
693

    
694
print FIC "\npara_pilotage_equi_global\n\n";
695

    
696
print FIC "para_syteme_lineaire\n\n";
697

    
698
print FIC "para_affichage\nFREQUENCE_SORTIE_FIL_DU_CALCUL 1\n\n";
699

    
700
print FIC "resultats pas_de_sortie_finale_\nCOPIE 0\n\n";
701

    
702
print FIC "_fin_point_info_\n";
703
close(FIC);
704

    
705

    
706
#---------------------
707
#ecriture du .CVisu
708
#---------------------
709
open(FIC, ">$fCVisu");
710
print FIC "
711
debut_fichier_commande_visu
712

    
713
  debut_visualisation_Gmsh
714
    debut_maillage_initial
715
      actif 1
716
      pseudo-homothetie_sur_les_maillages_ 0
717
      visualisation_references_sur_les_maillages_ 1
718
    fin_maillage_initial
719

    
720
    debut_choix_maillage
721
      actif 0
722
      1";
723
for(my $i=1; $i<=$#liste_fher; $i++) {$_ = $i + 1; print FIC " $_";}
724
print FIC " fin_choix_maillage
725
  fin_visualisation_Gmsh
726

    
727
fin_fichier_commande_visu
728
";
729
close(FIC);
730

    
731

    
732

    
733
#---------------------
734
#lancement du calcul
735
#---------------------
736
#cas de l option -saveInfo (sauvegarde des fichiers .info et .CVisu)
737
if($is_opt_saveInfo) {
738
  #on ajoute les fichiers .info et .CVisu a la liste des fichiers a ne pas effacer
739
  push(@liste_fic_a_ne_pas_effacer, $finfo, $fCVisu);
740
  print "\nopt -saveInfo => Les fichiers $finfo et $fCVisu ont ete sauvegardes...\n\n";
741
}
742

    
743
#-on lance le calcul avec redirection dans un fichier .log (au cas ou le calcul a plante => on propose la lecture de ce .log a l utilisateur)
744
my $fredir = "$racine_fic_tmp.log";
745
print "  creation du fichier _Gmsh.msh (calcul Herezh en cours)...\n";
746
system("rm -f $fGmsh $fredir");
747
system("echo \'#\' > $fredir; echo \'#fichier genere suite a l execution du script $NOM_PROG\' >> $fredir; echo \'#\' >> $fredir; echo \'\' >> $fredir");#affichage d un en-tete dans le fichier .log pour indiquer que ce fichier a ete cree lors de l execution de ce script
748
#-lancement de Herezh dans un processus fils pour permettre un ctrl+c a l utilisateur (et donc le traitement de la subroutine pointee par $SIG{INT})
749
my $pid_fils = fork();
750
#---------- processus fils
751
            if($pid_fils == 0) {
752
              system("echo n | ./$HZ_symbolic_link -f $finfo >> $fredir");#on lance avec "echo n" pour repondre automatiquement "non" au cas ou il y a une erreur de calcul Herezh
753
              exit;
754
            }
755
#---------- fin du processus fils
756
#attente de la fin du processus fils par son pere
757
waitpid($pid_fils, 0);
758

    
759

    
760
#cas ou la calcul n a pas fonctionne (si le fichier _Gmsh.msh n a pas ete cree)
761
#  => on propose a l utilisateur de visualiser le .log pour savoir ce qui s est passe
762
if(not -e $fGmsh) {
763
  print "\n**Erreur (prog:$NOM_PROG) : le calcul Herezh++ n a pas fonctionne (le fichier pour Gmsh n a pas ete cree)...\n\n";
764
  my $choix = -1;
765
  while($choix ne 'o' and $choix ne 'n') {
766
    print "  Voulez-vous visualiser l affichage Herezh++ du calcul ? (o/n) ";
767
    $choix = <STDIN>; chomp($choix); $choix = lc($choix);
768
  }
769
  if($choix eq 'o') {
770
    print "  => voir fichier $fredir\n";
771
    #on ajoute le fichier .log a la liste de fichiers a ne pas effacer
772
    push(@liste_fic_a_ne_pas_effacer, $fredir);
773
  }
774

    
775
  #destruction des fichiers temporaires
776
  efface_fic_temporaires();
777

    
778
  #arret du programme
779
  die "\nArret du programme a cause d un probleme d execution Herezh++...\n\n";
780
}
781

    
782

    
783
#---------------------
784
#lecture du .msh et reecriture pour modifier les couleurs selon le type de reference (noeud, arete, face, element)
785
#  et pour saisir la liste des types de reference dans l ordre du fichier .msh pour affecter des options Gmsh suivant le type de reference
786
#---------------------
787

    
788
#on affecte une isovaleur par couleur :
789
#   - 0 => gris    (dedie a l affichage du maillage)
790
#   - 1 => bleu    (dedie a l affichage des refs d  elements)
791
#   - 2 => vert    (dedie a l affichage des refs de faces)
792
#   - 3 => jaune   (dedie a l affichage des refs d  aretes)
793
#   - 4 => rouge   (dedie a l affichage des refs de noeuds)
794
#   - 5 => mauve   (dedie a l affichage des refs de points d integration)
795
my $couleur_RGB_maillage = '{190, 190, 190, 255}';#gris
796
my $couleur_RGB_element  = '{  0,   150, 255, 255}';#bleu
797
my $couleur_RGB_face     = '{  0, 255,   0, 255}';#vert
798
my $couleur_RGB_arete    = '{240, 200,   0, 255}';#jaune
799
my $couleur_RGB_noeud    = '{255,   0,   0, 255}';#rouge
800
my $couleur_RGB_pti      = '{238, 130,   238, 255}';#mauve
801

    
802
#jeu de couleur par type de reference (on utilise les isovaleur gmsh qui vont du bleu fonce au rouge fonce en passant par le vert et le jaune)
803
#  rq : pour donner une idee des couleur, si on fixe les bornes d isovaleur entre [1:4], on a : 1.7=bleu clair, 2.5=vert, 3=>jaune, 3.6=rouge fonce
804
my %table_couleur_type_ref = ('pt_integr'=>5, 'noeud'=>4, 'arete'=>3, 'face'=>2, 'element'=>1);
805

    
806
#on va lister les types de ref
807
my @liste_type_reference;#liste des types de references
808

    
809

    
810

    
811
#cas de l option -disable_A : on suuprime les listes de reference d aretes
812
#if($is_opt_disable_A) {
813
#  print "  opt:-disable_A => suppression des listes d aretes\n";
814
#  suppr_liste_aretes();
815
#}
816

    
817
#cas de l option -disable_F : on suuprime les listes de reference de faces
818
if($is_opt_disable_F) {
819
  print "  opt:-disable_F => suppression des listes de faces\n";
820
  suppr_liste_faces();
821
}
822

    
823
#cas de l option -disable_A : on suuprime les listes de reference d aretes
824
if($is_opt_disable_A) {
825
  print "  opt:-disable_A => suppression des listes d aretes\n";
826
  suppr_liste_aretes();
827
}
828

    
829

    
830

    
831
#fichier temporaire
832
my $ftmp = $fGmsh.rand(9999999); while(-e $ftmp) {$ftmp = $fGmsh.rand(9999999);}
833
open(FIC, "<$fGmsh");
834
open(Ftmp, ">$ftmp");
835
my $is_Element_data = 0;
836
my $couleur_type_ref;
837
print "  modification du fichier _Gmsh.msh...\n";
838
while(my $ligne = <FIC>) {
839

    
840
  #cas d un element data => on le recopie si il s agit d une reference existant reellement dans les maillages (avec la bonne isovaleur suivant le type de reference)
841
  if($ligne =~ /^\s*\$ElementData\s*$/io) {
842
    my $entete = $ligne;
843
    #on lit jusqu au nom de la reference
844
    while($ligne = <FIC>) {
845
      $entete .= $ligne;
846
      last if($ligne =~ /^\s*\"/o);
847
    }
848

    
849
    #selection de l isovaleur en fonction du type de reference
850
    #-ref de noeuds
851
    if($ligne =~ /^\s*\"\s*N(\S+)/o) {
852
      push(@liste_type_reference, 'noeud');
853
      $couleur_type_ref = $table_couleur_type_ref{'noeud'};
854
    }
855
    #-ref d aretes
856
    elsif($ligne =~ /^\s*\"\s*A(\S+)/o) {
857
      push(@liste_type_reference, 'arete');
858
      $couleur_type_ref = $table_couleur_type_ref{'arete'};
859
    }
860
    #-ref de faces
861
    elsif($ligne =~ /^\s*\"\s*F(\S+)/o) {
862
      push(@liste_type_reference, 'face');
863
      $couleur_type_ref = $table_couleur_type_ref{'face'};
864
    }
865
    #-ref d elements
866
    elsif($ligne =~ /^\s*\"\s*E(\S+)/o) {
867
      push(@liste_type_reference, 'element');
868
      $couleur_type_ref = $table_couleur_type_ref{'element'};
869
    }
870
    #-ref de points d integration
871
    elsif($ligne =~ /^\s*\"\s*G(\S+)/o) {
872
      push(@liste_type_reference, 'pt_integr');
873
      $couleur_type_ref = $table_couleur_type_ref{'pt_integr'};
874
    }
875

    
876
    #si le nom est une reference d elements creee par ce script => on ne l ecrit pas, on lit jusqu a la fin de l element data et on supprime cette ref de la liste @liste_type_reference
877
    if($ligne =~ /E_tmp_visu_elem_/o) {
878
      while($ligne = <FIC>) {last if($ligne =~ /^\s*\$EndElementData\s*$/io);}
879
      pop(@liste_type_reference);#suppression du dernier element de la liste
880
    }
881
    #si c est une reference reellement dans le maillage, on recopie l en-tete actuel et on recopie l element data avec l isovaleur
882
    else {
883
      $is_Element_data = 1;
884
      print Ftmp $entete;
885
      while($ligne = <FIC>) {
886
        $ligne = "$1 $couleur_type_ref\n" if ($ligne =~ /^\s*(\d+)\s+\d+\s*$/o);
887
        print Ftmp $ligne;
888
        last if($ligne =~ /^\s*\$EndElementData\s*$/io);
889
      }
890
    }
891
  }#if($ligne =~ /^\s*\$ElementData\s*$/io)
892

    
893
  #cas general : on recopie simplement la ligne courante
894
  else {
895
    print Ftmp $ligne;
896
  }
897
}
898
close(FIC);
899

    
900
#rajout d une ref supplementaire contenant tous les elements pour affichage des faces des elements 2D et 3D (on leur affecte l isovaleur 0, c est a dire couleur gris)
901
#  rq : les elements 1D se retrouvent egalement dans cette ref
902
print Ftmp "\$ElementData
903
1
904
\"Activer/Desactiver vue elements 2D 3D\"
905
0
906
3
907
0
908
1
909
$nb_elts_tot\n";
910
for(my $i=1; $i<=$nb_elts_tot; $i++) {
911
  print Ftmp "$i 0\n";#isovaleur 0
912
}
913
print Ftmp "\$EndElementData\n";
914
close(Ftmp);
915
system("mv -f $ftmp $fGmsh");
916

    
917

    
918

    
919
#---------------------
920
#lancement de la visu Gmsh
921
#---------------------
922
#-on cree un fichier .geo pour y ecrire dans l ordre :
923
#  - des options generales a toutes les vues
924
#  - un Merge du .msh
925
#  - des options au cas par cas par type de reference
926
open(FIC, ">$fgeo");
927

    
928
#variable donnant le nom du fichier .msh
929
print FIC "//nom du fichier .msh\n";
930
print FIC "fichier_msh = \"$fGmsh\";\n\n";
931

    
932
#-options generales
933
print FIC '
934
Geometry.Light = 0;     //desactivation de la lumiere (geometrie)
935
Mesh.Light = 0;         //desactivation de la lumiere (maillage)
936
View.Light = 0;         //desactivation de la lumiere (vue)
937
Mesh.ColorCarousel = 0; //type de couleur (0=by element type, 1=by elementary entity, 2=by physical entity, 3=by partition)
938
Geometry.Points = 0;    //affichage des points (=0 desactiver, =1 activer)
939
Mesh.Points = 0;        //affichage des noeuds (=0 desactiver, =1 activer)
940
Mesh.Lines = 1;         //affichage des lignes (elements 1D) (=0 desactiver, =1 activer)
941
Mesh.SurfaceEdges = 1;  //affichage des aretes des elements 2D (=0 desactiver, =1 activer)
942
Mesh.SurfaceFaces = 0;  //affichage des faces des elements 2D (=0 desactiver, =1 activer)
943
Mesh.VolumeEdges = 1;   //affichage des aretes des elements 3D (=0 desactiver, =1 activer)
944
Mesh.VolumeFaces = 0;   //affichage des faces des elements 3D (=0 desactiver, =1 activer)
945
View.Visible = 0;       //desactivation de toutes les vues au demarrage
946
View.ShowScale = 0;     //desactivation de la vue de l echelle d isovaleur
947
View.RangeType = 2;     //type de bornes des isovaleurs (2=Custom)
948
View.CustomMin = 0;     //borne mini isovaleur (rappel de la convention adoptee pour $NOM_PROG : 0=>maillage, 1=>element, 2=>face, 3=>arete, 4=>noeud, 5=>point integration)
949
View.CustomMax = 5;     //borne maxi isovaleur
950
View.PointType = 1;     //type d affichage des points (1=3D sphere)
951
View.PointSize = 4.;    //taille des points
952
View.LineType = 1;      //type d affichage des lignes (1=3D cylinder)
953
View.LineWidth = 3.;    //taille des lignes
954

    
955
Mesh.PointSize = 3.;   //taille des noeuds
956
Mesh.Color.Points = {0,0,0};          //on met toutes les couleurs des elements en noir pour que les noeuds et les aretes des elements soient en noir
957
Mesh.Color.Lines = {0,0,0};           // la couleur des faces des elements 2D et 3D sera geree par l isovaleur 0 (gris) de la derniere View intitulee : Activer/Desactiver vue elements 2D 3D
958
Mesh.Color.Triangles = {0,0,0};
959
Mesh.Color.Quadrangles = {0,0,0};
960
Mesh.Color.Tetrahedra = {0,0,0};
961
Mesh.Color.Hexahedra = {0,0,0};
962
Mesh.Color.Prisms = {0,0,0};
963
Mesh.Color.Pyramids = {0,0,0};
964
';
965

    
966
#echelle de couleur des isovaleurs
967
print FIC "//couleur isovaleur :  couleur 1 (gris)  => isovaleur=0 (maillage)\n";
968
print FIC "//                     couleur 2 (bleu)  => isovaleur=1 (ref elements)\n";
969
print FIC "//                     couleur 3 (vert)  => isovaleur=2 (ref faces)\n";
970
print FIC "//                     couleur 4 (jaune) => isovaleur=3 (ref aretes)\n";
971
print FIC "//                     couleur 5 (rouge) => isovaleur=4 (ref noeuds)\n";
972
print FIC "//                     couleur 6 (mauve) => isovaleur=5 (ref points integration)\n";
973
#             valeur isovaleur      0                        1                    2                  3                   4                    5
974
print FIC "View.ColorTable = {$couleur_RGB_maillage, $couleur_RGB_element, $couleur_RGB_face, $couleur_RGB_arete, $couleur_RGB_noeud, $couleur_RGB_pti};\n";
975

    
976
#-Merge du fichier .msh (rq : on passe par Sprintf pour utiliser la variable fichier_msh definie au debut)
977
print FIC "\nMerge Sprintf(fichier_msh);\n\n";
978

    
979
#on indique d afficher la vue speciale qui sert a afficher les faces des elements 2D 3D (la derniere qui a ete cree)
980
#  rq : pour cette vue, on remet l affichage classique pour les points et les lignes
981
print FIC "//options speciales pour la derniere vue qui sert a l affichage des faces des elements 2D et 3D\n";
982
my $no_derniere_vue = $#liste_type_reference + 1;#cette vue n est pas enregistree dans la liste, son numero est donc egal a la derniere + 1
983
#gestion option -wireframe (affichage ou non des faces des elements 2D et 3D au demarrage de gmsh)
984
if($is_opt_wireframe) {
985
  print FIC "View[$no_derniere_vue].Visible = 0;\n";
986
}
987
else {
988
  print FIC "View[$no_derniere_vue].Visible = 1;\n";
989
}
990
print FIC "View[$no_derniere_vue].PointType = 0;     //type d affichage des points (0=Color dot)\n";
991
print FIC "View[$no_derniere_vue].PointSize = 3.;    //taille des points\n";
992
print FIC "View[$no_derniere_vue].LineType = 0;		//type d affichage des lignes (0=Color segment)\n";
993
print FIC "View[$no_derniere_vue].LineWidth = 1.; 	//taille des lignes\n";
994
print FIC "View[$no_derniere_vue].Explode = 0.999;   //on reduit legerement la taille de cette vue pour eviter un conflit de couleur quand on affiche des ref de faces ou d elements par dessus\n";
995

    
996

    
997
#modif version 1.028 : ajout de 2 points pour eviter bug graphique
998
print FIC "\n";
999
print FIC "//points pour eviter bug graphique (on aide gmsh a retrouver les dimensions min et max pour eviter l espece de clipping bizarre qu il y a parfois)\n";
1000
$_[0] = $Xmin - 0.01*abs($Xmax-$Xmin);
1001
$_[1] = $Ymin - 0.01*abs($Ymax-$Ymin);
1002
$_[2] = $Zmin - 0.01*abs($Zmax-$Zmin);
1003
print FIC "p = newp; Point(p) = {$_[0],$_[1],$_[2],1};\n";
1004
$_[0] = $Xmax + 0.01*abs($Xmax-$Xmin);
1005
$_[1] = $Ymax + 0.01*abs($Ymax-$Ymin);
1006
$_[2] = $Zmax + 0.01*abs($Zmax-$Zmin);
1007
print FIC "p = newp; Point(p) = {$_[0],$_[1],$_[2],1};\n";
1008

    
1009
close(FIC);
1010

    
1011

    
1012
#lancement de la visualisation (sauf si l option -quit a ete utilisee)
1013
if($is_opt_quit) {
1014
  print "\nopt -quit : pas de visualisation Gmsh...\n\n";
1015
}
1016
else {
1017
  print "  visu Gmsh en cours (via fichiers $fgeo et $fGmsh)...\n";
1018
  system("$exeGMSH $fgeo");
1019
}
1020

    
1021
#cas de l option -saveVisu (sauvegarde des fichiers .geo et _Gmsh.msh)
1022
if($is_opt_saveVisu) {
1023
  #on ajoute les fichiers .geo et _Gmsh.msh a la liste des fichiers a ne pas effacer
1024
  push(@liste_fic_a_ne_pas_effacer, $fgeo, $fGmsh);
1025
  print "\nopt -saveVisu => Les fichiers $fgeo et $fGmsh ont ete sauvegardes...\n\n";
1026
}
1027

    
1028
#destruction des fichiers temporaires
1029
efface_fic_temporaires();
1030

    
1031

    
1032

    
1033

    
1034

    
1035

    
1036
#rq : cette subroutine utilise les variables globales $racine_fic_tmp et @liste_fic_a_ne_pas_effacer
1037
sub efface_fic_temporaires {
1038
  #on transforme la liste des fichiers a ne pas effacer en table d indicateur (liste @liste_fic_a_ne_pas_effacer)
1039
  my %NE_PAS_EFFACER;
1040
  foreach my $fic (@liste_fic_a_ne_pas_effacer) {$NE_PAS_EFFACER{$fic} = 1;}
1041
  #on saisit la liste actuelle des fichiers qui commencent comme le fichier .info
1042
  my @liste_fic_actuelle = glob("$racine_fic_tmp*");
1043
  #on efface seulement ceux qui n ont pas d indicateur %NE_PAS_EFFACER
1044
  foreach my $fic (@liste_fic_actuelle) {
1045
    system("rm -rf $fic") if(not defined($NE_PAS_EFFACER{$fic}));
1046
  }
1047
  #on efface le fichier inutile "ancienNom"
1048
  system("rm -f ancienNom");
1049

    
1050
  #on efface le lien symbolique vers la commande Herezh
1051
  system("rm -f $HZ_symbolic_link");
1052
}
1053

    
1054

    
1055
#surcouche de which pour traiter le cas d une commande en chemin absolu (cas qui apparemment ne marche pas avec la sub which d origine du package File::Which ??!!?!??!!!)
1056
# N EST PLUS UTILISE DEPUIS LA VERSION 1.01 => A LA PLACE, ON UTILISE LA SUB verif_cmd()
1057
##sub which_absolute {
1058
##  use File::Which;
1059
##  my $cmd = shift;
1060
##  my @path;
1061
##  #cas d une commande avec chemin absolu
1062
##  if($cmd =~ /^\// and -x $cmd) {
1063
##    @path = ($cmd);
1064
##  }
1065
##  #commande which classique
1066
##  push(@path, which($cmd));
1067
##  return(@path);
1068
##}
1069

    
1070
#cette subroutine verifie l existence d une commande dans $PATH (remplace l utilisation de which depuis la version 1.01)
1071
sub verif_cmd {
1072
  my $cmd = shift;
1073

    
1074
  #verif directe : est-ce que le fichier existe et est executable
1075
  return 1 if(-x $cmd);
1076

    
1077
  #sinon, on regarde dans les path
1078
  foreach my $path (split(/\s*:\s*/, $ENV{PATH})) {
1079
    return 1 if(-x "$path/$cmd");
1080
  }
1081

    
1082
  #cas ou la commande n existe pas
1083
  return 0;
1084
}
1085

    
1086
#cette subroutine renvoie le chemin absolu vers une commande (renvoie 0 si commande introuvable ou non executable)
1087
#  strategie :
1088
#     1- si la commande commence par "." ou "/" => on renvoie simplement son path absolu
1089
#     2- ensuite, on donne la priorite aux commandes presentes dans $PATH
1090
#      par exemple, si la commande toto.x est presente a la fois dans le repertoire courant et dans le repertoire de $PATH /Users/Dupont/bin :
1091
#                   alors si on passe la commande "toto.x" a cette subroutine, elle va renvoyer le path absolu vers le fichier present dans
1092
#                   /Users/Dupont/bin. Ce qui force l utilisateur a presciser par un "./" si il veut la commande du repertoire courant "./toto.x"
1093
sub absolute_path_cmd {
1094
  my $cmd = shift;
1095

    
1096
  my $absolute_cmd = 0;
1097

    
1098
  #1- commande commence par "." ou "/" => on renvoie simplement son path absolu
1099
  if(($cmd =~ /^\./ or $cmd =~ /^\//) and -e $cmd) {
1100
    $absolute_cmd = rel2abs($cmd);
1101
  }
1102

    
1103
  #2-
1104
    #2-a : d abord dans les $PATH
1105
    foreach my $path (split(/\s*:\s*/, $ENV{PATH})) {
1106
      if(-e "$path/$cmd") {
1107
        $absolute_cmd = rel2abs("$path/$cmd");
1108
        last;
1109
      }
1110
    }
1111
    #2-b : ensuite dans les repertoires hors $PATH
1112
    if(-e $cmd) {
1113
      $absolute_cmd = rel2abs($cmd);
1114
    }
1115

    
1116

    
1117
  if($absolute_cmd ne "0" and not -x $absolute_cmd) {
1118
    warn "**Attention (sub:verif_commande) : la commande $cmd existe ($absolute_cmd) mais le fichier n est pas executable...\n";
1119
    return 0;
1120
  }
1121

    
1122
  return $absolute_cmd;
1123
}#sub absolute_path_cmd
1124

    
1125

    
1126
#ecrire une liste de noeuds ou d elements
1127
#  rq : a priori, si on met trop de noeuds/elements sur une meme ligne, Herezh plante (donc on se limite 15 nombres par ligne)
1128
sub ecrire_liste_N_E {
1129
  my $handle = shift;#le handle de fichier est passe par une variable
1130
  my $nom_liste = shift;
1131
  my @liste_no = @_;#liste des noeuds ou d elements
1132

    
1133
  my $cpt; my $cpt_max = 15; my $nb_blancs;
1134

    
1135
  $nb_blancs = ""; $nb_blancs .= " " for(1 .. length($nom_liste));
1136
  $_ = shift(@liste_no);
1137
  print $handle " $nom_liste $_";
1138
  $cpt = 1;
1139
  foreach my $no (@liste_no) {
1140
    $cpt++;
1141
    if($cpt == 1) {print $handle " $nb_blancs $no";}
1142
    elsif($cpt == $cpt_max) {print $handle " $no\n"; $cpt = 0;}
1143
    else {print $handle " $no";}
1144
  }
1145
  print $handle "\n" if($cpt != $cpt_max);
1146
}#sub ecrire_liste_noeuds
1147

    
1148

    
1149
#----------------
1150
#sub qui lit un maillage herezh++ pour recuperer les noeuds, les elements et les listes de references
1151
#et les renvoier sous forme de reference (lecture du .her et d un .lis si il existe)
1152
#
1153
# exemple d appel :
1154
#  my ($nom_maillage, $nb_noeuds, $ref_tab_noeuds, $nb_elts, $ref_tab_elements, @ref_listes) = lecture_mail_her("fic_her");
1155
#
1156
#  avec - $nom_maillage     : nom du maillage (si il y en a un. sinon $nom_maillage sera egal a undef
1157
#       - $nb_noeuds        : nombre de noeuds (entier)
1158
#       - $ref_tab_noeuds   : reference vers un tableau de noeuds => $ref_tab_noeuds->[no noeud][0] : coordonnee x
1159
#                                                                    $ref_tab_noeuds->[no noeud][1] : coordonnee y
1160
#                                                                    $ref_tab_noeuds->[no noeud][2] : coordonnee z)
1161
#       - $nb_elts          : nombre d elements (entier)
1162
#       - $ref_tab_elements : reference vers une table de hashage => $ref_tab_elements->{no elt}{'TYPE'}      : type d element
1163
#                                                                    @{$ref_tab_elements->{no elt}{'CONNEX'}} : (liste des noeuds)
1164
#       - @ref_listes       : liste de references vers les tables de hashage contenant les listes de references de noeuds, aretes, faces et elements
1165
#                             => $ref_listes[0] : reference vers la table de hashage des listes de noeuds  => @{$ref_listes[0]->{'nom liste'}} : (liste des noeuds)
1166
#                                $ref_listes[1] : reference vers la table de hashage des listes d aretes   => @{$ref_listes[1]->{'nom liste'}} : (liste des aretes)
1167
#                                $ref_listes[2] : reference vers la table de hashage des listes de faces   => @{$ref_listes[2]->{'nom liste'}} : (liste des faces)
1168
#                                $ref_listes[3] : reference vers la table de hashage des listes d elements => @{$ref_listes[3]->{'nom liste'}} : (liste des elements)
1169
#                                $ref_listes[4] : reference vers la table de hashage des listes de points d integration => @{$ref_listes[4]->{'nom liste'}} : (liste des points d integration)
1170
#                                
1171
sub lecture_mail_her {
1172
  my $fher = shift;
1173

    
1174
  my $nom_maillage;
1175

    
1176
  #------------------------
1177
  # lecture du maillage .her
1178
  #------------------------
1179
  #-lecture de noeuds
1180
  my @tab_noeuds; my $nb_noeuds;
1181
  my $no_noeud = 0;
1182
  open(Fher, "<$fher");
1183
  while(<Fher>) {
1184
    if(/^\s*nom_maillage\s+(\S+)/o) {$nom_maillage = $1; next;}
1185
    next if(not /(\d+)\s+NOEUDS/o);
1186
    $nb_noeuds = $1;
1187
    last;
1188
  }
1189
  while(<Fher>) {
1190
    last if($no_noeud == $nb_noeuds);
1191
    next if(not /^\s*(\d+)\s+(\S+)\s+(\S+)\s+(\S+)\s*$/o);
1192
    $no_noeud = $1;
1193
    @{$tab_noeuds[$no_noeud]} = ($2,$3,$4);
1194
  }
1195

    
1196
  #-lecture des elements
1197
  my %tab_elements; my $nb_elts;
1198
  my $no_elt = 0;
1199
  while(<Fher>) {
1200
    next if(not /(\d+)\s+ELEMENTS/o);
1201
    $nb_elts = $1;
1202
    last;
1203
  }
1204
  while(<Fher>) {
1205
    last if($no_elt == $nb_elts);
1206
    next if(not /^\s*\d+\s+\w+\s+\w+/o);
1207
    s/^\s+//;s/\s+$//;
1208
    $_ =~ /^(\d+)\s+/;
1209
    $no_elt = $1; s/^(\d+)\s+//;
1210
    $_ =~ /\s+(\d+(?:\s+\d+)*)$/;
1211
    @{$tab_elements{$no_elt}{'CONNEX'}} = split(/\s+/, $1); s/\s+(\d+(?:\s+\d+)*)$//;
1212
    $tab_elements{$no_elt}{'TYPE'} = $_; $tab_elements{$no_elt}{'TYPE'} =~ s/\s+/ /g;
1213
  }
1214
  close(Fher);
1215

    
1216

    
1217
  #------------------------
1218
  # lecture des references (dans le .her et dans un eventuel .lis)
1219
  #------------------------
1220
  my $flis = $fher; $flis =~ s/.her$/.lis/;
1221
  my $nom_liste;
1222
  my $is_liste_en_cours;
1223
  my %listes_NOEUDS;
1224
  my %listes_ARETES;
1225
  my %listes_FACES;
1226
  my %listes_ELEMENTS;
1227
  my %listes_PTI;
1228

    
1229
  #-dans le .her
1230
  open(Fher, "<$fher");
1231
  $is_liste_en_cours = 0;
1232
  while(<Fher>) {
1233
    chomp;
1234
    if(/^\s*(N\S+)/o) {
1235
      $nom_liste = $1;
1236
      $is_liste_en_cours = 1;
1237
      s/^\s*N\S+\s+//; s/\s+$//;
1238
      push(@{$listes_NOEUDS{$nom_liste}},split(/\s+/,$_));
1239
    }
1240
    elsif(/^\s*noeuds/io or /^\s*elements/i or /^\s*[AFEG]/o) {
1241
      $is_liste_en_cours = 0;
1242
    }
1243
    elsif($is_liste_en_cours and /^\s*\d+(\s+\d+)*\s*$/io) {
1244
      s/^\s+//; s/\s+$//;
1245
      push(@{$listes_NOEUDS{$nom_liste}},split(/\s+/,$_));
1246
    }
1247
  }
1248
  close(Fher);
1249

    
1250
  open(Fher, "<$fher");
1251
  $is_liste_en_cours = 0;
1252
  while(<Fher>) {
1253
    chomp;
1254
    if(/^\s*(A\S+)/o) {
1255
      $nom_liste = $1;
1256
      $is_liste_en_cours = 1;
1257
      s/^\s*A\S+\s+//; s/\s+$//;
1258
      push(@{$listes_ARETES{$nom_liste}},split(/\s+/,$_));
1259
    }
1260
    elsif(/^\s*noeuds/io or /^\s*elements/i or /^\s*[NFEG]/o) {
1261
      $is_liste_en_cours = 0;
1262
    }
1263
    elsif($is_liste_en_cours and /^\s*\d+(\s+\d+)*\s*$/io) {
1264
      s/^\s+//; s/\s+$//;
1265
      push(@{$listes_ARETES{$nom_liste}},split(/\s+/,$_));
1266
    }
1267
  }
1268
  close(Fher);
1269

    
1270
  open(Fher, "<$fher");
1271
  $is_liste_en_cours = 0;
1272
  while(<Fher>) {
1273
    chomp;
1274
    if(/^\s*(F\S+)/) {
1275
      $nom_liste = $1;
1276
      $is_liste_en_cours = 1;
1277
      s/^\s*F\S+\s+//; s/\s+$//;
1278
      push(@{$listes_FACES{$nom_liste}},split(/\s+/,$_));
1279
    }
1280
    elsif(/^\s*noeuds/io or /^\s*elements/i or /^\s*[NAEG]/o) {
1281
      $is_liste_en_cours = 0;
1282
    }
1283
    elsif($is_liste_en_cours and /^\s*\d+(\s+\d+)*\s*$/io) {
1284
      s/^\s+//; s/\s+$//;
1285
      push(@{$listes_FACES{$nom_liste}},split(/\s+/,$_));
1286
    }
1287
  }
1288
  close(Fher);
1289

    
1290
  open(Fher, "<$fher");
1291
  $is_liste_en_cours = 0;
1292
  while(<Fher>) {
1293
    chomp;
1294
    if(/^\s*(E\S+)/o) {
1295
      $nom_liste = $1;
1296
      $is_liste_en_cours = 1;
1297
      s/^\s*E\S+\s+//; s/\s+$//;
1298
      push(@{$listes_ELEMENTS{$nom_liste}},split(/\s+/,$_));
1299
    }
1300
    elsif(/^\s*noeuds/io or /^\s*elements/io or /^\s*[NAFG]/o) {
1301
      $is_liste_en_cours = 0;
1302
    }
1303
    elsif($is_liste_en_cours and /^\s*\d+(\s+\d+)*\s*$/io) {
1304
      s/^\s+//; s/\s+$//;
1305
      push(@{$listes_ELEMENTS{$nom_liste}},split(/\s+/,$_));
1306
    }
1307
  }
1308
  close(Fher);
1309

    
1310
  open(Fher, "<$fher");
1311
  $is_liste_en_cours = 0;
1312
  while(<Fher>) {
1313
    chomp;
1314
    if(/^\s*(G\S+)/o) {
1315
      $nom_liste = $1;
1316
      $is_liste_en_cours = 1;
1317
      s/^\s*G\S+\s+//; s/\s+$//;
1318
      push(@{$listes_PTI{$nom_liste}},split(/\s+/,$_));
1319
    }
1320
    elsif(/^\s*noeuds/io or /^\s*elements/io or /^\s*[NAFE]/o) {
1321
      $is_liste_en_cours = 0;
1322
    }
1323
    elsif($is_liste_en_cours and /^\s*\d+(\s+\d+)*\s*$/io) {
1324
      s/^\s+//; s/\s+$//;
1325
      push(@{$listes_PTI{$nom_liste}},split(/\s+/,$_));
1326
    }
1327
  }
1328
  close(Fher);
1329

    
1330

    
1331
  #dans le .lis (si il existe)
1332
  if(-e $flis) {
1333

    
1334
  open(Flis, "<$flis");
1335
  $is_liste_en_cours = 0;
1336
  while(<Flis>) {
1337
    chomp;
1338
    if(/^\s*(N\S+)/o) {
1339
      $nom_liste = $1;
1340
      $is_liste_en_cours = 1;
1341
      s/^\s*N\S+\s+//; s/\s+$//;
1342
      push(@{$listes_NOEUDS{$nom_liste}},split(/\s+/,$_));
1343
    }
1344
    elsif(/^\s*noeuds/io or /^\s*elements/io or /^\s*[AFEG]/o) {
1345
      $is_liste_en_cours = 0;
1346
    }
1347
    elsif($is_liste_en_cours and /^\s*\d+(\s+\d+)*\s*$/i) {
1348
      s/^\s+//; s/\s+$//;
1349
      push(@{$listes_NOEUDS{$nom_liste}},split(/\s+/,$_));
1350
    }
1351
  }
1352
  close(Flis);
1353

    
1354
  open(Flis, "<$flis");
1355
  $is_liste_en_cours = 0;
1356
  while(<Flis>) {
1357
    chomp;
1358
    if(/^\s*(A\S+)/o) {
1359
      $nom_liste = $1;
1360
      $is_liste_en_cours = 1;
1361
      s/^\s*A\S+\s+//; s/\s+$//;
1362
      push(@{$listes_ARETES{$nom_liste}},split(/\s+/,$_));
1363
    }
1364
    elsif(/^\s*noeuds/io or /^\s*elements/io or /^\s*[NFEG]/o) {
1365
      $is_liste_en_cours = 0;
1366
    }
1367
    elsif($is_liste_en_cours and /^\s*\d+(\s+\d+)*\s*$/io) {
1368
      s/^\s+//; s/\s+$//;
1369
      push(@{$listes_ARETES{$nom_liste}},split(/\s+/,$_));
1370
    }
1371
  }
1372
  close(Flis);
1373

    
1374
  open(Flis, "<$flis");
1375
  $is_liste_en_cours = 0;
1376
  while(<Flis>) {
1377
    chomp;
1378
    if(/^\s*(F\S+)/o) {
1379
      $nom_liste = $1;
1380
      $is_liste_en_cours = 1;
1381
      s/^\s*F\S+\s+//; s/\s+$//;
1382
      push(@{$listes_FACES{$nom_liste}},split(/\s+/,$_));
1383
    }
1384
    elsif(/^\s*noeuds/io or /^\s*elements/io or /^\s*[NAEG]/o) {
1385
      $is_liste_en_cours = 0;
1386
    }
1387
    elsif($is_liste_en_cours and /^\s*\d+(\s+\d+)*\s*$/io) {
1388
      s/^\s+//; s/\s+$//;
1389
      push(@{$listes_FACES{$nom_liste}},split(/\s+/,$_));
1390
    }
1391
  }
1392
  close(Flis);
1393

    
1394
  open(Flis, "<$flis");
1395
  $is_liste_en_cours = 0;
1396
  while(<Flis>) {
1397
    chomp;
1398
    if(/^\s*(E\S+)/o) {
1399
      $nom_liste = $1;
1400
      $is_liste_en_cours = 1;
1401
      s/^\s*E\S+\s+//; s/\s+$//;
1402
      push(@{$listes_ELEMENTS{$nom_liste}},split(/\s+/,$_));
1403
    }
1404
    elsif(/^\s*noeuds/io or /^\s*elements/io or /^\s*[NAFG]/o) {
1405
      $is_liste_en_cours = 0;
1406
    }
1407
    elsif($is_liste_en_cours and /^\s*\d+(\s+\d+)*\s*$/io) {
1408
      s/^\s+//; s/\s+$//;
1409
      push(@{$listes_ELEMENTS{$nom_liste}},split(/\s+/,$_));
1410
    }
1411
  }
1412
  close(Flis);
1413

    
1414
  open(Flis, "<$flis");
1415
  $is_liste_en_cours = 0;
1416
  while(<Flis>) {
1417
    chomp;
1418
    if(/^\s*(G\S+)/o) {
1419
      $nom_liste = $1;
1420
      $is_liste_en_cours = 1;
1421
      s/^\s*G\S+\s+//; s/\s+$//;
1422
      push(@{$listes_PTI{$nom_liste}},split(/\s+/,$_));
1423
    }
1424
    elsif(/^\s*noeuds/io or /^\s*elements/io or /^\s*[NAFE]/o) {
1425
      $is_liste_en_cours = 0;
1426
    }
1427
    elsif($is_liste_en_cours and /^\s*\d+(\s+\d+)*\s*$/io) {
1428
      s/^\s+//; s/\s+$//;
1429
      push(@{$listes_PTI{$nom_liste}},split(/\s+/,$_));
1430
    }
1431
  }
1432
  close(Flis);
1433

    
1434
  }#if(-e $flis)
1435

    
1436
  #AFFICHAGE DES LISTES DE NOEUDS
1437
  #foreach my $nom (keys(%listes_NOEUDS)) {
1438
  #  print "$nom : @{$listes_NOEUDS{$nom}}\n";
1439
  #}
1440
  #AFFICHAGE DES LISTES D ARETES
1441
  #foreach my $nom (keys(%listes_ARETES)) {
1442
  #  print "$nom : @{$listes_ARETES{$nom}}\n";
1443
  #}
1444
  #AFFICHAGE DES LISTES DE FACES
1445
  #foreach my $nom (keys(%listes_FACES)) {
1446
  #  print "$nom : @{$listes_FACES{$nom}}\n";
1447
  #}
1448
  #AFFICHAGE DES LISTES D ELEMENTS
1449
  #foreach my $nom (keys(%listes_ELEMENTS)) {
1450
  #  print "$nom : @{$listes_ELEMENTS{$nom}}\n";
1451
  #}
1452
  #AFFICHAGE DES LISTES DE POINTS D INTEGRATION
1453
  #foreach my $nom (keys(%listes_PTI)) {
1454
  #  print "$nom : @{$listes_PTI{$nom}}\n";
1455
  #}
1456

    
1457
  return($nom_maillage, $nb_noeuds, \@tab_noeuds, $nb_elts, \%tab_elements,
1458
         \%listes_NOEUDS, \%listes_ARETES,
1459
         \%listes_FACES, \%listes_ELEMENTS, \%listes_PTI);
1460
}#sub lecture_mail_her
1461

    
1462

    
1463

    
1464

    
1465

    
1466
#cette subroutine est associee a l option -disable_F. Le but est de scruter le fichier .msh et de supprimer les 
1467
# listes de faces et les elements en lien avec ces listes de reference de faces
1468
#  **rq 1 : cette sub utilise la variable globale $fGmsh
1469
#  **rq 2 : cette sub modifie definitivement le fichier $fGmsh
1470
#
1471
sub suppr_liste_faces {
1472
  my $nb_elts;#nombre d elements original qui sera modifie en fonction du nombre d elements a supprimer
1473

    
1474
  #saisie du nombre d elements original
1475
  my @liste_elts_a_supprimer;
1476
  open(my $Hlocal, "<$fGmsh");
1477
  while(<$Hlocal>) {
1478
    if(not defined $nb_elts and /^\s*\$Elements/io) {
1479
      $_ = <$Hlocal>;
1480
      ($nb_elts) = $_ =~ /(\d+)/;
1481
      last;
1482
    }
1483
  }
1484

    
1485
  #constitution d une table d indicateur de suppression d un element (par defaut : pas de suppression, donc => $elt_a_supprimer[no elt] = 0
1486
  my @elt_a_supprimer; for(1 .. $nb_elts) {$elt_a_supprimer[$_] = 0;}
1487
  MAIN_WHILE:while(<$Hlocal>) {
1488
    next if(not /^\s*\$ElementData\s*$/io);
1489

    
1490
    #par cette boucle, on ne va traiter que les listes de faces (reperees par une ligne commencant par "F)
1491
    #  pour les autres types de ref, on recommencera un nouveau tour de MAIN_WHILE
1492
    while(<$Hlocal>) {
1493
      next MAIN_WHILE if(/^\s*\$EndElementData\s*$/io);
1494
      last if(/^\s*\"\s*F\S+/o);#on passe a la boucle suivante si c est une liste de faces
1495
    }
1496

    
1497
    #on traite la liste de faces : les elements de cet ElementData seront a supprimer (on l indique en mettant 1 dans la table d indicateur)
1498
    while(<$Hlocal>) {
1499
      last if(/^\s*\$EndElementData\s*$/io);
1500
      next if(not /^\s*(\d+)\s+\d+\s*$/o);
1501
      $elt_a_supprimer[$1] = 1;#on indique que c est un element a supprimer
1502
    }
1503
  }
1504
  close($Hlocal);
1505

    
1506
  #constitution d une table de correspondance entre ancien numero et nouveau numero d elements
1507
  #et du nouveau nombre d element
1508
  my @tab_corresp_elt_old_new;
1509
  my $nb_elts_new = 0;
1510
  for(my $i=1; $i<=$nb_elts; $i++) {
1511
    next if($elt_a_supprimer[$i]);#on passe si l element est a supprimer
1512

    
1513
    #element a conserver => on incremente le nouveau nombre d elements et on fait la correspondance entre l ancien numero ($i) et le nouveau ($nb_elts_new)
1514
    $nb_elts_new++;
1515
    $tab_corresp_elt_old_new[$i] = $nb_elts_new;#nouveau numero pour cet element
1516
  }
1517

    
1518
  #desormais, on a toutes les infos pour reecrire le fichier $fGmsh en supprimant les references de faces et en renumerotant
1519
  # les elements en fonction de @tab_corresp_elt_old_new
1520
  open($Hlocal, "<$fGmsh");
1521
  open(my $Htmp, ">$fGmsh.tmp");
1522

    
1523
  #traitement de la liste des elements
1524
  while(<$Hlocal>) {
1525
    print $Htmp $_;
1526
    next if(not /^\s*\$Elements/io);
1527
    <$Hlocal>;
1528
    print $Htmp "$nb_elts_new\n";
1529
    while(<$Hlocal>) {
1530
      if(/^\s*\$EndElements\s*$/io) {
1531
        print $Htmp $_;
1532
        last;
1533
      }
1534

    
1535
      next if(not /^\s*(\d+)/o);
1536
      my $no_elt = $1;
1537
      next if(not defined $tab_corresp_elt_old_new[$no_elt]);#rq : les elements a supprimer n ont pas de correspondance
1538
      s/^(\s*)$no_elt/$1$tab_corresp_elt_old_new[$no_elt]/;
1539
      print $Htmp $_;
1540
    }
1541
    last;
1542
  }
1543

    
1544
  #traitement des ElementData
1545
  while(my $ligne = <$Hlocal>) {
1546

    
1547
    #cas d un ElementData
1548
    if($ligne =~ /^\s*\$ElementData\s*$/io) {
1549
      my $entete = $ligne;
1550
      #on lit jusqu au nom de la reference
1551
      while($ligne = <$Hlocal>) {
1552
        $entete .= $ligne;
1553
        last if($ligne =~ /^\s*\"/o);
1554
      }
1555

    
1556
      #pas de recopie si c est une reference de faces
1557
      if($ligne =~ /^\s*\"\s*F\S+/o) {
1558
        while($ligne = <$Hlocal>) {
1559
          last if($ligne =~ /^\s*\$EndElementData\s*$/io);
1560
        }
1561
      }
1562
      #si c est autre chose qu une reference de faces, on modifie les numeros d elements en fonction de la table de correspondance
1563
      else {
1564
        print $Htmp $entete;
1565
        while($ligne = <$Hlocal>) {
1566
          if($ligne =~ /^\s*(\d+)\s+\d+\s*$/o) {
1567
            my $no_elt = $1;
1568
            $ligne =~ s/^(\s*)\d+/$1$tab_corresp_elt_old_new[$no_elt]/;
1569
          }
1570
          print $Htmp $ligne;
1571
          last if($ligne =~ /^\s*\$EndElementData\s*$/io);
1572
        }
1573
      }
1574

    
1575
    }
1576

    
1577
    #autre chose qu un ElementData
1578
    else {
1579
      print $Htmp $ligne;
1580
    }
1581
  }
1582
  close($Htmp);
1583
  close($Hlocal);
1584

    
1585
  system("mv -f $fGmsh.tmp $fGmsh");
1586
}#sub suppr_liste_faces
1587

    
1588
#cette subroutine est associee a l option -disable_A. Le but est de scruter le fichier .msh et de supprimer les 
1589
# listes d aretes et les elements en lien avec ces listes de reference d aretes
1590
#  **rq 1 : cette sub utilise la variable globale $fGmsh
1591
#  **rq 2 : cette sub modifie definitivement le fichier $fGmsh
1592
#
1593
sub suppr_liste_aretes {
1594
  my $nb_elts;#nombre d elements original qui sera modifie en fonction du nombre d elements a supprimer
1595

    
1596
  #saisie du nombre d elements original
1597
  my @liste_elts_a_supprimer;
1598
  open(my $Hlocal, "<$fGmsh");
1599
  while(<$Hlocal>) {
1600
    if(not defined $nb_elts and /^\s*\$Elements/io) {
1601
      $_ = <$Hlocal>;
1602
      ($nb_elts) = $_ =~ /(\d+)/;
1603
      last;
1604
    }
1605
  }
1606

    
1607
  #constitution d une table d indicateur de suppression d un element (par defaut : pas de suppression, donc => $elt_a_supprimer[no elt] = 0
1608
  my @elt_a_supprimer; for(1 .. $nb_elts) {$elt_a_supprimer[$_] = 0;}
1609
  MAIN_WHILE:while(<$Hlocal>) {
1610
    next if(not /^\s*\$ElementData\s*$/io);
1611

    
1612
    #par cette boucle, on ne va traiter que les listes d aretes (reperees par une ligne commencant par "A)
1613
    #  pour les autres types de ref, on recommencera un nouveau tour de MAIN_WHILE
1614
    while(<$Hlocal>) {
1615
      next MAIN_WHILE if(/^\s*\$EndElementData\s*$/io);
1616
      last if(/^\s*\"\s*A\S+/o);#on passe a la boucle suivante si c est une liste d aretes
1617
    }
1618

    
1619
    #on traite la liste d aretes : les elements de cet ElementData seront a supprimer (on l indique en mettant 1 dans la table d indicateur)
1620
    while(<$Hlocal>) {
1621
      last if(/^\s*\$EndElementData\s*$/io);
1622
      next if(not /^\s*(\d+)\s+\d+\s*$/o);
1623
      $elt_a_supprimer[$1] = 1;#on indique que c est un element a supprimer
1624
    }
1625
  }
1626
  close($Hlocal);
1627

    
1628
  #constitution d une table de correspondance entre ancien numero et nouveau numero d elements
1629
  #et du nouveau nombre d element
1630
  my @tab_corresp_elt_old_new;
1631
  my $nb_elts_new = 0;
1632
  for(my $i=1; $i<=$nb_elts; $i++) {
1633
    next if($elt_a_supprimer[$i]);#on passe si l element est a supprimer
1634

    
1635
    #element a conserver => on incremente le nouveau nombre d elements et on fait la correspondance entre l ancien numero ($i) et le nouveau ($nb_elts_new)
1636
    $nb_elts_new++;
1637
    $tab_corresp_elt_old_new[$i] = $nb_elts_new;#nouveau numero pour cet element
1638
  }
1639

    
1640
  #desormais, on a toutes les infos pour reecrire le fichier $fGmsh en supprimant les references d aretes et en renumerotant
1641
  # les elements en fonction de @tab_corresp_elt_old_new
1642
  open($Hlocal, "<$fGmsh");
1643
  open(my $Htmp, ">$fGmsh.tmp");
1644

    
1645
  #traitement de la liste des elements
1646
  while(<$Hlocal>) {
1647
    print $Htmp $_;
1648
    next if(not /^\s*\$Elements/io);
1649
    <$Hlocal>;
1650
    print $Htmp "$nb_elts_new\n";
1651
    while(<$Hlocal>) {
1652
      if(/^\s*\$EndElements\s*$/io) {
1653
        print $Htmp $_;
1654
        last;
1655
      }
1656

    
1657
      next if(not /^\s*(\d+)/o);
1658
      my $no_elt = $1;
1659
      next if(not defined $tab_corresp_elt_old_new[$no_elt]);#rq : les elements a supprimer n ont pas de correspondance
1660
      s/^(\s*)$no_elt/$1$tab_corresp_elt_old_new[$no_elt]/;
1661
      print $Htmp $_;
1662
    }
1663
    last;
1664
  }
1665

    
1666
  #traitement des ElementData
1667
  while(my $ligne = <$Hlocal>) {
1668

    
1669
    #cas d un ElementData
1670
    if($ligne =~ /^\s*\$ElementData\s*$/io) {
1671
      my $entete = $ligne;
1672
      #on lit jusqu au nom de la reference
1673
      while($ligne = <$Hlocal>) {
1674
        $entete .= $ligne;
1675
        last if($ligne =~ /^\s*\"/o);
1676
      }
1677

    
1678
      #pas de recopie si c est une reference d aretes
1679
      if($ligne =~ /^\s*\"\s*A\S+/o) {
1680
        while($ligne = <$Hlocal>) {
1681
          last if($ligne =~ /^\s*\$EndElementData\s*$/io);
1682
        }
1683
      }
1684
      #si c est autre chose qu une reference d aretes, on modifie les numeros d elements en fonction de la table de correspondance
1685
      else {
1686
        print $Htmp $entete;
1687
        while($ligne = <$Hlocal>) {
1688
          if($ligne =~ /^\s*(\d+)\s+\d+\s*$/o) {
1689
            my $no_elt = $1;
1690
            $ligne =~ s/^(\s*)\d+/$1$tab_corresp_elt_old_new[$no_elt]/;
1691
          }
1692
          print $Htmp $ligne;
1693
          last if($ligne =~ /^\s*\$EndElementData\s*$/io);
1694
        }
1695
      }
1696

    
1697
    }
1698

    
1699
    #autre chose qu un ElementData
1700
    else {
1701
      print $Htmp $ligne;
1702
    }
1703
  }
1704
  close($Htmp);
1705
  close($Hlocal);
1706

    
1707
  system("mv -f $fGmsh.tmp $fGmsh");
1708
}#sub suppr_liste_aretes
(17-17/24)
Redmine Appliance - Powered by TurnKey Linux