source: orange-bioinformatics/Orange/bioinformatics/widgets/prototypes/OWDataFiles.py @ 1633:b8852fdd1a0f

Revision 1633:b8852fdd1a0f, 10.3 KB checked in by mitar, 2 years ago (diff)

Fixing imports.

Line 
1"""
2<name>Data Files</name>
3<description>Reads data from designated directory.</description>
4<icon>icons/ChipDataFiles.png</icon>
5<priority>1050</priority>
6<contact>Peter Juvan (peter.juvan@fri.uni-lj.si)</contact>
7"""
8
9import os, os.path
10
11import orange
12from Orange.OrangeWidgets.OWWidget import *
13from Orange.OrangeWidgets import OWGUI
14
15import warnings
16warnings.filterwarnings("ignore", "'strain'", orange.AttributeWarning)
17
18class DataFiles(orange.Orange):
19    """Structure for communicating multiple ExampleTables:
20    [(name1,[exampleTable1a,exampleTable1b,...]), (name2,[exampleTable2a,...]), ...]
21    """
22    pass
23
24
25class ExampleSelection(orange.Orange):
26    """Structure for selection of examples: (selectorName, [0,1,...])
27    """
28    pass
29
30
31class OWDataFiles(OWWidget):
32    settingsList  = ["recentDirs", "selectedDirName", "applyOnChange"]
33
34    def __init__(self, parent=None, signalManager = None, loaddata=1):
35        OWWidget.__init__(self, parent, signalManager, 'Data Files', wantMainArea = 0, resizingEnabled = 1)
36
37        self.callbackDeposit = []
38
39        self.inputs = []
40        self.outputs = [("Examples", ExampleTable), ("Structured Data", DataFiles)]
41
42        self.dataStructure = []
43        self.datasets = None
44        self.lastSentIds = []
45
46        # Settings
47        self.recentDirs=[] 
48        self.selectedDirName = "None"
49        self.applyOnChange = 0
50        self.loadSettings()
51
52        # CONTROLS
53        box = OWGUI.widgetBox(self.controlArea, "Directory", addSpace = True, orientation=0)
54        self.dircombo=QComboBox(box)
55        box.layout().addWidget(self.dircombo)
56        button = OWGUI.button(box, self, '...', callback = self.browseDirectory, disabled=0)
57        button.setMaximumWidth(25)
58        # connecting GUI to code
59        self.connect(self.dircombo,SIGNAL('activated(int)'),self.selectDir)
60
61        # info
62        box = OWGUI.widgetBox(self.controlArea, "Info", addSpace = True)
63        self.infoa = OWGUI.widgetLabel(box, 'No data loaded.')
64        self.infob = OWGUI.widgetLabel(box, '')
65        self.infoc = OWGUI.widgetLabel(box, '')
66           
67        # LIST VIEW
68        frmListView = OWGUI.widgetBox(self.controlArea, None, addSpace = True)
69        self.tree = QTreeWidget(frmListView)
70        self.tree.setSelectionMode(QAbstractItemView.MultiSelection)
71        self.tree.setHeaderLabel("Directory/Data File")
72        frmListView.layout().addWidget(self.tree)
73        self.connect(self.tree,SIGNAL('itemSelectionChanged()'),self.selectionChanged)
74
75        # Output
76        box = OWGUI.widgetBox(self.controlArea, "Output", addSpace = True)
77        OWGUI.checkBox(box, self, 'applyOnChange', 'Commit data on selection change')
78        self.commitBtn = OWGUI.button(box, self, "Commit", callback=self.sendData, disabled=1)
79        self.resize(300,600)
80
81        # initial settings           
82        self.recentDirs=filter(os.path.exists,self.recentDirs)
83        self.setDirlist()
84        self.dircombo.setCurrentIndex(0)
85        if self.recentDirs!=[] and loaddata:
86            self.loadData(self.recentDirs[0])
87           
88    def setFileTree(self):
89        self.disconnect(self.tree,SIGNAL('itemSelectionChanged()'),self.selectionChanged)
90        self.tree.clear()
91        self.listitems = []
92        for d in self.dataStructure:
93            (dirname, files) = d
94            diritem = QTreeWidgetItem(self.tree, [dirname], QTreeWidgetItem.UserType)
95            diritem.setSelected(1)
96            self.listitems.append(diritem)
97            diritem.setExpanded(1)
98            diritem.name = dirname
99            for f in files:
100                item = QTreeWidgetItem(diritem, [f.name], QTreeWidgetItem.UserType)
101                item.setSelected(1)
102                self.listitems.append(item)
103                item.data = f
104        self.connect(self.tree,SIGNAL('itemSelectionChanged()'),self.selectionChanged)
105               
106    def selectionChanged(self):
107        if self.applyOnChange:
108            self.sendData()
109
110    # checks which data has been selected, builds a data structure, and sends it out
111    def sendData(self):
112        data = []
113        # clear what has been previously sent
114        for id in self.lastSentIds:
115            self.send("Examples", None, id)
116        self.lastSentIds = []
117        # send new data
118        id = 0
119        for tIdx in range(self.tree.topLevelItemCount()):
120            dir = self.tree.topLevelItem(tIdx)
121            if dir in self.tree.selectedItems():
122                files = []
123                for cIdx in range(dir.childCount()):
124                    f = dir.child(cIdx)
125                    if f in self.tree.selectedItems():
126                        files.append(f.data)
127                        self.send("Examples", f.data, id)
128                        self.lastSentIds.append(id)
129                        id += 1
130                data.append((dir.name, files))
131        #print "DATAS", data
132        self.send("Structured Data", data)
133
134    # Loads the data from a root directory, sends the data to the output channels
135    def loadData(self, root):
136        dataStructure = [] # structured [(dirname0, [d00, d01, ...]), ...]
137        datasets = []  # flat list containing all the data sets
138        dirs = os.listdir(root)
139        lenDirs = len(dirs)
140        if lenDirs:
141            self.progressBarInit()
142            pbStep = 100./lenDirs
143        for d in dirs:
144            dirname = os.path.join(root, d)
145            if os.path.isdir(dirname):
146                dirdata = []   
147                files  = os.listdir(dirname)
148                for f in files:
149                    name, ext = os.path.splitext(f)
150                    if ext in ['.tab', '.txt', '.data']:
151                        try:
152                            data = None
153                            data = orange.ExampleTable(os.path.join(dirname,f))
154                            data.name = name
155                            data.strain = os.path.basename(dirname)
156                            dirdata.append(data)
157                        except orange.KernelException:
158                            print 'Warning: file %s\\%s not in appropriate format' %(dirname, f)
159                if len(dirdata):
160                    dataStructure.append((os.path.split(dirname)[1], dirdata))
161                    datasets = datasets + dirdata
162            self.progressBarAdvance(pbStep)
163        if lenDirs:
164            self.progressBarFinished()
165
166        # enable commit, set file tree
167        self.commitBtn.setEnabled(len(dataStructure))
168        self.dataStructure = dataStructure
169        self.datasets = datasets
170        self.setFileTree()
171
172        # set infos (sumarize the data)
173        if len(dataStructure):
174            numSets = len(self.dataStructure)
175            numFiles = len(self.datasets)
176            self.infoa.setText("%d set%s, total of %d data file%s." % (numSets, ["", "s"][numSets!=1], numFiles, ["","s"][numFiles!=1]))
177            # construct lists that sumarize the data
178            numExamplesList = []
179            numAttrList = []
180            hasClass = []
181            attrNameList = []
182            for et in datasets:
183                numExamplesList.append(len(et))
184                numAttrList.append(len(et.domain.attributes))
185                hasClass.append(et.domain.classVar != None)
186                for attr in et.domain.attributes:
187                    if attr.name not in attrNameList:
188                        attrNameList.append(attr.name)
189            # report the number of attributes/class
190            if len(numAttrList):
191                minNumAttr = min(numAttrList)
192                maxNumAttr = max(numAttrList)
193                if minNumAttr != maxNumAttr:
194                    infob = "From %d to %d attribute%s (%d in total)" % (minNumAttr, maxNumAttr, ["","s"][maxNumAttr!=1], len(attrNameList))
195                else:
196                    infob = "%d attribute%s" % (maxNumAttr, ["","s"][maxNumAttr!=1])
197            else:
198                infob = "No attributes"
199            if sum(hasClass) == len(hasClass):
200                infob += ", all files contain class variable."
201            elif sum(hasClass) == 0:
202                infob += ", no class variable."
203            else:
204                infob += ", some files contain class variable."
205            self.infob.setText(infob)
206            # report the number of examples
207            if len(numExamplesList):
208                infoc = "Files contain "
209                minNumE = min(numExamplesList)
210                maxNumE = max(numExamplesList)
211                if minNumE == maxNumE:
212                    infoc += "%d example%s, " % (maxNumE, ["","s"][maxNumE!=1])
213                else:
214                    infoc += "from %d to %d example%s, " % (minNumE, maxNumE, ["","s"][maxNumE!=1])
215                infoc += "%d in total." % sum(numExamplesList)
216            else:
217                infoc = "Files contain no examples."
218            self.infoc.setText(infoc)
219
220            # Add a directory to the start of the file list.
221            # If it exists, move it to the start of the list
222            if root in self.recentDirs:
223                self.recentDirs.remove(root)
224            self.recentDirs.insert(0, root)
225            self.setDirlist()
226            self.selectedDirName = root
227               
228        else:
229            self.infoa.setText('No data on input.')
230            self.infob.setText('')
231            self.infoc.setText('')
232
233        # read data
234        if self.applyOnChange:
235            self.sendData()
236
237    # displays a file dialog and selects a directory
238    def browseDirectory(self):
239        if len(self.recentDirs):
240            startdir=self.recentDirs[0]
241        else:
242            startdir ="."
243        dirname=str(QFileDialog.getExistingDirectory(self, 'Data Directory', startdir, QFileDialog.ShowDirsOnly))
244        if len(dirname):
245            self.loadData(str(dirname))
246
247    def setDirlist(self):
248        self.dircombo.clear()
249        if len(self.recentDirs):
250            for dir in self.recentDirs:
251                (upperdir,dirname)=os.path.split(dir)
252                # leave out the path
253                self.dircombo.insertItem(self.dircombo.count(), dirname)
254        else:
255            self.dircombo.insertItem(0,"(none)")
256
257    # called when user makes a selection from the drop-down menu
258    def selectDir(self, n):
259        if self.recentDirs:
260            self.loadData(self.recentDirs[n])
261        else:
262            self.loadData("(none)")
263
264
265
266if __name__=="__main__":
267    a=QApplication(sys.argv)
268    ow=OWDataFiles()
269    ow.show()
270    ow.loadData("/home/marko/anova/smallchipdata")
271    a.exec_()
272    ow.saveSettings()
Note: See TracBrowser for help on using the repository browser.