1 # -*- coding: utf-8 -*-
2 # CONFIGURATION MANAGEMENT OF EDF VERSION
3 # ======================================================================
4 # COPYRIGHT (C) 1991 - 2002 EDF R&D WWW.CODE-ASTER.ORG
5 # THIS PROGRAM IS FREE SOFTWARE; YOU CAN REDISTRIBUTE IT AND/OR MODIFY
6 # IT UNDER THE TERMS OF THE GNU GENERAL PUBLIC LICENSE AS PUBLISHED BY
7 # THE FREE SOFTWARE FOUNDATION; EITHER VERSION 2 OF THE LICENSE, OR
8 # (AT YOUR OPTION) ANY LATER VERSION.
10 # THIS PROGRAM IS DISTRIBUTED IN THE HOPE THAT IT WILL BE USEFUL, BUT
11 # WITHOUT ANY WARRANTY; WITHOUT EVEN THE IMPLIED WARRANTY OF
12 # MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. SEE THE GNU
13 # GENERAL PUBLIC LICENSE FOR MORE DETAILS.
15 # YOU SHOULD HAVE RECEIVED A COPY OF THE GNU GENERAL PUBLIC LICENSE
16 # ALONG WITH THIS PROGRAM; IF NOT, WRITE TO EDF R&D CODE_ASTER,
17 # 1 AVENUE DU GENERAL DE GAULLE, 92141 CLAMART CEDEX, FRANCE.
20 # ======================================================================
22 import string,types,os
25 from copy import copy,deepcopy
33 from widgets import showinfo
34 from widgets import askopenfilename
35 from widgets import ListeChoix
36 from widgets import FenetreDeSelection
37 from widgets import FenetreDeParametre
39 from Noyau.N_CR import justify_text
40 from Ihm.I_LASSD import LASSD
41 from Extensions.parametre import PARAMETRE
43 from utils import substract_list
44 from plusieurspanel import PLUSIEURS_Panel
45 from uniqueassdpanel import UNIQUE_ASSD_Panel
50 class PLUSIEURS_BASE_Panel(PLUSIEURS_Panel):
52 Classe définissant le panel associé aux mots-clés qui demandent
53 à l'utilisateur de donner une liste de valeurs qui ne sont pas
54 à choisir dans une liste discrètes et qui sont de type de base :
55 entier, réel, string,...
57 def makeValeurPage(self,page):
59 Crée la page de saisie d'une liste de valeurs à priori quelconques,
60 cad qui ne sont pas à choisir dans une liste prédéfinie
62 #print "CCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCC"
64 #print "A priori on ne doit plus passer dans cette methode "
66 #print "CCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCC"
67 # On récupère la bulle d'aide du panneau, l'objet, l'aide,min et max (cardinalité de la liste),
68 # et la liste des valeurs déjà affectées à l'objet courant
69 bulle_aide=self.get_bulle_aide()
70 objet_mc = self.node.item.get_definition()
71 aide = self.get_aide()
72 aide = justify_text(texte=aide)
73 min,max = self.node.item.GetMinMax()
74 l_valeurs = self.node.item.GetListeValeurs()
76 # création des frames globales
77 self.frame1 = Frame(page,relief='groove',bd=2)
78 self.frame2 = Frame(page)
79 self.frame1.place(relx=0.,rely=0.,relwidth=1.,relheight=0.85)
80 self.frame2.place(relx=0.,rely=0.85,relwidth=1,relheight=0.15)
81 self.frame_right = Frame(self.frame1)
82 self.frame_right.place(relx=0.35,rely=0.,relwidth=0.65,relheight=1.)
84 # création des frames internes
85 self.frame_valeurs = Frame(self.frame1)
86 self.frame_valeurs.place(relx=0.02,rely=0.05,relwidth=0.35,relheight=0.95)
87 self.frame_boutons_fleches = Frame(self.frame_right)
88 self.frame_boutons_fleches.place(relx=0.,rely=0.2,relwidth=0.2,relheight=0.5)
89 self.frame_choix = Frame(self.frame_right)
90 self.frame_choix.place(relx=0.2,rely=0.2,relwidth=0.7,relheight=0.8)
91 self.frame_aide = Frame(self.frame_right)
92 self.frame_aide.place(relx=0.1,rely=0.8,relwidth=0.8,relheight=0.2)
93 self.frame_boutons = Frame(self.frame2)
94 #self.frame_boutons.place(relx=0.35,rely=0.,relwidth=0.3,relheight=1.)
95 self.frame_boutons.place(relx=0.2,rely=0.,relwidth=1,relheight=1.)
96 for fram in (self.frame1,self.frame2,self.frame_right,self.frame_valeurs,
97 self.frame_boutons_fleches,self.frame_choix,self.frame_aide,self.frame_boutons):
98 fram.bind("<Button-3>",lambda e,s=self,a=bulle_aide : s.parent.appli.affiche_aide(e,a))
99 fram.bind("<ButtonRelease-3>",self.parent.appli.efface_aide)
101 # création des objets dans les frames
102 liste_commandes_valeurs = (("<Button-1>",self.selectValeur),
103 ("<Button-3>",self.deselectValeur),
104 ("<Double-Button-1>",self.sup_valeur_sans_into))
105 self.Liste_valeurs=ListeChoix(self,self.frame_valeurs,l_valeurs,liste_commandes = liste_commandes_valeurs,
106 titre="Valeur(s) actuelle(s)")
108 # Création de l'entry ou de la liste des SD
109 # PN : pour ajouter les validators
110 self.label = Label(self.frame_choix,text="Valeur :")
111 self.make_entry(frame = self.frame_choix,command = self.add_valeur_plusieurs_base)
112 self.label.place(relx=0.05,rely=0.2)
114 # Création d'un bouton "Importer ..." et d'un bouton "Paramatres" sur le panel.
115 bouton_valeurs_fichier = Button(self.frame_choix,
117 command=self.select_in_file)
118 bouton_valeurs_fichier.place(relx=0.28,rely=0.4,relwidth=0.6)
119 bouton_parametres = Button(self.frame_choix, text="Parametres", command=self.affiche_parametre)
120 bouton_parametres.place(relx=0.28,rely=0.6,relwidth=0.6)
121 self.ajout_valeurs = None
123 # boutons Ajouter et Supprimer
124 bouton_add = Button(self.frame_boutons_fleches,
125 image = images.get_image('arrow_left'),
126 command = self.add_valeur_plusieurs_base)
127 bouton_sup = Button(self.frame_boutons_fleches,
128 image = images.get_image('arrow_right'),
129 command = self.sup_valeur_sans_into)
130 bouton_add.place(relx=0.3,rely=0.35)
131 bouton_sup.place(relx=0.3,rely=0.65)
132 # affichage de l'aide
133 self.frame_aide.update()
134 self.aide = Label(self.frame_aide,
138 wraplength=int(self.frame_aide.winfo_width()*0.8))
139 self.aide.place(relx=0.5,rely=0.5,anchor='center',relwidth=1)
140 self.Liste_valeurs.affiche_liste()
141 if len(l_valeurs) > 0 :
142 liste_marque=l_valeurs[-1]
143 self.Liste_valeurs.surligne(liste_marque)
144 self.selectValeur(liste_marque)
145 # boutons Accepter et Annuler
146 bouton_accepter = Button(self.frame_boutons,
148 command = lambda s=self,m=min,M=max : s.accepte_modifs_valeur(m,M))
149 bouton_annuler = Button(self.frame_boutons,
151 command = self.annule_modifs_valeur)
152 bouton_accepter.place(relx=0.2, rely=0.2,relwidth=0.25)
153 bouton_annuler.place(relx=0.5, rely=0.2,relwidth=0.25)
154 #for but in (bouton_accepter,bouton_annuler):
155 # but.pack(side='left',padx=4)
157 def affiche_parametre(self) :
158 if self.node.item.get_liste_param_possible() != [ ]:
160 for param in self.node.item.get_liste_param_possible():
161 txtparam=txtparam+repr(param)+"\n"
163 showerror("Aucun parametre ","Pas de parametre de ce type")
166 self.self.fenetreparam.destroy()
169 self.fenetreparam=FenetreDeParametre( self, self.node.item, self.parent.appli, txtparam)
171 def valid_valeur(self):
172 self.add_valeur_plusieurs_base()
174 def add_valeur_plusieurs_base(self,name=None):
178 valeur,validite,commentaire=self.get_valeur()
180 self.parent.appli.affiche_infos(commentaire)
184 if type(valeur) in (types.ListType,types.TupleType) :
186 while (indice < len(valeur)):
188 if self.node.item.wait_complex :
189 if (v== 'RI' or v == 'MP'):
191 t=tuple([v,valeur[indice+1],valeur[indice+2]])
196 commentaire = "Veuillez entrer le complexe sous forme aster ou sous forme python"
197 self.parent.appli.affiche_infos(commentaire)
199 else : # ce n'est pas un tuple à la mode aster
202 else: # on n'attend pas un complexe
206 atraiter.append(valeur)
208 for valeur in atraiter :
209 encorevalide=self.node.item.valide_item(valeur)
210 # qdsjfkllllllllllllllllll
212 listecourante=self.Liste_valeurs.get_liste()
213 encorevalide=self.node.item.valide_liste_partielle(valeur,listecourante)
214 if not encorevalide : encorevalide = -1
215 self.add_valeur_sans_into(valeur,encorevalide)
217 def select_in_file(self):
218 """ Permet d'ouvrir un fichier choisi par l'utilisateur. """
219 nom_fichier = askopenfilename(title="Choix fichier :")
225 f = open(nom_fichier, "rb")
226 selection_texte = f.read()
228 self.ajout_valeurs = FenetreDeSelection(self,
231 titre="Sélection de valeurs",
232 texte=selection_texte)
234 traceback.print_exc()
235 showinfo("Erreur de fichier","impossible d'ouvir le fichier "+nom_fichier)
237 def get_bulle_aide(self):
239 Retourne l'aide associée au panneau courant
241 return """Taper dans la boîte de saisie de droite la valeur que
242 vous voulez affecter au mot-clé simple.
243 - Cliquez sur la flèche gauche ou pressez <Return> pour la faire glisser
244 dans la liste des valeurs que vous voulez affecter au mot-clé simple
245 - Un clic sur une valeur de la liste la sélectionne
246 - Un clic sur la flèche droite ou un double-clic retire la valeur
247 sélectionnée de la liste
248 - Cliquez sur 'Valider' pour que la nouvelle valeur désirée soit affectée
250 - Cliquez sur 'Annuler' pour annuler toutes les modifications faites
251 depuis le dernier clic sur 'Valider'"""
255 Retourne la phrase d'aide indiquant de quel type de base doivent être les valeurs
256 que saisit l'utilisateur
259 mc = self.node.item.get_definition()
260 d_aides = { 'TXM' : 'chaînes de caractères',
265 if not d_aides.has_key(type) : return 'Type de base inconnu'
267 commentaire="Une liste de "+d_aides[type]+" de longueur " + `mc.min` + " est attendue"
269 commentaire="Une liste de "+d_aides[type]+" est attendue (min="+`mc.min`+",max="+`mc.max`+')'
271 aideval=self.node.item.aide()
272 commentaire=commentaire +"\n"+aideval
275 def make_entry(self,frame,command,x=0.28,y=0.2):
276 self.entry = Entry(frame,relief='sunken')
277 self.entry.place(relx=0.28,rely=y,relwidth=0.6)
278 self.entry.bind("<Return>",lambda e,c=command:c())
279 self.entry.bind("<KP_Enter>",lambda e,c=command:c())
282 #def make_entry(self,frame,command,x=0.28,y=0.2):
284 Crée l'entry de saisie de la valeur souhaitée : distingue le
285 cas d'un complexe attendu, d'une autre valeur quelconque
287 #print "CCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCC"
289 #print "A priori on ne doit plus passer dans cette methode "
291 #print "CCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCC"
292 #if self.node.item.wait_complex():
293 # self.typ_cplx=StringVar()
294 # self.typ_cplx.set('RI')
295 # rb1 = Radiobutton(frame, text='RI',variable=self.typ_cplx,value='RI')
296 # rb2 = Radiobutton(frame, text='MP',variable=self.typ_cplx,value='MP')
297 # self.entry1 = Pmw.EntryField(frame,validate='real')
298 # self.entry2 = Pmw.EntryField(frame,validate='real')
299 # rb1.place(relx=0.05,rely = 0.4)
300 # rb2.place(relx=0.05,rely = 0.6)
301 # self.entry1.component('entry').bind("<Return>",lambda e,s=self:s.entry2.component('entry').focus)
302 # self.entry2.component('entry').bind("<Return>",lambda e,c=command:c())
303 # self.entry1.component('entry').bind("<KP_Enter>",lambda e,s=self:s.entry2.component('entry').focus)
304 # self.entry2.component('entry').bind("<KP_Enter>",lambda e,c=command:c())
305 # self.entry1.place(relx=0.27,rely = 0.5,relwidth=0.35)
306 # self.entry2.place(relx=0.65,rely = 0.5,relwidth=0.35)
307 # self.entry1.focus()
309 # self.entry = Entry(frame,relief='sunken')
310 # self.entry.place(relx=0.28,rely=0.2,relwidth=0.6)
311 # self.entry.place(relx=0.28,rely=y,relwidth=0.6)
312 # self.entry.bind("<Return>",lambda e,c=command:c())
313 # self.entry.bind("<KP_Enter>",lambda e,c=command:c())
316 def get_valeur(self):
318 Retourne la valeur saisie par l'utilisateur dans self.entry
321 if hasattr(self,'entry'):
322 # Traitement d'une entree unique
323 valeurentree = self.entry.get()
324 if (valeurentree == None or valeurentree ==""):
326 if (valeurentree[0] != "(") and (valeurentree.find(',') < len(valeurentree)):
328 for v in valeurentree.split(','):
329 vsimple,validite=self.node.item.eval_valeur(v)
330 # Pn If ajoute pour le panneau "double"
331 #if isinstance(vsimple,LASSD) :
332 # commentaire = "impossible de mélanger reels et liste prédéfinie"
336 valeurs.append(vsimple)
338 commentaire = "impossible d'évaluer : %s " %`valeurentree`
342 valeur,validite=self.node.item.eval_valeur(valeurentree)
343 if not validite and commentaire == "":
344 commentaire = "impossible d'évaluer : %s " %`valeurentree`
345 return valeur,validite,commentaire
347 # # Traitement d'une entree de type complexe
349 # valeur= (self.typ_cplx.get(),
350 # string.atof(self.entry1.get()),
351 # string.atof(self.entry2.get()))
354 # #traceback.print_exc()
355 # return None,0,"impossible d'évaluer la valeur d'entree"
357 def erase_valeur(self):
359 Efface la valeur donnée par l'utilisateur dans l'entry
361 if hasattr(self,'entry'):
362 self.entry.delete(0,END)
364 self.typ_cplx.set('RI')
365 self.entry1.delete(0,END)
366 self.entry2.delete(0,END)
369 def display_valeur(self,val=None):
371 Affiche la valeur passée en argument dans l'entry de saisie.
372 Par défaut affiche la valeur du mot-clé simple
375 valeur = self.node.item.object.getval()
378 if not valeur : return
380 if hasattr(self,'entry'):
381 # Traitement d'une entree unique
382 self.entry.delete(0,END)
383 self.entry.insert(0,str(valeur))
385 # Traitement d'une entree de type complexe
386 typ_cplx,x1,x2=valeur
387 self.entry1.delete(0,END)
388 self.entry2.delete(0,END)
389 self.typ_cplx.set(typ_cplx)
390 self.entry1.setentry(x1)
391 self.entry2.setentry(x2)
393 class PLUSIEURS_BASE_OR_UNELISTE_Panel(PLUSIEURS_BASE_Panel,UNIQUE_ASSD_Panel):
395 def makeValeurPage(self,page):
397 Crée la page de saisie d'une liste de valeurs à priori quelconques,
398 cad qui ne sont pas à choisir dans une liste prédéfinie
400 # On récupère la bulle d'aide du panneau, l'objet, l'aide,min et max (cardinalité de la liste),
401 # et la liste des valeurs déjà affectées à l'objet courant
402 bulle_aide=self.get_bulle_aide()
403 objet_mc = self.node.item.get_definition()
404 aide = self.get_aide()
405 aide = justify_text(texte=aide)
406 aide2 = self.get_aide2()
407 aide2 = justify_text(texte=aide2)
408 min,max = self.node.item.GetMinMax()
409 l_valeurs = self.node.item.GetListeValeurs()
411 if isinstance(i,LASSD) :
412 affiche_entry=l_valeurs
415 # Il faut traiter ici pour avoir le choix entre une liste
416 # deja constituee (listr8aster) ou manuelle
418 # création des frames globales
419 self.frame1 = Frame(page,relief='groove',bd=2)
420 self.frame2 = Frame(page)
421 self.frame1.place(relx=0.,rely=0.,relwidth=1.,relheight=0.9)
422 self.frame2.place(relx=0.,rely=0.9,relwidth=1,relheight=0.1)
424 # création des frames internes dans frame1
425 self.frame_valeurs = Frame(self.frame1)
426 self.frame_valeurs.place(relx=0.02,rely=0.55,relwidth=0.35,relheight=0.45)
427 self.frame_haut = Frame(self.frame1)
428 self.frame_haut.place(relx=0.02,rely=0.02,relwidth=0.98,relheight=0.45)
429 self.frame_bas = Frame(self.frame1)
430 self.frame_bas.place(relx=0.37,rely=0.55,relwidth=0.63,relheight=0.45)
432 # création des frames internes dans frame_right
433 self.frame_fleches = Frame(self.frame_bas)
434 self.frame_fleches.place(relx=0.,rely=0.4,relwidth=0.2,relheight=0.5)
435 self.frame_choix = Frame(self.frame_bas)
436 self.frame_choix.place(relx=0.2,rely=0.1,relwidth=0.75,relheight=1)
438 # affichage de l'aide
439 self.aide = Label(self.frame_haut, text = aide, justify='center', anchor='center',)
440 self.aide.place(relx=0.72,rely=0.25,anchor='center',relwidth=1)
441 self.aide2 = Label(self.frame2, text = aide2,)
442 self.aide2.place(relx=0.4,rely=0.01,relwidth=0.6)
444 # Création d'un bouton "Importer ..." et d'un bouton "Parametres" sur le panel.
445 bouton_valeurs_fichier = Button(self.frame_choix,
447 command=self.select_in_file)
448 bouton_valeurs_fichier.place(relx=0.28,rely=0.0,relwidth=0.6)
449 bouton_parametres = Button(self.frame_choix, text="Parametres", command=self.affiche_parametre)
450 bouton_parametres.place(relx=0.28,rely=0.25,relwidth=0.6)
451 self.ajout_valeurs = None
454 # Création de la liste des SD
455 liste_noms_sd = self.node.item.get_sd_avant_du_bon_type_pour_type_de_base()
456 liste_noms_sd = self.tri(liste_noms_sd)
457 self.listbox = Pmw.ScrolledListBox(self.frame_haut,
460 #label_text="Structures de données du type\n requis parl'objet courant :",
461 label_text="Listes du type\n requis parl'objet courant :",
463 dblclickcommand=lambda s=self,c=UNIQUE_ASSD_Panel.valid_valeur : s.choose_valeur_from_list(c))
464 self.listbox.place(relx=0.00,rely=0.00,relwidth=0.4)
466 # On eneleve le label pour gagner de la place
467 #self.label = Label(self.frame_choix,text="Valeur :")
468 #self.label.place(relx=0.05,rely=0.85)
469 self.make_entry(frame = self.frame_choix,command = self.add_valeur_plusieurs_base,x=0.28,y=0.55)
471 # boutons Ajouter et Supprimer
472 bouton_add = Button(self.frame_fleches, image = images.get_image('arrow_left'),
473 command = self.add_valeur_plusieurs_base)
474 bouton_sup = Button(self.frame_fleches, image = images.get_image('arrow_right'),
475 command = self.sup_valeur_sans_into)
476 bouton_add.place(relx=0.2,rely=0.25)
477 bouton_sup.place(relx=0.2,rely=0.70)
480 # boutons Accepter et Annuler dans frame2
481 bouton_accepter = Button(self.frame2, text='Valider',
482 command = lambda s=self,m=min,M=max : s.accepte_modifs_valeur(m,M))
483 bouton_annuler = Button(self.frame2, text = 'Annuler',
484 command = self.annule_modifs_valeur)
485 for but in (bouton_accepter,bouton_annuler):
486 but.pack(side='left',padx=5)
488 # création des objets dans les frames
489 liste_commandes_valeurs = (("<Button-1>",self.selectValeur),
490 ("<Button-3>",self.deselectValeur),
491 ("<Double-Button-1>",self.sup_valeur_sans_into))
492 self.Liste_valeurs = ListeChoix(self,self.frame_valeurs,l_valeurs,
493 liste_commandes = liste_commandes_valeurs,
494 titre="Valeur(s) non-prédéfinies(s)",
498 for fram in (self.frame1,self.frame2,self.frame_bas,self.frame_haut,self.frame_valeurs,
499 self.frame_fleches,self.frame_choix):
500 fram.bind("<Button-3>",lambda e,s=self,a=bulle_aide: s.parent.appli.affiche_aide(e,a))
501 fram.bind("<ButtonRelease-3>",self.parent.appli.efface_aide)
503 self.Liste_valeurs.affiche_liste()
504 if len(l_valeurs) > 0 :
505 liste_marque=l_valeurs[-1]
506 self.Liste_valeurs.surligne(liste_marque)
510 Retourne la phrase d'aide indiquant de quel type de base doivent être les valeurs
511 saisies par l'utilisateur
513 commentaire="Ce motclef accepte soit un nom de liste déja définie soit une liste manuelle de valeurs"
517 min,max = self.node.item.GetMinMax()
518 aideval=self.node.item.aide()
519 commentaire="min : " + str(min) + ", max : " + str(max)
520 aideval=commentaire + aideval
523 def choose_valeur_from_list(self,command):
525 Affecte à valeur choisie la sélection courante dans la liste des choix proposés
528 self.Liste_valeurs.liste=[]
529 self.Liste_valeurs.affiche_liste()
530 if len(self.listbox.get()) == 0 : return
531 choix = self.listbox.getcurselection()[0]
533 d["valeurentree"]=choix
534 apply(command,(self,),d)
538 def tri(self,liste_noms_sd):
540 d_types = { 'TXM' : type('A'),
545 # On enleve seulement ceux qu'on peut
546 # Sur certaines listes, il est possible qu'on ne
547 # sache pas déterminer le type
549 typespossibles=self.node.item.object.definition.type
551 for t in typespossibles:
552 if t in d_types.keys() :
553 typecherche = d_types[t]
555 for liste in liste_noms_sd:
556 valeur,validite=self.node.item.eval_valeur(liste)
557 for mc in valeur.etape.mc_liste :
559 if type(mc.valeur) in (types.ListType,types.TupleType) :
560 typeliste=type(mc.valeur[0])
562 typeliste=type(mc.valeur)
563 if type(mc.valeur[0]) == typecherche:
564 listefinale.append(liste)
566 listefinale.append(liste)