CMS 3D CMS Logo

ConfigEditorTabController.py
Go to the documentation of this file.
1 from __future__ import absolute_import
2 from __future__ import print_function
3 import sys
4 import logging
5 import os.path
6 import copy
7 
8 from PyQt4.QtCore import SIGNAL,QString,QCoreApplication
9 from PyQt4.QtGui import QMessageBox,QFileDialog
10 
11 from Vispa.Main.Application import Application
12 from Vispa.Main.Exceptions import exception_traceback
13 from Vispa.Share.ThreadChain import ThreadChain
14 from Vispa.Plugins.Browser.BrowserTabController import BrowserTabController
15 from Vispa.Views.WidgetView import WidgetView
16 from Vispa.Plugins.ConfigEditor.ConfigEditorBoxView import ConfigEditorBoxView,ConnectionStructureView,SequenceStructureView
17 from Vispa.Gui.TextDialog import TextDialog
18 
19 try:
20  from FWCore.GuiBrowsers.DOTExport import DotExport
21  import_dotexport_error=None
22 except Exception as e:
23  import_dotexport_error=(str(e),exception_traceback())
24 
25 try:
26  from Vispa.Plugins.EdmBrowser.EventContentDialog import EventContentDialog
27  event_content_error=None
28 except Exception as e:
29  event_content_error=(str(e),exception_traceback())
30 
31 try:
32  from .ToolDataAccessor import ToolDataAccessor,ConfigToolBase,standardConfigDir
33  from .ToolDialog import ToolDialog
34  import_tools_error=None
35 except Exception as e:
36  import_tools_error=(str(e),exception_traceback())
37 
39  """
40  """
41  def __init__(self, plugin):
42  logging.debug(__name__ + ": __init__")
43  BrowserTabController.__init__(self, plugin)
44 
45  self._editorName = ""
46  self._thread = None
47  self._originalSizes=[100,1,200]
48  self._toolDialog=None
49  self._updateCenterView=False
50  self.setEditable(False)
51 
52  self._configMenu = self.plugin().application().createPluginMenu('&Config')
53  self._configToolBar = self.plugin().application().createPluginToolBar('&Config')
54  openEditorAction = self.plugin().application().createAction('&Open in custom editor', self.openEditor, "F6")
55  self._configMenu.addAction(openEditorAction)
56  chooseEditorAction = self.plugin().application().createAction('&Choose custom editor...', self.chooseEditor, "Ctrl+T")
57  self._configMenu.addAction(chooseEditorAction)
58  self._configMenu.addSeparator()
59  self._dumpAction = self.plugin().application().createAction('&Dump python config to single file...', self.dumpPython, "Ctrl+D")
60  self._configMenu.addAction(self._dumpAction)
61  self._dotExportAction = self.plugin().application().createAction('&Export dot graphic...', self.exportDot, "Ctrl+G")
62  self._configMenu.addAction(self._dotExportAction)
63  self._historyAction = self.plugin().application().createAction('&Show history...', self.history, "Ctrl+H")
64  self._configMenu.addAction(self._historyAction)
65  self._eventContentAction = self.plugin().application().createAction('&Browse event content...', self.eventContent, "Ctrl+Shift+C")
66  self._configMenu.addAction(self._eventContentAction)
67  self._configMenu.addSeparator()
68  self._editorAction = self.plugin().application().createAction('&Edit using ConfigEditor', self.startEditMode, "F8")
69  self._configMenu.addAction(self._editorAction)
70  self._configToolBar.addAction(self._editorAction)
71 
72  #@staticmethod
74  """ Returns supported file type: py.
75  """
76  return [('py', 'Config file')]
77  staticSupportedFileTypes = staticmethod(staticSupportedFileTypes)
78 
79  def dotExportAction(self):
80  return self._dotExportAction
81 
82  def updateViewMenu(self):
83  BrowserTabController.updateViewMenu(self)
84  self.disconnect(self.tab().centerView(), SIGNAL("doubleClicked"), self.onCenterViewDoubleClicked)
85  self.connect(self.tab().centerView(), SIGNAL("doubleClicked"), self.onCenterViewDoubleClicked)
86 
87  def onCenterViewDoubleClicked(self,object):
88  logging.debug(__name__ + ": onCenterViewDoubleClicked()")
89  self.tab().treeView().select(object)
90  self.onTreeViewSelected(object)
91 
92  def updateCenterView(self, propertyView=True):
93  """ Fill the center view from an item in the TreeView and update it """
94  if not self._updateCenterView:
95  # Do not update the very first time
96  self._updateCenterView=True
97  return
98  statusMessage = self.plugin().application().startWorking("Updating center view")
99  if propertyView:
100  self.selectDataAccessor(True)
101  else:
102  self.selectDataAccessor(self.tab().propertyView().dataObject())
103  if self._thread != None and self._thread.isRunning():
104  self.dataAccessor().cancelOperations()
105  while self._thread.isRunning():
106  if not Application.NO_PROCESS_EVENTS:
107  QCoreApplication.instance().processEvents()
108  objects = []
109  select=self.tab().treeView().selection()
110  if select != None:
111  if self.currentCenterViewClassId() == self.plugin().viewClassId(ConnectionStructureView):
112  self.tab().centerView().setArrangeUsingRelations(True)
113  if self.tab().centerView().checkNumberOfObjects():
114  if self.dataAccessor().isContainer(select):
115  self._thread = ThreadChain(self.dataAccessor().readConnections, [select]+self.dataAccessor().allChildren(select))
116  else:
117  self._thread = ThreadChain(self.dataAccessor().readConnections, [select], True)
118  while self._thread.isRunning():
119  if not Application.NO_PROCESS_EVENTS:
120  QCoreApplication.instance().processEvents()
121  self.tab().centerView().setConnections(self._thread.returnValue())
122  self.tab().centerView().setDataObjects(self.dataAccessor().nonSequenceChildren(select))
123  else:
124  self.tab().centerView().setDataObjects([])
125  elif self.currentCenterViewClassId() == self.plugin().viewClassId(SequenceStructureView):
126  self.tab().centerView().setArrangeUsingRelations(False)
127  self.tab().centerView().setDataObjects([select])
128  self.tab().centerView().setConnections({})
129  if (self.currentCenterViewClassId() == self.plugin().viewClassId(ConnectionStructureView) or self.currentCenterViewClassId() == self.plugin().viewClassId(SequenceStructureView)) and \
130  self.tab().centerView().updateContent(True):
131  if not self.dataAccessor().isContainer(select) and self.currentCenterViewClassId() == self.plugin().viewClassId(ConnectionStructureView):
132  self.tab().centerView().select(select,500)
133  else:
134  self.tab().centerView().restoreSelection()
135  select = self.tab().centerView().selection()
136  if select != None:
137  if self.tab().propertyView().dataObject() != select and propertyView:
138  self.tab().propertyView().setDataObject(select)
139  self.tab().propertyView().updateContent()
140  if import_tools_error==None and self.tab().editorSplitter():
141  self.updateConfigHighlight()
142  self.plugin().application().stopWorking(statusMessage)
143 
144  def activated(self):
145  """ Shows plugin menus when user selects tab.
146  """
147  logging.debug(__name__ + ": activated()")
148  BrowserTabController.activated(self)
149  self.plugin().application().showPluginMenu(self._configMenu)
150  self.plugin().application().showPluginToolBar(self._configToolBar)
151  self._editorAction.setVisible(not self.tab().editorSplitter())
152  if self.tab().editorSplitter():
153  self._applyPatToolAction.setVisible(self.dataAccessor().process()!=None)
154  self.tab().mainWindow().application().showZoomToolBar()
155 
156  def openEditor(self):
157  """ Call editor """
158  logging.debug(__name__ + ": openEditor")
159  selected_object = self.tab().propertyView().dataObject()
160  filename = self.dataAccessor().fullFilename(selected_object)
161  if self._editorName != "" and selected_object != None and os.path.exists(filename):
162  if os.path.expandvars("$CMSSW_RELEASE_BASE") in filename:
163  QMessageBox.information(self.tab(), "Opening readonly file...", "This file is from $CMSSW_RELEASE_BASE and readonly")
164  command = self._editorName
165  command += " " + filename
166  command += " &"
167  os.system(command)
168 
169  def chooseEditor(self, _editorName=""):
170  """ Choose editor using FileDialog """
171  logging.debug(__name__ + ": chooseEditor")
172  if _editorName == "":
173  _editorName = str(QFileDialog.getSaveFileName(self.tab(), "Choose editor", self._editorName, "Editor (*)", None , QFileDialog.DontConfirmOverwrite or QFileDialog.DontResolveSymlinks))
174  if not os.path.exists(_editorName):
175  _editorName = os.path.basename(_editorName)
176  if _editorName != None and _editorName != "":
177  self._editorName = _editorName
178  self.saveIni()
179 
180  def dumpPython(self, fileName=None):
181  """ Dump python configuration to file """
182  logging.debug(__name__ + ": dumpPython")
183  dump = self.dataAccessor().dumpPython()
184  if dump == None:
185  logging.error(self.__class__.__name__ +": dumpPython() - "+"Cannot dump this config because it does not contain a 'process'.\nNote that only 'cfg' files contain a 'process'.")
186  self.plugin().application().errorMessage("Cannot dump this config because it does not contain a 'process'.\nNote that only 'cfg' files contain a 'process'.")
187  return None
188  filter = QString("")
189  if not fileName:
190  defaultname = os.path.splitext(self._filename)[0] + "_dump" + os.path.splitext(self._filename)[1]
191  fileName = str(QFileDialog.getSaveFileName(self.tab(), "Save python config...", defaultname, "Python config (*.py)", filter))
192  if fileName != "":
193  name = fileName
194  ext = "PY"
195  if os.path.splitext(fileName)[1].upper().strip(".") == ext:
196  name = os.path.splitext(fileName)[0]
197  ext = os.path.splitext(fileName)[1].upper().strip(".")
198  text_file = open(name + "." + ext.lower(), "w")
199  text_file.write(dump)
200  text_file.close()
201 
202  def history(self):
203  """ Show config history """
204  logging.debug(__name__ + ": history")
205  history = self.dataAccessor().history()
206  if history == None:
207  logging.error(self.__class__.__name__ +": history() - "+"Cannot show config history because it does not contain a 'process'.\nNote that only 'cfg' files contain a 'process'.")
208  self.plugin().application().errorMessage("Cannot show config history because it does not contain 'process'.\nNote that only 'cfg' files contain a 'process'.")
209  return None
210  dialog=TextDialog(self.tab(), "Configuration history", history, True, "This window lists the parameter changes and tools applied in this configuration file before it was loaded into ConfigEditor.")
211  dialog.exec_()
212 
213  def eventContent(self):
214  """ Open event content dialog """
215  logging.debug(__name__ + ": eventContent")
216  if event_content_error!=None:
217  logging.error(__name__ + ": Could not import EventContentDialog: "+event_content_error[1])
218  self.plugin().application().errorMessage("Could not import EventContentDialog (see logfile for details):\n"+event_content_error[0])
219  return
220  dialog=EventContentDialog(self.tab(),"This dialog let's you check if the input needed by your configuration file is in a dataformat or edm root file. You can compare either to a dataformat definition from a txt file (e.g. RECO_3_3_0) or any edm root file by selecting an input file.\n\nBranches that are used as input by your configuration but not present in the dataformat or file are marked in red.\nBranches that are newly created by your configuration are marked in green.")
221  dialog.setConfigDataAccessor(self.dataAccessor())
222  dialog.exec_()
223 
224  def loadIni(self):
225  """ read options from ini """
226  ini = self.plugin().application().ini()
227  if ini.has_option("config", "editor"):
228  self._editorName = str(ini.get("config", "editor"))
229  else:
230  self._editorName = "emacs"
231  if ini.has_option("config", "CurrentView"):
232  proposed_view = ini.get("config", "CurrentView")
233  else:
234  proposed_view = self.plugin().viewClassId(ConnectionStructureView)
235  self.switchCenterView(proposed_view)
236  if ini.has_option("config", "box content script") and isinstance(self.centerView(),ConfigEditorBoxView):
237  self.centerView().setBoxContentScript(str(ini.get("config", "box content script")))
238  self._boxContentDialog.setScript(str(ini.get("config", "box content script")))
239 
240  def scriptChanged(self, script):
241  BrowserTabController.scriptChanged(self, script)
242  self.saveIni()
243 
244  def saveIni(self):
245  """ write options to ini """
246  ini = self.plugin().application().ini()
247  if not ini.has_section("config"):
248  ini.add_section("config")
249  ini.set("config", "editor", self._editorName)
250  if self.currentCenterViewClassId():
251  ini.set("config", "CurrentView", self.currentCenterViewClassId())
252  if isinstance(self.centerView(),ConfigEditorBoxView):
253  ini.set("config", "box content script", self.centerView().boxContentScript())
254  self.plugin().application().writeIni()
255 
256  def exportDot(self, fileName=None):
257  if import_dotexport_error!=None:
258  logging.error(__name__ + ": Could not import DOTExport: "+import_dotexport_error[1])
259  self.plugin().application().errorMessage("Could not import DOTExport (see logfile for details):\n"+import_dotexport_error[0])
260  return
261  dot = DotExport()
262  if self.currentCenterViewClassId() == self.plugin().viewClassId(ConnectionStructureView):
263  presets = {'seqconnect':False, 'tagconnect':True, 'seq':False, 'services':False, 'es':False, 'endpath':True, 'source':True, 'legend':False}
264  else:
265  presets = {'seqconnect':True, 'tagconnect':False, 'seq':True, 'services':False, 'es':False, 'endpath':True, 'source':True, 'legend':False}
266  for opt, val in presets.items():
267  dot.setOption(opt, val)
268  types = ""
269  for ft in dot.file_types:
270  if types != "":
271  types += ";;"
272  types += ft.upper() + " File (*." + ft.lower() + ")"
273  filter = QString("PDF File (*.pdf)")
274  if not fileName:
275  defaultname = os.path.splitext(self._filename)[0] + "_export"
276  fileName = str(QFileDialog.getSaveFileName(self.tab(), "Export dot graphic...", defaultname, types, filter))
277  if fileName != "":
278  name = fileName
279  ext = str(filter).split(" ")[0].lower()
280  if os.path.splitext(fileName)[1].lower().strip(".") in dot.file_types:
281  name = os.path.splitext(fileName)[0]
282  ext = os.path.splitext(fileName)[1].lower().strip(".")
283  try:
284  dot.export(self.dataAccessor(), name + "." + ext, ext)
285  except Exception:
286  try:
287  dot.export(self.dataAccessor(), name + ".dot", "dot")
288  logging.error(self.__class__.__name__ +": exportDot() - "+"'dot' executable not found which is needed for conversion to '*." + ext + "'. Created '*.dot' file instead.")
289  self.plugin().application().errorMessage("'dot' executable not found which is needed for conversion to '*." + ext + "'. Created '*.dot' file instead.")
290  except Exception as e:
291  logging.error(self.__class__.__name__ +": exportDot() - "+"Could not export dot graphic (see logfile for details): " + str(e))
292  self.plugin().application().errorMessage("Could not export dot graphic: " + exception_traceback())
293 
294  def readFile(self, filename):
295  """ Reads in the file in a separate thread.
296  """
297  self._updateCenterView=False
298  if self.dataAccessor().open(filename):
299  self._dumpAction.setEnabled(self.dataAccessor().process()!=None)
300  self._historyAction.setEnabled(self.dataAccessor().process()!=None)
301  self._eventContentAction.setEnabled(self.dataAccessor().process()!=None)
302  self._editorAction.setEnabled(self.dataAccessor().process()!=None)
303  if self.plugin().application().commandLineOptions().saveimage:
304  self.tab().centerView().updateConnections()
305  self.saveImage(self.plugin().application().commandLineOptions().saveimage)
306  print("Saved image to", self.plugin().application().commandLineOptions().saveimage, ".")
307  sys.exit(2)
308  return True
309  return False
310 
311  def save(self, filename=''):
312  logging.debug(__name__ + ': save')
313  self.startEditMode()
314  if filename != "":
315  if os.path.basename(filename) == os.path.basename(self.dataAccessor().configFile()):
316  logging.error(self.__class__.__name__ +": save() - "+"Cannot use name of original configuration file: "+str(filename))
317  self.plugin().application().errorMessage("Cannot use name of original configuration file.")
318  elif BrowserTabController.save(self, filename):
319  self.dataAccessor().setIsReplaceConfig()
320  return True
321  else:
322  return False
323  elif self.dataAccessor().isReplaceConfig():
324  return BrowserTabController.save(self, filename)
325  return self.tab().mainWindow().application().saveFileAsDialog()
326 
327  def writeFile(self, filename):
328  """ Write replace config file.
329  """
330  logging.debug(__name__ + ': writeFile')
331 
332  text_file = open(filename, "w")
333  text_file.write(self.toolDataAccessor().topLevelObjects()[0].dumpPython()[1])
334  if self.dataAccessor().process():
335  text_file.write(self.dataAccessor().process().dumpHistory(False))
336  text_file.close()
337  return True
338 
339  def open(self, filename=None, update=True):
340  if BrowserTabController.open(self, filename, update):
341  if self.dataAccessor().isReplaceConfig():
342  self.startEditMode()
343  return True
344  return False
345 
346  def startEditMode(self):
347  logging.debug(__name__ + ": startEditMode")
348  if import_tools_error!=None:
349  logging.error(__name__ + ": Could not import tools for ConfigEditor: "+import_tools_error[1])
350  self.plugin().application().errorMessage("Could not import tools for ConfigEditor (see logfile for details):\n"+import_tools_error[0])
351  return
352  if self.tab().editorSplitter():
353  return
354  if self._filename and not self.dataAccessor().process():
355  logging.error(__name__ + ": Config does not contain a process and cannot be edited using ConfigEditor.")
356  self.plugin().application().errorMessage("Config does not contain a process and cannot be edited using ConfigEditor.")
357  return
358  if self._filename and not self.dataAccessor().isReplaceConfig():
359  self.setFilename(None)
360  self.updateLabel()
361  self.tab().createEditor()
362  self.setEditable(True)
363  self.tab().verticalSplitter().setSizes(self._originalSizes)
364 
365  self._importAction = self.plugin().application().createAction('&Import configuration...', self.importButtonClicked, "F2")
366  self._configMenu.addAction(self._importAction)
367  self._configToolBar.addAction(self._importAction)
368  self._applyPatToolAction = self.plugin().application().createAction('&Apply tool...', self.applyButtonClicked, "F3")
369  self._configMenu.addAction(self._applyPatToolAction)
370  self._configToolBar.addAction(self._applyPatToolAction)
371  self.activated()
372 
373  self._toolDataAccessor=ToolDataAccessor()
374  self._toolDataAccessor.setConfigDataAccessor(self.dataAccessor())
375  self.tab().editorTableView().setDataAccessor(self._toolDataAccessor)
376  self.connect(self.tab().editorTableView(), SIGNAL('importButtonClicked'), self.importButtonClicked)
377  self.connect(self.tab().editorTableView(), SIGNAL('applyButtonClicked'), self.applyButtonClicked)
378  self.connect(self.tab().editorTableView(), SIGNAL('removeButtonClicked'), self.removeButtonClicked)
379  self.connect(self.tab().editorTableView(), SIGNAL('selected'), self.codeSelected)
380  self.connect(self.tab().propertyView(), SIGNAL('valueChanged'), self.valueChanged)
381  self._updateCode()
382 
383  def toolDataAccessor(self):
384  return self._toolDataAccessor
385 
386  def minimizeEditor(self):
387  if self.tab().originalButton().isChecked():
388  self._originalSizes=self.tab().verticalSplitter().sizes()
389  self.tab().minimizeButton().setChecked(True)
390  self.tab().originalButton().setChecked(False)
391  self.tab().maximizeButton().setChecked(False)
392  self.tab().verticalSplitter().setSizes([100, 1, 0])
393 
394  def originalEditor(self):
395  self.tab().minimizeButton().setChecked(False)
396  self.tab().originalButton().setChecked(True)
397  self.tab().maximizeButton().setChecked(False)
398  self.tab().verticalSplitter().setSizes(self._originalSizes)
399 
400  def maximizeEditor(self):
401  if self.tab().originalButton().isChecked():
402  self._originalSizes=self.tab().verticalSplitter().sizes()
403  self.tab().minimizeButton().setChecked(False)
404  self.tab().originalButton().setChecked(False)
405  self.tab().maximizeButton().setChecked(True)
406  self.tab().verticalSplitter().setSizes([0, 1, 100])
407 
408  def _updateCode(self,propertyView=True):
409  logging.debug(__name__ + ": _updateCode")
410  self.tab().propertyView().setEnabled(False)
411  self.toolDataAccessor().updateToolList()
412  self.tab().editorTableView().setDataObjects(self.toolDataAccessor().topLevelObjects())
413  if self.tab().editorTableView().updateContent():
414  self.tab().editorTableView().restoreSelection()
415  self.updateContent(False,propertyView)
416  self.tab().propertyView().setEnabled(True)
417 
418  def importConfig(self,filename):
419  logging.debug(__name__ + ": importConfig")
420  statusMessage = self.plugin().application().startWorking("Import python configuration in Editor")
421  try:
422  good=self.open(filename,False)
423  except:
424  logging.error(__name__ + ": Could not open configuration file: "+exception_traceback())
425  self.plugin().application().errorMessage("Could not open configuration file (see log file for details).")
426  self.plugin().application().stopWorking(statusMessage,"failed")
427  return False
428  if not good:
429  logging.error(__name__ + ": Could not open configuration file.")
430  self.plugin().application().errorMessage("Could not open configuration file.")
431  self.plugin().application().stopWorking(statusMessage,"failed")
432  return False
433  if not self.dataAccessor().process():
434  logging.error(__name__ + ": Config does not contain a process and cannot be edited using ConfigEditor.")
435  self.plugin().application().errorMessage("Config does not contain a process and cannot be edited using ConfigEditor.")
436  self.plugin().application().stopWorking(statusMessage,"failed")
437  return False
438  if self._filename and not self.dataAccessor().isReplaceConfig():
439  self.setFilename(None)
440  self.updateLabel()
441  self.toolDataAccessor().setConfigDataAccessor(self.dataAccessor())
442  self.tab().propertyView().setDataObject(None)
443  self._updateCode()
444  self._applyPatToolAction.setVisible(True)
445  self.plugin().application().stopWorking(statusMessage)
446  return True
447 
449  if self.tab().editorTableView().selection() in self.toolDataAccessor().toolModules().keys():
450  self.tab().centerView().highlight(self.toolDataAccessor().toolModules()[self.tab().editorTableView().selection()])
451  else:
452  self.tab().centerView().highlight([])
453 
455  logging.debug(__name__ + ": importButtonClicked")
456  filename = QFileDialog.getOpenFileName(
457  self.tab(),'Select a configuration file',standardConfigDir,"Python configuration (*.py)")
458  if not filename.isEmpty():
459  self.importConfig(str(filename))
460 
462  logging.debug(__name__ + ": applyButtonClicked")
463  if not self._toolDialog:
464  self._toolDialog=ToolDialog()
465  self._toolDialog.setDataAccessor(self._toolDataAccessor)
466  if not self._toolDialog.exec_():
467  return
468  if not self.toolDataAccessor().addTool(self._toolDialog.tool()):
469  return
470  self.setModified(True)
471  self._updateCode()
472  self.tab().editorTableView().select(self.tab().editorTableView().dataObjects()[-2])
473  self.codeSelected(self.tab().editorTableView().dataObjects()[-2])
474 
475  def removeButtonClicked(self,object):
476  logging.debug(__name__ + ": removeButtonClicked")
477  if not object or not self.dataAccessor().process() or\
478  self._toolDataAccessor.label(object) in ["Import","ApplyTool"]:
479  return
480  if not self.toolDataAccessor().removeTool(object):
481  self.plugin().application().errorMessage("Could not apply tool. See log file for details.")
482  return
483  self.setModified(True)
484  self._updateCode()
485  self.tab().editorTableView().select(self.tab().editorTableView().dataObjects()[-1])
486  self.codeSelected(self.tab().editorTableView().dataObjects()[-1])
487 
488  def onSelected(self, select):
489  self.selectDataAccessor(select)
490  BrowserTabController.onSelected(self, select)
491 
492  def refresh(self):
493  self.tab().propertyView().setDataObject(None)
494  BrowserTabController.refresh(self)
495 
496  def updateContent(self, filtered=False, propertyView=True):
497  if import_tools_error==None and isinstance(object,ConfigToolBase):
498  propertyView=False
499  else:
500  self.tab().propertyView().setDataAccessor(self.dataAccessor())
501  BrowserTabController.updateContent(self, filtered, propertyView)
502 
503  def select(self, object):
504  self.selectDataAccessor(object)
505  BrowserTabController.select(self, object)
506 
507  def selectDataAccessor(self,object):
508  if import_tools_error==None and isinstance(object,ConfigToolBase):
509  self.tab().propertyView().setDataAccessor(self.toolDataAccessor())
510  else:
511  self.tab().propertyView().setDataAccessor(self.dataAccessor())
512 
513  def codeSelected(self,select):
514  if self.tab().propertyView().dataObject() != select:
515  statusMessage = self.plugin().application().startWorking("Updating property view")
516  self.tab().propertyView().setDataAccessor(self.toolDataAccessor())
517  self.tab().propertyView().setDataObject(select)
518  self.tab().propertyView().updateContent()
519  self.plugin().application().stopWorking(statusMessage)
520  self.updateConfigHighlight()
521 
522  def valueChanged(self,name):
523  if isinstance(self.tab().propertyView().dataObject(),ConfigToolBase):
524  if self._toolDataAccessor.label(self.tab().propertyView().dataObject())=="Import":
525  filename=self.toolDataAccessor().propertyValue(self.tab().propertyView().dataObject(),"filename")
526  return self.importConfig(filename)
527  else:
528  self.toolDataAccessor().updateProcess()
529  self.setModified(True)
530  self._updateCode(False)
531  self.codeSelected(self.tab().editorTableView().selection())
532  else:
533  self._updateCode()
selection
main part
Definition: corrVsCorr.py:100
def setModified(self, modified=True)
S & print(S &os, JobReport::InputFile const &f)
Definition: JobReport.cc:66
def open(self, filename=None, update=True)
def updateLabel(self, prefix="", titletext="")
#define str(s)
double split
Definition: MVATrainer.cc:139