1 # CONFIGURATION MANAGEMENT OF EDF VERSION
2 # ======================================================================
3 # COPYRIGHT (C) 1991 - 2002 EDF R&D WWW.CODE-ASTER.ORG
4 # THIS PROGRAM IS FREE SOFTWARE; YOU CAN REDISTRIBUTE IT AND/OR MODIFY
5 # IT UNDER THE TERMS OF THE GNU GENERAL PUBLIC LICENSE AS PUBLISHED BY
6 # THE FREE SOFTWARE FOUNDATION; EITHER VERSION 2 OF THE LICENSE, OR
7 # (AT YOUR OPTION) ANY LATER VERSION.
9 # THIS PROGRAM IS DISTRIBUTED IN THE HOPE THAT IT WILL BE USEFUL, BUT
10 # WITHOUT ANY WARRANTY; WITHOUT EVEN THE IMPLIED WARRANTY OF
11 # MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. SEE THE GNU
12 # GENERAL PUBLIC LICENSE FOR MORE DETAILS.
14 # YOU SHOULD HAVE RECEIVED A COPY OF THE GNU GENERAL PUBLIC LICENSE
15 # ALONG WITH THIS PROGRAM; IF NOT, WRITE TO EDF R&D CODE_ASTER,
16 # 1 AVENUE DU GENERAL DE GAULLE, 92141 CLAMART CEDEX, FRANCE.
19 # ======================================================================
21 import string,types,os
24 from tkFileDialog import *
25 from tkMessageBox import showinfo
26 from copy import copy,deepcopy
34 from widgets import ListeChoix
35 from widgets import FenetreDeSelection
37 from Noyau.N_CR import justify_text
38 from utils import substract_list
41 class newSIMPPanel(panels.OngletPanel):
43 Classe virtuelle servant de classe mère à toutes les classes Panel
44 servant à afficher et récupérer la valeur d'un mot-clé simple.
45 Le panel est différent suivant le type de la valeur attendu
49 Méthode appelée par le constructeur de OngletPanel :
50 construit le notebook à 2 onglets utilisé par tous les panels de
51 tous les mots-clés simples
53 nb = Pmw.NoteBook(self,raisecommand=self.raisecmd)
54 nb.pack(fill = 'both', expand = 1)
56 nb.add('Valeur', tab_text='Saisir valeur')
57 #nb.add('Commentaire',tab_text='Insérer commentaire')
58 self.makeValeurPage(nb.page('Valeur'))
59 #self.makeCommentairePage(nb.page("Commentaire"))
62 # ----------------------------------------------------------------------------------------
63 # Méthodes utilisées pour l'affectation de la valeur donnée par l'utilisateur
65 # ----------------------------------------------------------------------------------------
67 def reset_old_valeur(self,name=None,mess='Valeur du mot-clé enregistrée'):
69 Enregistre val comme valeur de self.node.item.object SANS
70 faire de test de validité ni ré-évaluer l'ancienne valeur
71 permet de rester avec des valeurs non entrees et de ne pas
72 ré-évaluer des entiers par exemple
74 if self.parent.modified == 'n' : self.parent.init_modif()
75 self.node.item.set_valeur(name)
76 self.parent.appli.affiche_infos(mess)
77 if self.node.item.get_position()=='global':
78 self.node.etape.verif_all()
79 elif self.node.item.get_position()=='global_jdc':
80 self.node.racine.verif_all()
82 self.node.parent.verif()
85 def record_valeur(self,name=None,mess='Valeur du mot-clé enregistrée'):
87 Enregistre val comme valeur de self.node.item.object
88 en evaluant l item et en le validant
90 if self.parent.modified == 'n' : self.parent.init_modif()
95 valeurentree= self.entry.get()
96 self.entry.delete(0,END)
97 if valeurentree == '': valeurentree=None
98 valeur,validite=self.node.item.eval_valeur(valeurentree)
100 valeur= self.entry.get()
101 commentaire = "impossible d'évaluer : %s " %`valeurentree`
102 self.parent.appli.affiche_infos(commentaire)
105 if self.node.item.is_list() :
106 validite=self.node.item.valide_liste_complete(valeur)
107 commentaire=self.node.item.info_erreur_liste()
109 validite=self.node.item.valide_item(valeur)
110 commentaire=self.node.item.info_erreur_item()
113 self.node.item.set_valeur(valeur)
114 self.parent.appli.affiche_infos(mess)
115 if self.node.item.get_position()=='global':
116 self.node.etape.verif_all()
117 elif self.node.item.get_position()=='global_jdc':
118 self.node.racine.verif_all()
120 self.node.parent.verif()
122 if self.node.item.isvalid():
123 self.node.parent.select()
125 self.parent.appli.affiche_infos(commentaire)
127 # ----------------------------------------------------------------------------------------
128 # Méthodes utilisées pour la manipulation des items dans les listes de choix
129 # ----------------------------------------------------------------------------------------
130 def selectValeur(self,name):
131 self.selected_valeur = name
133 def deselectValeur(self,name):
134 self.selectValeur = None
136 def sup_valeur(self,name=None):
138 Supprime la valeur selectionnée de la liste des valeurs et la rajoute
139 à la liste des choix possibles
141 if hasattr(self,'selected_valeur') :
142 if ( self.selected_valeur != None and self.selected_valeur != ''):
143 liste_valeurs = self.Liste_valeurs.get_liste()
144 liste_valeurs.remove(self.selected_valeur)
145 self.Liste_valeurs.put_liste(liste_valeurs)
146 listeActuelle=self.Liste_valeurs.get_liste()
147 liste_choix=self.node.item.get_liste_possible(listeActuelle)
148 self.Liste_choix.put_liste(liste_choix)
149 self.selected_valeur = None
151 def add_choix(self,name=None):
153 Ajoute le choix selectionné à la liste des valeurs et le retire
154 de la liste des choix possibles
157 if hasattr(self,'selected_choix') :
158 if (self.selected_choix != None and self.selected_choix != ''):
159 min,max = self.node.item.GetMinMax()
160 liste_valeurs = self.Liste_valeurs.get_liste()
161 if len(liste_valeurs) >= max :
162 self.parent.appli.affiche_infos("La liste ne peut pas avoir plus de %d éléments" %max)
164 liste_valeurs.append(self.selected_choix)
165 self.Liste_valeurs.put_liste(liste_valeurs)
166 listeActuelle=self.Liste_valeurs.get_liste()
167 liste_choix=self.node.item.get_liste_possible(listeActuelle)
168 self.Liste_choix.put_liste(liste_choix)
169 self.selected_choix = None
171 def selectChoix(self,name):
172 self.selected_choix = name
174 def deselectChoix(self,name):
175 self.selectChoix = None
177 def raisecmd(self,page):
183 class SHELLPanel(newSIMPPanel):
185 Classe Panel utilisé pour les mots-clés simples qui attendent un shell pour valeur
188 def makeValeurPage(self,page):
190 Affiche la page concernant l'objet pointé par self qui attend un shell
192 objet_mc = self.node.item.get_definition()
193 aide = self.gen_aide()
194 aide = justify_text(texte=aide)
195 self.frame = Frame(page)
196 self.frame.place(relx=0,rely=0,relwidth=1,relheight=1)
197 label_aide = Label(self.frame,text = aide)
198 label_aide.place(relx=0.5,rely=0.1,anchor='center')
199 self.text = Text(self.frame,bg='gray95')
200 self.text.place(relx=0.2,rely=0.2,relwidth=0.6,relheight=0.6)
201 but_val = Button(self.frame,text='Valider',command = self.valide_shell)
202 but_ann = Button(self.frame,text='Annuler',command = self.annule_shell)
203 but_val.place(relx=0.35,rely=0.9,anchor='center')
204 but_ann.place(relx=0.65,rely=0.9,anchor='center')
205 self.display_valeur()
209 Retourne une chaîne de caractères d'aide sur la valeur qu'attend l'objet
212 return "Un shell est attendu"
214 def valide_shell(self,event=None):
216 Récupère la valeur saisie par l'utilisateur dans self.text
217 et la stocke dans l'objet MCSIMP courant
219 texte = self.text.get(1.0,END)
220 self.record_valeur(texte)
222 def annule_shell(self,event=None):
224 Annule toute saisie dans self.text
226 self.text.delete(0,END)
228 def display_valeur(self,val=None):
230 Affiche la valeur de l'objet pointé par self
235 valeur = self.node.item.get_valeur()
236 if valeur == None or valeur == '': return
237 self.text.insert(END,valeur)
239 class PLUSIEURS_Panel(newSIMPPanel):
241 Classe virtuelle servant de classe mère à toutes celles définissant
242 un panneau pour un mot-clé simple qui attend une liste de valeurs
244 def accepte_modifs_valeur(self,min,max):
246 Méthode qui récupère la liste des valeurs donnée par l'utilisateur
247 et l'affecte au mot-clé courant.
249 l1_valeurs = self.Liste_valeurs.get_liste()
251 for val in l1_valeurs :
252 if val != '' and val != None :
253 l_valeurs.append(val)
255 longueur = len(l_valeurs)
256 if longueur < min or longueur > max :
257 self.parent.appli.affiche_infos("Valeur refusée : nombre d'éléments incorrect dans la liste")
260 valeur = tuple(l_valeurs)
262 valeur = l_valeurs[0]
266 self.parent.appli.affiche_infos("Valeur acceptée")
267 self.record_valeur(valeur)
268 #if self.node.item.isvalid():
269 # self.node.parent.select()
270 # fermeture de la fenêtre de sélection
271 if self.ajout_valeurs:
272 self.ajout_valeurs.quit()
274 def annule_modifs_valeur(self):
276 RAZ de la liste des valeurs (annule toutes les valeurs saisies par l'utilisateur)
279 # fermeture de la fenêtre de sélection
280 if self.ajout_valeurs:
281 self.ajout_valeurs.quit()
283 def add_valeur_sans_into(self,name=None,encorevalide=1):
285 Lit ce que l'utilisateur a saisi dans self.entry et cherche à
287 - si la valeur est acceptable, elle est ajoutée dans la liste des valeurs
288 - sinon elle est refusée
289 encorevalide vaut 1 si le validateur trouve l item et la liste correctes
290 0 si le validateur trouve la valeur de l item incorrecte
291 -1 si le validateur trouve la liste incorrecte
294 commentaire="Valeur incorrecte : ajout à la liste refusé"
297 # Lecture de la zone de saisie et evaluation si nécessaire
301 valeurentree = self.get_valeur()
302 if valeurentree == '': valeur=None
303 valeurentree,testvalide=self.node.item.eval_valeur(valeur)
304 if (not testvalide) :
305 commentaire = "impossible d'évaluer : %s " %`valeurentree`
307 # Pas de traitement des valeurs nulles ( a priori clic involontaire
308 if (valeur == None or valeur =="") :
309 commentaire = "Pas de saisie des valeurs nulles"
313 testtype = self.node.item.object.verif_type(valeur)
315 commentaire ="Type de la valeur incorrecte"
318 if (encorevalide ==0) :
319 commentaire=self.node.item.info_erreur_item()
320 if (encorevalide == -1) :
321 commentaire=self.node.item.info_erreur_liste()
322 # On traite le cas ou la liste n est pas valide pour un pb de cardinalite
323 min,max = self.node.item.GetMinMax()
324 if len(self.Liste_valeurs.get_liste()) >= max :
325 commentaire="La liste a déjà atteint le nombre maximum d'éléments,ajout refusé"
327 if testvalide and (encorevalide == 1):
328 min,max = self.node.item.GetMinMax()
331 liste_valeurs = self.Liste_valeurs.get_liste()
332 if len(liste_valeurs) >= max :
333 commentaire="La liste a déjà atteint le nombre maximum d'éléments,ajout refusé"
335 liste_valeurs.append(valeur)
336 self.Liste_valeurs.put_liste(liste_valeurs)
338 commentaire="Nouvelle valeur acceptée"
340 commentaire ="Type de la valeur incorrecte"
343 self.parent.appli.affiche_infos(commentaire)
345 def sup_valeur_sans_into(self,name=None):
347 Méthode qui sert à retirer de la liste des valeurs la valeur sélectionnée
349 liste_valeurs = self.Liste_valeurs.get_liste()
351 liste_valeurs.remove(self.selected_valeur)
353 # la valeur sélectionnée n'est pas dans la liste
355 self.Liste_valeurs.put_liste(liste_valeurs)
356 self.display_valeur(self.selected_valeur)
357 self.selected_valeur = None
359 def display_valeur(self,val=None):
361 Affiche la valeur passée en argument dans l'entry de saisie.
362 Par défaut affiche la valeur du mot-clé simple
365 valeur = self.node.item.getval()
368 self.entry.delete(0,END)
369 if not valeur : return
370 self.entry.insert(0,str(valeur))
373 class PLUSIEURS_INTO_Panel(PLUSIEURS_Panel):
375 Classe servant à définir le panneau permettant d'afficher et de saisir une
376 liste de valeurs à choisir parmi une liste discrètes de valeurs possibles
378 def makeValeurPage(self,page):
380 Génère la page de saisie de plusieurs valeurs parmi un ensemble discret
383 self.ajout_valeurs = None
384 # On récupère la bulle d'aide du panneau, l'objet, min et max (cardinalité de la liste),
385 # la liste des choix et la liste des valeurs
386 aide = self.get_aide()
387 aide = justify_text(texte=aide)
388 bulle_aide=self.get_bulle_aide()
389 objet_mc = self.node.item.get_definition()
390 min,max = self.node.item.GetMinMax()
391 #l_choix=list(objet_mc.into)
392 l_valeurs = self.node.item.GetListeValeurs()
393 l_choix= self.node.item.get_liste_possible(l_valeurs)
394 # reinitialisation de l_valeurs
395 l_valeurs = self.node.item.GetListeValeurs()
397 # remplissage du panneau
398 self.frame_valeurs = Frame(page)
399 self.frame_valeurs.place(relx=0.05,rely=0.05,relwidth=0.35,relheight=0.7)
400 self.frame_boutons_fleches = Frame(page)
401 self.frame_boutons_fleches.place(relx=0.4,rely=0.,relwidth=0.2,relheight=0.7)
402 self.frame_choix = Frame(page)
403 self.frame_choix.place(relx=0.6,rely=0.05,relwidth=0.35,relheight=0.7)
404 self.frame_boutons = Frame(page)
405 self.frame_boutons.place(relx=0.35,rely=0.87,relwidth=0.3,relheight=0.1)
406 self.frame_aide = Frame(page)
407 self.frame_aide.place(relx=0.1,rely=0.75,relwidth=0.9,relheight=0.1)
408 liste_commandes_valeurs = (("<Button-1>",self.selectValeur),
409 ("<Button-3>",self.deselectValeur),
410 ("<Double-Button-1>",self.sup_valeur))
411 liste_commandes_choix = (("<Button-1>",self.selectChoix),
412 ("<Button-3>",self.deselectChoix),
413 ("<Double-Button-1>",self.add_choix))
414 self.Liste_valeurs = ListeChoix(self,self.frame_valeurs,
415 l_valeurs,liste_commandes = liste_commandes_valeurs,
416 titre="Valeur(s) actuelle(s)")
417 self.Liste_choix = ListeChoix(self,self.frame_choix,l_choix,
418 liste_commandes = liste_commandes_choix,
419 titre= "Valeurs possibles")
420 bouton_add = Button(self.frame_boutons_fleches,
422 image = images.get_image('arrow_left'),
423 command = self.add_choix)
424 bouton_sup = Button(self.frame_boutons_fleches,
426 image = images.get_image('arrow_right'),
427 command = self.sup_valeur)
428 bouton_accepter = Button(self.frame_boutons,
430 command = lambda s=self,m=min,M=max : s.accepte_modifs_valeur(m,M))
431 bouton_annuler = Button(self.frame_boutons,
433 command = self.annule_modifs_valeur)
434 bouton_add.place(relx=0.3,rely=0.35)
435 bouton_sup.place(relx=0.3,rely=0.65)
436 for but in (bouton_accepter,bouton_annuler):
437 but.pack(side='left',padx=5)
438 self.Liste_valeurs.affiche_liste()
439 self.Liste_choix.affiche_liste()
440 for fram in (self.frame_valeurs,self.frame_boutons_fleches,self.frame_choix,self.frame_boutons):
441 fram.bind("<Button-3>",lambda e,s=self,a=bulle_aide : s.parent.appli.affiche_aide(e,a))
442 fram.bind("<ButtonRelease-3>",self.parent.appli.efface_aide)
443 self.frame_aide.update()
444 self.aide = Label(self.frame_aide,
448 wraplength=int(self.frame_aide.winfo_width()*0.8))
449 self.aide.place(relx=0.5,rely=0.5,anchor='center',relwidth=1)
453 Retourne la phrase d'aide indiquant de quel type de base doivent être les valeurs
454 que saisit l'utilisateur
457 mc = self.node.item.get_definition()
458 d_aides = { 'TXM' : 'chaînes de caractères',
463 if not d_aides.has_key(type) :
465 return str(mc.min)+" valeur(s) est(sont) attendue(s)"
467 return "entrez entre "+str(mc.min)+" et "+str(mc.max)+" valeurs"
469 commentaire="Une liste de "+str(mc.min)+" "+d_aides[type]+" est attendue"
471 commentaire="Entre "+str(mc.min)+" et "+str(mc.max)+" valeurs de type "+d_aides[type]+" sont attendues"
472 aideval=self.node.item.aide()
473 commentaire=commentaire + "\n" + aideval
476 def get_bulle_aide(self):
478 Retourne la bulle d'aide du panneau (affichée par clic droit)
480 return """Un clic sur une valeur des deux listes la sélectionne.
481 - Un clic sur la flèche gauche stocke la valeur possible sélectionnée
482 dans la liste des valeurs que vous voulez affecter au mot-clé simple
483 - Un clic sur la flèche droite déstocke la valeur du mot-clé simple
484 sélectionnée (elle apparaît alors à nouveau comme choix possible
485 dans la liste des choix à droite)
486 - Cliquez sur 'Valider' pour affecter la liste des valeurs sélectionnées
487 au mot-clé simple courant
488 - Cliquez sur 'Annuler' pour restaurer la valeur du mot-clé simple
489 avant toute modification depuis le dernier 'Valider'"""
491 class PLUSIEURS_BASE_Panel(PLUSIEURS_Panel):
493 Classe définissant le panel associé aux mots-clés qui demandent
494 à l'utilisateur de donner une liste de valeurs qui ne sont pas
495 à choisir dans une liste discrètes et qui sont de type de base :
496 entier, réel, string,...
498 def makeValeurPage(self,page):
500 Crée la page de saisie d'une liste de valeurs à priori quelconques,
501 cad qui ne sont pas à choisir dans une liste prédéfinie
503 # On récupère la bulle d'aide du panneau, l'objet, l'aide,min et max (cardinalité de la liste),
504 # et la liste des valeurs déjà affectées à l'objet courant
505 bulle_aide=self.get_bulle_aide()
506 objet_mc = self.node.item.get_definition()
507 aide = self.get_aide()
508 aide = justify_text(texte=aide)
509 min,max = self.node.item.GetMinMax()
510 l_valeurs = self.node.item.GetListeValeurs()
512 # création des frames globales
513 self.frame1 = Frame(page,relief='groove',bd=2)
514 self.frame2 = Frame(page)
515 self.frame1.place(relx=0.,rely=0.,relwidth=1.,relheight=0.85)
516 self.frame2.place(relx=0.,rely=0.85,relwidth=1,relheight=0.15)
517 self.frame_right = Frame(self.frame1)
518 self.frame_right.place(relx=0.35,rely=0.,relwidth=0.65,relheight=1.)
520 # création des frames internes
521 self.frame_valeurs = Frame(self.frame1)
522 self.frame_valeurs.place(relx=0.02,rely=0.05,relwidth=0.35,relheight=0.95)
523 self.frame_boutons_fleches = Frame(self.frame_right)
524 self.frame_boutons_fleches.place(relx=0.,rely=0.2,relwidth=0.2,relheight=0.5)
525 self.frame_choix = Frame(self.frame_right)
526 self.frame_choix.place(relx=0.2,rely=0.2,relwidth=0.7,relheight=0.5)
527 self.frame_aide = Frame(self.frame_right)
528 self.frame_aide.place(relx=0.1,rely=0.7,relwidth=0.8,relheight=0.3)
529 self.frame_boutons = Frame(self.frame2)
530 self.frame_boutons.place(relx=0.35,rely=0.,relwidth=0.3,relheight=1.)
531 for fram in (self.frame1,self.frame2,self.frame_right,self.frame_valeurs,
532 self.frame_boutons_fleches,self.frame_choix,self.frame_aide,self.frame_boutons):
533 fram.bind("<Button-3>",lambda e,s=self,a=bulle_aide : s.parent.appli.affiche_aide(e,a))
534 fram.bind("<ButtonRelease-3>",self.parent.appli.efface_aide)
536 # création des objets dans les frames
537 liste_commandes_valeurs = (("<Button-1>",self.selectValeur),
538 ("<Button-3>",self.deselectValeur),
539 ("<Double-Button-1>",self.sup_valeur_sans_into))
540 self.Liste_valeurs = ListeChoix(self,self.frame_valeurs,l_valeurs,liste_commandes = liste_commandes_valeurs,
541 titre="Valeur(s) actuelle(s)")
543 # Création de l'entry ou de la liste des SD
544 self.label = Label(self.frame_choix,text="Valeur :")
545 # PN : pour ajouter les validators
546 self.make_entry(frame = self.frame_choix,command = self.add_valeur_plusieurs_base)
547 self.label.place(relx=0.05,rely=0.5)
549 # Création d'un bouton "Importer ..." sur le panel.
550 bouton_valeurs_fichier = Button(self.frame_choix,
552 command=self.select_in_file)
553 bouton_valeurs_fichier.place(relx=0.28,rely=0.7,relwidth=0.6)
554 self.ajout_valeurs = None
556 # boutons Ajouter et Supprimer
557 bouton_add = Button(self.frame_boutons_fleches,
558 image = images.get_image('arrow_left'),
559 command = self.add_valeur_plusieurs_base)
560 bouton_sup = Button(self.frame_boutons_fleches,
561 image = images.get_image('arrow_right'),
562 command = self.sup_valeur_sans_into)
563 bouton_add.place(relx=0.3,rely=0.35)
564 bouton_sup.place(relx=0.3,rely=0.65)
565 # affichage de l'aide
566 self.frame_aide.update()
567 self.aide = Label(self.frame_aide,
571 wraplength=int(self.frame_aide.winfo_width()*0.8))
572 self.aide.place(relx=0.5,rely=0.5,anchor='center',relwidth=1)
573 self.Liste_valeurs.affiche_liste()
574 # boutons Accepter et Annuler
575 bouton_accepter = Button(self.frame_boutons,
577 command = lambda s=self,m=min,M=max : s.accepte_modifs_valeur(m,M))
578 bouton_annuler = Button(self.frame_boutons,
580 command = self.annule_modifs_valeur)
581 for but in (bouton_accepter,bouton_annuler):
582 but.pack(side='left',padx=5)
584 def add_valeur_plusieurs_base(self,name=None):
588 valeurentree = self.get_valeur()
589 if valeurentree == '': valeur=None
590 valeur,validite=self.node.item.eval_valeur(valeurentree)
592 commentaire = "impossible d'évaluer : %s " %`valeurentree`
593 self.parent.appli.affiche_infos(commentaire)
596 encorevalide=self.node.item.valide_item(valeur)
598 listecourante=self.Liste_valeurs.get_liste()
599 encorevalide=self.node.item.valide_liste_partielle(valeur,listecourante)
600 if not encorevalide : encorevalide = -1
601 self.add_valeur_sans_into(valeur,encorevalide)
603 def select_in_file(self):
604 """ Permet d'ouvrir un fichier choisi par l'utilisateur. """
605 nom_fichier = askopenfilename(title="Choix fichier :")
606 if nom_fichier == "":
609 f = open(nom_fichier, "rb")
610 selection_texte = f.read()
612 self.ajout_valeurs = FenetreDeSelection(self,
615 titre="Sélection de valeurs",
616 texte=selection_texte)
618 traceback.print_exc()
619 showinfo("Erreur de fichier","impossible d'ouvir le fichier "+nom_fichier)
621 def get_bulle_aide(self):
623 Retourne l'aide associée au panneau courant
625 return """Taper dans la boîte de saisie de droite la valeur que
626 vous voulez affecter au mot-clé simple.
627 - Cliquez sur la flèche gauche ou pressez <Return> pour la faire glisser
628 dans la liste des valeurs que vous voulez affecter au mot-clé simple
629 - Un clic sur une valeur de la liste la sélectionne
630 - Un clic sur la flèche droite ou un double-clic retire la valeur
631 sélectionnée de la liste
632 - Cliquez sur 'Valider' pour que la nouvelle valeur désirée soit affectée
634 - Cliquez sur 'Annuler' pour annuler toutes les modifications faites
635 depuis le dernier clic sur 'Valider'"""
639 Retourne la phrase d'aide indiquant de quel type de base doivent être les valeurs
640 que saisit l'utilisateur
643 mc = self.node.item.get_definition()
644 d_aides = { 'TXM' : 'chaînes de caractères',
649 if not d_aides.has_key(type) : return 'Type de base inconnu'
651 commentaire="Une liste de "+d_aides[type]+" chaînes de caractères est attendue"
653 commentaire="Une liste de "+d_aides[type]+" est attendue (min="+`mc.min`+",max="+`mc.max`+')'
654 aideval=self.node.item.aide()
655 commentaire=commentaire +"\n"+aideval
658 def make_entry(self,frame,command):
660 Crée l'entry de saisie de la valeur souhaitée : distingue le
661 cas d'un complexe attendu, d'une autre valeur quelconque
663 if self.node.item.wait_complex():
664 self.typ_cplx=StringVar()
665 self.typ_cplx.set('RI')
666 rb1 = Radiobutton(frame, text='RI',variable=self.typ_cplx,value='RI')
667 rb2 = Radiobutton(frame, text='MP',variable=self.typ_cplx,value='MP')
668 self.entry1 = Pmw.EntryField(frame,validate='real')
669 self.entry2 = Pmw.EntryField(frame,validate='real')
670 rb1.place(relx=0.05,rely = 0.4)
671 rb2.place(relx=0.05,rely = 0.6)
672 self.entry1.component('entry').bind("<Return>",lambda e,s=self:s.entry2.component('entry').focus)
673 self.entry2.component('entry').bind("<Return>",lambda e,c=command:c())
674 self.entry1.place(relx=0.27,rely = 0.5,relwidth=0.35)
675 self.entry2.place(relx=0.65,rely = 0.5,relwidth=0.35)
678 self.entry = Entry(frame,relief='sunken')
679 self.entry.place(relx=0.28,rely=0.5,relwidth=0.6)
680 self.entry.bind("<Return>",lambda e,c=command:c())
683 def get_valeur(self):
685 Retourne la valeur saisie par l'utilisateur dans self.entry
687 return self.entry.get()
689 def erase_valeur(self):
691 Efface la valeur donnée par l'utilisateur dans l'entry
693 self.entry.delete(0,END)
695 class PLUSIEURS_ASSD_Panel(PLUSIEURS_Panel):
697 Classe définissant le panel associé aux mots-clés qui demandent
698 à l'utilisateur de donner une liste de valeurs qui ne sont pas
699 à choisir dans une liste discrètes et qui sont de type dérivé d'ASSD
701 def makeValeurPage(self,page):
703 Génère la page de saisie de plusieurs noms de SD parmi un ensemble discret
704 de SD possibles, cad d'un type cohérent avec les types attendus par le mot-clé simple
706 # On récupère la bulle d'aide du panneau, l'objet, l'aide, min et max (cardinalité de la liste),
707 # la liste des valeurs déjà affectées à l'objet courant et la liste des SD du bon type
708 bulle_aide=self.get_bulle_aide()
709 self.ajout_valeurs=None
710 objet_mc = self.node.item.get_definition()
711 aide = self.get_aide()
712 aide = justify_text(texte=aide)
713 min,max = self.node.item.GetMinMax()
714 l_valeurs = self.node.item.GetListeValeurs()
715 l_choix=self.node.item.get_sd_avant_du_bon_type()
717 # remplissage du panneau
718 self.frame_valeurs = Frame(page)
719 self.frame_valeurs.place(relx=0.05,rely=0.05,relwidth=0.35,relheight=0.7)
720 self.frame_boutons_fleches = Frame(page)
721 self.frame_boutons_fleches.place(relx=0.4,rely=0.,relwidth=0.2,relheight=0.7)
722 self.frame_choix = Frame(page)
723 self.frame_choix.place(relx=0.6,rely=0.05,relwidth=0.35,relheight=0.7)
724 self.frame_boutons = Frame(page)
725 self.frame_boutons.place(relx=0.35,rely=0.87,relwidth=0.3,relheight=0.1)
726 liste_commandes_valeurs = (("<Button-1>",self.selectValeur),
727 ("<Button-3>",self.deselectValeur),
728 ("<Double-Button-1>",self.sup_valeur_sans_into))
729 liste_commandes_choix = (("<Button-1>",self.selectChoix),
730 ("<Button-3>",self.deselectChoix),
731 # ("<Double-Button-1>",self.add_valeur_sans_into))
732 ("<Double-Button-1>",self.add_eval_valeur_sans_into))
733 self.Liste_valeurs = ListeChoix(self,self.frame_valeurs,l_valeurs,liste_commandes = liste_commandes_valeurs,
734 titre="Valeur(s) actuelle(s)")
735 self.Liste_choix = ListeChoix(self,self.frame_choix,l_choix,liste_commandes = liste_commandes_choix,
736 titre= "Valeurs possibles")
737 bouton_add = Button(self.frame_boutons_fleches,
739 image = images.get_image('arrow_left'),
740 # command = self.add_valeur_sans_into)
741 command = self.add_eval_valeur_sans_into)
742 bouton_sup = Button(self.frame_boutons_fleches,
744 image = images.get_image('arrow_right'),
745 command = self.sup_valeur_sans_into)
746 bouton_accepter = Button(self.frame_boutons,
748 command = lambda s=self,m=min,M=max : s.accepte_modifs_valeur(m,M))
749 bouton_annuler = Button(self.frame_boutons,
751 command = self.annule_modifs_valeur)
752 bouton_add.place(relx=0.3,rely=0.35)
753 bouton_sup.place(relx=0.3,rely=0.65)
754 for but in (bouton_accepter,bouton_annuler):
755 but.pack(side='left',padx=5)
756 self.Liste_valeurs.affiche_liste()
757 self.Liste_choix.affiche_liste()
758 for fram in (self.frame_valeurs,self.frame_boutons_fleches,self.frame_choix,self.frame_boutons):
759 fram.bind("<Button-3>",lambda e,s=self,a=bulle_aide : s.parent.appli.affiche_aide(e,a))
760 fram.bind("<ButtonRelease-3>",self.parent.appli.efface_aide)
762 def add_eval_valeur_sans_into(self,valeurentree=None):
763 valeur,validite=self.node.item.eval_valeur(valeurentree)
765 commentaire = "impossible d'évaluer : %s " %`valeurentree`
766 self.parent.appli.affiche_infos(commentaire)
768 self.add_valeur_sans_into(valeur)
770 def get_bulle_aide(self):
772 Retourne la bulle d'aide associée au panneau
774 return """Un clic sur une valeur des deux listes la sélectionne.
775 - Un clic sur la flèche gauche stocke la valeur possible sélectionnée
776 dans la liste des valeurs que vous voulez affecter au mot-clé simple
777 - Un clic sur la flèche droite déstocke la valeur du mot-clé simple
778 sélectionnée (elle apparaît alors à nouveau comme choix possible
779 dans la liste des choix à droite)
780 - Cliquez sur 'Valider' pour affecter la liste des valeurs sélectionnées
781 au mot-clé simple courant
782 - Cliquez sur 'Annuler' pour restaurer la valeur du mot-clé simple
783 avant toute modification depuis le dernier 'Valider'"""
787 Retourne la phrase d'aide indiquant de quel type doivent être les
788 valeurs que doit entrer l'utilisateur
791 mc = self.node.item.get_definition()
792 type = mc.type[0].__name__
794 for typ in mc.type[1:] :
795 type = type + ' ou '+typ.__name__
797 commentaire="Une liste de "+`mc.min`+" objets de type "+type+" est attendue"
799 commentaire="Une liste d'objets de type "+type+" est attendue (min="+`mc.min`+",max="+`mc.max`+')'
800 aideval=self.node.item.aide()
801 commentaire=commentaire +"\n"+ aideval
805 def sup_valeur(self,name=None):
807 Supprime la valeur selectionnée de la liste des valeurs et la rajoute
808 à la liste des choix possibles
810 liste_valeurs = self.Liste_valeurs.get_liste()
811 liste_valeurs.remove(self.selected_valeur)
812 liste_choix = self.node.item.get_definition().into
813 liste_choix = substract_list(liste_choix,liste_valeurs)
814 self.Liste_valeurs.put_liste(liste_valeurs)
815 self.Liste_choix.put_liste(liste_choix)
816 self.selected_valeur = None
818 def erase_valeur(self):
821 def get_valeur(self):
823 Retourne la valeur sélectionnée dans la liste des choix
825 return self.selected_choix
827 def display_valeur(self,val=None):
829 Affiche la valeur passée en argument dans l'entry de saisie.
830 Par défaut affiche la valeur du mot-clé simple
832 # Il n'y a pas d'entry pour ce type de panneau
836 class UNIQUE_Panel(newSIMPPanel):
838 Classe virtuelle servant de classe mère à toutes celles définissant un panneau
839 permettant l'affichage et la saisie d'une valeur unique pour le mot-clé simple
842 def erase_valeur(self):
844 Efface l'entry de saisie
846 self.entry.delete(0,END)
848 def get_valeur(self):
850 Retourne la valeur donnée par l'utilisateur
852 return self.entry.get()
854 def valid_valeur(self):
856 Teste si la valeur fournie par l'utilisateur est une valeur permise :
857 - si oui, l'enregistre
858 - si non, restaure l'ancienne valeur
860 if self.parent.modified == 'n' : self.parent.init_modif()
861 anc_val = self.node.item.get_valeur()
862 valeurentree = self.get_valeur()
864 valeur,validite=self.node.item.eval_valeur(valeurentree)
866 commentaire = "impossible d'évaluer : %s " %`valeurentree`
867 self.parent.appli.affiche_infos(commentaire)
870 test = self.node.item.set_valeur(valeur)
873 mess = "impossible d'évaluer : %s " %`valeur`
874 self.parent.appli.affiche_infos("Valeur du mot-clé non autorisée : "+mess)
875 elif self.node.item.isvalid() :
876 self.parent.appli.affiche_infos('Valeur du mot-clé enregistrée')
877 if self.node.item.get_position()=='global':
878 self.node.etape.verif_all()
879 elif self.node.item.get_position()=='global_jdc':
880 self.node.racine.verif_all()
882 self.node.parent.verif()
884 self.node.parent.select()
886 cr = self.node.item.get_cr()
887 mess = "Valeur du mot-clé non autorisée :"+cr.get_mess_fatal()
888 self.reset_old_valeur(anc_val,mess=mess)
890 class UNIQUE_INTO_Panel(UNIQUE_Panel):
892 Classe définissant le panel associé aux mots-clés qui demandent
893 à l'utilisateur de choisir une seule valeur parmi une liste de valeurs
896 def makeValeurPage(self,page):
898 Génère la page de saisie d'une seule valeur parmi un ensemble
901 # récupération de la bulle d'aide et de l'objet mc
902 bulle_aide=self.get_bulle_aide()
903 objet_mc = self.node.item.get_definition()
904 # remplissage du panel
905 self.frame_valeur = Frame(page)
906 self.frame_valeur.pack(fill='both',expand=1)
907 self.frame_valeur.bind("<Button-3>",lambda e,s=self,a=bulle_aide :
908 s.parent.appli.affiche_aide(e,a))
909 self.frame_valeur.bind("<ButtonRelease-3>",self.parent.appli.efface_aide)
910 #l_choix=list(objet_mc.into)
912 l_choix=self.node.item.get_liste_possible([])
913 self.label = Label(self.frame_valeur,text='Choisir une valeur :')
914 self.label.pack(side='top')
915 self.frame = Frame(page)
916 self.frame.place(relx=0.33,rely=0.2,relwidth=0.33,relheight=0.6)
917 liste_commandes = (("<Button-1>",self.selectChoix),
918 ("<Button-3>",self.deselectChoix),
919 ("<Double-Button-1>",self.record_valeur))
920 self.Liste_choix = ListeChoix(self,self.frame,l_choix,
921 liste_commandes = liste_commandes,
922 titre="Valeurs possibles")
923 self.Liste_choix.affiche_liste()
925 def get_bulle_aide(self):
927 Retourne la bulle d'aide affectée au panneau courant (affichée par clic droit)
929 return """Double-cliquez sur la valeur désirée
930 pour valoriser le mot-clé simple courant"""
932 class UNIQUE_ASSD_Panel(UNIQUE_Panel):
934 Classe servant à définir le panneau associé aux objets qui attendent une valeur unique
935 d'un type dérivé d'ASSD
937 def valid_valeur_automatique(self):
939 Réalise la validation d'un concept sans remonter dans le
940 node parent dans le cas ou il n'y a qu'un concept possible (liste de longueur 1)
941 Identique à valid_valeur moins appel de self.node.parent.select()
942 On pourrait supposer que le seul concept présent est valide et donc ne pas
943 réaliser tous les tests de vérification.
945 if self.parent.modified == 'n' : self.parent.init_modif()
946 valeur = self.get_valeur()
948 anc_val = self.node.item.get_valeur()
949 valeur,validite=self.node.item.eval_valeur_item(valeur)
950 test = self.node.item.set_valeur(valeur)
952 mess = "impossible d'évaluer : %s " %`valeur`
953 self.parent.appli.affiche_infos("Valeur du mot-clé non autorisée :"+mess)
954 elif self.node.item.isvalid() :
955 self.parent.appli.affiche_infos('Valeur du mot-clé enregistrée')
956 if self.node.item.get_position()=='global':
957 self.node.etape.verif_all()
958 elif self.node.item.get_position()=='global_jdc':
959 self.node.racine.verif_all()
961 self.node.parent.verif()
964 cr = self.node.item.get_cr()
965 mess = "Valeur du mot-clé non autorisée :"+cr.get_mess_fatal()
966 self.reset_old_valeur(anc_val,mess=mess)
968 def makeValeurPage(self,page):
970 Génère la page de saisie de la valeur du mot-clé simple courant qui doit être une
971 SD de type dérivé d'ASSD
973 # Récupération de l'aide associée au panneau, de l'aide destinée à l'utilisateur,
974 # et de la liste des SD du bon type (constituant la liste des choix)
975 bulle_aide=self.get_bulle_aide()
977 aide= justify_text(texte=aide)
978 liste_noms_sd = self.node.item.get_sd_avant_du_bon_type()
979 # Remplissage du panneau
980 self.valeur_choisie = StringVar()
981 self.valeur_choisie.set('')
982 min,max = self.node.item.GetMinMax()
983 if (min == 1 and min == max and len(liste_noms_sd)==1):
984 if self.valeur_choisie.get() != liste_noms_sd[0]:
985 self.valeur_choisie.set(liste_noms_sd[0])
986 self.valid_valeur_automatique()
988 self.frame_valeur = Frame(page)
989 self.frame_valeur.pack(fill='both',expand=1)
990 self.frame_valeur.bind("<Button-3>",lambda e,s=self,a=bulle_aide : s.parent.appli.affiche_aide(e,a))
991 self.frame_valeur.bind("<ButtonRelease-3>",self.parent.appli.efface_aide)
992 self.listbox = Pmw.ScrolledListBox(self.frame_valeur,
995 label_text="Structures de données du type\n requis par l'objet courant :",
997 selectioncommand=self.select_valeur_from_list,
998 dblclickcommand=lambda s=self,c=self.valid_valeur : s.choose_valeur_from_list(c))
999 self.listbox.place(relx=0.5,rely=0.3,relheight=0.4,anchor='center')
1000 Label(self.frame_valeur,text='Structure de donnée choisie :').place(relx=0.05,rely=0.6)
1001 #self.label_valeur = Label(self.frame_valeur,textvariable=self.valeur_choisie)
1002 Label(self.frame_valeur,textvariable=self.valeur_choisie).place(relx=0.5,rely=0.6)
1003 # affichage de la valeur courante
1004 self.display_valeur()
1006 def get_bulle_aide(self):
1008 Retourne l'aide associée au panneau
1010 return "Double-cliquez sur la structure de donnée désirée pour valoriser le mot-clé simple courant"
1014 Retourne la phrase d'aide indiquant de quel type doit être la valeur à donner par l'utilisateur
1016 mc = self.node.item.get_definition()
1017 type = mc.type[0].__name__
1019 for typ in mc.type[1:] :
1020 type = type + ' ou '+typ.__name__
1021 commentaire="Un objet de type "+type+" est attendu"
1022 aideval=self.node.item.aide()
1023 commentaire=commentaire +"\n"+ aideval
1027 def select_valeur_from_list(self):
1029 Affecte à valeur choisie la sélection courante dans la liste des choix proposée
1031 if len(self.listbox.get()) == 0 : return
1032 choix = self.listbox.getcurselection()[0]
1033 self.valeur_choisie.set(choix)
1035 def choose_valeur_from_list(self,command):
1037 Affecte à valeur choisie la sélection courante dans la liste des choix proposée
1040 if len(self.listbox.get()) == 0 : return
1041 choix = self.listbox.getcurselection()[0]
1042 self.valeur_choisie.set(choix)
1043 apply(command,(),{})
1045 def get_valeur(self):
1047 Retourne la valeur donnée par l'utilisateur au MCS
1049 return self.valeur_choisie.get()
1051 def display_valeur(self):
1053 Affiche la valeur de l'objet pointé par self
1055 valeur = self.node.item.get_valeur()
1056 if valeur == None or valeur == '' : return # pas de valeur à afficher ...
1057 self.valeur_choisie.set(valeur.nom)
1059 def erase_valeur(self):
1062 class UNIQUE_SDCO_Panel(UNIQUE_ASSD_Panel):
1064 Classe servant à définir le panneau correspondant à un mot-clé simple
1065 qui attend une valeur unique de type dérivé d'ASSD ou non encore
1066 existante (type CO(...) utilisé dans les macros uniquement)
1068 def makeValeurPage(self,page):
1070 Génère la page de saisie de la valeur du mot-clé simple courant qui doit être une SD de type dérivé
1073 # Récupération de l'aide associée au panneau, de l'aide destinée à l'utilisateur,
1074 # et de la liste des SD du bon type (constituant la liste des choix)
1075 bulle_aide=self.get_bulle_aide()
1076 aide=self.get_aide()
1077 aide= justify_text(texte=aide)
1078 liste_noms_sd = self.node.item.get_sd_avant_du_bon_type()
1079 # Remplissage du panneau
1080 self.frame_valeur = Frame(page)
1081 self.frame_valeur.pack(fill='both',expand=1)
1082 self.frame_valeur.bind("<Button-3>",lambda e,s=self,a=bulle_aide : s.parent.appli.affiche_aide(e,a))
1083 self.frame_valeur.bind("<ButtonRelease-3>",self.parent.appli.efface_aide)
1084 # affichage de la liste des SD existantes et du bon type
1085 self.listbox = Pmw.ScrolledListBox(self.frame_valeur,
1086 items=liste_noms_sd,
1088 label_text="Structures de données du type\n requis par l'objet courant :",
1090 selectioncommand=self.select_valeur_from_list,
1091 dblclickcommand=lambda s=self,c=self.valid_valeur : s.choose_valeur_from_list(c))
1092 self.listbox.place(relx=0.5,rely=0.3,relheight=0.4,anchor='center')
1093 # affichage du bouton 'Nouveau concept'
1094 self.b_co = Pmw.OptionMenu(self.frame_valeur,labelpos='w',label_text = "Nouveau concept : ",
1095 items = ('NON','OUI'),menubutton_width=10)
1096 self.b_co.configure(command = lambda e,s=self : s.ask_new_concept())
1097 self.b_co.place(relx=0.05,rely=0.6,anchor='w')
1098 self.label_co = Label(self.frame_valeur,text='Nom du nouveau concept :')
1099 self.entry_co = Entry(self.frame_valeur)
1100 self.entry_co.bind('<Return>',self.valid_nom_concept_co)
1101 # affichage du label de la structure de donnée choisie
1102 self.l_resu = Label(self.frame_valeur,text='Structure de donnée choisie :')
1103 self.valeur_choisie = StringVar()
1104 self.label_valeur = Label(self.frame_valeur,textvariable=self.valeur_choisie)
1105 self.frame_valeur.update()
1106 self.aide = Label(self.frame_valeur,
1108 wraplength=int(self.frame_valeur.winfo_width()*0.8),
1110 self.aide.place(relx=0.5,rely=0.85,anchor='n')
1111 # affichage de la valeur courante
1112 self.display_valeur()
1114 def get_bulle_aide(self):
1116 Retourne la bulle d'aide du panneau
1118 return """Double-cliquez sur la structure de donnée désirée
1119 pour valoriser le mot-clé simple courant ou cliquez sur NOUVEAU CONCEPT pour
1120 entrer le nom d'un concept non encore existant"""
1122 def valid_valeur(self):
1124 Teste si la valeur fournie par l'utilisateur est une valeur permise :
1125 - si oui, l'enregistre
1126 - si non, restaure l'ancienne valeur
1128 if self.parent.modified == 'n' : self.parent.init_modif()
1129 valeur = self.get_valeur()
1131 anc_val = self.node.item.get_valeur()
1132 test_CO=self.node.item.is_CO(anc_val)
1133 test = self.node.item.set_valeur(valeur)
1135 mess = "impossible d'évaluer : %s " %`valeur`
1136 self.parent.appli.affiche_infos("Valeur du mot-clé non autorisée :"+mess)
1138 elif self.node.item.isvalid() :
1139 self.parent.appli.affiche_infos('Valeur du mot-clé enregistrée')
1141 # il faut egalement propager la destruction de l'ancien concept
1142 self.node.item.delete_valeur_co(valeur=anc_val)
1143 # et on force le recalcul des concepts de sortie de l'etape
1144 self.node.item.object.etape.get_type_produit(force=1)
1145 # et le recalcul du contexte
1146 self.node.item.object.etape.parent.reset_context()
1147 self.node.parent.select()
1149 cr = self.node.item.get_cr()
1150 mess = "Valeur du mot-clé non autorisée :"+cr.get_mess_fatal()
1151 self.reset_old_valeur(anc_val,mess=mess)
1153 if self.node.item.get_position()=='global':
1154 self.node.etape.verif_all()
1155 elif self.node.item.get_position()=='global_jdc':
1156 self.node.racine.verif_all()
1158 self.node.parent.verif()
1161 def valid_nom_concept_co(self,event=None):
1163 Lit le nom donné par l'utilisateur au concept de type CO qui doit être
1164 la valeur du MCS courant et stocke cette valeur
1166 if self.parent.modified == 'n' : self.parent.init_modif()
1167 anc_val = self.node.item.get_valeur()
1168 nom_concept = self.entry_co.get()
1169 test,mess=self.node.item.set_valeur_co(nom_concept)
1171 # On n'a pas pu créer le concept
1172 self.parent.appli.affiche_infos(mess)
1174 elif self.node.item.isvalid() :
1175 self.parent.appli.affiche_infos('Valeur du mot-clé enregistrée')
1176 self.node.parent.select()
1178 cr = self.node.item.get_cr()
1179 mess = "Valeur du mot-clé non autorisée :"+cr.get_mess_fatal()
1180 self.reset_old_valeur(anc_val,mess=mess)
1182 if self.node.item.get_position()=='global':
1183 self.node.etape.verif_all()
1184 elif self.node.item.get_position()=='global_jdc':
1185 self.node.racine.verif_all()
1187 self.node.parent.verif()
1188 if self.node.item.isvalid():
1189 self.node.parent.select()
1192 def ask_new_concept(self):
1194 Crée une entry dans le panneau d'un MCS qui attend un concept OU un CO() afin de
1195 permettre à l'utilisateur de donner le nom du nouveau concept
1197 new_concept = self.b_co.getcurselection()
1198 if new_concept == 'OUI':
1199 self.label_co.place(relx=0.05,rely=0.7)
1200 self.entry_co.place(relx=0.45,rely=0.7,relwidth=0.25)
1201 self.l_resu.place_forget()
1202 self.label_valeur.place_forget()
1203 self.entry_co.focus()
1204 elif new_concept == 'NON':
1205 # On est passe de OUI à NON, on supprime la valeur
1206 # PN correction de bug (on passe de non a non et cela supprime la valeur)
1207 # ajout du if de le ligne suivane
1208 if self.node.item.is_CO():
1209 self.node.item.delete_valeur_co()
1210 self.record_valeur(name=None,mess="Suppression CO enregistrée")
1211 self.label_co.place_forget()
1212 self.entry_co.place_forget()
1213 self.l_resu.place(relx=0.05,rely=0.7)
1214 self.label_valeur.place(relx=0.45,rely=0.7)
1216 def display_valeur(self):
1218 Affiche la valeur de l'objet pointé par self
1220 valeur = self.node.item.get_valeur()
1221 if valeur == None or valeur == '':
1222 self.valeur_choisie.set('')
1223 return # pas de valeur à afficher ...
1224 # il faut configurer le bouton si la valeur est un objet CO
1225 # sinon afficher le nom du concept dans self.valeur_choisie
1226 if self.node.item.is_CO():
1227 self.b_co.invoke('OUI')
1228 self.entry_co.insert(0,valeur.nom)
1230 self.valeur_choisie.set(valeur.nom)
1232 def record_valeur(self,name=None,mess='Valeur du mot-clé enregistrée'):
1234 Enregistre val comme valeur de self.node.item.object SANS faire de test de validité
1236 if self.parent.modified == 'n' : self.parent.init_modif()
1240 self.entry_co.delete(0,END)
1241 valeur= self.entry_co.get()
1242 self.node.item.set_valeur_co(valeur)
1243 self.parent.appli.affiche_infos(mess)
1244 # On met a jour le display dans le panneau
1245 self.display_valeur()
1246 if self.node.item.get_position()=='global':
1247 self.node.etape.verif_all()
1248 elif self.node.item.get_position()=='global_jdc':
1249 self.node.racine.verif_all()
1251 self.node.parent.verif()
1252 if self.node.item.isvalid():
1253 self.node.parent.select()
1257 class UNIQUE_BASE_Panel(UNIQUE_Panel):
1259 Classe servant à définir le panneau associé aux mots-clés simples qui attendent
1260 une valeur d'un type de base (entier, réel ou string).
1262 def makeValeurPage(self,page):
1264 Génère la page de saisie de la valeur du mot-clé simple courant qui doit être de type
1265 de base cad entier, réel, string ou complexe
1267 # Récupération de l'aide associée au panneau, de l'aide destinée à l'utilisateur,
1268 # et de la liste des SD du bon type (constituant la liste des choix)
1269 bulle_aide=self.get_bulle_aide()
1270 aide=self.get_aide()
1271 aide= justify_text(texte=aide)
1272 liste_noms_sd = self.node.item.get_sd_avant_du_bon_type()
1273 # Remplissage du panneau
1274 self.frame_valeur = Frame(page)
1275 self.frame_valeur.pack(fill='both',expand=1)
1276 self.frame_valeur.bind("<Button-3>",lambda e,s=self,a=bulle_aide : s.parent.appli.affiche_aide(e,a))
1277 self.frame_valeur.bind("<ButtonRelease-3>",self.parent.appli.efface_aide)
1278 self.label = Label(self.frame_valeur,text='Valeur :')
1279 self.label.place(relx=0.1,rely=0.5)
1280 self.entry = Entry(self.frame_valeur,relief='sunken')
1281 self.entry.place(relx=0.28,rely=0.5,relwidth=0.6)
1282 self.entry.bind("<Return>",lambda e,c=self.valid_valeur:c())
1284 # aide associée au panneau
1285 self.frame_valeur.update()
1286 self.aide = Label(self.frame_valeur,
1288 wraplength=int(self.frame_valeur.winfo_width()*0.8),
1290 self.aide.place(relx=0.5,rely=0.7,anchor='n')
1291 # affichage de la valeur du MCS
1292 self.display_valeur()
1296 Retourne la phrase d'aide indiquant de quel type doit être la valeur
1297 du mot-clé simple fournie par l'utilisateur
1299 mc = self.node.item.get_definition()
1300 d_aides = { 'TXM' : "Une chaîne de caractères est attendue",
1301 'R' : "Un réel est attendu",
1302 'I' : "Un entier est attendu"}
1304 commentaire=d_aides.get(type,"Type de base inconnu")
1305 aideval=self.node.item.aide()
1306 commentaire=commentaire +"\n"+ aideval
1309 def get_bulle_aide(self):
1311 Retourne la bulle d'aide associée au panneau et affichée par clic droit
1313 return """Saisissez la valeur que vous voulez affecter au mot-clé simple
1314 dans la zone de saisie et pressez <Return>"""
1316 def display_valeur(self):
1318 Affiche la valeur de l'objet pointé par self
1320 valeur = self.node.item.get_valeur()
1321 if valeur == None or valeur == '' : return # pas de valeur à afficher ...
1322 self.entry.delete(0,END)
1323 self.entry.insert(0,valeur)
1326 class UNIQUE_COMP_Panel(UNIQUE_Panel):
1328 Classe servant à définir le panneau associé aux mots-clés simples
1329 qui attendent une valeur de type complexe
1331 def makeValeurPage(self,page):
1333 Génère la page de saisie de la valeur du mot-clé simple courant qui doit être de type
1334 de base cad entier, réel, string ou complexe
1336 # Récupération de l'aide associée au panneau et de l'aide destinée à l'utilisateur
1337 bulle_aide=self.get_bulle_aide()
1338 aide=self.get_aide()
1339 aide= justify_text(texte=aide)
1340 # Remplissage du panneau
1341 self.frame_valeur = Frame(page)
1342 self.frame_valeur.pack(fill='both',expand=1)
1343 self.frame_valeur.bind("<Button-3>",lambda e,s=self,a=bulle_aide : s.parent.appli.affiche_aide(e,a))
1344 self.frame_valeur.bind("<ButtonRelease-3>",self.parent.appli.efface_aide)
1345 self.label = Label(self.frame_valeur,text='Valeur :')
1346 self.label.place(relx=0.1,rely=0.5)
1347 self.typ_cplx=StringVar()
1348 self.typ_cplx.set('RI')
1349 rb1 = Radiobutton(self.frame_valeur, text='RI',variable=self.typ_cplx,value='RI')
1350 rb2 = Radiobutton(self.frame_valeur, text='MP',variable=self.typ_cplx,value='MP')
1351 self.entry1 = Pmw.EntryField(self.frame_valeur,validate='real')
1352 self.entry2 = Pmw.EntryField(self.frame_valeur,validate='real')
1353 rb1.place(relx=0.05,rely = 0.4)
1354 rb2.place(relx=0.05,rely = 0.6)
1355 self.entry1.component('entry').bind("<Return>",lambda e,s=self:s.entry2.component('entry').focus())
1356 self.entry2.component('entry').bind("<Return>",lambda e,c=self.valid_valeur:c())
1357 self.entry1.place(relx=0.27,rely = 0.5,relwidth=0.35)
1358 self.entry2.place(relx=0.65,rely = 0.5,relwidth=0.35)
1360 self.frame_valeur.update()
1361 self.aide = Label(self.frame_valeur,
1363 wraplength=int(self.frame_valeur.winfo_width()*0.8),
1365 self.aide.place(relx=0.5,rely=0.7,anchor='n')
1366 # affichage de la valeur du MCS
1367 self.display_valeur()
1369 def display_valeur(self):
1371 Affiche la valeur de l'objet pointé par self
1373 valeur = self.node.item.get_valeur()
1374 if valeur == None or valeur == '' : return # pas de valeur à afficher ...
1375 typ_cplx,x1,x2=valeur
1376 self.entry1.delete(0,END)
1377 self.entry2.delete(0,END)
1378 self.typ_cplx.set(typ_cplx)
1379 self.entry1.setentry(x1)
1380 self.entry2.setentry(x2)
1382 def get_bulle_aide(self):
1384 Retourne la bulle d'aide du panneau
1386 return """-Choisissez votre format de saisie du complexe :
1387 \t 'RI' = parties réelle et imaginaire
1388 \t 'MP' = module/phase (en degrés)
1389 - Saisissez ensuite dans les deux zones de saisie les deux nombres attendus"""
1393 Retourne la phrase d'aide décrivant le type de la valeur que peut prendre
1394 le mot-clé simple courant
1396 commentaire='Un complexe est attendu'
1397 aideval=self.node.item.aide()
1398 commentaire=commentaire +"\n"+ aideval
1401 def get_valeur(self):
1403 Retourne le complexe saisi par l'utilisateur
1406 l.append(self.typ_cplx.get())
1407 l.append(string.atof(self.entry1.get()))
1408 l.append(string.atof(self.entry2.get()))
1411 def erase_valeur(self):
1413 Efface les entries de saisie
1415 self.typ_cplx = 'RI'
1416 self.entry1.delete(0,END)
1417 self.entry2.delete(0,END)
1419 class SIMPTreeItem(Objecttreeitem.AtomicObjectTreeItem):
1420 panel = newSIMPPanel
1426 def affect_panel(self):
1428 Cette méthode attribue le panel à l'objet pointé par self en fonction de la
1429 nature de la valeur demandée pour cet objet
1431 #print "affect_panel : ",self.nom,self.is_list(),self.has_into(), self.get_into(None)
1432 if self.wait_shell():
1433 # l'objet attend un shell
1434 self.panel = SHELLPanel
1435 elif self.has_into():
1436 # l'objet prend sa (ses) valeur(s) dans un ensemble discret de valeurs
1438 self.panel = PLUSIEURS_INTO_Panel
1440 self.panel = UNIQUE_INTO_Panel
1442 # l'objet prend une ou des valeurs à priori quelconques
1444 # on attend une liste de valeurs mais de quel type ?
1445 if self.wait_assd():
1446 # on attend une liste de SD
1447 self.panel = PLUSIEURS_ASSD_Panel
1449 # on attend une liste de valeurs de types debase (entiers, réels,...)
1450 self.panel = PLUSIEURS_BASE_Panel
1452 # on n'attend qu'une seule valeur mais de quel type ?
1454 # on attend une SD ou un objet de la classe CO (qui n'existe pas encore)
1455 self.panel = UNIQUE_SDCO_Panel
1456 elif self.wait_assd():
1458 self.panel = UNIQUE_ASSD_Panel
1460 # on attend une valeur d'un type de base (entier,réel,...)
1461 if self.wait_complex():
1462 # on attend un complexe
1463 self.panel = UNIQUE_COMP_Panel
1465 # on attend un entier, un réel ou une string
1466 self.panel = UNIQUE_BASE_Panel
1467 #print "affect_panel : ",self.panel
1471 Cette méthode indique si le mot cle simple attend une liste (valeur de retour 1)
1472 ou s'il n'en attend pas (valeur de retour 0)
1474 Deux cas principaux peuvent se presenter : avec validateurs ou bien sans.
1475 Dans le cas sans validateur, l'information est donnée par l'attribut max
1476 de la definition du mot cle.
1477 Dans le cas avec validateur, il faut combiner l'information précédente avec
1478 celle issue de l'appel de la méthode is_list sur le validateur.On utilisera
1479 l'operateur ET pour effectuer cette combinaison (AndVal).
1482 min,max = self.GetMinMax()
1486 # Dans le cas avec validateurs, pour que le mot cle soit considéré
1487 # comme acceptant une liste, il faut que max soit supérieur a 1
1488 # ET que la méthode is_list du validateur retourne 1. Dans les autres cas
1489 # on retournera 0 (n'attend pas de liste)
1490 if self.definition.validators :
1491 is_a_list= self.definition.validators.is_list() * is_a_list
1494 def get_into(self,liste_courante=None):
1496 Cette méthode retourne la liste de choix proposée par le mot cle. Si le mot cle ne propose
1497 pas de liste de choix, la méthode retourne None.
1498 L'argument d'entrée liste_courante, s'il est différent de None, donne la liste des choix déjà
1499 effectués par l'utilisateur. Dans ce cas, la méthode get_into doit calculer la liste des choix
1500 en en tenant compte.
1501 Cette méthode part du principe que la relation entre into du mot clé et les validateurs est
1502 une relation de type ET (AndVal).
1504 if not self.object.definition.validators :
1505 return self.object.definition.into
1507 return self.object.definition.validators.get_into(liste_courante,self.definition.into)
1511 Cette méthode indique si le mot cle simple propose un choix (valeur de retour 1)
1512 ou s'il n'en propose pas (valeur de retour 0)
1514 Deux cas principaux peuvent se presenter : avec validateurs ou bien sans.
1515 Dans le cas sans validateur, l'information est donnée par l'attribut into
1516 de la definition du mot cle.
1517 Dans le cas avec validateurs, pour que le mot cle soit considéré
1518 comme proposant un choix, il faut que into soit présent OU
1519 que la méthode has_into du validateur retourne 1. Dans les autres cas
1520 on retournera 0 (ne propose pas de choix)
1523 if self.definition.into:
1525 elif self.definition.validators :
1526 has_an_into= self.definition.validators.has_into()
1529 def valide_item(self,item):
1531 On fait un try except pour les erreurs de types (exple
1532 on rentre 1 pour une chaine de caracteres
1535 if self.definition.validators :
1537 valide=self.definition.validators.verif_item(item)
1542 def valide_liste_partielle(self,item,listecourante):
1543 valeuravant=self.object.valeur
1544 valeur=listecourante
1546 valeur = tuple(valeur)
1547 retour=self.object.set_valeur(valeur)
1549 if self.object.isvalid():
1551 elif self.definition.validators :
1552 validite=self.definition.validators.valide_liste_partielle(valeur)
1555 min,max=self.GetMinMax()
1556 if len(valeur) < min :
1558 retour=self.object.set_valeur(valeuravant)
1561 def valide_liste_complete (self,valeur):
1562 valeuravant=self.object.valeur
1563 retour=self.object.set_valeur(valeur)
1565 if self.object.isvalid():
1567 retour=self.object.set_valeur(valeuravant)
1570 def info_erreur_item(self) :
1572 if self.definition.validators :
1573 commentaire=self.definition.validators.info_erreur_item()
1578 if self.definition.validators :
1579 commentaire=self.definition.validators.aide()
1582 def info_erreur_liste(self) :
1584 if self.definition.validators :
1585 commentaire=self.definition.validators.info_erreur_liste()
1588 def SetText(self, text):
1591 self.object.setval(value)
1595 def GetIconName(self):
1597 return "ast-green-ball"
1598 elif self.object.isoblig():
1599 return "ast-red-ball"
1601 return "ast-yel-ball"
1606 Retourne le texte à afficher dans l'arbre représentant la valeur de l'objet
1609 text= self.object.GetText()
1614 Méthode booléenne qui retourne 1 si l'objet pointé par self
1615 attend un objet de type ASSD qui n'existe pas encore (type CO()),
1618 return self.object.wait_co()
1620 def wait_geom(self):
1622 Méthode booléenne qui retourne 1 si l'objet pointé par self
1623 attend un objet GEOM, 0 sinon
1625 return self.object.wait_geom()
1627 def wait_complex(self):
1628 """ Méthode booléenne qui retourne 1 si l'objet pointé par self
1629 attend un complexe, 0 sinon """
1630 if 'C' in self.object.definition.type:
1635 def wait_reel(self):
1636 """ Méthode booléenne qui retourne 1 si l'objet pointé par self
1637 attend un réel, 0 sinon """
1638 if 'R' in self.object.definition.type:
1643 def wait_shell(self):
1644 """ Méthode booléenne qui retourne 1 si l'objet pointé par self
1645 attend un shell, 0 sinon """
1646 if 'shell' in self.object.definition.type:
1651 def wait_into(self):
1652 """ Méthode booléenne qui retourne 1 si l'objet pointé par self
1653 prend ses valeurs dans un ensemble discret (into), 0 sinon """
1654 if self.object.definition.into != None :
1659 def wait_assd(self):
1660 """Méthode booléenne qui retourne 1 si l'objet pointé par self
1661 attend un objet de type ASSD ou dérivé, 0 sinon """
1662 return self.object.wait_assd()
1665 return self.object.getval()
1667 def GetMinMax(self):
1668 """ Retourne les valeurs min et max de la définition de object """
1669 return self.object.get_min_max()
1671 def GetMultiplicite(self):
1673 Retourne la multiplicité des valeurs affectées à l'objet
1674 représenté par l'item. Pour le moment retourne invariablement 1.
1680 Retourne le type de valeur attendu par l'objet représenté par l'item.
1682 return self.object.get_type()
1684 def GetIntervalle(self):
1686 Retourne le domaine de valeur attendu par l'objet représenté
1689 return self.object.getintervalle()
1691 def IsInIntervalle(self,valeur):
1693 Retourne 1 si la valeur est dans l'intervalle permis par
1694 l'objet représenté par l'item.
1696 return self.object.isinintervalle(valeur)
1698 def set_valeur_co(self,nom_co):
1700 Affecte au MCS pointé par self l'objet de type CO et de nom nom_co
1702 return self.object.set_valeur_co(nom_co)
1704 def get_sd_avant_du_bon_type(self):
1706 Retourne la liste des noms des SD présentes avant l'étape qui contient
1707 le MCS pointé par self et du type requis par ce MCS
1709 a=self.object.etape.parent.get_sd_avant_du_bon_type(self.object.etape,self.object.definition.type)
1710 return self.object.etape.parent.get_sd_avant_du_bon_type(self.object.etape,
1711 self.object.definition.type)
1713 def GetListeValeurs(self) :
1714 """ Retourne la liste des valeurs de object """
1715 return self.object.get_liste_valeurs()
1721 valide=self.object.isvalid()
1722 return self.object.isvalid()
1724 def eval_valeur(self,valeur):
1725 """ Lance l'interprétation de 'valeur' (chaîne de caractères) comme valeur
1726 de l'objet pointé par self :
1727 - retourne l'objet associé si on a pu interpréter (entier, réel, ASSD,...)
1728 - retourne 'valeur' (chaîne de caractères) sinon
1729 - retourne None en cas d invalidite
1730 - retourne invalide si 1 des objets du tuple l est
1733 if type(valeur) in (types.ListType,types.TupleType) :
1735 for item in valeur :
1736 newvaleur,validiteitem=self.eval_valeur_item(item)
1737 valeurretour.append(newvaleur)
1738 if validiteitem == 0:
1741 valeurretour,validite= self.eval_valeur_item(valeur)
1744 return valeurretour,validite
1746 def eval_valeur_item(self,valeur):
1747 if valeur==None or valeur == "" :
1750 if self.wait_reel():
1751 valeurinter = self.traite_reel(valeur)
1752 valeurretour,validite= self.object.eval_valeur(valeurinter)
1753 elif self.wait_geom():
1754 valeurretour,validite = valeur,1
1756 valeurretour,validite= self.object.eval_valeur(valeur)
1758 if type(valeur) == types.StringType and self.object.wait_TXM():
1759 essai_valeur="'" + valeur + "'"
1760 valeurretour,validite= self.object.eval_valeur(essai_valeur)
1761 if hasattr(valeurretour,'__class__'):
1762 if valeurretour.__class__.__name__ in ('PARAMETRE','PARAMETRE_EVAL'):
1766 valeurretour=Accas.CO(valeur)
1771 # on est dans le cas où on a évalué et où on n'aurait pas du
1772 if self.object.wait_TXM() :
1773 if type(valeurretour) != types.StringType:
1774 valeurretour=str(valeur)
1777 return valeurretour,validite
1780 def is_CO(self,valeur=None):
1782 Indique si valeur est un concept produit de la macro
1783 Cette méthode n'a de sens que pour un MCSIMP d'une MACRO
1784 Si valeur vaut None on teste la valeur du mot cle
1786 # Pour savoir si un concept est un nouveau concept de macro
1787 # on regarde s'il est présent dans l'attribut sdprods de l'étape
1788 # ou si son nom de classe est CO.
1789 # Il faut faire les 2 tests car une macro non valide peut etre
1790 # dans un etat pas tres catholique avec des CO pas encore types
1791 # et donc pas dans sdprods (resultat d'une exception dans type_sdprod)
1792 if not valeur:valeur=self.object.valeur
1793 if valeur in self.object.etape.sdprods:return 1
1794 if type(valeur) is not types.InstanceType:return 0
1795 if valeur.__class__.__name__ == 'CO':return 1
1798 def delete_valeur_co(self,valeur=None):
1800 Supprime la valeur du mot cle (de type CO)
1801 il faut propager la destruction aux autres etapes
1803 if not valeur : valeur=self.object.valeur
1804 # XXX faut il vraiment appeler del_sdprod ???
1805 #self.object.etape.parent.del_sdprod(valeur)
1806 self.object.etape.parent.delete_concept(valeur)
1808 def get_liste_possible(self,listeActuelle=[]):
1809 if hasattr(self.definition.validators,'into'):
1810 self.get_definition().into=self.definition.validators.into
1811 valeurspossibles = self.get_definition().into
1813 for item in valeurspossibles:
1814 encorevalide=self.valide_item(item)
1816 listevalideitem.append(item)
1817 # on ne verifie pas la liste des choix si max = 1
1818 # (sinon cela enleve tous les choix possibles)
1819 min,max=self.GetMinMax()
1822 for item in listevalideitem:
1824 for item2 in listeActuelle : listetravail.append(item2)
1825 encorevalide=self.valide_liste_partielle(item,listetravail)
1827 listevalideliste.append(item)
1829 listevalideliste=listevalideitem
1830 return listevalideliste
1832 def traite_reel(self,valeur):
1834 Cette fonction a pour but de rajouter le '.' en fin de chaîne pour un réel
1835 ou de détecter si on fait référence à un concept produit par DEFI_VALEUR
1838 valeur = string.strip(valeur)
1839 liste_reels = self.get_sd_avant_du_bon_type()
1840 if valeur in liste_reels:
1842 if len(valeur) >= 3 :
1843 if valeur[0:4] == 'EVAL' :
1844 # on a trouvé un EVAL --> on retourne directement la valeur
1846 if string.find(valeur,'.') == -1 :
1847 # aucun '.' n'a été trouvé dans valeur --> on en rajoute un à la fin
1854 treeitem = SIMPTreeItem
1855 objet = Accas.MCSIMP