...
[iramuteq] / ProfList.py
1 # -*- coding: utf-8 -*-
2
3 #----------------------------------------------------------------------------
4 # Name:         ListCtrl.py
5 # Author:       Pierre Ratinaud
6
7
8 #comes from ListCtrl.py from the demo tool of wxPython:
9 # Author:       Robin Dunn & Gary Dumer
10 #
11 # Created:
12 # Copyright:    (c) 1998 by Total Control Software
13 # Licence:      wxWindows license
14 #----------------------------------------------------------------------------
15
16 import os
17 import sys
18 import  wx
19 import  wx.lib.mixins.listctrl  as  listmix
20 #from tabsimi import DoSimi
21 from listlex import ListForSpec
22 from chemins import ConstructPathOut, ffr
23 from dialog import PrefExport, PrefUCECarac, SearchDial, message, MessageImage, BarFrame
24 from tableau import Tableau, copymatrix
25 from search_tools import SearchFrame
26 import webbrowser
27 #import cStringIO
28 import tempfile
29 import codecs
30 from functions import exec_rcode, progressbar, treat_var_mod, doconcorde
31 from PrintRScript import barplot
32 from textclassechd import ClasseCHD
33 from shutil import copyfile
34 from operator import itemgetter
35 from copy import copy
36
37 #---------------------------------------------------------------------------
38 class ProfListctrlPanel(wx.ListCtrl, listmix.ListCtrlAutoWidthMixin, listmix.ColumnSorterMixin):
39     def __init__(self, parent, gparent, profclasse, Alceste=False, cl=0):
40         wx.ListCtrl.__init__( self, parent, -1, style=wx.LC_REPORT|wx.LC_VIRTUAL|wx.LC_HRULES|wx.LC_VRULES)
41
42         self.parent = parent
43         self.Alceste = Alceste
44         self.Source = gparent
45         self.cl = cl
46         self.var_mod = {}
47         self.them_mod = {}
48
49         line1 = profclasse.pop(0)
50         classen = [line for line in profclasse if line[0] != '*' and line[0] != '*****']
51         try :
52             self.lenact = profclasse.index([u'*****', u'*', u'*', u'*', u'*', u'*', '', ''])
53             profclasse.pop(self.lenact)
54         except ValueError:
55             try :
56                 self.lenact = profclasse.index([u'*', u'*', u'*', u'*', u'*', u'*', '', ''])
57                 profclasse.pop(self.lenact)
58             except ValueError:
59                 self.lenact = len(profclasse)
60         try :
61             self.lensup = profclasse.index([u'*', u'*', u'*', u'*', u'*', u'*', '', ''])
62             self.lensup = self.lensup - self.lenact
63             profclasse.pop(self.lensup)
64         except ValueError: 
65             self.lensup = len(profclasse) - self.lenact
66         self.lenet = len(profclasse) - (self.lenact + self.lensup)
67 #        print self.lenact, self.lensup, self.lenet
68         for i,  line in enumerate(classen) :
69             line[0] = i
70         dictdata = dict(zip([i for i in range(0,len(classen))], classen))
71
72         if self.lenact != 0 :
73             self.la = [dictdata[i][6] for i in range(0, self.lenact)]
74             self.lchi = [dictdata[i][4] for i in range(0, self.lenact)]
75             self.lfreq = [dictdata[i][1] for i in range(0, self.lenact)]
76         else :
77             self.la = []
78             self.lchi = []
79             self.lfreq = []
80         self.tmpchi = None
81             
82         #adding some art
83         self.il = wx.ImageList(16, 16)
84         a={"sm_up":"GO_UP","sm_dn":"GO_DOWN","w_idx":"WARNING","e_idx":"ERROR","i_idx":"QUESTION"}
85         for k,v in a.items():
86             s="self.%s= self.il.Add(wx.ArtProvider_GetBitmap(wx.ART_%s,wx.ART_TOOLBAR,(16,16)))" % (k,v)
87             exec(s)
88         self.SetImageList(self.il, wx.IMAGE_LIST_SMALL)
89
90         #adding some attributes (colourful background for each item rows)
91         self.attr1 = wx.ListItemAttr()
92         self.attr1.SetBackgroundColour((220, 220, 220))
93         self.attrsg = wx.ListItemAttr()
94         self.attrsg.SetBackgroundColour((230, 230, 230))
95         self.attr2 = wx.ListItemAttr()
96         self.attr2.SetBackgroundColour((190, 249, 236))
97         self.attr2s = wx.ListItemAttr()
98         self.attr2s.SetBackgroundColour((211, 252, 244))        
99         self.attr3 = wx.ListItemAttr()
100         self.attr3.SetBackgroundColour((245, 180, 180))
101         self.attr3s = wx.ListItemAttr()
102         self.attr3s.SetBackgroundColour((245, 190, 190))
103
104
105         self.InsertColumn(0, "num", wx.LIST_FORMAT_RIGHT)
106         self.InsertColumn(1, "eff. s.t.", wx.LIST_FORMAT_RIGHT)
107         self.InsertColumn(2, "eff. total", wx.LIST_FORMAT_RIGHT)
108         self.InsertColumn(3, "pourcentage", wx.LIST_FORMAT_RIGHT)
109         self.InsertColumn(4, "chi2", wx.LIST_FORMAT_RIGHT)
110         self.InsertColumn(5, "Type", wx.LIST_FORMAT_RIGHT)
111         self.InsertColumn(6, "forme", wx.LIST_FORMAT_RIGHT)
112         self.InsertColumn(7, "p", wx.LIST_FORMAT_RIGHT)
113         
114
115         self.SetColumnWidth(0, 60)
116         self.SetColumnWidth(1, 70)
117         self.SetColumnWidth(2, 80)
118         self.SetColumnWidth(3, 100)
119         self.SetColumnWidth(4, 70)
120         self.SetColumnWidth(5, 60)
121         self.SetColumnWidth(6, 140)
122         self.SetColumnWidth(7, wx.LIST_AUTOSIZE)
123
124         #These two should probably be passed to init more cleanly
125         #setting the numbers of items = number of elements in the dictionary
126         self.itemDataMap = dictdata
127         self.itemIndexMap = dictdata.keys()
128         self.SetItemCount(len(dictdata))
129         
130         #mixins
131         listmix.ListCtrlAutoWidthMixin.__init__(self)
132         listmix.ColumnSorterMixin.__init__(self, len(classen[0]))
133
134         #sort by genre (column 2), A->Z ascending order (1)
135         self.SortListItems(0, 1)
136
137         #events
138         #self.Bind(wx.EVT_LIST_ITEM_SELECTED, self.OnItemSelected)
139         self.Bind(wx.EVT_LIST_ITEM_ACTIVATED, self.OnPopupTwo, self)
140         #self.Bind(wx.EVT_LIST_ITEM_DESELECTED, self.OnItemDeselected)
141         self.Bind(wx.EVT_LIST_COL_CLICK, self.OnColClick)
142
143         # for wxMSW
144         self.Bind(wx.EVT_COMMAND_RIGHT_CLICK, self.OnRightClick)
145
146         # for wxGTK
147         self.Bind(wx.EVT_RIGHT_UP, self.OnRightClick)
148
149         #for searching
150         search_id = wx.NewId()
151         searchall_id = wx.NewId()
152         concord_id = wx.NewId()
153         self.parent.Bind(wx.EVT_MENU, self.onsearch, id = search_id)
154         self.parent.Bind(wx.EVT_MENU, self.onsearchall, id = searchall_id)
155         self.accel_tbl = wx.AcceleratorTable([(wx.ACCEL_CTRL, ord('F'), search_id),
156                                               (wx.ACCEL_CTRL|wx.ACCEL_SHIFT, ord('F'), searchall_id)])
157         self.SetAcceleratorTable(self.accel_tbl)
158
159
160
161     def OnColClick(self,event):
162         event.Skip()
163
164     def OnItemSelected(self, event):
165         self.currentItem = event.m_itemIndex
166
167     def OnItemActivated(self, event):
168         self.currentItem = event.m_itemIndex
169
170     def getColumnText(self, index, col):
171         item = self.GetItem(index, col)
172         return item.GetText()
173
174     def OnItemDeselected(self, evt):
175         pass
176     #---------------------------------------------------
177     # These methods are callbacks for implementing the
178     # "virtualness" of the list...
179
180     def OnGetItemText(self, item, col):
181         index=self.itemIndexMap[item]
182         s = self.itemDataMap[index][col]
183         return s
184
185     def OnGetItemImage(self, item):
186         index=self.itemIndexMap[item]
187         genre=self.itemDataMap[index][2]
188
189         if genre=="Rock":
190             return self.w_idx
191         elif genre=="Jazz":
192             return self.e_idx
193         elif genre=="New Age":
194             return self.i_idx
195         else:
196             return -1
197
198     def OnGetItemAttr(self, item):
199         index=self.itemIndexMap[item]
200         if index < self.lenact :
201             if item % 2 :
202                 return self.attr1
203             else :
204                 return self.attrsg
205         elif index >= self.lenact and index < (self.lenact + self.lensup) :
206             if item % 2 :
207                 return self.attr2
208             else :
209                 return self.attr2s
210         elif index >= (self.lenact + self.lensup) :
211             if item % 2 :
212                 return self.attr3
213             else :
214                 return self.attr3s
215         else :
216             return None
217
218     #---------------------------------------------------
219     # Matt C, 2006/02/22
220     # Here's a better SortItems() method --
221     # the ColumnSorterMixin.__ColumnSorter() method already handles the ascending/descending,
222     # and it knows to sort on another column if the chosen columns have the same value.
223
224     def SortItems(self,sorter=cmp):
225         items = list(self.itemDataMap.keys())
226         items.sort(sorter)
227         self.itemIndexMap = items
228         
229         # redraw the list
230         self.Refresh()
231
232     # Used by the ColumnSorterMixin, see wx/lib/mixins/listctrl.py
233     def GetListCtrl(self):
234         return self
235
236     # Used by the ColumnSorterMixin, see wx/lib/mixins/listctrl.py
237     def GetSortImages(self):
238         return (self.sm_dn, self.sm_up)
239
240     def onsearch(self, evt) :
241         self.dial = SearchDial(self, self, 6, True)
242         self.dial.CenterOnParent()
243         self.dial.Show()
244         #self.dial.Destroy()
245
246     def onsearchall(self, evt) :
247         if 'FrameSearch' not in dir(self.Source) :
248             self.Source.FrameSearch = SearchFrame(self.parent, -1, u"Rechercher...", self.Source.corpus)
249         self.dial = SearchDial(self, self.Source.FrameSearch.liste, 1, False)
250         self.dial.CenterOnParent()
251         self.dial.Show()
252         #self.dial.Destroy()
253
254     def OnRightClick(self, event):
255
256         # only do this part the first time so the events are only bound once
257         if self.Alceste:
258             if not hasattr(self, "popupID1"):
259                 self.popupID1 = wx.NewId()
260                 self.popupID2 = wx.NewId()
261                 self.popupID3 = wx.NewId()
262                 self.popupID4 = wx.NewId()
263                 self.popupID5 = wx.NewId()
264                 self.popupID6 = wx.NewId()
265                 self.popupID7 = wx.NewId()
266                 self.popupID8 = wx.NewId()
267                 self.popupID9 = wx.NewId()
268                 #self.popupID10 = wx.NewId()
269                 self.popupIDgraph = wx.NewId()
270                 self.idseg = wx.NewId()
271                 self.iducecarac = wx.NewId()
272                 self.idtablex = wx.NewId()
273                 self.idchimod = wx.NewId()
274                 self.idwordgraph = wx.NewId()
275                 self.popup_proxe = wx.NewId()
276                 self.idlexdendro = wx.NewId()
277                 self.idcloud = wx.NewId()
278                 self.idexport = wx.NewId()
279                 self.idexporttropes = wx.NewId()
280                 self.idexportowledge = wx.NewId()
281                 self.onmaketgen = wx.NewId()
282             #    self.export_classes = wx.NewId()
283    
284                 self.Bind(wx.EVT_MENU, self.OnPopupOne, id=self.popupID1)
285                 self.Bind(wx.EVT_MENU, self.OnPopupTwo, id=self.popupID2)
286                 self.Bind(wx.EVT_MENU, self.OnPopupThree, id=self.popupID3)
287                 self.Bind(wx.EVT_MENU, self.OnPopupFour, id=self.popupID4)
288                 self.Bind(wx.EVT_MENU, self.OnPopupFive, id=self.popupID5)
289                 self.Bind(wx.EVT_MENU, self.OnPopupSix, id=self.popupID6)
290                 self.Bind(wx.EVT_MENU, self.OnPopupSeven, id=self.popupID7)
291                 self.Bind(wx.EVT_MENU, self.OnPopupHeight, id=self.popupID8)
292                 self.Bind(wx.EVT_MENU, self.OnPopupNine, id=self.popupID9)
293                 #self.Bind(wx.EVT_MENU, self.OnPopupSpec, id=self.popupID10)
294                 self.Bind(wx.EVT_MENU, self.on_graph, id=self.popupIDgraph)
295                 self.Bind(wx.EVT_MENU, self.on_segments, id=self.idseg)
296                 self.Bind(wx.EVT_MENU, self.on_uce_carac, id = self.iducecarac)
297                 self.Bind(wx.EVT_MENU, self.on_tablex, id = self.idtablex)
298                 self.Bind(wx.EVT_MENU, self.quest_var_mod, id = self.idchimod)
299                 self.Bind(wx.EVT_MENU, self.onwordgraph, id = self.idwordgraph)
300                 self.Bind(wx.EVT_MENU, self.onproxe, id = self.popup_proxe)
301                 self.Bind(wx.EVT_MENU, self.onlexdendro, id = self.idlexdendro)
302                 self.Bind(wx.EVT_MENU, self.oncloud, id = self.idcloud)
303                 self.Bind(wx.EVT_MENU, self.onexport, id = self.idexport)
304                 self.Bind(wx.EVT_MENU, self.onexporttropes, id = self.idexporttropes)
305                 self.Bind(wx.EVT_MENU, self.onexportowledge, id = self.idexportowledge)
306                 self.Bind(wx.EVT_MENU, self.OnMakeTgen, id=self.onmaketgen)
307              #  self.Bind(wx.EVT_MENU, self.on_export_classes, id = self.export_classes)
308    #            self.Bind(wx.EVT_MENU, self.OnPopupThree, id=self.popupID3)
309     
310             # make a menu
311             menu = wx.Menu()
312             menu.Append(self.popupID1, u"Formes associées")
313             menu.Append(self.idtablex, u"Chi2 par classe")
314             menu.Append(self.idlexdendro, u"Chi2 par classe + dendro")
315             menu.Append(self.idchimod, u"Chi2 modalités de la variable")
316             menu.Append(self.idwordgraph, u"Graphe du mot")
317             #menu.Append(self.export_classes, u"Exporter le corpus...") 
318             
319             #menu.Append(self.popupID10, u"Spécificités")
320
321             menu_conc = wx.Menu()
322             menu_conc.Append(self.popupID2, u"dans les segments de texte de la classe")
323             menu_conc.Append(self.popupID3, u"dans les segments de texte classés")
324             menu_conc.Append(self.popupID4, u"dans tous les segments de texte")
325             menu.AppendMenu(-1, u"Concordancier", menu_conc)
326             menu.Append(self.onmaketgen, _(u"Make Tgen").decode('utf8'))
327             menu_cnrtl = wx.Menu()      
328             menu_cnrtl.Append(self.popupID5, u"Définition")
329             menu_cnrtl.Append(self.popupID6, u"Etymologie")
330             menu_cnrtl.Append(self.popupID7, u"Synonymie")
331             menu_cnrtl.Append(self.popupID8, u"Antonymie")
332             menu_cnrtl.Append(self.popupID9, u"Morphologie")
333             menu_cnrtl.Append(self.popup_proxe, u"Proxémie")
334             menu.AppendMenu(-1, u"Outils du CNRTL", menu_cnrtl)
335             menu.AppendSeparator()
336             menu.Append(self.popupIDgraph, u"Graphe de la classe")
337             menu.Append(self.idseg, u"Segments répétés")
338             menu.Append(self.iducecarac, u"Segments de texte caractéristiques")
339             menu.Append(self.idcloud, u"Nuage de la classe")
340             menu.Append(self.idexport, u'Exporter...')
341             menu.Append(self.idexporttropes, 'Exporter pour Tropes')
342             menu.Append(self.idexportowledge, 'Exporter pour Owledge')
343             #menu.Append(self.popupID2, u"Concordancier")
344     #        menu.Append(self.popupID3, "recharger")
345     
346             self.PopupMenu(menu)
347             menu.Destroy()
348         elif 'tableau' in dir(self.Source) :
349             if not hasattr(self, "pop1"):
350                 self.pop1 = wx.NewId()
351                 self.pop2 = wx.NewId()
352                 self.pop3 = wx.NewId()
353                 self.Bind(wx.EVT_MENU, self.quest_simi, id=self.pop1)
354                 self.Bind(wx.EVT_MENU, self.on_tablex, id=self.pop2)
355                 self.Bind(wx.EVT_MENU, self.quest_var_mod, id=self.pop3)
356
357             menu = wx.Menu()
358             menu.Append(self.pop2, u"Chi2 par classe")
359             menu.Append(self.pop3, u"Chi2 modalités de la variable")
360             menu.AppendSeparator()
361             menu.Append(self.pop1, u"Graphe de la classe")
362             self.PopupMenu(menu)
363             menu.Destroy()
364
365     def oncloud(self, evt) :
366         if 'corpus' in dir(self.Source):
367             corpus = self.Source.corpus
368         prof = [[self.la[i], self.lchi[i], self.lfreq[i]] for i, val in enumerate(self.la)]
369         parametres = copy(self.Source.parametres)
370         parametres['clusterprof'] = prof
371         parametres['type'] = 'clustercloud'
372         parametres['prof'] = self.Source.pathout['actprof_classe_%i.csv' % self.cl]
373         del  parametres['uuid']
374         #if not os.path.exists(self.Source.pathout['actprof_classe_%i.csv' % self.lc]) :
375         #    with open(self.Source.pathout['actprof_classe_%i.csv' % self.lc], 'w') as f :
376         #        f.write('\n'.join(prof).encode(self.parent.syscoding))
377         self.parent.OnClusterCloud(self.Source.corpus, parametres = parametres)
378
379     def onexport(self, evt) :
380         if 'corpus' in dir(self.Source):
381             corpus = self.Source.corpus
382         if self.Source.parametres['classif_mode'] != 2 :
383             uci = False
384         else :
385             uci = True
386         corpus.export_classe(self.Source.pathout['classe_%i_export.txt' % self.cl], self.cl, uci = uci)
387         dial = wx.MessageDialog(self, self.Source.pathout['classe_%i_export.txt' % self.cl], u"Export", wx.OK|wx.ICON_INFORMATION)
388         dial.ShowModal()
389         dial.Destroy()
390         #if 'corpus' in dir(self.Source):
391         #    corpus = self.Source.corpus
392         #ClasseCHD(self.parent, corpus, self.cl)
393     
394     def onexporttropes(self, evt) :
395         if 'corpus' in dir(self.Source):
396             corpus = self.Source.corpus
397         if self.Source.parametres['classif_mode'] != 2 :
398             uci = False
399         else :
400             uci = True
401         fileout = self.Source.pathout['export_tropes_classe_%i.txt' % self.cl]
402         corpus.export_tropes(fileout, self.cl, uci = uci)
403     
404     def onexportowledge(self, evt):
405         if 'corpus' in dir(self.Source):
406             corpus = self.Source.corpus
407         if self.Source.parametres['classif_mode'] != 2 :
408             uci = False
409         else :
410             uci = True
411         repout = self.Source.pathout['export_owledge_classe_%i' % self.cl]
412         if not os.path.exists(repout) :
413             os.mkdir(repout)
414         corpus.export_owledge(repout, self.cl, uci = uci)        
415
416     def getselectedwords(self) :
417         words = [self.getColumnText(self.GetFirstSelected(), 6)]
418         last = self.GetFirstSelected()
419         while self.GetNextSelected(last) != -1:
420             last = self.GetNextSelected(last)
421             words.append(self.getColumnText(last, 6))
422         return words
423
424     def quest_var_mod(self, evt) :  
425         word = self.getselectedwords()[0]
426         if len(word.split('_')) <= 1 :
427             dial = wx.MessageDialog(self, u"Ce n'est pas une forme du type variable_modalité", u"Problème", wx.OK | wx.ICON_WARNING)
428             dial.CenterOnParent()
429             dial.ShowModal()
430             dial.Destroy()
431             return
432             
433         if 'corpus' in dir(self.Source):
434             corpus = self.Source.corpus
435             if word.startswith(u'-*') :
436                 if self.them_mod == {} :
437                     self.them_mod = self.Source.corpus.make_theme_dict()
438                 var_mod = self.them_mod
439             else :
440                 if self.var_mod == {} :
441                     self.var_mod = self.Source.corpus.make_etoiles_dict()
442                 var_mod = self.var_mod
443         else :
444             corpus = self.Source.tableau
445             if self.var_mod == {} :
446                 self.var_mod = treat_var_mod([val for val in corpus.actives] + [val for val in corpus.sups])
447             var_mod = self.var_mod
448         with codecs.open(self.Source.pathout['chisqtable'], 'r', corpus.parametres['syscoding']) as f :
449             chistable = [line.replace('\n','').replace('\r','').replace('"','').replace(',','.').split(';') for line in f]
450         title = chistable[0]
451         title.pop(0)
452         chistable.pop(0)
453         vchistable = [line[1:] for line in chistable]
454         fchistable = [line[0] for line in chistable]
455
456         var = word.split('_')
457         #words = ['_'.join([var[0],word]) for word in self.var_mod[var[0]]]
458         try :
459             words = [word for word in var_mod[var[0]]]
460         except KeyError:
461             dial = wx.MessageDialog(self, _(u"This is not a meta-data"), u"Problème", wx.OK | wx.ICON_WARNING)
462             dial.CenterOnParent()
463             dial.ShowModal()
464             dial.Destroy()
465             return            
466         words.sort()
467         tableout = []
468         kwords = []
469         for word in words :
470             if word in fchistable :
471                 tableout.append(vchistable[fchistable.index(word)])
472                 kwords.append(word)
473         BarFrame(self.Source.parent, tableout, title, kwords)
474
475     def quest_simi(self, evt) :
476         tableau = self.Source.tableau
477         tab = tableau.make_table_from_classe(self.cl, self.la)
478         pathout = ConstructPathOut(self.Source.pathout.dirout, 'simi_classe_%i' %self.cl)
479         if self.tmpchi is None :
480             self.tmpchi = os.path.join(pathout,'chi.csv')
481             with open(self.tmpchi, 'w') as f:
482                 f.write('\n'.join([str(val) for val in self.lchi]))
483         self.filename = os.path.join(pathout,'mat01.csv')
484         tableau.printtable(self.filename, tab)
485         del tab
486         paramsimi = {'coeff' : 0,
487                           'layout' : 2,
488                           'type_graph' : 1,
489                           'arbremax' : 1,
490                           'coeff_tv' : 1,
491                           'coeff_tv_nb' : 0,
492                           'tvprop' : 0,
493                           'tvmin' : 5,
494                           'tvmax' : 30,
495                           'coeff_te' : 1,
496                           'coeff_temin' : 1,
497                           'coeff_temax' : 10,
498                           'label_v': 1,
499                           'label_e': 1,
500                           'vcex' : 0,
501                           'vcexmin' : 10,
502                           'vcexmax' : 25,
503                           'cex' : 10,
504                           'cexfromchi' : True,
505                           'sfromchi': False,
506                           'seuil_ok' : 0,
507                           'seuil' : 1,
508                           'cols' : (255,0,0),
509                           'cola' : (200,200,200),
510                           'width' : 1000,
511                           'height' : 1000,
512                           'first' : True,
513                           'keep_coord' : True,
514                           'alpha' : 20,
515                           'film': False,
516                           'com' : 0,
517                           'communities' : 0,
518                           'halo' : 0,
519                           'tmpchi': self.tmpchi,
520                           'fromprof' : True,
521                           'edgecurved' : True,
522                           }
523         act = {}
524         tableau = copymatrix(tableau)
525         tableau.chi = {}
526         tableau.lchi = self.lchi
527         #tableau.parametres['fromprof'] = True
528         for i, val in enumerate(self.la) :
529             act[val] = [self.lfreq[i]]
530             tableau.chi[val] = [self.lchi[i]]
531         paramsimi['listactives'] = copy(self.la)
532         paramsimi['actives'] = copy(act)
533         paramsimi['pathout'] = pathout
534         self.parent.SimiCluster(parametres = paramsimi, fromprof = ffr(self.filename), tableau = tableau)
535
536     def onwordgraph(self, evt):
537         word = self.getColumnText(self.GetFirstSelected(), 6)
538         if self.tmpchi is None :
539             self.tmpchi = os.path.join(self.Source.parametres['pathout'],'chi_%i.csv' % self.cl)
540             with open(self.tmpchi, 'w') as f:
541                 f.write('\n'.join([str(val) for val in self.lchi]))
542         index = self.la.index(word)
543         parametres = {'type' : 'clustersimitxt', 
544                         'pathout' : self.Source.parametres['pathout'],
545                         'word' : index ,
546                         'lem' : self.Source.parametres['lem'],
547                         'tmpchi' : self.tmpchi}
548         #try :
549         self.parent.SimiFromCluster(self.parent, self.Source.corpus, self.la, self.lfreq, self.lchi, self.cl - 1, parametres = parametres, dlg = progressbar(self, 4))
550         #except :
551         #    print 'not acitve'
552
553     def on_graph(self, evt):
554         if self.tmpchi is None :
555             self.tmpchi = os.path.join(self.Source.parametres['pathout'],'chi_%i.csv' % self.cl)
556             with open(self.tmpchi, 'w') as f:
557                 f.write('\n'.join([str(val) for val in self.lchi]))
558         parametres = {'type' : 'clustersimitxt', 
559                         'pathout' : self.Source.parametres['pathout'],
560                         'lem' : self.Source.parametres['lem'],
561                         'tmpchi' : self.tmpchi}
562
563         self.parent.SimiFromCluster(self.parent, self.Source.corpus, self.la, self.lfreq, self.lchi, self.cl - 1, parametres = parametres, dlg = progressbar(self, 4))
564
565     def on_segments(self,evt) :
566         dlg = progressbar(self, 2)
567         corpus = self.Source.corpus
568         uces = corpus.lc[self.cl-1]
569         if self.Source.parametres['classif_mode'] != 2 :
570             uci = False
571         else :
572             uci = True
573         l = []
574         dlg.Update(1, u'Segments...')
575         for i in range(2,10) :
576             li = corpus.find_segments_in_classe(uces, i, 1000, uci = uci)
577             if li == [] :
578                 break
579             else :
580                 l += li
581         l.sort(reverse = True)
582         d = {}
583         dlg.Update(2, 'Tri...')
584         for i, line in enumerate(l) :
585             d[i] = [line[1],line[0], line[2]]
586         first = ['','','']
587         para={'dico': d,'fline':first}
588         dlg.Destroy()
589         win = wliste(self, -1, u"Segments répétés - Classe %i" % self.cl, d, first, size=(600, 500))
590         win.Show(True)
591
592     def on_uce_carac(self,evt) :
593         dial = PrefUCECarac(self, self.parent)
594         dial.CenterOnParent()
595         if dial.ShowModal() == wx.ID_OK :
596             limite = dial.spin_eff.GetValue()
597             atype = dial.radio_type.GetSelection()
598             dlg = progressbar(self,maxi = 4)
599             corpus = self.Source.corpus
600             uces = corpus.lc[self.cl-1]
601             if self.Source.parametres['classif_mode'] != 2 :
602                 uci = False
603             else :
604                 uci = True
605             tab = corpus.make_table_with_classe(uces, self.la, uci = uci)
606             tab.pop(0)
607             dlg.Update(2, u'score...')
608             if atype == 0 :
609                 ntab = [round(sum([self.lchi[i] for i, word in enumerate(line) if word == 1]),2) for line in tab]
610             else :
611                 ntab = [round(sum([self.lchi[i] for i, word in enumerate(line) if word == 1])/float(sum(line)),2) if sum(line)!=0 else 0 for line in tab]
612             ntab2 = [[ntab[i], uces[i]] for i, val in enumerate(ntab)]
613             del ntab
614             ntab2.sort(reverse = True)
615             ntab2 = ntab2[:limite]
616             nuces = [val[1] for val in ntab2]
617             dlg.Update(3, u'concordancier...')
618             ucis_txt, ucestxt = doconcorde(corpus, nuces, self.la, uci = uci)
619             items = dict([[i, '<br>'.join([ucis_txt[i], '<table bgcolor = #1BF0F7 border=0><tr><td><b>score : %.2f</b></td></tr></table><br>' % ntab2[i][0], ucestxt[i]])] for i, uce in enumerate(nuces)])
620             dlg.Update(4, u'texte...')
621             win = message(self, items, u"Segments de texte caractéristiques - Classe %i" % self.cl, (750, 600), uceids = nuces)
622             #win.html = '<html>\n' + '<br>'.join(['<br>'.join([ucis_txt[i], '<table bgcolor = #1BF0F7 border=0><tr><td><b>score : %.2f</b></td></tr></table>' % ntab2[i][0], ucestxt[i]]) for i in range(0,len(ucestxt))]) + '\n</html>'
623             #win.HtmlPage.SetPage(win.html)
624             dlg.Destroy()
625             win.Show(True)
626     
627     def on_tablex(self, evt):
628         if 'corpus' in dir(self.Source):
629             corpus = self.Source.corpus
630         else :
631             corpus = self.Source.tableau
632         with codecs.open(self.Source.pathout['chisqtable'], 'r', corpus.parametres['syscoding']) as f :
633             chistable = [line.replace('\n','').replace('\r','').replace('"','').replace(',','.').split(';') for line in f]
634         title = chistable[0]
635         title.pop(0)
636         chistable.pop(0)
637         vchistable = [line[1:] for line in chistable]
638         fchistable = [line[0] for line in chistable]
639         words = self.getselectedwords()
640         tableout = [vchistable[fchistable.index(word)] for word in words]
641         tmpgraph = tempfile.mktemp(dir=self.Source.parent.TEMPDIR)
642         nbcl = len(title)
643         nbwords = len(words)
644         BarFrame(self.Source.parent, tableout, title, words)
645
646     def onlexdendro(self, evt):
647         if 'corpus' in dir(self.Source):
648             corpus = self.Source.corpus
649         else :
650             corpus = self.Source.tableau
651         with codecs.open(self.Source.pathout['chisqtable'], 'r', corpus.parametres['syscoding']) as f :
652             chistable = [line.replace('\n','').replace('\r','').replace('"','').replace(',','.').split(';') for line in f]
653         title = chistable[0]
654         title.pop(0)
655         chistable.pop(0)
656         vchistable = [line[1:] for line in chistable]
657         fchistable = [line[0] for line in chistable]
658         words = self.getselectedwords()
659         tableout = [vchistable[fchistable.index(word)] for word in words]
660         BarFrame(self.Source.parent, tableout, title, words, tree = self.Source.pathout['Rdendro'])
661
662     def make_concord(self, uces, title, color = 'red') :
663         corpus = self.Source.corpus
664         ListWord = [self.getColumnText(self.GetFirstSelected(), 6)]
665         last = self.GetFirstSelected()
666         while self.GetNextSelected(last) != -1:
667             last = self.GetNextSelected(last)
668             ListWord.append(self.getColumnText(last, 6))
669         ucef = []
670         if self.Source.parametres['classif_mode'] != 2 :
671             for word in ListWord : 
672                 uci = False
673                 ucef += list(set(corpus.getlemuces(word)).intersection(uces))
674         else :
675             for word in ListWord : 
676                 ucef += list(set(corpus.getlemucis(word)).intersection(uces))            
677                 uci = True
678         ucis_txt, ucestxt = doconcorde(corpus, ucef, ListWord, uci = uci)
679         items = dict([[i, '<br><br>'.join([ucis_txt[i], ucestxt[i]])] for i in range(0,len(ucestxt))])
680         win = message(self, items, title, (800, 500), uceids = ucef)
681         return win
682
683     def OnPopupTwo(self, event):
684         if 'corpus' in dir(self.Source) :
685             corpus = self.Source.corpus
686             uces = corpus.lc[self.cl-1]
687             win = self.make_concord(uces, "Concordancier - Classe %i" % self.cl)
688             win.Show(True)
689     
690     def OnPopupThree(self, event):
691         corpus = self.Source.corpus
692         uces = [classe[i] for classe in corpus.lc for i in range(0,len(classe))]
693         win = self.make_concord(uces, "Concordancier - Segments de texte classés")
694         win.Show(True)
695         
696     def OnPopupFour(self, event):
697         corpus = self.Source.corpus
698         uces = [classe[i] for classe in corpus.lc for i in range(0,len(classe))] + corpus.lc0
699         win = self.make_concord(uces, "Concordancier - Tous les segments de texte")
700         win.Show(True)
701
702     def OnPopupFive(self, event):
703         word = self.getColumnText(self.GetFirstSelected(), 6)
704         lk = "http://www.cnrtl.fr/definition/" + word
705         webbrowser.open(lk)
706
707     def OnPopupSix(self, event):  
708         word = self.getColumnText(self.GetFirstSelected(), 6)
709         lk = "http://www.cnrtl.fr/etymologie/" + word
710         webbrowser.open(lk)
711         
712     def OnPopupSeven(self, event):        
713         word = self.getColumnText(self.GetFirstSelected(), 6)
714         lk = "http://www.cnrtl.fr/synonymie/" + word
715         webbrowser.open(lk)
716         
717     def OnPopupHeight(self, event):  
718         word = self.getColumnText(self.GetFirstSelected(), 6)
719         lk = "http://www.cnrtl.fr/antonymie/" + word
720         webbrowser.open(lk)
721         
722     def OnPopupNine(self, event):            
723         word = self.getColumnText(self.GetFirstSelected(), 6)
724         lk = "http://www.cnrtl.fr/morphologie/" + word
725         webbrowser.open(lk)
726
727     def onproxe(self, evt) :
728         word = self.getColumnText(self.GetFirstSelected(), 6)
729         lk = "http://www.cnrtl.fr/proxemie/" + word
730         webbrowser.open(lk)
731
732     def OnPopupOne(self, event):
733         corpus = self.Source.corpus
734         #print 'ATTENTION PRINT ET TABLE'
735         #corpus.make_et_table()
736         word = self.getColumnText(self.GetFirstSelected(), 6)
737         lems = corpus.getlems()
738         uces = corpus.lc[self.cl-1]
739         rep = []
740         #FIXME : donner aussi eff reel a la place de nb uce
741         for forme in lems[word].formes :
742             if self.Source.parametres['classif_mode'] != 2 :
743                 ucef = list(set(corpus.getworduces(forme)).intersection(uces))
744             else :
745                 ucef = list(set(corpus.getworducis(forme)).intersection(uces))
746             #ucef = [uce for uce in corpus.formes[forme][1] if uce in uces]
747             if ucef != [] :
748                 nb = len(ucef)
749                 rep.append([corpus.getforme(forme).forme, nb])
750         rep.sort(key = itemgetter(1), reverse = True)
751         #win = message(self, u"Formes associées", wx.Size(300, 200))
752         items = dict([[i, '\t:\t'.join([str(val) for val in forme])] for i, forme in enumerate(rep)])
753         win = message(self, items, u"Formes associées", (300, 200))
754         #win.html = '<html>\n' + '<br>'.join([' : '.join([str(val) for val in forme]) for forme in rep]) + '\n</html>'
755         #win.HtmlPage.SetPage(win.html)
756         win.Show(True)
757     
758     def OnMakeTgen(self, evt):
759         self.parent.tree.OnTgenEditor(self.getselectedwords())    
760
761
762 class wliste(wx.Frame):
763     def __init__(self, parent, id, title, d, fline, size=(600, 500)):
764         wx.Frame.__init__(self, parent, id)
765         self.liste = ListForSpec(self, parent, d, fline[1:], menu = False)
766         self.button_1 = wx.Button(self, -1, "Fermer")
767         self.Bind(wx.EVT_BUTTON, self.OnCloseMe, self.button_1)
768         self.Bind(wx.EVT_CLOSE, self.OnCloseWindow)
769         self.__do_layout()
770
771     def __do_layout(self):
772         sizer_1 = wx.BoxSizer(wx.VERTICAL)
773         sizer_2 = wx.BoxSizer(wx.VERTICAL)
774         sizer_2.Add(self.liste, 1, wx.EXPAND | wx.ADJUST_MINSIZE, 0)
775         sizer_2.Add(self.button_1, 0, wx.ALIGN_CENTER_HORIZONTAL | wx.ADJUST_MINSIZE, 0)
776         sizer_1.Add(sizer_2, 1, wx.EXPAND, 0)
777         self.SetAutoLayout(True)
778         self.SetSizer(sizer_1)
779         self.Layout()
780         
781     def OnCloseMe(self, event):
782         self.Close(True)
783
784     def OnCloseWindow(self, event):
785         self.Destroy()