Salome HOME
ajout pour accepter les accents sous python 2.3
[tools/eficas.git] / Editeur / composimp.py
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.
9 #
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.
14 #
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.
18 #
19 #
20 # ======================================================================
21 # Modules Python
22 import string,types,os
23 from Tkinter import *
24 import Pmw
25 from copy import copy,deepcopy
26 import traceback
27
28 # Modules Eficas
29 import Objecttreeitem
30 import prefs
31 import panels
32 import images
33 from widgets import ListeChoix
34 from widgets import FenetreDeSelection
35
36 from Noyau.N_CR import justify_text
37 from utils import substract_list
38
39       
40 class SIMPTreeItem(Objecttreeitem.AtomicObjectTreeItem):
41   from newsimppanel import newSIMPPanel
42   panel = newSIMPPanel
43
44   def init(self) :
45       self.expandable = 0
46       self.affect_panel()
47
48
49   def affect_panel(self):
50       """
51       Cette méthode attribue le panel à l'objet pointé par self en fonction de la
52       nature de la valeur demandée pour cet objet
53       """
54       from uniquepanel import UNIQUE_Panel
55       from plusieurspanel import PLUSIEURS_Panel
56
57       #print "affect_panel : ",self.nom,self.is_list(),self.has_into(), self.get_into(None)
58
59       if self.wait_shell():
60           # l'objet attend un shell
61           from shellpanel import SHELLPanel
62           self.panel = SHELLPanel
63       elif self.has_into():
64           # l'objet prend sa (ses) valeur(s) dans un ensemble discret de valeurs
65           if self.is_list() :
66              from plusieursintopanel import PLUSIEURS_INTO_Panel
67              self.panel = PLUSIEURS_INTO_Panel
68           else:
69              from uniqueintopanel import UNIQUE_INTO_Panel
70              self.panel = UNIQUE_INTO_Panel
71       else:
72           # l'objet prend une ou des valeurs à priori quelconques
73           if self.is_list() :
74               # on attend une liste de valeurs mais de quel type ?
75               if self.wait_assd():
76                   # on attend une liste de SD
77                   from plusieursassdpanel import PLUSIEURS_ASSD_Panel
78                   self.panel = PLUSIEURS_ASSD_Panel
79               else:
80                   # on attend une liste de valeurs de types debase (entiers, réels,...)
81                   from plusieursbasepanel import PLUSIEURS_BASE_Panel
82                   self.panel = PLUSIEURS_BASE_Panel
83           else:
84               # on n'attend qu'une seule valeur mais de quel type ?
85               if self.wait_co():
86                   # on attend une SD ou un objet de la classe CO (qui n'existe pas encore)
87                   from uniquesdcopanel import UNIQUE_SDCO_Panel
88                   self.panel = UNIQUE_SDCO_Panel
89               elif self.wait_assd():
90                   # on attend une SD
91                   from uniqueassdpanel import UNIQUE_ASSD_Panel
92                   self.panel = UNIQUE_ASSD_Panel
93               else:
94                   # on attend une valeur d'un type de base (entier,réel,...)
95                   if self.wait_complex():
96                       # on attend un complexe
97                       from uniquecomppanel import UNIQUE_COMP_Panel
98                       self.panel = UNIQUE_COMP_Panel
99                   else:
100                       # on attend un entier, un réel ou une string
101                       from uniquebasepanel import UNIQUE_BASE_Panel
102                       self.panel = UNIQUE_BASE_Panel
103       # cas particulier des fonctions
104       genea = self.get_genealogie()
105       if "VALE" in genea or "VALE_C" in genea:
106          if "DEFI_FONCTION" in genea :
107             from fonctionpanel import FONCTION_Panel
108             self.panel=FONCTION_Panel
109       #---------------------------------------------------------
110       # PN ajout pour lancement de Salome
111       #---------------------------------------------------------
112       if  self.appli.salome != 0 :
113           import panelsSalome
114
115           self.clef_fonction="SALOME"
116           for i in range(0,len( genea )) :
117              self.clef_fonction=self.clef_fonction+"_"+ genea[i]
118
119           self.select_noeud_maille=0
120           if (self.clef_fonction.find("GROUP_NO") != -1)  :
121              self.select_noeud_maille=1
122           if (self.clef_fonction.find("GROUP_MA") != -1) :
123              self.select_noeud_maille=1
124
125           recherche=panelsSalome.dict_classes_salome[self.panel]
126           if hasattr(recherche,self.clef_fonction):
127              self.panel=recherche
128           if self.select_noeud_maille==1 :
129              self.panel=recherche
130
131
132   #-----------------------------------------------
133   #
134   # Methodes liees aux informations sur le Panel
135   # ou au mot-clef simple
136   #
137   #-----------------------------------------------
138   # is_list
139   # get_into            a priori inutile --> commentee
140   # has_into
141   # wait_into           a priori inutile --> commentee
142   # GetMinMax
143   # GetMultiplicite
144   # GetIntervalle
145   # GetListeValeurs
146   # get_liste_possible
147
148   def is_list(self):
149       """
150           Cette méthode indique si le mot cle simple attend une liste (valeur de retour 1)
151           ou s'il n'en attend pas (valeur de retour 0)
152
153           Deux cas principaux peuvent se presenter : avec validateurs ou bien sans.
154           Dans le cas sans validateur, l'information est donnée par l'attribut max
155           de la definition du mot cle.
156           Dans le cas avec validateur, il faut combiner l'information précédente avec
157           celle issue de l'appel de la méthode is_list sur le validateur.On utilisera
158           l'operateur ET pour effectuer cette combinaison (AndVal).
159       """
160       is_a_list=0
161       min,max = self.GetMinMax()
162       assert (min <= max)
163       if max > 1 :
164                 is_a_list=1
165       # Dans le cas avec validateurs, pour que le mot cle soit considéré
166       # comme acceptant une liste, il faut que max soit supérieur a 1
167       # ET que la méthode is_list du validateur retourne 1. Dans les autres cas
168       # on retournera 0 (n'attend pas de liste)
169       if self.definition.validators :
170          is_a_list= self.definition.validators.is_list() * is_a_list
171       return is_a_list 
172
173   #def get_into(self,liste_courante=None):
174   #    """
175   #        Cette méthode retourne la liste de choix proposée par le mot cle. Si le mot cle ne propose
176   #        pas de liste de choix, la méthode retourne None.
177   #        L'argument d'entrée liste_courante, s'il est différent de None, donne la liste des choix déjà
178   #        effectués par l'utilisateur. Dans ce cas, la méthode get_into doit calculer la liste des choix
179   #        en en tenant compte.
180   #        Cette méthode part du principe que la relation entre into du mot clé et les validateurs est
181   #        une relation de type ET (AndVal).
182   #    """
183   #    if not self.object.definition.validators :
184   #       return self.object.definition.into
185   #    else:
186   #       return self.object.definition.validators.get_into(liste_courante,self.definition.into)
187
188   def has_into(self):
189       """
190           Cette méthode indique si le mot cle simple propose un choix (valeur de retour 1)
191           ou s'il n'en propose pas (valeur de retour 0)
192
193           Deux cas principaux peuvent se presenter : avec validateurs ou bien sans.
194           Dans le cas sans validateur, l'information est donnée par l'attribut into
195           de la definition du mot cle.
196           Dans le cas avec validateurs, pour que le mot cle soit considéré
197           comme proposant un choix, il faut que into soit présent OU
198           que la méthode has_into du validateur retourne 1. Dans les autres cas
199           on retournera 0 (ne propose pas de choix)
200       """
201       has_an_into=0
202       if self.definition.into:
203          has_an_into=1
204       elif self.definition.validators :
205          has_an_into= self.definition.validators.has_into()
206       return has_an_into
207
208 #  def wait_into(self):
209 #      """ Méthode booléenne qui retourne 1 si l'objet pointé par self
210 #      prend ses valeurs dans un ensemble discret (into), 0 sinon """
211 #      if self.object.definition.into != None :
212 #          return 1
213 #      else:
214 #          return 0
215
216   def GetMinMax(self):
217       """ Retourne les valeurs min et max de la définition de object """
218       return self.object.get_min_max()
219
220   def GetMultiplicite(self):
221       """ A préciser.
222           Retourne la multiplicité des valeurs affectées à l'objet
223           représenté par l'item. Pour le moment retourne invariablement 1.
224       """
225       return 1
226
227   def GetIntervalle(self):
228       """ 
229            Retourne le domaine de valeur attendu par l'objet représenté 
230            par l'item.
231       """
232       return self.object.getintervalle()
233
234   def GetListeValeurs(self) :
235       """ Retourne la liste des valeurs de object """
236       return self.object.get_liste_valeurs()
237     
238   def get_liste_possible(self,listeActuelle=[]):
239       if hasattr(self.definition.validators,'into'):
240          self.get_definition().into=self.definition.validators.into 
241       valeurspossibles = self.get_definition().into
242       # CCAR : Ne serait-il pas preferable d'appeler get_into ?
243       #valeurspossibles=self.get_into(listeActuelle)
244
245       listevalideitem=[]
246       for item in valeurspossibles:
247           encorevalide=self.valide_item(item)
248           if encorevalide :
249              listevalideitem.append(item)
250       # on ne verifie pas la liste des choix si max = 1 
251       # (sinon cela enleve tous les choix possibles)
252       min,max=self.GetMinMax()
253       if max != 1 : 
254          listevalideliste=[]
255          for item in listevalideitem:
256              listetravail=[]
257              for item2 in listeActuelle : listetravail.append(item2)
258              encorevalide=self.valide_liste_partielle(item,listetravail)
259              if encorevalide :
260                 listevalideliste.append(item)
261       else :
262          listevalideliste=listevalideitem
263       return listevalideliste
264
265
266   #--------------------------------------------------
267   #
268   # Methodes liees a la validite des valeurs saisies
269   #
270   #---------------------------------------------------
271   # valide_item
272   # valide_liste_partielle
273   # valide_liste_complete
274   # info_erreur_item
275   # info_erreur_liste
276   # IsInIntervalle
277   # isvalid
278
279   def valide_item(self,item):
280       """
281         On fait un try except pour les erreurs de type (exple
282         on rentre 1 pour une chaine de caracteres
283       """
284       valide=1
285       if self.definition.validators :
286          try :
287             valide=self.definition.validators.verif_item(item)
288          except :
289             valide = 0
290       return valide
291      
292   def valide_liste_partielle(self,item,listecourante):
293       valeuravant=self.object.valeur
294       valeur=listecourante
295       valeur.append(item)
296       valeur = tuple(valeur)
297       retour=self.object.set_valeur(valeur)
298       validite=0
299       if self.object.isvalid():
300          validite=1
301       elif self.definition.validators :
302          validite=self.definition.validators.valide_liste_partielle(valeur)
303
304       if validite==0:
305          min,max=self.GetMinMax()
306          if len(valeur) < min :
307             validite=1
308       retour=self.object.set_valeur(valeuravant)
309       return validite 
310
311   def valide_liste_complete (self,valeur):
312       valeuravant=self.object.valeur
313       retour=self.object.set_valeur(valeur)
314       validite=0
315       if self.object.isvalid():
316          validite=1
317       retour=self.object.set_valeur(valeuravant)
318       return validite
319      
320   def info_erreur_item(self) :
321       commentaire=""
322       if self.definition.validators :
323          commentaire=self.definition.validators.info_erreur_item()
324       return commentaire
325       
326   def aide(self) :
327       commentaire=""
328       if self.definition.validators :
329          commentaire=self.definition.validators.aide()
330       return commentaire
331
332   def info_erreur_liste(self) :
333       commentaire=""
334       if self.definition.validators :
335          commentaire=self.definition.validators.info_erreur_liste()
336       return commentaire
337
338   def IsInIntervalle(self,valeur):
339       """ 
340           Retourne 1 si la valeur est dans l'intervalle permis par
341           l'objet représenté par l'item.
342       """
343       return self.object.isinintervalle(valeur)
344
345   def isvalid(self):
346     valide=self.object.isvalid()
347     return self.object.isvalid()
348
349   #--------------------------------------------------
350   #
351   # Autres ...
352   #
353   #---------------------------------------------------
354   # SetText     a priori inutilisee --> commentee
355   # GetIconName
356   # GetText
357   # getval     a  priori inutilisee --> commentee
358   # set_valeur_co
359   # get_sd_avant_du_bon_type
360   # verif       a  priori inutilisee --> commentee
361   # delete_valeur_co
362
363   #def SetText(self, text):
364   #  try:
365   #    value = eval(text)
366   #    self.object.setval(value)
367   #  except:
368   #    pass
369
370   def GetIconName(self):
371     if self.isvalid():
372       return "ast-green-ball"
373     elif self.object.isoblig():
374       return "ast-red-ball"
375     else:
376       return "ast-yel-ball"
377
378   def GetText(self):
379     """
380     Classe SIMPTreeItem
381     Retourne le texte à afficher dans l'arbre représentant la valeur de l'objet
382     pointé par self 
383     """
384     text= self.object.GetText()
385     return text
386     
387   #def getval(self):
388   #    return self.object.getval()
389
390   def set_valeur_co(self,nom_co):
391       """
392       Affecte au MCS pointé par self l'objet de type CO et de nom nom_co
393       """
394       return self.object.set_valeur_co(nom_co)
395       
396   def get_sd_avant_du_bon_type(self):
397       """
398       Retourne la liste des noms des SD présentes avant l'étape qui contient
399       le MCS pointé par self et du type requis par ce MCS
400       """
401       a=self.object.etape.parent.get_sd_avant_du_bon_type(self.object.etape,self.object.definition.type)
402       return self.object.etape.parent.get_sd_avant_du_bon_type(self.object.etape,
403                                                                self.object.definition.type)
404
405   #def verif(self):
406   #    pass
407
408   def delete_valeur_co(self,valeur=None):
409       """
410            Supprime la valeur du mot cle (de type CO)
411            il faut propager la destruction aux autres etapes
412       """
413       if not valeur : valeur=self.object.valeur
414       # XXX faut il vraiment appeler del_sdprod ???
415       #self.object.etape.parent.del_sdprod(valeur)
416       self.object.etape.parent.delete_concept(valeur)
417
418   #-----------------------------------------------
419   #
420   # Methodes liees au type de l objet attendu
421   #
422   #-----------------------------------------------
423   # wait_co 
424   # wait_geom
425   # wait_complex
426   # wait_reel
427   # wait_shell
428   # wait_assd
429   # GetType
430
431   def wait_co(self):
432       """
433       Méthode booléenne qui retourne 1 si l'objet pointé par self
434       attend un objet de type ASSD qui n'existe pas encore (type CO()),
435       0 sinon
436       """
437       return self.object.wait_co()
438
439   def wait_geom(self):
440       """
441       Méthode booléenne qui retourne 1 si l'objet pointé par self
442       attend un objet GEOM, 0 sinon
443       """
444       return self.object.wait_geom()
445     
446   def wait_complex(self):
447       """ Méthode booléenne qui retourne 1 si l'objet pointé par self
448       attend un complexe, 0 sinon """
449       if 'C' in self.object.definition.type:
450           return 1
451       else:
452           return 0
453
454   def wait_reel(self):
455       """ Méthode booléenne qui retourne 1 si l'objet pointé par self
456       attend un réel, 0 sinon """
457       if 'R' in self.object.definition.type:
458           return 1
459       else:
460           return 0
461         
462   def wait_shell(self):
463       """ Méthode booléenne qui retourne 1 si l'objet pointé par self
464       attend un shell, 0 sinon """
465       if 'shell' in self.object.definition.type:
466           return 1
467       else:
468           return 0
469
470   def wait_assd(self):
471       """Méthode booléenne qui retourne 1 si l'objet pointé par self
472       attend un objet de type ASSD ou dérivé, 0 sinon """
473       return self.object.wait_assd()
474     
475   def GetType(self):
476       """ 
477           Retourne le type de valeur attendu par l'objet représenté par l'item.
478       """
479       return self.object.get_type()
480
481   #-----------------------------------------------------
482   #
483   # Methodes liees  a l evaluation de la valeur saisie
484   #
485   #-----------------------------------------------------
486   # eval_valeur
487   # eval_valeur_item
488   # is_CO
489   # traite_reel
490
491   def eval_valeur(self,valeur):
492       """ Lance l'interprétation de 'valeur' (chaîne de caractères) comme valeur
493       de l'objet pointé par self :
494         - retourne l'objet associé si on a pu interpréter (entier, réel, ASSD,...)
495         - retourne 'valeur' (chaîne de caractères) sinon
496         - retourne None en cas d invalidite
497         - retourne invalide si 1 des objets du tuple l est
498       """
499       validite=1
500       if type(valeur) in (types.ListType,types.TupleType) :
501          valeurretour=[]
502          for item in valeur :
503              newvaleur,validiteitem=self.eval_valeur_item(item)
504              valeurretour.append(newvaleur)
505              if validiteitem == 0:
506                 validite=0
507       else :
508          valeurretour,validite= self.eval_valeur_item(valeur)
509       if validite == 0 :
510          valeurretour = None
511       return valeurretour,validite
512
513   def eval_valeur_item(self,valeur):
514       """ Lance l'interprétation de 'valeur' qui doit ne pas etre un tuple 
515           - va retourner la valeur de retour et la validite
516             selon le type de l objet attendu
517           - traite les reels et les parametres 
518       """ 
519       if valeur==None or valeur == "" :
520          return None,0
521       validite=1
522       if self.wait_reel():
523              valeurinter = self.traite_reel(valeur)
524              valeurretour,validite= self.object.eval_valeur(valeurinter)
525       elif self.wait_geom():
526              valeurretour,validite = valeur,1
527       else :
528              valeurretour,validite= self.object.eval_valeur(valeur)
529       if validite == 0:
530          if type(valeur) == types.StringType and self.object.wait_TXM():
531             essai_valeur="'" + valeur + "'"
532             valeurretour,validite= self.object.eval_valeur(essai_valeur)
533       if hasattr(valeurretour,'__class__'):
534          if valeurretour.__class__.__name__ in ('PARAMETRE','PARAMETRE_EVAL'):
535             validite=1
536       if self.wait_co():
537          try:
538             valeurretour=Accas.CO(valeur)
539          except:
540             valeurretour=None
541             validite=0
542       # on est dans le cas où on a évalué et où on n'aurait pas du
543       if self.object.wait_TXM() :
544           if type(valeurretour) != types.StringType:
545              valeurretour=str(valeur)
546              validite=1
547       return valeurretour,validite
548       
549   def is_CO(self,valeur=None):
550       """
551          Indique si valeur est un concept produit de la macro
552          Cette méthode n'a de sens que pour un MCSIMP d'une MACRO
553          Si valeur vaut None on teste la valeur du mot cle
554       """
555       # Pour savoir si un concept est un nouveau concept de macro
556       # on regarde s'il est présent dans l'attribut sdprods de l'étape
557       # ou si son nom de classe est CO.
558       # Il faut faire les 2 tests car une macro non valide peut etre
559       # dans un etat pas tres catholique avec des CO pas encore types
560       # et donc pas dans sdprods (resultat d'une exception dans type_sdprod)
561       if not valeur:valeur=self.object.valeur
562       if valeur in self.object.etape.sdprods:return 1
563       if type(valeur) is not types.InstanceType:return 0
564       if valeur.__class__.__name__ == 'CO':return 1
565       return 0
566
567   def is_param(self,valeur) :
568       for param in self.jdc.params:
569           if (repr(param) == valeur):
570              return 1
571       return 0
572
573   def traite_reel(self,valeur):
574       """
575       Cette fonction a pour but de rajouter le '.' en fin de chaîne pour un réel
576       ou de détecter si on fait référence à un concept produit par DEFI_VALEUR
577       ou un EVAL ...
578       """
579       valeur = string.strip(valeur)
580       liste_reels = self.get_sd_avant_du_bon_type()
581       if valeur in liste_reels:
582           return valeur
583       if len(valeur) >= 3 :
584           if valeur[0:4] == 'EVAL' :
585               # on a trouvé un EVAL --> on retourne directement la valeur
586               return valeur
587       if string.find(valeur,'.') == -1 :
588           # aucun '.' n'a été trouvé dans valeur --> on en rajoute un à la fin
589           if (self.is_param(valeur)):
590               return valeur
591           else:
592               return valeur+'.'
593       else:
594           return valeur
595         
596
597 import Accas
598 treeitem = SIMPTreeItem
599 objet = Accas.MCSIMP
600