示例#1
0
 def __init__(self, var, parent=None, **kwargs):
     PyListModel.__init__(self, [], parent, **kwargs)
     self.wrap(var.values)
     self.colorPalette = OWColorPalette.ColorPaletteHSV(len(self))
     self.connect(self, SIGNAL("columnsInserted(QModelIndex, int, int)"),
                  self.updateColors)
     self.connect(self, SIGNAL("columnsRemoved(QModelIndex, int, int)"),
                  self.updateColors)
示例#2
0
    def _setup_gui_values(self):
        self.values_edit = QListView()
        self.values_edit.setEditTriggers(QTreeView.CurrentChanged)
        self.values_model = PyListModel(flags=Qt.ItemIsSelectable | \
                                        Qt.ItemIsEnabled | Qt.ItemIsEditable)
        self.values_edit.setModel(self.values_model)

        self.values_model.dataChanged.connect(self.on_values_changed)
        self.main_form.addRow("Values", self.values_edit)
示例#3
0
 def __init__(self, parent=None, signalManager=None, name="R Script"):
     OWWidget.__init__(self, parent, signalManager, name)
     
     self.inputs = [("in_data", ExampleTable, self.setData), ("in_distance", orange.SymMatrix, self.setDistance)]
     self.outputs = [("out_data", ExampleTable), ("out_distance", orange.SymMatrix), ("out_learner", orange.Learner), ("out_classifier", orange.Classifier)]
     
     self.in_data, self.in_distance = None, None
     self.scriptLibraryList = [RScript("New script", "x <- c(1,2,5)\ny <- c(2,1 6)\nplot(x,y)\n")]
     self.selectedScriptIndex = 0
     
     self.lastDir = os.path.expanduser("~/script.R")
     
     self.loadSettings()
     
     self.defaultFont = QFont("Monaco") if sys.platform == "darwin" else QFont("Courier")
     
     self.splitter = QSplitter(Qt.Vertical, self.mainArea)
     self.mainArea.layout().addWidget(self.splitter)
     self.scriptEdit = RScriptEditor()
     self.splitter.addWidget(self.scriptEdit)
     self.console = RPy2Console({}, self)
     self.splitter.addWidget(self.console)
     self.splitter.setSizes([2,1])
     
     self.libraryModel = PyListModel([], self, Qt.ItemIsEnabled | Qt.ItemIsSelectable | Qt.ItemIsEditable)
     self.libraryModel.wrap(self.scriptLibraryList)
     
     self.infoBox = OWGUI.widgetLabel(OWGUI.widgetBox(self.controlArea, "Info", addSpace=True), "")
     self.infoBox.setText("<p>Execute R script</p>Input variables<li><ul>in_data</ul><ul>in_distance</ul></li>Output variables:<li><ul>out_data</ul></p/>")
     
     box = OWGUI.widgetBox(self.controlArea, "Library", addSpace=True)
     
     self.libraryWidget = LibraryWidget()
     self.libraryView = self.libraryWidget.view
     box.layout().addWidget(self.libraryWidget)
     
     self.libraryWidget.view.setItemDelegate(ScriptItemDelegate(self))
     self.libraryWidget.setScriptModel(self.libraryModel)
     self.libraryWidget.setDocumentEditor(self.scriptEdit)
     
     box = OWGUI.widgetBox(self.controlArea, "Run")
     OWGUI.button(box, self, "Execute", callback=self.runScript, tooltip="Execute the script")
     OWGUI.rubber(self.controlArea)
     
     
     self.connect(self.libraryWidget.addScriptAction, SIGNAL("triggered()"), self.onAddNewScript)
     self.connect(self.libraryWidget.updateScriptAction, SIGNAL("triggered()"), self.onUpdateScript)
     self.connect(self.libraryWidget.removeScriptAction, SIGNAL("triggered()"), self.onRemoveScript)
     self.connect(self.libraryWidget.addScriptFromFile, SIGNAL("triggered()"), self.onAddScriptFromFile)
     self.connect(self.libraryWidget.saveScriptToFile, SIGNAL("triggered()"), self.onSaveScriptToFile)
     
     self.connect(self.libraryView.selectionModel(), SIGNAL("selectionChanged(QItemSelection, QItemSelection)"), self.onScriptSelection)
     
     self._cachedDocuments = {}
     
     self.resize(800, 600)
     QTimer.singleShot(30, self.initGrDevice)
    def _setup_gui_values(self):
        self.values_edit = QListView()
        self.values_edit.setEditTriggers(QTreeView.CurrentChanged)
        self.values_model = PyListModel(flags=Qt.ItemIsSelectable | \
                                        Qt.ItemIsEnabled | Qt.ItemIsEditable)
        self.values_edit.setModel(self.values_model)

        self.values_model.dataChanged.connect(self.on_values_changed)
        self.main_form.addRow("Values", self.values_edit)
示例#5
0
    def __init__(self, parent=None, signalManager=None):
        OWWidget.__init__(self, parent, signalManager, 'Python Script')

        self.inputs = [
            ("in_data", Orange.data.Table, self.setExampleTable, Default),
            ("in_distance", Orange.misc.SymMatrix, self.setDistanceMatrix,
             Default),
            ("in_learner", Orange.core.Learner, self.setLearner, Default),
            ("in_classifier", Orange.core.Classifier, self.setClassifier,
             Default), ("in_object", object, self.setObject)
        ]

        self.outputs = [("out_data", Orange.data.Table),
                        ("out_distance", Orange.misc.SymMatrix),
                        ("out_learner", Orange.core.Learner),
                        ("out_classifier", Orange.core.Classifier, Dynamic),
                        ("out_object", object, Dynamic)]

        self.in_data = None
        self.in_distance = None
        self.in_learner = None
        self.in_classifier = None
        self.in_object = None
        self.auto_execute = False

        self.libraryListSource = [
            Script("Hello world", "print 'Hello world'\n")
        ]
        self.currentScriptIndex = 0
        self.splitterState = None
        self.loadSettings()

        for s in self.libraryListSource:
            s.flags = 0

        self._cachedDocuments = {}

        self.infoBox = OWGUI.widgetBox(self.controlArea, 'Info')
        OWGUI.label(
            self.infoBox, self,
            "<p>Execute python script.</p><p>Input variables:<ul><li> " +
            "<li>".join(t[0] for t in self.inputs) +
            "</ul></p><p>Output variables:<ul><li>" +
            "<li>".join(t[0] for t in self.outputs) + "</ul></p>")

        self.libraryList = PyListModel([],
                                       self,
                                       flags=Qt.ItemIsSelectable
                                       | Qt.ItemIsEnabled | Qt.ItemIsEditable)

        self.libraryList.wrap(self.libraryListSource)

        self.controlBox = OWGUI.widgetBox(self.controlArea, 'Library')
        self.controlBox.layout().setSpacing(1)

        self.libraryView = QListView(
            editTriggers=QListView.DoubleClicked | QListView.EditKeyPressed,
            sizePolicy=QSizePolicy(QSizePolicy.Ignored, QSizePolicy.Preferred))
        self.libraryView.setItemDelegate(ScriptItemDelegate(self))
        self.libraryView.setModel(self.libraryList)

        self.libraryView.selectionModel().selectionChanged.connect(
            self.onSelectedScriptChanged)
        self.controlBox.layout().addWidget(self.libraryView)

        w = ModelActionsWidget()

        self.addNewScriptAction = action = QAction("+", self)
        action.setToolTip("Add a new script to the library")
        action.triggered.connect(self.onAddScript)
        w.addAction(action)

        action = QAction(unicodedata.lookup("MINUS SIGN"), self)
        action.setToolTip("Remove script from library")
        action.triggered.connect(self.onRemoveScript)
        w.addAction(action)

        action = QAction("Update", self)
        action.setToolTip("Save changes in the editor to library")
        action.setShortcut(QKeySequence(QKeySequence.Save))
        action.triggered.connect(self.commitChangesToLibrary)
        w.addAction(action)

        action = QAction("More", self, toolTip="More actions")

        new_from_file = QAction("Import a script from a file", self)
        save_to_file = QAction("Save selected script to a file", self)
        save_to_file.setShortcut(QKeySequence(QKeySequence.SaveAs))

        new_from_file.triggered.connect(self.onAddScriptFromFile)
        save_to_file.triggered.connect(self.saveScript)

        menu = QMenu(w)
        menu.addAction(new_from_file)
        menu.addAction(save_to_file)
        action.setMenu(menu)
        button = w.addAction(action)
        button.setPopupMode(QToolButton.InstantPopup)

        w.layout().setSpacing(1)

        self.controlBox.layout().addWidget(w)

        self.runBox = OWGUI.widgetBox(self.controlArea, 'Run')
        OWGUI.button(self.runBox, self, "Execute", callback=self.execute)
        OWGUI.checkBox(self.runBox,
                       self,
                       "auto_execute",
                       "Auto execute",
                       tooltip=("Run the script automatically whenever "
                                "the inputs to the widget change."))

        self.splitter = QSplitter(Qt.Vertical, self.mainArea)
        self.mainArea.layout().addWidget(self.splitter)

        self.defaultFont = defaultFont = \
            "Monaco" if sys.platform == "darwin" else "Courier"

        self.textBox = OWGUI.widgetBox(self, 'Python script')
        self.splitter.addWidget(self.textBox)
        self.text = PythonScriptEditor(self)
        self.textBox.layout().addWidget(self.text)

        self.textBox.setAlignment(Qt.AlignVCenter)
        self.text.setTabStopWidth(4)

        self.text.modificationChanged[bool].connect(self.onModificationChanged)

        self.consoleBox = OWGUI.widgetBox(self, 'Console')
        self.splitter.addWidget(self.consoleBox)
        self.console = PythonConsole(self.__dict__, self)
        self.consoleBox.layout().addWidget(self.console)
        self.console.document().setDefaultFont(QFont(defaultFont))
        self.consoleBox.setAlignment(Qt.AlignBottom)
        self.console.setTabStopWidth(4)

        select_row(self.libraryView, self.currentScriptIndex)

        self.splitter.setSizes([2, 1])
        if self.splitterState is not None:
            self.splitter.restoreState(QByteArray(self.splitterState))

        self.splitter.splitterMoved[int, int].connect(self.onSpliterMoved)
        self.controlArea.layout().addStretch(1)
        self.resize(800, 600)
示例#6
0
class OWPythonScript(OWWidget):

    settingsList = [
        "libraryListSource", "currentScriptIndex", "splitterState",
        "auto_execute"
    ]

    def __init__(self, parent=None, signalManager=None):
        OWWidget.__init__(self, parent, signalManager, 'Python Script')

        self.inputs = [
            ("in_data", Orange.data.Table, self.setExampleTable, Default),
            ("in_distance", Orange.misc.SymMatrix, self.setDistanceMatrix,
             Default),
            ("in_learner", Orange.core.Learner, self.setLearner, Default),
            ("in_classifier", Orange.core.Classifier, self.setClassifier,
             Default), ("in_object", object, self.setObject)
        ]

        self.outputs = [("out_data", Orange.data.Table),
                        ("out_distance", Orange.misc.SymMatrix),
                        ("out_learner", Orange.core.Learner),
                        ("out_classifier", Orange.core.Classifier, Dynamic),
                        ("out_object", object, Dynamic)]

        self.in_data = None
        self.in_distance = None
        self.in_learner = None
        self.in_classifier = None
        self.in_object = None
        self.auto_execute = False

        self.libraryListSource = [
            Script("Hello world", "print 'Hello world'\n")
        ]
        self.currentScriptIndex = 0
        self.splitterState = None
        self.loadSettings()

        for s in self.libraryListSource:
            s.flags = 0

        self._cachedDocuments = {}

        self.infoBox = OWGUI.widgetBox(self.controlArea, 'Info')
        OWGUI.label(
            self.infoBox, self,
            "<p>Execute python script.</p><p>Input variables:<ul><li> " +
            "<li>".join(t[0] for t in self.inputs) +
            "</ul></p><p>Output variables:<ul><li>" +
            "<li>".join(t[0] for t in self.outputs) + "</ul></p>")

        self.libraryList = PyListModel([],
                                       self,
                                       flags=Qt.ItemIsSelectable
                                       | Qt.ItemIsEnabled | Qt.ItemIsEditable)

        self.libraryList.wrap(self.libraryListSource)

        self.controlBox = OWGUI.widgetBox(self.controlArea, 'Library')
        self.controlBox.layout().setSpacing(1)

        self.libraryView = QListView(
            editTriggers=QListView.DoubleClicked | QListView.EditKeyPressed,
            sizePolicy=QSizePolicy(QSizePolicy.Ignored, QSizePolicy.Preferred))
        self.libraryView.setItemDelegate(ScriptItemDelegate(self))
        self.libraryView.setModel(self.libraryList)

        self.libraryView.selectionModel().selectionChanged.connect(
            self.onSelectedScriptChanged)
        self.controlBox.layout().addWidget(self.libraryView)

        w = ModelActionsWidget()

        self.addNewScriptAction = action = QAction("+", self)
        action.setToolTip("Add a new script to the library")
        action.triggered.connect(self.onAddScript)
        w.addAction(action)

        action = QAction(unicodedata.lookup("MINUS SIGN"), self)
        action.setToolTip("Remove script from library")
        action.triggered.connect(self.onRemoveScript)
        w.addAction(action)

        action = QAction("Update", self)
        action.setToolTip("Save changes in the editor to library")
        action.setShortcut(QKeySequence(QKeySequence.Save))
        action.triggered.connect(self.commitChangesToLibrary)
        w.addAction(action)

        action = QAction("More", self, toolTip="More actions")

        new_from_file = QAction("Import a script from a file", self)
        save_to_file = QAction("Save selected script to a file", self)
        save_to_file.setShortcut(QKeySequence(QKeySequence.SaveAs))

        new_from_file.triggered.connect(self.onAddScriptFromFile)
        save_to_file.triggered.connect(self.saveScript)

        menu = QMenu(w)
        menu.addAction(new_from_file)
        menu.addAction(save_to_file)
        action.setMenu(menu)
        button = w.addAction(action)
        button.setPopupMode(QToolButton.InstantPopup)

        w.layout().setSpacing(1)

        self.controlBox.layout().addWidget(w)

        self.runBox = OWGUI.widgetBox(self.controlArea, 'Run')
        OWGUI.button(self.runBox, self, "Execute", callback=self.execute)
        OWGUI.checkBox(self.runBox,
                       self,
                       "auto_execute",
                       "Auto execute",
                       tooltip=("Run the script automatically whenever "
                                "the inputs to the widget change."))

        self.splitter = QSplitter(Qt.Vertical, self.mainArea)
        self.mainArea.layout().addWidget(self.splitter)

        self.defaultFont = defaultFont = \
            "Monaco" if sys.platform == "darwin" else "Courier"

        self.textBox = OWGUI.widgetBox(self, 'Python script')
        self.splitter.addWidget(self.textBox)
        self.text = PythonScriptEditor(self)
        self.textBox.layout().addWidget(self.text)

        self.textBox.setAlignment(Qt.AlignVCenter)
        self.text.setTabStopWidth(4)

        self.text.modificationChanged[bool].connect(self.onModificationChanged)

        self.consoleBox = OWGUI.widgetBox(self, 'Console')
        self.splitter.addWidget(self.consoleBox)
        self.console = PythonConsole(self.__dict__, self)
        self.consoleBox.layout().addWidget(self.console)
        self.console.document().setDefaultFont(QFont(defaultFont))
        self.consoleBox.setAlignment(Qt.AlignBottom)
        self.console.setTabStopWidth(4)

        select_row(self.libraryView, self.currentScriptIndex)

        self.splitter.setSizes([2, 1])
        if self.splitterState is not None:
            self.splitter.restoreState(QByteArray(self.splitterState))

        self.splitter.splitterMoved[int, int].connect(self.onSpliterMoved)
        self.controlArea.layout().addStretch(1)
        self.resize(800, 600)

    def setExampleTable(self, et):
        self.in_data = et

    def setDistanceMatrix(self, dm):
        self.in_distance = dm

    def setLearner(self, learner):
        self.in_learner = learner

    def setClassifier(self, classifier):
        self.in_classifier = classifier

    def setObject(self, obj):
        self.in_object = obj

    def handleNewSignals(self):
        if self.auto_execute:
            self.execute()

    def selectedScriptIndex(self):
        rows = self.libraryView.selectionModel().selectedRows()
        if rows:
            return [i.row() for i in rows][0]
        else:
            return None

    def setSelectedScript(self, index):
        select_row(self.libraryView, index)

    def onAddScript(self, *args):
        self.libraryList.append(Script("New script", "", 0))
        self.setSelectedScript(len(self.libraryList) - 1)

    def onAddScriptFromFile(self, *args):
        filename = QFileDialog.getOpenFileName(
            self, 'Open Python Script', os.path.expanduser("~/"),
            'Python files (*.py)\nAll files(*.*)')

        filename = unicode(filename)
        if filename:
            name = os.path.basename(filename)
            self.libraryList.append(
                Script(name,
                       open(filename, "rb").read(), 0, filename))
            self.setSelectedScript(len(self.libraryList) - 1)

    def onRemoveScript(self, *args):
        index = self.selectedScriptIndex()
        if index is not None:
            del self.libraryList[index]
            select_row(self.libraryView, max(index - 1, 0))

    def onSelectedScriptChanged(self, selected, deselected):
        index = [i.row() for i in selected.indexes()]
        if index:
            current = index[0]
            self.text.setDocument(self.documentForScript(current))
            self.currentScriptIndex = current

    def documentForScript(self, script=0):
        if type(script) != Script:
            script = self.libraryList[script]

        if script not in self._cachedDocuments:
            doc = QTextDocument(self)
            doc.setDocumentLayout(QPlainTextDocumentLayout(doc))
            doc.setPlainText(script.script)
            doc.setDefaultFont(QFont(self.defaultFont))
            doc.highlighter = PythonSyntaxHighlighter(doc)
            doc.modificationChanged[bool].connect(self.onModificationChanged)
            doc.setModified(False)
            self._cachedDocuments[script] = doc
        return self._cachedDocuments[script]

    def commitChangesToLibrary(self, *args):
        index = self.selectedScriptIndex()
        if index is not None:
            self.libraryList[index].script = unicode(self.text.toPlainText())
            self.text.document().setModified(False)
            self.libraryList.emitDataChanged(index)

    def onModificationChanged(self, modified):
        index = self.selectedScriptIndex()
        if index is not None:
            self.libraryList[index].flags = Script.Modified if modified else 0
            self.libraryList.emitDataChanged(index)

    def onSpliterMoved(self, pos, ind):
        self.splitterState = str(self.splitter.saveState())

    def saveScript(self):
        index = self.selectedScriptIndex()
        filename = os.path.expanduser("~/")
        if index is not None:
            script = self.libraryList[index]
            filename = script.sourceFileName or filename

        filename = QFileDialog.getSaveFileName(
            self, 'Save Python Script', filename,
            'Python files (*.py)\nAll files(*.*)')

        self.codeFile = unicode(filename)

        if self.codeFile:
            fn = ""
            head, tail = os.path.splitext(self.codeFile)
            if not tail:
                fn = head + ".py"
            else:
                fn = self.codeFile

            f = open(fn, 'w')
            f.write(self.text.toPlainText())
            f.close()

    def execute(self):
        self._script = str(self.text.toPlainText())
        self.console.write("\nRunning script:\n")
        self.console.push("exec(_script)")
        self.console.new_prompt(sys.ps1)
        for out in self.outputs:
            signal = out[0]
            self.send(signal, getattr(self, signal, None))
class DiscreteVariableEditor(VariableEditor):
    """An editor widget for editing a discrete variable.
    
    Extends the :class:`VariableEditor` to enable editing of
    variables values.
    
    """
    def setup_gui(self):
        layout = QVBoxLayout()
        self.setLayout(layout)
        
        self.main_form = QFormLayout()
        self.main_form.setFieldGrowthPolicy(QFormLayout.AllNonFixedFieldsGrow)
        layout.addLayout(self.main_form)
        
        self._setup_gui_name()
        self._setup_gui_values()
        self._setup_gui_labels()
        
    def _setup_gui_values(self):
        self.values_edit = QListView()
        self.values_edit.setEditTriggers(QListView.DoubleClicked | \
                                         QListView.EditKeyPressed)
        self.values_model = PyListModel(flags=Qt.ItemIsSelectable | \
                                        Qt.ItemIsEnabled | Qt.ItemIsEditable)
        self.values_edit.setModel(self.values_model)
        
        self.values_model.dataChanged.connect(self.on_values_changed)
        self.main_form.addRow("Values", self.values_edit)

    def set_data(self, var):
        """Set the variable to edit
        """
        VariableEditor.set_data(self, var)
        self.values_model.wrap([])
        if var is not None:
            for v in var.values:
                self.values_model.append(v)
                
    def get_data(self):
        """Retrieve the modified variable
        """
        name = str(self.name_edit.text())
        labels = self.labels_model.get_dict()
        values = map(str, self.values_model)
        
        if not self.is_same():
            var = type(self.var)(name, values=values)
            var.attributes.update(labels)
            self.var = var
        else:
            var = self.var
            
        return var
            
    def is_same(self):
        """Is the current model state the same as the input. 
        """
        values = map(str, self.values_model)
        return VariableEditor.is_same(self) and self.var.values == values
    
    def clear(self):
        """Clear the model state.
        """
        VariableEditor.clear(self)
        self.values_model.wrap([])
        
    @QtCore.Slot()
    def on_values_changed(self):
        self.maybe_commit()
    def __init__(self, parent=None, signalManager=None):
        OWWidget.__init__(self, parent, signalManager, 'MultiData Python Script')
        
        self.inputs = [("in_data", ExampleTable, self.setExampleTable, Default + Multiple),
                       ("in_distance", orange.SymMatrix, self.setDistanceMatrix),
                       ("in_network", Orange.network.Graph, self.setNetwork),
                       ("in_learners", orange.Learner, self.setLearner, Default + Multiple),
                       ("in_classifiers", orange.Classifier, self.setClassifier, Default + Multiple),
                       ("in_misc", object, self.setMisc, Default + Multiple)]
        self.outputs = [("out_data", ExampleTable), 
                        ("out_distance", orange.SymMatrix), 
                        ("out_network", Orange.network.Graph), 
                        ("out_learner", orange.Learner), 
                        ("out_classifier", orange.Classifier, Dynamic),
                        ("out_test_results", Orange.evaluation.testing.ExperimentResults),
                        ("out_misc", object)]
        
        self.in_data = []
        self.in_data_dict = {}   # TODO: switch to weakref?
        self.in_learners = []
        self.in_learner_dict = {}
        self.in_classifiers = []
        self.in_classifier_dict = {}
        self.in_misc = []
        self.in_misc_dict = {}

        self.in_network = None
        self.in_distance = None
        
        self.codeFile = ''
        self.libraryListSource = [Script("Hello world", "print 'Hello world'\n")]
        self.currentScriptIndex = 0
        self.splitterState = None
        self.loadSettings()
        
        for s in self.libraryListSource:
            s.flags = 0
        
        self._cachedDocuments = {}
        
        self.infoBox = OWGUI.widgetBox(self.controlArea, 'Info')
        label = OWGUI.label(self.infoBox, self, "<p>Execute python script.</p><p>Input variables:<ul><li> " + \
                    "<li>".join(t[0] for t in self.inputs) + "</ul></p><p>Output variables:<ul><li>" + \
                    "<li>".join(t[0] for t in self.outputs) + "</ul></p>")
        self.libraryList = PyListModel([], self, flags=Qt.ItemIsSelectable | Qt.ItemIsEnabled | Qt.ItemIsEditable)
#        self.libraryList.append(Script("Hello world", "print 'Hello world'\n"))
        self.libraryList.wrap(self.libraryListSource)
        
        self.controlBox = OWGUI.widgetBox(self.controlArea, 'Library')
        self.controlBox.layout().setSpacing(1)
        self.libraryView = QListView()
        self.libraryView.setEditTriggers(QListView.DoubleClicked | QListView.EditKeyPressed)
        self.libraryView.setSizePolicy(QSizePolicy.Ignored, QSizePolicy.Preferred)
        self.libraryView.setItemDelegate(ScriptItemDelegate(self))
        self.libraryView.setModel(self.libraryList)
        self.connect(self.libraryView.selectionModel(), SIGNAL("selectionChanged(QItemSelection, QItemSelection)"), self.onSelectedScriptChanged)
        self.controlBox.layout().addWidget(self.libraryView)
        w = ModelActionsWidget()
        
        self.addNewScriptAction = action = QAction("+", self)
        action.pyqtConfigure(toolTip="Add a new script to the library")
        self.connect(action, SIGNAL("triggered()"), self.onAddScript)
        new_empty = QAction("Add a new empty script", action)
        new_from_file = QAction("Add a new script from a file", action)
        self.connect(new_empty, SIGNAL("triggered()"), self.onAddScript)
        self.connect(new_from_file, SIGNAL("triggered()"), self.onAddScriptFromFile)
        menu = QMenu(w)
        menu.addAction(new_empty)
        menu.addAction(new_from_file)
        
#        action.setMenu(menu)
        button = w.addAction(action)
        
        self.removeAction = action = QAction("-", self)
        action.pyqtConfigure(toolTip="Remove script from library")
        self.connect(action, SIGNAL("triggered()"), self.onRemoveScript)
        w.addAction(action)
        
        action = QAction("Update", self)
        action.pyqtConfigure(toolTip="Save changes in the editor to library")
        action.setShortcut(QKeySequence(QKeySequence.Save))
        self.connect(action, SIGNAL("triggered()"), self.commitChangesToLibrary)
        b = w.addAction(action)
#        b.setSizePolicy(QSizePolicy.MinimumExpanding, QSizePolicy.Fixed)
        
        action = QAction("More", self)
        action.pyqtConfigure(toolTip="More actions") #, icon=self.style().standardIcon(QStyle.SP_ToolBarHorizontalExtensionButton))
        
        self.openScriptFromFileAction = new_from_file = QAction("Import a script from a file", self)
        self.saveScriptToFile = save_to_file = QAction("Save selected script to a file", self)
        save_to_file.setShortcut(QKeySequence(QKeySequence.SaveAs))
        
        self.connect(new_from_file, SIGNAL("triggered()"), self.onAddScriptFromFile)
        self.connect(save_to_file, SIGNAL("triggered()"), self.saveScript)
        
        menu = QMenu(w)
        menu.addAction(new_from_file)
        menu.addAction(save_to_file)
        action.setMenu(menu)
        b = w.addAction(action)
        b.setPopupMode(QToolButton.InstantPopup) 
        ## TODO: set the space for the indicator
        
        w.layout().setSpacing(1)
        
        self.controlBox.layout().addWidget(w)
                    
#        OWGUI.button(self.controlBox, self, "Open...", callback=self.openScript)
#        OWGUI.button(self.controlBox, self, "Save...", callback=self.saveScript)
        
        self.runBox = OWGUI.widgetBox(self.controlArea, 'Run')
        OWGUI.button(self.runBox, self, "Execute", callback=self.execute)
        
        self.splitCanvas = QSplitter(Qt.Vertical, self.mainArea)
        self.mainArea.layout().addWidget(self.splitCanvas)
        
        self.defaultFont = defaultFont = "Monaco" if sys.platform == "darwin" else "Courier"
        self.textBox = OWGUI.widgetBox(self, 'MultiData Python script')
        self.splitCanvas.addWidget(self.textBox)
        self.text = PythonScriptEditor(self)
        self.textBox.layout().addWidget(self.text)
        
        self.textBox.setAlignment(Qt.AlignVCenter)
        self.text.setTabStopWidth(4)
        
        self.connect(self.text, SIGNAL("modificationChanged(bool)"), self.onModificationChanged)
        
        self.saveAction = action = QAction("&Save", self.text)
        action.pyqtConfigure(toolTip="Save script to file")
        action.setShortcut(QKeySequence(QKeySequence.Save))
        action.setShortcutContext(Qt.WidgetWithChildrenShortcut)
        self.connect(action, SIGNAL("triggered()"), self.saveScript)
        
        self.consoleBox = OWGUI.widgetBox(self, 'Console')
        self.splitCanvas.addWidget(self.consoleBox)
        self.console = PythonConsole(self.__dict__, self)
        self.consoleBox.layout().addWidget(self.console)
        self.console.document().setDefaultFont(QFont(defaultFont))
        self.consoleBox.setAlignment(Qt.AlignBottom)
        self.console.setTabStopWidth(4)
        
        self.openScript(self.codeFile)
        try:
            self.libraryView.selectionModel().select(self.libraryList.index(self.currentScriptIndex), QItemSelectionModel.ClearAndSelect)
        except Exception:
            pass
        self.splitCanvas.setSizes([2, 1])
        if self.splitterState is not None:
            self.splitCanvas.restoreState(QByteArray(self.splitterState))
        
        self.connect(self.splitCanvas, SIGNAL("splitterMoved(int, int)"), lambda pos, ind: setattr(self, "splitterState", str(self.splitCanvas.saveState())))
        self.controlArea.layout().addStretch(1)
        self.resize(800,600)
class OWMultiDataPythonScript(OWWidget):
    
    settingsList = ["codeFile", "libraryListSource", "currentScriptIndex", "splitterState"]
                    
    def __init__(self, parent=None, signalManager=None):
        OWWidget.__init__(self, parent, signalManager, 'MultiData Python Script')
        
        self.inputs = [("in_data", ExampleTable, self.setExampleTable, Default + Multiple),
                       ("in_distance", orange.SymMatrix, self.setDistanceMatrix),
                       ("in_network", Orange.network.Graph, self.setNetwork),
                       ("in_learners", orange.Learner, self.setLearner, Default + Multiple),
                       ("in_classifiers", orange.Classifier, self.setClassifier, Default + Multiple),
                       ("in_misc", object, self.setMisc, Default + Multiple)]
        self.outputs = [("out_data", ExampleTable), 
                        ("out_distance", orange.SymMatrix), 
                        ("out_network", Orange.network.Graph), 
                        ("out_learner", orange.Learner), 
                        ("out_classifier", orange.Classifier, Dynamic),
                        ("out_test_results", Orange.evaluation.testing.ExperimentResults),
                        ("out_misc", object)]
        
        self.in_data = []
        self.in_data_dict = {}   # TODO: switch to weakref?
        self.in_learners = []
        self.in_learner_dict = {}
        self.in_classifiers = []
        self.in_classifier_dict = {}
        self.in_misc = []
        self.in_misc_dict = {}

        self.in_network = None
        self.in_distance = None
        
        self.codeFile = ''
        self.libraryListSource = [Script("Hello world", "print 'Hello world'\n")]
        self.currentScriptIndex = 0
        self.splitterState = None
        self.loadSettings()
        
        for s in self.libraryListSource:
            s.flags = 0
        
        self._cachedDocuments = {}
        
        self.infoBox = OWGUI.widgetBox(self.controlArea, 'Info')
        label = OWGUI.label(self.infoBox, self, "<p>Execute python script.</p><p>Input variables:<ul><li> " + \
                    "<li>".join(t[0] for t in self.inputs) + "</ul></p><p>Output variables:<ul><li>" + \
                    "<li>".join(t[0] for t in self.outputs) + "</ul></p>")
        self.libraryList = PyListModel([], self, flags=Qt.ItemIsSelectable | Qt.ItemIsEnabled | Qt.ItemIsEditable)
#        self.libraryList.append(Script("Hello world", "print 'Hello world'\n"))
        self.libraryList.wrap(self.libraryListSource)
        
        self.controlBox = OWGUI.widgetBox(self.controlArea, 'Library')
        self.controlBox.layout().setSpacing(1)
        self.libraryView = QListView()
        self.libraryView.setEditTriggers(QListView.DoubleClicked | QListView.EditKeyPressed)
        self.libraryView.setSizePolicy(QSizePolicy.Ignored, QSizePolicy.Preferred)
        self.libraryView.setItemDelegate(ScriptItemDelegate(self))
        self.libraryView.setModel(self.libraryList)
        self.connect(self.libraryView.selectionModel(), SIGNAL("selectionChanged(QItemSelection, QItemSelection)"), self.onSelectedScriptChanged)
        self.controlBox.layout().addWidget(self.libraryView)
        w = ModelActionsWidget()
        
        self.addNewScriptAction = action = QAction("+", self)
        action.pyqtConfigure(toolTip="Add a new script to the library")
        self.connect(action, SIGNAL("triggered()"), self.onAddScript)
        new_empty = QAction("Add a new empty script", action)
        new_from_file = QAction("Add a new script from a file", action)
        self.connect(new_empty, SIGNAL("triggered()"), self.onAddScript)
        self.connect(new_from_file, SIGNAL("triggered()"), self.onAddScriptFromFile)
        menu = QMenu(w)
        menu.addAction(new_empty)
        menu.addAction(new_from_file)
        
#        action.setMenu(menu)
        button = w.addAction(action)
        
        self.removeAction = action = QAction("-", self)
        action.pyqtConfigure(toolTip="Remove script from library")
        self.connect(action, SIGNAL("triggered()"), self.onRemoveScript)
        w.addAction(action)
        
        action = QAction("Update", self)
        action.pyqtConfigure(toolTip="Save changes in the editor to library")
        action.setShortcut(QKeySequence(QKeySequence.Save))
        self.connect(action, SIGNAL("triggered()"), self.commitChangesToLibrary)
        b = w.addAction(action)
#        b.setSizePolicy(QSizePolicy.MinimumExpanding, QSizePolicy.Fixed)
        
        action = QAction("More", self)
        action.pyqtConfigure(toolTip="More actions") #, icon=self.style().standardIcon(QStyle.SP_ToolBarHorizontalExtensionButton))
        
        self.openScriptFromFileAction = new_from_file = QAction("Import a script from a file", self)
        self.saveScriptToFile = save_to_file = QAction("Save selected script to a file", self)
        save_to_file.setShortcut(QKeySequence(QKeySequence.SaveAs))
        
        self.connect(new_from_file, SIGNAL("triggered()"), self.onAddScriptFromFile)
        self.connect(save_to_file, SIGNAL("triggered()"), self.saveScript)
        
        menu = QMenu(w)
        menu.addAction(new_from_file)
        menu.addAction(save_to_file)
        action.setMenu(menu)
        b = w.addAction(action)
        b.setPopupMode(QToolButton.InstantPopup) 
        ## TODO: set the space for the indicator
        
        w.layout().setSpacing(1)
        
        self.controlBox.layout().addWidget(w)
                    
#        OWGUI.button(self.controlBox, self, "Open...", callback=self.openScript)
#        OWGUI.button(self.controlBox, self, "Save...", callback=self.saveScript)
        
        self.runBox = OWGUI.widgetBox(self.controlArea, 'Run')
        OWGUI.button(self.runBox, self, "Execute", callback=self.execute)
        
        self.splitCanvas = QSplitter(Qt.Vertical, self.mainArea)
        self.mainArea.layout().addWidget(self.splitCanvas)
        
        self.defaultFont = defaultFont = "Monaco" if sys.platform == "darwin" else "Courier"
        self.textBox = OWGUI.widgetBox(self, 'MultiData Python script')
        self.splitCanvas.addWidget(self.textBox)
        self.text = PythonScriptEditor(self)
        self.textBox.layout().addWidget(self.text)
        
        self.textBox.setAlignment(Qt.AlignVCenter)
        self.text.setTabStopWidth(4)
        
        self.connect(self.text, SIGNAL("modificationChanged(bool)"), self.onModificationChanged)
        
        self.saveAction = action = QAction("&Save", self.text)
        action.pyqtConfigure(toolTip="Save script to file")
        action.setShortcut(QKeySequence(QKeySequence.Save))
        action.setShortcutContext(Qt.WidgetWithChildrenShortcut)
        self.connect(action, SIGNAL("triggered()"), self.saveScript)
        
        self.consoleBox = OWGUI.widgetBox(self, 'Console')
        self.splitCanvas.addWidget(self.consoleBox)
        self.console = PythonConsole(self.__dict__, self)
        self.consoleBox.layout().addWidget(self.console)
        self.console.document().setDefaultFont(QFont(defaultFont))
        self.consoleBox.setAlignment(Qt.AlignBottom)
        self.console.setTabStopWidth(4)
        
        self.openScript(self.codeFile)
        try:
            self.libraryView.selectionModel().select(self.libraryList.index(self.currentScriptIndex), QItemSelectionModel.ClearAndSelect)
        except Exception:
            pass
        self.splitCanvas.setSizes([2, 1])
        if self.splitterState is not None:
            self.splitCanvas.restoreState(QByteArray(self.splitterState))
        
        self.connect(self.splitCanvas, SIGNAL("splitterMoved(int, int)"), lambda pos, ind: setattr(self, "splitterState", str(self.splitCanvas.saveState())))
        self.controlArea.layout().addStretch(1)
        self.resize(800,600)

    def setDistanceMatrix(self, dm):
        self.in_distance = dm
        
    def setNetwork(self, net):
        self.in_network = net

    def setExampleTable(self, table, widget_tuple):
        # dictionary of id(input) to exampletable, if data is not None
        # if existing entry turns to None, remove.
        if table is None:
            self.in_data_dict.pop(widget_tuple, None)
        else:
            self.in_data_dict[widget_tuple] = table
        self.in_data = self.in_data_dict.values()
        
    def setLearner(self, learner, widget_tuple):
        # dictionary of id(input) to exampletable, if data is not None
        # if existing entry turns to None, remove.
        if learner is None:
            self.in_learner_dict.pop(widget_tuple, None)
        else:
            self.in_learner_dict[widget_tuple] = learner
        self.in_learners = self.in_learner_dict.values()
        
    def setClassifier(self, classifier, widget_tuple):
        # dictionary of id(input) to exampletable, if data is not None
        # if existing entry turns to None, remove.
        if classifier is None:
            self.in_classifier_dict.pop(widget_tuple, None)
        else:
            self.in_classifier_dict[widget_tuple] = classifier
        self.in_classifiers = self.in_classifier_dict.values()

    def setMisc(self, misc, widget_tuple):
        # dictionary of id(input) to exampletable, if data is not None
        # if existing entry turns to None, remove.
        if misc is None:
            self.in_misc_dict.pop(widget_tuple, None)
        else:
            self.in_misc_dict[widget_tuple] = misc
        self.in_misc = self.in_misc_dict.values()
        
    def selectedScriptIndex(self):
        rows = self.libraryView.selectionModel().selectedRows()
        if rows:
            return  [i.row() for i in rows][0]
        else:
            return None
        
    def setSelectedScript(self, index):
        selection = self.libraryView.selectionModel()
        selection.select(self.libraryList.index(index), QItemSelectionModel.ClearAndSelect)
        
    def onAddScript(self, *args):
        self.libraryList.append(Script("New script", "", 0))
        self.setSelectedScript(len(self.libraryList) - 1)
        
    def onAddScriptFromFile(self, *args):
        file = QFileDialog.getOpenFileName(self, 'Open Python Script', self.codeFile, 'Python files (*.py)\nAll files(*.*)')
        file = unicode(file)
        if file:
            name = os.path.basename(file)
            self.libraryList.append(Script(name, open(file, "rb").read(), 0, file))
            self.setSelectedScript(len(self.libraryList) - 1)
    
    def onRemoveScript(self, *args):
        index = self.selectedScriptIndex()
        if index is not None:
            del self.libraryList[index]
            self.libraryView.selectionModel().select(self.libraryList.index(max(index - 1, 0)), QItemSelectionModel.ClearAndSelect)
    
    def onSaveScriptToFile(self, *args):
        index = self.selectedScriptIndex()
        if index is not None:
            self.saveScript()
            
    def onSelectedScriptChanged(self, selected, deselected):
        index = [i.row() for i in selected.indexes()]
        if index:
            current = index[0] 
            if current >= len(self.libraryList):
                self.addNewScriptAction.trigger()
                return
            self.text.setDocument(self.documentForScript(current))
            self.currentScriptIndex = current
            
    def documentForScript(self, script=0):
        if type(script) != Script:
            script = self.libraryList[script]
        if script not in self._cachedDocuments:
            doc = QTextDocument(self)
            doc.setDocumentLayout(QPlainTextDocumentLayout(doc))
            doc.setPlainText(script.script)
            doc.setDefaultFont(QFont(self.defaultFont))
            doc.highlighter = PythonSyntaxHighlighter(doc)
            self.connect(doc, SIGNAL("modificationChanged(bool)"), self.onModificationChanged)
            doc.setModified(False)
            self._cachedDocuments[script] = doc
        return self._cachedDocuments[script]
    
    def commitChangesToLibrary(self, *args):
        index = self.selectedScriptIndex()
        if index is not None:
            self.libraryList[index].script = self.text.toPlainText()
            self.text.document().setModified(False)
            self.libraryList.emitDataChanged(index)
            
    def onModificationChanged(self, modified):
        index = self.selectedScriptIndex()
        if index is not None:
            self.libraryList[index].flags = Script.Modified if modified else 0
            self.libraryList.emitDataChanged(index)
        
    def updateSelecetdScriptState(self):
        index = self.selectedScriptIndex()
        if index is not None:
            script = self.libraryList[index]
            self.libraryList[index] = Script(script.name, self.text.toPlainText(), 0)
            
    def openScript(self, filename=None):
        if filename == None:
            filename = unicode(QFileDialog.getOpenFileName(self, 'Open Python Script',
                               self.codeFile, 'Python files (*.py)\nAll files(*.*)'))
            self.codeFile = filename
        else:
            self.codeFile = filename
            
        if self.codeFile == "":
            return
            
        self.error(0)
        try:
            f = open(self.codeFile, 'r')
        except (IOError, OSError), ex:
            self.text.setPlainText("")
            return
        
        self.text.setPlainText(f.read())
        f.close()
示例#10
0
class OWPythonScript(OWWidget):

    settingsList = [
        "codeFile", "libraryListSource", "currentScriptIndex", "splitterState"
    ]

    def __init__(self, parent=None, signalManager=None):
        OWWidget.__init__(self, parent, signalManager, 'Python Script')

        self.inputs = [
            ("in_data", ExampleTable, self.setExampleTable),
            ("in_distance", orange.SymMatrix, self.setDistanceMatrix),
            ("in_network", Orange.network.Graph, self.setNetwork),
            ("in_learner", orange.Learner, self.setLearner),
            ("in_classifier", orange.Classifier, self.setClassifier)
        ]
        self.outputs = [("out_data", ExampleTable),
                        ("out_distance", orange.SymMatrix),
                        ("out_network", Orange.network.Graph),
                        ("out_learner", orange.Learner),
                        ("out_classifier", orange.Classifier, Dynamic)]

        self.in_data = None
        self.in_network = None
        self.in_distance = None
        self.in_learner = None
        self.in_classifier = None

        self.codeFile = ''
        self.libraryListSource = [
            Script("Hello world", "print 'Hello world'\n")
        ]
        self.currentScriptIndex = 0
        self.splitterState = None
        self.loadSettings()

        for s in self.libraryListSource:
            s.flags = 0

        self._cachedDocuments = {}

        self.infoBox = OWGUI.widgetBox(self.controlArea, 'Info')
        label = OWGUI.label(self.infoBox, self, "<p>Execute python script.</p><p>Input variables:<ul><li> " + \
                    "<li>".join(t[0] for t in self.inputs) + "</ul></p><p>Output variables:<ul><li>" + \
                    "<li>".join(t[0] for t in self.outputs) + "</ul></p>")
        self.libraryList = PyListModel([],
                                       self,
                                       flags=Qt.ItemIsSelectable
                                       | Qt.ItemIsEnabled | Qt.ItemIsEditable)
        #        self.libraryList.append(Script("Hello world", "print 'Hello world'\n"))
        self.libraryList.wrap(self.libraryListSource)

        self.controlBox = OWGUI.widgetBox(self.controlArea, 'Library')
        self.controlBox.layout().setSpacing(1)
        self.libraryView = QListView()
        self.libraryView.pyqtConfigure(editTriggers=QListView.DoubleClicked
                                       | QListView.SelectedClicked)
        self.libraryView.setSizePolicy(QSizePolicy.Ignored,
                                       QSizePolicy.Preferred)
        self.libraryView.setItemDelegate(ScriptItemDelegate(self))
        self.libraryView.setModel(self.libraryList)
        self.connect(
            self.libraryView.selectionModel(),
            SIGNAL("selectionChanged(QItemSelection, QItemSelection)"),
            self.onSelectedScriptChanged)
        self.controlBox.layout().addWidget(self.libraryView)
        w = ModelActionsWidget()

        self.addNewScriptAction = action = QAction("+", self)
        action.pyqtConfigure(toolTip="Add a new script to the library")
        self.connect(action, SIGNAL("triggered()"), self.onAddScript)
        new_empty = QAction("Add a new empty script", action)
        new_from_file = QAction("Add a new script from a file", action)
        self.connect(new_empty, SIGNAL("triggered()"), self.onAddScript)
        self.connect(new_from_file, SIGNAL("triggered()"),
                     self.onAddScriptFromFile)
        menu = QMenu(w)
        menu.addAction(new_empty)
        menu.addAction(new_from_file)

        #        action.setMenu(menu)
        button = w.addAction(action)

        self.removeAction = action = QAction("-", self)
        action.pyqtConfigure(toolTip="Remove script from library")
        self.connect(action, SIGNAL("triggered()"), self.onRemoveScript)
        w.addAction(action)

        action = QAction("Update", self)
        action.pyqtConfigure(toolTip="Save changes in the editor to library")
        action.setShortcut(QKeySequence(QKeySequence.Save))
        self.connect(action, SIGNAL("triggered()"),
                     self.commitChangesToLibrary)
        b = w.addAction(action)
        #        b.setSizePolicy(QSizePolicy.MinimumExpanding, QSizePolicy.Fixed)

        action = QAction("More", self)
        action.pyqtConfigure(
            toolTip="More actions"
        )  #, icon=self.style().standardIcon(QStyle.SP_ToolBarHorizontalExtensionButton))

        self.openScriptFromFileAction = new_from_file = QAction(
            "Import a script from a file", self)
        self.saveScriptToFile = save_to_file = QAction(
            "Save selected script to a file", self)
        save_to_file.setShortcut(QKeySequence(QKeySequence.SaveAs))

        self.connect(new_from_file, SIGNAL("triggered()"),
                     self.onAddScriptFromFile)
        self.connect(save_to_file, SIGNAL("triggered()"), self.saveScript)

        menu = QMenu(w)
        menu.addAction(new_from_file)
        menu.addAction(save_to_file)
        action.setMenu(menu)
        b = w.addAction(action)
        b.setPopupMode(QToolButton.InstantPopup)
        ## TODO: set the space for the indicator

        w.layout().setSpacing(1)

        self.controlBox.layout().addWidget(w)

        #        OWGUI.button(self.controlBox, self, "Open...", callback=self.openScript)
        #        OWGUI.button(self.controlBox, self, "Save...", callback=self.saveScript)

        self.runBox = OWGUI.widgetBox(self.controlArea, 'Run')
        OWGUI.button(self.runBox, self, "Execute", callback=self.execute)

        self.splitCanvas = QSplitter(Qt.Vertical, self.mainArea)
        self.mainArea.layout().addWidget(self.splitCanvas)

        self.defaultFont = defaultFont = "Monaco" if sys.platform == "darwin" else "Courier"
        self.textBox = OWGUI.widgetBox(self, 'Python script')
        self.splitCanvas.addWidget(self.textBox)
        self.text = PythonScriptEditor(self)
        self.textBox.layout().addWidget(self.text)

        self.textBox.setAlignment(Qt.AlignVCenter)
        self.text.setTabStopWidth(4)

        self.connect(self.text, SIGNAL("modificationChanged(bool)"),
                     self.onModificationChanged)

        self.saveAction = action = QAction("&Save", self.text)
        action.pyqtConfigure(toolTip="Save script to file")
        action.setShortcut(QKeySequence(QKeySequence.Save))
        action.setShortcutContext(Qt.WidgetWithChildrenShortcut)
        self.connect(action, SIGNAL("triggered()"), self.saveScript)

        self.consoleBox = OWGUI.widgetBox(self, 'Console')
        self.splitCanvas.addWidget(self.consoleBox)
        self.console = PythonConsole(self.__dict__, self)
        self.consoleBox.layout().addWidget(self.console)
        self.console.document().setDefaultFont(QFont(defaultFont))
        self.consoleBox.setAlignment(Qt.AlignBottom)
        self.console.setTabStopWidth(4)

        self.openScript(self.codeFile)
        try:
            self.libraryView.selectionModel().select(
                self.libraryList.index(self.currentScriptIndex),
                QItemSelectionModel.ClearAndSelect)
        except Exception:
            pass
        self.splitCanvas.setSizes([2, 1])
        if self.splitterState is not None:
            self.splitCanvas.restoreState(QByteArray(self.splitterState))

        self.connect(
            self.splitCanvas, SIGNAL("splitterMoved(int, int)"),
            lambda pos, ind: setattr(self, "splitterState",
                                     str(self.splitCanvas.saveState())))
        self.controlArea.layout().addStretch(1)
        self.resize(800, 600)

    def setExampleTable(self, et):
        self.in_data = et

    def setDistanceMatrix(self, dm):
        self.in_distance = dm

    def setNetwork(self, net):
        self.in_network = net

    def setLearner(self, learner):
        self.in_learner = learner

    def setClassifier(self, classifier):
        self.in_classifier = classifier

    def selectedScriptIndex(self):
        rows = self.libraryView.selectionModel().selectedRows()
        if rows:
            return [i.row() for i in rows][0]
        else:
            return None

    def setSelectedScript(self, index):
        selection = self.libraryView.selectionModel()
        selection.select(self.libraryList.index(index),
                         QItemSelectionModel.ClearAndSelect)

    def onAddScript(self, *args):
        self.libraryList.append(Script("New script", "", 0))
        self.setSelectedScript(len(self.libraryList) - 1)

    def onAddScriptFromFile(self, *args):
        file = QFileDialog.getOpenFileName(
            self, 'Open Python Script', self.codeFile,
            'Python files (*.py)\nAll files(*.*)')
        if file:
            file = str(file)
            name = os.path.basename(file)
            self.libraryList.append(
                Script(name,
                       open(file, "rb").read(), 0, file))
            self.setSelectedScript(len(self.libraryList) - 1)

    def onRemoveScript(self, *args):
        index = self.selectedScriptIndex()
        if index is not None:
            del self.libraryList[index]
            self.libraryView.selectionModel().select(
                self.libraryList.index(max(index - 1, 0)),
                QItemSelectionModel.ClearAndSelect)

    def onSaveScriptToFile(self, *args):
        index = self.selectedScriptIndex()
        if index is not None:
            self.saveScript()

    def onSelectedScriptChanged(self, selected, deselected):
        index = [i.row() for i in selected.indexes()]
        if index:
            current = index[0]
            if current >= len(self.libraryList):
                self.addNewScriptAction.trigger()
                return
            self.text.setDocument(self.documentForScript(current))
            self.currentScriptIndex = current

    def documentForScript(self, script=0):
        if type(script) != Script:
            script = self.libraryList[script]
        if script not in self._cachedDocuments:
            doc = QTextDocument(self)
            doc.setDocumentLayout(QPlainTextDocumentLayout(doc))
            doc.setPlainText(script.script)
            doc.setDefaultFont(QFont(self.defaultFont))
            doc.highlighter = PythonSyntaxHighlighter(doc)
            self.connect(doc, SIGNAL("modificationChanged(bool)"),
                         self.onModificationChanged)
            doc.setModified(False)
            self._cachedDocuments[script] = doc
        return self._cachedDocuments[script]

    def commitChangesToLibrary(self, *args):
        index = self.selectedScriptIndex()
        if index is not None:
            self.libraryList[index].script = self.text.toPlainText()
            self.text.document().setModified(False)
            self.libraryList.emitDataChanged(index)

    def onModificationChanged(self, modified):
        index = self.selectedScriptIndex()
        if index is not None:
            self.libraryList[index].flags = Script.Modified if modified else 0
            self.libraryList.emitDataChanged(index)

    def updateSelecetdScriptState(self):
        index = self.selectedScriptIndex()
        if index is not None:
            script = self.libraryList[index]
            self.libraryList[index] = Script(script.name,
                                             self.text.toPlainText(), 0)

    def openScript(self, filename=None):
        if filename == None:
            self.codeFile = str(
                QFileDialog.getOpenFileName(
                    self, 'Open Python Script', self.codeFile,
                    'Python files (*.py)\nAll files(*.*)'))
        else:
            self.codeFile = filename

        if self.codeFile == "":
            return

        self.error(0)
        try:
            f = open(self.codeFile, 'r')
        except (IOError, OSError), ex:
            self.text.setPlainText("")
            return

        self.text.setPlainText(f.read())
        f.close()
示例#11
0
 def __init__(self, var, parent=None, **kwargs):
     PyListModel.__init__(self, [], parent, **kwargs)
     self.wrap(var.values)
     self.colorPalette = OWColorPalette.ColorPaletteHSV(len(self))
示例#12
0
 def data(self, index, role=Qt.DisplayRole):
     if role == Qt.DecorationRole:
         i = index.row()
         return QVariant(self.itemQIcon(i))
     else:
         return PyListModel.data(self, index, role)
示例#13
0
class DiscreteVariableEditor(VariableEditor):
    """An editor widget for editing a discrete variable.

    Extends the :class:`VariableEditor` to enable editing of
    variables values.

    """
    def setup_gui(self):
        layout = QVBoxLayout()
        self.setLayout(layout)

        self.main_form = QFormLayout()
        self.main_form.setFieldGrowthPolicy(QFormLayout.AllNonFixedFieldsGrow)
        layout.addLayout(self.main_form)

        self._setup_gui_name()
        self._setup_gui_values()
        self._setup_gui_labels()

    def _setup_gui_values(self):
        self.values_edit = QListView()
        self.values_edit.setEditTriggers(QTreeView.CurrentChanged)
        self.values_model = PyListModel(flags=Qt.ItemIsSelectable | \
                                        Qt.ItemIsEnabled | Qt.ItemIsEditable)
        self.values_edit.setModel(self.values_model)

        self.values_model.dataChanged.connect(self.on_values_changed)
        self.main_form.addRow("Values", self.values_edit)

    def set_data(self, var):
        """Set the variable to edit
        """
        VariableEditor.set_data(self, var)
        self.values_model.wrap([])
        if var is not None:
            for v in var.values:
                self.values_model.append(v)

    def get_data(self):
        """Retrieve the modified variable
        """
        name = str(self.name_edit.text())
        labels = self.labels_model.get_dict()
        values = map(str, self.values_model)

        if not self.is_same():
            var = type(self.var)(name, values=values)
            var.attributes.update(labels)
            self.var = var
        else:
            var = self.var

        return var

    def is_same(self):
        """Is the current model state the same as the input.
        """
        values = map(str, self.values_model)
        return VariableEditor.is_same(self) and self.var.values == values

    def clear(self):
        """Clear the model state.
        """
        VariableEditor.clear(self)
        self.values_model.wrap([])

    @QtCore.Slot()
    def on_values_changed(self):
        self.maybe_commit()
示例#14
0
    def __init__(self, parent=None, signalManager=None, name="Preprocess"):
        OWWidget.__init__(self, parent, signalManager, name)

        self.inputs = [("Example Table", ExampleTable, self.setData)
                       ]  #, ("Learner", orange.Learner, self.setLearner)]
        self.outputs = [("Preprocess", orngWrap.PreprocessedLearner),
                        ("Preprocessed Example Table", ExampleTable)
                        ]  #, ("Preprocessor", orange.Preprocessor)]

        self.autoCommit = False
        self.changedFlag = False

        #        self.allSchemas = [PreprocessorSchema("Default" , [Preprocessor_discretize(method=orange.EntropyDiscretization()), Preprocessor_dropMissing()])]
        self.allSchemas = [("Default", [
            Preprocessor_discretizeEntropy(
                method=orange.EntropyDiscretization()),
            Preprocessor_dropMissing()
        ], 0)]

        self.lastSelectedSchemaIndex = 0

        self.preprocessorsList = PyListModel([], self)

        box = OWGUI.widgetBox(self.controlArea, "Preprocessors", addSpace=True)
        box.layout().setSpacing(1)

        self.setStyleSheet("QListView::item { margin: 1px;}")
        self.preprocessorsListView = QListView()
        self.preprocessorsListSelectionModel = ListSingleSelectionModel(
            self.preprocessorsList, self)
        self.preprocessorsListView.setItemDelegate(
            PreprocessorItemDelegate(self))
        self.preprocessorsListView.setModel(self.preprocessorsList)

        self.preprocessorsListView.setSelectionModel(
            self.preprocessorsListSelectionModel)
        self.preprocessorsListView.setSelectionMode(QListView.SingleSelection)

        self.connect(self.preprocessorsListSelectionModel,
                     SIGNAL("selectedIndexChanged(QModelIndex)"),
                     self.onPreprocessorSelection)
        self.connect(self.preprocessorsList,
                     SIGNAL("dataChanged(QModelIndex, QModelIndex)"),
                     lambda arg1, arg2: self.commitIf)

        box.layout().addWidget(self.preprocessorsListView)

        self.addPreprocessorAction = QAction("+", self)
        self.addPreprocessorAction.pyqtConfigure(
            toolTip="Add a new preprocessor to the list")
        self.removePreprocessorAction = QAction("-", self)
        self.removePreprocessorAction.pyqtConfigure(
            toolTip="Remove selected preprocessor from the list")
        self.removePreprocessorAction.setEnabled(False)

        self.connect(
            self.preprocessorsListSelectionModel,
            SIGNAL("selectedIndexChanged(QModelIndex)"), lambda index: self.
            removePreprocessorAction.setEnabled(index.isValid()))

        actionsWidget = ModelActionsWidget(
            [self.addPreprocessorAction, self.removePreprocessorAction])
        actionsWidget.layout().setSpacing(1)
        actionsWidget.layout().addStretch(10)

        box.layout().addWidget(actionsWidget)

        self.connect(self.addPreprocessorAction, SIGNAL("triggered()"),
                     self.onAddPreprocessor)
        self.connect(self.removePreprocessorAction, SIGNAL("triggered()"),
                     self.onRemovePreprocessor)

        box = OWGUI.widgetBox(self.controlArea, "Saved Schemas", addSpace=True)

        self.schemaFilterEdit = OWGUIEx.LineEditFilter(self)
        box.layout().addWidget(self.schemaFilterEdit)

        self.schemaList = PyListModel([],
                                      self,
                                      flags=Qt.ItemIsSelectable
                                      | Qt.ItemIsEditable | Qt.ItemIsEnabled)
        self.schemaListProxy = PySortFilterProxyModel(filter_fmt="{0.name}",
                                                      parent=self)
        self.schemaListProxy.setFilterCaseSensitivity(Qt.CaseInsensitive)
        self.schemaListProxy.setSourceModel(self.schemaList)
        self.schemaListView = QListView()
        self.schemaListView.setItemDelegate(PreprocessorSchemaDelegate(self))
        #        self.schemaListView.setModel(self.schemaList)
        self.schemaListView.setModel(self.schemaListProxy)
        self.connect(self.schemaFilterEdit, SIGNAL("textEdited(QString)"),
                     self.schemaListProxy.setFilterRegExp)
        box.layout().addWidget(self.schemaListView)

        self.schemaListSelectionModel = ListSingleSelectionModel(
            self.schemaListProxy, self)
        self.schemaListView.setSelectionMode(QListView.SingleSelection)
        self.schemaListView.setSelectionModel(self.schemaListSelectionModel)

        self.connect(self.schemaListSelectionModel,
                     SIGNAL("selectedIndexChanged(QModelIndex)"),
                     self.onSchemaSelection)

        self.addSchemaAction = QAction("+", self)
        self.addSchemaAction.pyqtConfigure(
            toolTip="Add a new preprocessor schema")
        self.updateSchemaAction = QAction("Update", self)
        self.updateSchemaAction.pyqtConfigure(
            toolTip="Save changes made in the current schema")
        self.removeSchemaAction = QAction("-", self)
        self.removeSchemaAction.pyqtConfigure(toolTip="Remove selected schema")

        self.updateSchemaAction.setEnabled(False)
        self.removeSchemaAction.setEnabled(False)

        actionsWidget = ModelActionsWidget([])
        actionsWidget.addAction(self.addSchemaAction)
        actionsWidget.addAction(self.updateSchemaAction).setSizePolicy(
            QSizePolicy.MinimumExpanding, QSizePolicy.Fixed)
        actionsWidget.addAction(self.removeSchemaAction)
        actionsWidget.layout().setSpacing(1)

        box.layout().addWidget(actionsWidget)

        self.connect(self.addSchemaAction, SIGNAL("triggered()"),
                     self.onAddSchema)
        self.connect(self.updateSchemaAction, SIGNAL("triggered()"),
                     self.onUpdateSchema)
        self.connect(self.removeSchemaAction, SIGNAL("triggered()"),
                     self.onRemoveSchema)

        self.addPreprocessorsMenuActions = actions = []
        for name, pp, kwargs in self.preprocessors:
            action = QAction(name, self)
            self.connect(action,
                         SIGNAL("triggered()"),
                         lambda pp=pp, kwargs=kwargs: self.addPreprocessor(
                             pp(**kwargs)))
            actions.append(action)

        box = OWGUI.widgetBox(self.controlArea, "Output")
        cb = OWGUI.checkBox(box,
                            self,
                            "autoCommit",
                            "Commit on any change",
                            callback=self.commitIf)
        b = OWGUI.button(box, self, "Commit", callback=self.commit)
        OWGUI.setStopper(self, b, cb, "changedFlag", callback=self.commitIf)

        self.mainAreaStack = QStackedLayout()
        self.stackedEditorsCache = {}

        OWGUI.widgetBox(self.mainArea, orientation=self.mainAreaStack)

        self.data = None
        self.learner = None

        self.loadSettings()
        self.activateLoadedSettings()
示例#15
0
class OWPreprocess(OWWidget):
    contextHandlers = {"": PerfectDomainContextHandler("", [""])}
    settingsList = ["allSchemas", "lastSelectedSchemaIndex"]

    # Default preprocessors
    preprocessors = [("Discretize", Preprocessor_discretizeEntropy, {}),
                     ("Continuize", Preprocessor_continuize, {}),
                     ("Impute", Preprocessor_impute, {}),
                     ("Feature selection", Preprocessor_featureSelection, {}),
                     ("Sample", Preprocessor_sample, {})]

    # Editor widgets for preprocessors
    EDITORS = {
        Preprocessor_discretize: DiscretizeEditor,
        Preprocessor_discretizeEntropy: DiscretizeEditor,
        Preprocessor_removeContinuous: DiscretizeEditor,
        Preprocessor_continuize: ContinuizeEditor,
        Preprocessor_removeDiscrete: ContinuizeEditor,
        Preprocessor_impute: ImputeEditor,
        Preprocessor_imputeByLearner: ImputeEditor,
        Preprocessor_dropMissing: ImputeEditor,
        Preprocessor_featureSelection: FeatureSelectEditor,
        Preprocessor_sample: SampleEditor,
        type(None): QWidget
    }

    def __init__(self, parent=None, signalManager=None, name="Preprocess"):
        OWWidget.__init__(self, parent, signalManager, name)

        self.inputs = [("Example Table", ExampleTable, self.setData)
                       ]  #, ("Learner", orange.Learner, self.setLearner)]
        self.outputs = [("Preprocess", orngWrap.PreprocessedLearner),
                        ("Preprocessed Example Table", ExampleTable)
                        ]  #, ("Preprocessor", orange.Preprocessor)]

        self.autoCommit = False
        self.changedFlag = False

        #        self.allSchemas = [PreprocessorSchema("Default" , [Preprocessor_discretize(method=orange.EntropyDiscretization()), Preprocessor_dropMissing()])]
        self.allSchemas = [("Default", [
            Preprocessor_discretizeEntropy(
                method=orange.EntropyDiscretization()),
            Preprocessor_dropMissing()
        ], 0)]

        self.lastSelectedSchemaIndex = 0

        self.preprocessorsList = PyListModel([], self)

        box = OWGUI.widgetBox(self.controlArea, "Preprocessors", addSpace=True)
        box.layout().setSpacing(1)

        self.setStyleSheet("QListView::item { margin: 1px;}")
        self.preprocessorsListView = QListView()
        self.preprocessorsListSelectionModel = ListSingleSelectionModel(
            self.preprocessorsList, self)
        self.preprocessorsListView.setItemDelegate(
            PreprocessorItemDelegate(self))
        self.preprocessorsListView.setModel(self.preprocessorsList)

        self.preprocessorsListView.setSelectionModel(
            self.preprocessorsListSelectionModel)
        self.preprocessorsListView.setSelectionMode(QListView.SingleSelection)

        self.connect(self.preprocessorsListSelectionModel,
                     SIGNAL("selectedIndexChanged(QModelIndex)"),
                     self.onPreprocessorSelection)
        self.connect(self.preprocessorsList,
                     SIGNAL("dataChanged(QModelIndex, QModelIndex)"),
                     lambda arg1, arg2: self.commitIf)

        box.layout().addWidget(self.preprocessorsListView)

        self.addPreprocessorAction = QAction("+", self)
        self.addPreprocessorAction.pyqtConfigure(
            toolTip="Add a new preprocessor to the list")
        self.removePreprocessorAction = QAction("-", self)
        self.removePreprocessorAction.pyqtConfigure(
            toolTip="Remove selected preprocessor from the list")
        self.removePreprocessorAction.setEnabled(False)

        self.connect(
            self.preprocessorsListSelectionModel,
            SIGNAL("selectedIndexChanged(QModelIndex)"), lambda index: self.
            removePreprocessorAction.setEnabled(index.isValid()))

        actionsWidget = ModelActionsWidget(
            [self.addPreprocessorAction, self.removePreprocessorAction])
        actionsWidget.layout().setSpacing(1)
        actionsWidget.layout().addStretch(10)

        box.layout().addWidget(actionsWidget)

        self.connect(self.addPreprocessorAction, SIGNAL("triggered()"),
                     self.onAddPreprocessor)
        self.connect(self.removePreprocessorAction, SIGNAL("triggered()"),
                     self.onRemovePreprocessor)

        box = OWGUI.widgetBox(self.controlArea, "Saved Schemas", addSpace=True)

        self.schemaFilterEdit = OWGUIEx.LineEditFilter(self)
        box.layout().addWidget(self.schemaFilterEdit)

        self.schemaList = PyListModel([],
                                      self,
                                      flags=Qt.ItemIsSelectable
                                      | Qt.ItemIsEditable | Qt.ItemIsEnabled)
        self.schemaListProxy = PySortFilterProxyModel(filter_fmt="{0.name}",
                                                      parent=self)
        self.schemaListProxy.setFilterCaseSensitivity(Qt.CaseInsensitive)
        self.schemaListProxy.setSourceModel(self.schemaList)
        self.schemaListView = QListView()
        self.schemaListView.setItemDelegate(PreprocessorSchemaDelegate(self))
        #        self.schemaListView.setModel(self.schemaList)
        self.schemaListView.setModel(self.schemaListProxy)
        self.connect(self.schemaFilterEdit, SIGNAL("textEdited(QString)"),
                     self.schemaListProxy.setFilterRegExp)
        box.layout().addWidget(self.schemaListView)

        self.schemaListSelectionModel = ListSingleSelectionModel(
            self.schemaListProxy, self)
        self.schemaListView.setSelectionMode(QListView.SingleSelection)
        self.schemaListView.setSelectionModel(self.schemaListSelectionModel)

        self.connect(self.schemaListSelectionModel,
                     SIGNAL("selectedIndexChanged(QModelIndex)"),
                     self.onSchemaSelection)

        self.addSchemaAction = QAction("+", self)
        self.addSchemaAction.pyqtConfigure(
            toolTip="Add a new preprocessor schema")
        self.updateSchemaAction = QAction("Update", self)
        self.updateSchemaAction.pyqtConfigure(
            toolTip="Save changes made in the current schema")
        self.removeSchemaAction = QAction("-", self)
        self.removeSchemaAction.pyqtConfigure(toolTip="Remove selected schema")

        self.updateSchemaAction.setEnabled(False)
        self.removeSchemaAction.setEnabled(False)

        actionsWidget = ModelActionsWidget([])
        actionsWidget.addAction(self.addSchemaAction)
        actionsWidget.addAction(self.updateSchemaAction).setSizePolicy(
            QSizePolicy.MinimumExpanding, QSizePolicy.Fixed)
        actionsWidget.addAction(self.removeSchemaAction)
        actionsWidget.layout().setSpacing(1)

        box.layout().addWidget(actionsWidget)

        self.connect(self.addSchemaAction, SIGNAL("triggered()"),
                     self.onAddSchema)
        self.connect(self.updateSchemaAction, SIGNAL("triggered()"),
                     self.onUpdateSchema)
        self.connect(self.removeSchemaAction, SIGNAL("triggered()"),
                     self.onRemoveSchema)

        self.addPreprocessorsMenuActions = actions = []
        for name, pp, kwargs in self.preprocessors:
            action = QAction(name, self)
            self.connect(action,
                         SIGNAL("triggered()"),
                         lambda pp=pp, kwargs=kwargs: self.addPreprocessor(
                             pp(**kwargs)))
            actions.append(action)

        box = OWGUI.widgetBox(self.controlArea, "Output")
        cb = OWGUI.checkBox(box,
                            self,
                            "autoCommit",
                            "Commit on any change",
                            callback=self.commitIf)
        b = OWGUI.button(box, self, "Commit", callback=self.commit)
        OWGUI.setStopper(self, b, cb, "changedFlag", callback=self.commitIf)

        self.mainAreaStack = QStackedLayout()
        self.stackedEditorsCache = {}

        OWGUI.widgetBox(self.mainArea, orientation=self.mainAreaStack)

        self.data = None
        self.learner = None

        self.loadSettings()
        self.activateLoadedSettings()

    def activateLoadedSettings(self):
        try:
            self.allSchemas = [
                PreprocessorSchemaDelegate.asSchema(obj)
                for obj in self.allSchemas
            ]
            for s in self.allSchemas:
                s.modified = False
            self.schemaList.wrap(self.allSchemas)
            self.schemaListSelectionModel.select(
                self.schemaList.index(
                    min(self.lastSelectedSchemaIndex,
                        len(self.schemaList) - 1)),
                QItemSelectionModel.ClearAndSelect)
            self.commit()
        except Exception as ex:
            print(repr(ex))

    def setData(self, data=None):
        self.data = data
#        self.commit()

    def setLearner(self, learner=None):
        self.learner = learner
#        self.commit()

    def handleNewSignals(self):
        self.commit()

    def selectedSchemaIndex(self):
        rows = self.schemaListSelectionModel.selectedRows()
        rows = [self.schemaListProxy.mapToSource(row) for row in rows]
        if rows:
            return rows[0]
        else:
            return QModelIndex()

    def addPreprocessor(self, prep):
        self.preprocessorsList.append(prep)
        self.preprocessorsListSelectionModel.select(
            self.preprocessorsList.index(len(self.preprocessorsList) - 1),
            QItemSelectionModel.ClearAndSelect)
        self.commitIf()
        self.setSchemaModified(True)

    def onAddPreprocessor(self):
        action = QMenu.exec_(self.addPreprocessorsMenuActions, QCursor.pos())

    def onRemovePreprocessor(self):
        index = self.preprocessorsListSelectionModel.selectedRow()
        if index.isValid():
            row = index.row()
            del self.preprocessorsList[row]
            newrow = min(max(row - 1, 0), len(self.preprocessorsList) - 1)
            if newrow > -1:
                self.preprocessorsListSelectionModel.select(
                    self.preprocessorsList.index(newrow),
                    QItemSelectionModel.ClearAndSelect)
            self.commitIf()
            self.setSchemaModified(True)

    def onPreprocessorSelection(self, index):
        if index.isValid():
            pp = self.preprocessorsList[index.row()]
            self.currentSelectedIndex = index.row()
            self.showEditWidget(pp)
        else:
            self.showEditWidget(None)

    def onSchemaSelection(self, index):
        self.updateSchemaAction.setEnabled(index.isValid())
        self.removeSchemaAction.setEnabled(index.isValid())
        if index.isValid():
            self.lastSelectedSchemaIndex = index.row()
            self.setActiveSchema(index.data().toPyObject())

    def onAddSchema(self):
        schema = list(self.preprocessorsList)
        self.schemaList.append(
            PreprocessorSchema(
                "New schema", schema,
                self.preprocessorsListSelectionModel.selectedRow().row()))
        index = self.schemaList.index(len(self.schemaList) - 1)
        index = self.schemaListProxy.mapFromSource(index)
        self.schemaListSelectionModel.setCurrentIndex(
            index, QItemSelectionModel.ClearAndSelect)
        self.schemaListView.edit(index)

    def onUpdateSchema(self):
        #        index = self.schemaListSelectionModel.selectedRow()
        index = self.selectedSchemaIndex()
        if index.isValid():
            row = index.row()
            schema = self.schemaList[row]
            self.schemaList[row] = PreprocessorSchema(
                schema.name, list(self.preprocessorsList),
                self.preprocessorsListSelectionModel.selectedRow().row())

    def onRemoveSchema(self):
        #        index = self.schemaListSelectionModel.selectedRow()
        index = self.selectedSchemaIndex()
        if index.isValid():
            row = index.row()
            del self.schemaList[row]
            newrow = min(max(row - 1, 0), len(self.schemaList) - 1)
            if newrow > -1:
                self.schemaListSelectionModel.select(
                    self.schemaListProxy.mapFromSource(
                        self.schemaList.index(newrow)),
                    QItemSelectionModel.ClearAndSelect)

    def setActiveSchema(self, schema):
        if schema.modified and hasattr(schema, "_tmp_preprocessors"):
            self.preprocessorsList[:] = list(schema._tmp_preprocessors)
        else:
            self.preprocessorsList[:] = list(schema.preprocessors)
        self.preprocessorsListSelectionModel.select(
            schema.selectedPreprocessor, QItemSelectionModel.ClearAndSelect)
        self.commitIf()

    def showEditWidget(self, pp):
        w = self.stackedEditorsCache.get(type(pp), None)
        if w is None:
            w = self.EDITORS[type(pp)](self.mainArea)
            self.stackedEditorsCache[type(pp)] = w
            self.connect(w, SIGNAL("dataChanged"), self.setEditedPreprocessor)
            self.mainAreaStack.addWidget(w)
        self.mainAreaStack.setCurrentWidget(w)
        w.data = pp
        w.show()

    def setEditedPreprocessor(self, pp):
        self.preprocessorsList[
            self.preprocessorsListSelectionModel.selectedRow().row()] = pp

        self.setSchemaModified(True)
        self.commitIf()


#        self.onUpdateSchema()

    def setSchemaModified(self, state):
        #        index = self.schemaListSelectionModel.selectedRow()
        index = self.selectedSchemaIndex()
        if index.isValid():
            row = index.row()
            self.schemaList[row].modified = True
            self.schemaList[row]._tmp_preprocessors = list(
                self.preprocessorsList)
            self.schemaList.emitDataChanged([row])

    def commitIf(self):
        if self.autoCommit:
            self.commit()
        else:
            self.changedFlag = True

    def commit(self):
        wrap = orngWrap.PreprocessedLearner(list(self.preprocessorsList))
        if self.data is not None:
            data = wrap.processData(self.data)
            self.send("Preprocessed Example Table", data)
        self.send("Preprocess", wrap)

        #        self.send("Preprocessor", Preprocessor_preprocessorList(list(self.preprocessorsList)))
        self.changedFlag = False
示例#16
0
    def __init__(self, parent=None, signalManager=None):
        OWWidget.__init__(self, parent, signalManager, 'Python Script')

        self.inputs = [("in_data", Orange.data.Table, self.setExampleTable,
                        Default),
                       ("in_distance", Orange.misc.SymMatrix,
                        self.setDistanceMatrix, Default),
                       ("in_learner", Orange.core.Learner, self.setLearner,
                        Default),
                       ("in_classifier", Orange.core.Classifier,
                        self.setClassifier, Default),
                       ("in_object", object, self.setObject)]

        self.outputs = [("out_data", Orange.data.Table),
                        ("out_distance", Orange.misc.SymMatrix),
                        ("out_learner", Orange.core.Learner),
                        ("out_classifier", Orange.core.Classifier, Dynamic),
                        ("out_object", object, Dynamic)]

        self.in_data = None
        self.in_distance = None
        self.in_learner = None
        self.in_classifier = None
        self.in_object = None
        self.auto_execute = False

        self.libraryListSource = [Script("Hello world",
                                         "print 'Hello world'\n")]
        self.currentScriptIndex = 0
        self.splitterState = None
        self.loadSettings()

        for s in self.libraryListSource:
            s.flags = 0

        self._cachedDocuments = {}

        self.infoBox = OWGUI.widgetBox(self.controlArea, 'Info')
        OWGUI.label(
            self.infoBox, self,
            "<p>Execute python script.</p><p>Input variables:<ul><li> " +
            "<li>".join(t[0] for t in self.inputs) +
            "</ul></p><p>Output variables:<ul><li>" +
            "<li>".join(t[0] for t in self.outputs) +
            "</ul></p>"
        )

        self.libraryList = PyListModel(
           [], self,
           flags=Qt.ItemIsSelectable | Qt.ItemIsEnabled | Qt.ItemIsEditable
        )

        self.libraryList.wrap(self.libraryListSource)

        self.controlBox = OWGUI.widgetBox(self.controlArea, 'Library')
        self.controlBox.layout().setSpacing(1)

        self.libraryView = QListView(
            editTriggers=QListView.DoubleClicked |
                         QListView.EditKeyPressed,
            sizePolicy=QSizePolicy(QSizePolicy.Ignored,
                                   QSizePolicy.Preferred)
        )
        self.libraryView.setItemDelegate(ScriptItemDelegate(self))
        self.libraryView.setModel(self.libraryList)

        self.libraryView.selectionModel().selectionChanged.connect(
            self.onSelectedScriptChanged
        )
        self.controlBox.layout().addWidget(self.libraryView)

        w = ModelActionsWidget()

        self.addNewScriptAction = action = QAction("+", self)
        action.setToolTip("Add a new script to the library")
        action.triggered.connect(self.onAddScript)
        w.addAction(action)

        action = QAction(unicodedata.lookup("MINUS SIGN"), self)
        action.setToolTip("Remove script from library")
        action.triggered.connect(self.onRemoveScript)
        w.addAction(action)

        action = QAction("Update", self)
        action.setToolTip("Save changes in the editor to library")
        action.setShortcut(QKeySequence(QKeySequence.Save))
        action.triggered.connect(self.commitChangesToLibrary)
        w.addAction(action)

        action = QAction("More", self, toolTip="More actions")

        new_from_file = QAction("Import a script from a file", self)
        save_to_file = QAction("Save selected script to a file", self)
        save_to_file.setShortcut(QKeySequence(QKeySequence.SaveAs))

        new_from_file.triggered.connect(self.onAddScriptFromFile)
        save_to_file.triggered.connect(self.saveScript)

        menu = QMenu(w)
        menu.addAction(new_from_file)
        menu.addAction(save_to_file)
        action.setMenu(menu)
        button = w.addAction(action)
        button.setPopupMode(QToolButton.InstantPopup)

        w.layout().setSpacing(1)

        self.controlBox.layout().addWidget(w)

        self.runBox = OWGUI.widgetBox(self.controlArea, 'Run')
        OWGUI.button(self.runBox, self, "Execute", callback=self.execute)
        OWGUI.checkBox(self.runBox, self, "auto_execute", "Auto execute",
                       tooltip=("Run the script automatically whenever "
                                "the inputs to the widget change."))

        self.splitter = QSplitter(Qt.Vertical, self.mainArea)
        self.mainArea.layout().addWidget(self.splitter)

        self.defaultFont = defaultFont = \
            "Monaco" if sys.platform == "darwin" else "Courier"

        self.textBox = OWGUI.widgetBox(self, 'Python script')
        self.splitter.addWidget(self.textBox)
        self.text = PythonScriptEditor(self)
        self.textBox.layout().addWidget(self.text)

        self.textBox.setAlignment(Qt.AlignVCenter)
        self.text.setTabStopWidth(4)

        self.text.modificationChanged[bool].connect(self.onModificationChanged)

        self.consoleBox = OWGUI.widgetBox(self, 'Console')
        self.splitter.addWidget(self.consoleBox)
        self.console = PythonConsole(self.__dict__, self)
        self.consoleBox.layout().addWidget(self.console)
        self.console.document().setDefaultFont(QFont(defaultFont))
        self.consoleBox.setAlignment(Qt.AlignBottom)
        self.console.setTabStopWidth(4)

        select_row(self.libraryView, self.currentScriptIndex)

        self.splitter.setSizes([2, 1])
        if self.splitterState is not None:
            self.splitter.restoreState(QByteArray(self.splitterState))

        self.splitter.splitterMoved[int, int].connect(self.onSpliterMoved)
        self.controlArea.layout().addStretch(1)
        self.resize(800, 600)
示例#17
0
class OWPythonScript(OWWidget):

    settingsList = ["libraryListSource", "currentScriptIndex",
                    "splitterState", "auto_execute"]

    def __init__(self, parent=None, signalManager=None):
        OWWidget.__init__(self, parent, signalManager, 'Python Script')

        self.inputs = [("in_data", Orange.data.Table, self.setExampleTable,
                        Default),
                       ("in_distance", Orange.misc.SymMatrix,
                        self.setDistanceMatrix, Default),
                       ("in_learner", Orange.core.Learner, self.setLearner,
                        Default),
                       ("in_classifier", Orange.core.Classifier,
                        self.setClassifier, Default),
                       ("in_object", object, self.setObject)]

        self.outputs = [("out_data", Orange.data.Table),
                        ("out_distance", Orange.misc.SymMatrix),
                        ("out_learner", Orange.core.Learner),
                        ("out_classifier", Orange.core.Classifier, Dynamic),
                        ("out_object", object, Dynamic)]

        self.in_data = None
        self.in_distance = None
        self.in_learner = None
        self.in_classifier = None
        self.in_object = None
        self.auto_execute = False

        self.libraryListSource = [Script("Hello world",
                                         "print 'Hello world'\n")]
        self.currentScriptIndex = 0
        self.splitterState = None
        self.loadSettings()

        for s in self.libraryListSource:
            s.flags = 0

        self._cachedDocuments = {}

        self.infoBox = OWGUI.widgetBox(self.controlArea, 'Info')
        OWGUI.label(
            self.infoBox, self,
            "<p>Execute python script.</p><p>Input variables:<ul><li> " +
            "<li>".join(t[0] for t in self.inputs) +
            "</ul></p><p>Output variables:<ul><li>" +
            "<li>".join(t[0] for t in self.outputs) +
            "</ul></p>"
        )

        self.libraryList = PyListModel(
           [], self,
           flags=Qt.ItemIsSelectable | Qt.ItemIsEnabled | Qt.ItemIsEditable
        )

        self.libraryList.wrap(self.libraryListSource)

        self.controlBox = OWGUI.widgetBox(self.controlArea, 'Library')
        self.controlBox.layout().setSpacing(1)

        self.libraryView = QListView(
            editTriggers=QListView.DoubleClicked |
                         QListView.EditKeyPressed,
            sizePolicy=QSizePolicy(QSizePolicy.Ignored,
                                   QSizePolicy.Preferred)
        )
        self.libraryView.setItemDelegate(ScriptItemDelegate(self))
        self.libraryView.setModel(self.libraryList)

        self.libraryView.selectionModel().selectionChanged.connect(
            self.onSelectedScriptChanged
        )
        self.controlBox.layout().addWidget(self.libraryView)

        w = ModelActionsWidget()

        self.addNewScriptAction = action = QAction("+", self)
        action.setToolTip("Add a new script to the library")
        action.triggered.connect(self.onAddScript)
        w.addAction(action)

        action = QAction(unicodedata.lookup("MINUS SIGN"), self)
        action.setToolTip("Remove script from library")
        action.triggered.connect(self.onRemoveScript)
        w.addAction(action)

        action = QAction("Update", self)
        action.setToolTip("Save changes in the editor to library")
        action.setShortcut(QKeySequence(QKeySequence.Save))
        action.triggered.connect(self.commitChangesToLibrary)
        w.addAction(action)

        action = QAction("More", self, toolTip="More actions")

        new_from_file = QAction("Import a script from a file", self)
        save_to_file = QAction("Save selected script to a file", self)
        save_to_file.setShortcut(QKeySequence(QKeySequence.SaveAs))

        new_from_file.triggered.connect(self.onAddScriptFromFile)
        save_to_file.triggered.connect(self.saveScript)

        menu = QMenu(w)
        menu.addAction(new_from_file)
        menu.addAction(save_to_file)
        action.setMenu(menu)
        button = w.addAction(action)
        button.setPopupMode(QToolButton.InstantPopup)

        w.layout().setSpacing(1)

        self.controlBox.layout().addWidget(w)

        self.runBox = OWGUI.widgetBox(self.controlArea, 'Run')
        OWGUI.button(self.runBox, self, "Execute", callback=self.execute)
        OWGUI.checkBox(self.runBox, self, "auto_execute", "Auto execute",
                       tooltip=("Run the script automatically whenever "
                                "the inputs to the widget change."))

        self.splitter = QSplitter(Qt.Vertical, self.mainArea)
        self.mainArea.layout().addWidget(self.splitter)

        self.defaultFont = defaultFont = \
            "Monaco" if sys.platform == "darwin" else "Courier"

        self.textBox = OWGUI.widgetBox(self, 'Python script')
        self.splitter.addWidget(self.textBox)
        self.text = PythonScriptEditor(self)
        self.textBox.layout().addWidget(self.text)

        self.textBox.setAlignment(Qt.AlignVCenter)
        self.text.setTabStopWidth(4)

        self.text.modificationChanged[bool].connect(self.onModificationChanged)

        self.consoleBox = OWGUI.widgetBox(self, 'Console')
        self.splitter.addWidget(self.consoleBox)
        self.console = PythonConsole(self.__dict__, self)
        self.consoleBox.layout().addWidget(self.console)
        self.console.document().setDefaultFont(QFont(defaultFont))
        self.consoleBox.setAlignment(Qt.AlignBottom)
        self.console.setTabStopWidth(4)

        select_row(self.libraryView, self.currentScriptIndex)

        self.splitter.setSizes([2, 1])
        if self.splitterState is not None:
            self.splitter.restoreState(QByteArray(self.splitterState))

        self.splitter.splitterMoved[int, int].connect(self.onSpliterMoved)
        self.controlArea.layout().addStretch(1)
        self.resize(800, 600)

    def setExampleTable(self, et):
        self.in_data = et

    def setDistanceMatrix(self, dm):
        self.in_distance = dm

    def setLearner(self, learner):
        self.in_learner = learner

    def setClassifier(self, classifier):
        self.in_classifier = classifier

    def setObject(self, obj):
        self.in_object = obj

    def handleNewSignals(self):
        if self.auto_execute:
            self.execute()

    def selectedScriptIndex(self):
        rows = self.libraryView.selectionModel().selectedRows()
        if rows:
            return  [i.row() for i in rows][0]
        else:
            return None

    def setSelectedScript(self, index):
        select_row(self.libraryView, index)

    def onAddScript(self, *args):
        self.libraryList.append(Script("New script", "", 0))
        self.setSelectedScript(len(self.libraryList) - 1)

    def onAddScriptFromFile(self, *args):
        filename = QFileDialog.getOpenFileName(
            self, 'Open Python Script',
            os.path.expanduser("~/"),
            'Python files (*.py)\nAll files(*.*)'
        )

        filename = unicode(filename)
        if filename:
            name = os.path.basename(filename)
            self.libraryList.append(Script(name, open(filename, "rb").read(),
                                           0, filename))
            self.setSelectedScript(len(self.libraryList) - 1)

    def onRemoveScript(self, *args):
        index = self.selectedScriptIndex()
        if index is not None:
            del self.libraryList[index]
            select_row(self.libraryView, max(index - 1, 0))

    def onSelectedScriptChanged(self, selected, deselected):
        index = [i.row() for i in selected.indexes()]
        if index:
            current = index[0]
            self.text.setDocument(self.documentForScript(current))
            self.currentScriptIndex = current

    def documentForScript(self, script=0):
        if type(script) != Script:
            script = self.libraryList[script]

        if script not in self._cachedDocuments:
            doc = QTextDocument(self)
            doc.setDocumentLayout(QPlainTextDocumentLayout(doc))
            doc.setPlainText(script.script)
            doc.setDefaultFont(QFont(self.defaultFont))
            doc.highlighter = PythonSyntaxHighlighter(doc)
            doc.modificationChanged[bool].connect(self.onModificationChanged)
            doc.setModified(False)
            self._cachedDocuments[script] = doc
        return self._cachedDocuments[script]

    def commitChangesToLibrary(self, *args):
        index = self.selectedScriptIndex()
        if index is not None:
            self.libraryList[index].script = unicode(self.text.toPlainText())
            self.text.document().setModified(False)
            self.libraryList.emitDataChanged(index)

    def onModificationChanged(self, modified):
        index = self.selectedScriptIndex()
        if index is not None:
            self.libraryList[index].flags = Script.Modified if modified else 0
            self.libraryList.emitDataChanged(index)

    def onSpliterMoved(self, pos, ind):
        self.splitterState = str(self.splitter.saveState())

    def saveScript(self):
        index = self.selectedScriptIndex()
        filename = os.path.expanduser("~/")
        if index is not None:
            script = self.libraryList[index]
            filename = script.sourceFileName or filename

        filename = QFileDialog.getSaveFileName(
            self, 'Save Python Script',
            filename,
            'Python files (*.py)\nAll files(*.*)'
        )

        self.codeFile = unicode(filename)

        if self.codeFile:
            fn = ""
            head, tail = os.path.splitext(self.codeFile)
            if not tail:
                fn = head + ".py"
            else:
                fn = self.codeFile

            f = open(fn, 'w')
            f.write(self.text.toPlainText())
            f.close()

    def execute(self):
        self._script = str(self.text.toPlainText())
        self.console.write("\nRunning script:\n")
        self.console.push("exec(_script)")
        self.console.new_prompt(sys.ps1)
        for out in self.outputs:
            signal = out[0]
            self.send(signal, getattr(self, signal, None))
示例#18
0
    def __init__(self, parent=None, signalManager=None):
        OWWidget.__init__(self, parent, signalManager, 'Python Script')

        self.inputs = [
            ("in_data", ExampleTable, self.setExampleTable),
            ("in_distance", orange.SymMatrix, self.setDistanceMatrix),
            ("in_network", Orange.network.Graph, self.setNetwork),
            ("in_learner", orange.Learner, self.setLearner),
            ("in_classifier", orange.Classifier, self.setClassifier)
        ]
        self.outputs = [("out_data", ExampleTable),
                        ("out_distance", orange.SymMatrix),
                        ("out_network", Orange.network.Graph),
                        ("out_learner", orange.Learner),
                        ("out_classifier", orange.Classifier, Dynamic)]

        self.in_data = None
        self.in_network = None
        self.in_distance = None
        self.in_learner = None
        self.in_classifier = None

        self.codeFile = ''
        self.libraryListSource = [
            Script("Hello world", "print 'Hello world'\n")
        ]
        self.currentScriptIndex = 0
        self.splitterState = None
        self.loadSettings()

        for s in self.libraryListSource:
            s.flags = 0

        self._cachedDocuments = {}

        self.infoBox = OWGUI.widgetBox(self.controlArea, 'Info')
        label = OWGUI.label(self.infoBox, self, "<p>Execute python script.</p><p>Input variables:<ul><li> " + \
                    "<li>".join(t[0] for t in self.inputs) + "</ul></p><p>Output variables:<ul><li>" + \
                    "<li>".join(t[0] for t in self.outputs) + "</ul></p>")
        self.libraryList = PyListModel([],
                                       self,
                                       flags=Qt.ItemIsSelectable
                                       | Qt.ItemIsEnabled | Qt.ItemIsEditable)
        #        self.libraryList.append(Script("Hello world", "print 'Hello world'\n"))
        self.libraryList.wrap(self.libraryListSource)

        self.controlBox = OWGUI.widgetBox(self.controlArea, 'Library')
        self.controlBox.layout().setSpacing(1)
        self.libraryView = QListView()
        self.libraryView.pyqtConfigure(editTriggers=QListView.DoubleClicked
                                       | QListView.SelectedClicked)
        self.libraryView.setSizePolicy(QSizePolicy.Ignored,
                                       QSizePolicy.Preferred)
        self.libraryView.setItemDelegate(ScriptItemDelegate(self))
        self.libraryView.setModel(self.libraryList)
        self.connect(
            self.libraryView.selectionModel(),
            SIGNAL("selectionChanged(QItemSelection, QItemSelection)"),
            self.onSelectedScriptChanged)
        self.controlBox.layout().addWidget(self.libraryView)
        w = ModelActionsWidget()

        self.addNewScriptAction = action = QAction("+", self)
        action.pyqtConfigure(toolTip="Add a new script to the library")
        self.connect(action, SIGNAL("triggered()"), self.onAddScript)
        new_empty = QAction("Add a new empty script", action)
        new_from_file = QAction("Add a new script from a file", action)
        self.connect(new_empty, SIGNAL("triggered()"), self.onAddScript)
        self.connect(new_from_file, SIGNAL("triggered()"),
                     self.onAddScriptFromFile)
        menu = QMenu(w)
        menu.addAction(new_empty)
        menu.addAction(new_from_file)

        #        action.setMenu(menu)
        button = w.addAction(action)

        self.removeAction = action = QAction("-", self)
        action.pyqtConfigure(toolTip="Remove script from library")
        self.connect(action, SIGNAL("triggered()"), self.onRemoveScript)
        w.addAction(action)

        action = QAction("Update", self)
        action.pyqtConfigure(toolTip="Save changes in the editor to library")
        action.setShortcut(QKeySequence(QKeySequence.Save))
        self.connect(action, SIGNAL("triggered()"),
                     self.commitChangesToLibrary)
        b = w.addAction(action)
        #        b.setSizePolicy(QSizePolicy.MinimumExpanding, QSizePolicy.Fixed)

        action = QAction("More", self)
        action.pyqtConfigure(
            toolTip="More actions"
        )  #, icon=self.style().standardIcon(QStyle.SP_ToolBarHorizontalExtensionButton))

        self.openScriptFromFileAction = new_from_file = QAction(
            "Import a script from a file", self)
        self.saveScriptToFile = save_to_file = QAction(
            "Save selected script to a file", self)
        save_to_file.setShortcut(QKeySequence(QKeySequence.SaveAs))

        self.connect(new_from_file, SIGNAL("triggered()"),
                     self.onAddScriptFromFile)
        self.connect(save_to_file, SIGNAL("triggered()"), self.saveScript)

        menu = QMenu(w)
        menu.addAction(new_from_file)
        menu.addAction(save_to_file)
        action.setMenu(menu)
        b = w.addAction(action)
        b.setPopupMode(QToolButton.InstantPopup)
        ## TODO: set the space for the indicator

        w.layout().setSpacing(1)

        self.controlBox.layout().addWidget(w)

        #        OWGUI.button(self.controlBox, self, "Open...", callback=self.openScript)
        #        OWGUI.button(self.controlBox, self, "Save...", callback=self.saveScript)

        self.runBox = OWGUI.widgetBox(self.controlArea, 'Run')
        OWGUI.button(self.runBox, self, "Execute", callback=self.execute)

        self.splitCanvas = QSplitter(Qt.Vertical, self.mainArea)
        self.mainArea.layout().addWidget(self.splitCanvas)

        self.defaultFont = defaultFont = "Monaco" if sys.platform == "darwin" else "Courier"
        self.textBox = OWGUI.widgetBox(self, 'Python script')
        self.splitCanvas.addWidget(self.textBox)
        self.text = PythonScriptEditor(self)
        self.textBox.layout().addWidget(self.text)

        self.textBox.setAlignment(Qt.AlignVCenter)
        self.text.setTabStopWidth(4)

        self.connect(self.text, SIGNAL("modificationChanged(bool)"),
                     self.onModificationChanged)

        self.saveAction = action = QAction("&Save", self.text)
        action.pyqtConfigure(toolTip="Save script to file")
        action.setShortcut(QKeySequence(QKeySequence.Save))
        action.setShortcutContext(Qt.WidgetWithChildrenShortcut)
        self.connect(action, SIGNAL("triggered()"), self.saveScript)

        self.consoleBox = OWGUI.widgetBox(self, 'Console')
        self.splitCanvas.addWidget(self.consoleBox)
        self.console = PythonConsole(self.__dict__, self)
        self.consoleBox.layout().addWidget(self.console)
        self.console.document().setDefaultFont(QFont(defaultFont))
        self.consoleBox.setAlignment(Qt.AlignBottom)
        self.console.setTabStopWidth(4)

        self.openScript(self.codeFile)
        try:
            self.libraryView.selectionModel().select(
                self.libraryList.index(self.currentScriptIndex),
                QItemSelectionModel.ClearAndSelect)
        except Exception:
            pass
        self.splitCanvas.setSizes([2, 1])
        if self.splitterState is not None:
            self.splitCanvas.restoreState(QByteArray(self.splitterState))

        self.connect(
            self.splitCanvas, SIGNAL("splitterMoved(int, int)"),
            lambda pos, ind: setattr(self, "splitterState",
                                     str(self.splitCanvas.saveState())))
        self.controlArea.layout().addStretch(1)
        self.resize(800, 600)
 def __init__(self, var, parent=None, **kwargs):
     PyListModel.__init__(self, [], parent, **kwargs)
     self.wrap(var.values)
     self.colorPalette = OWColorPalette.ColorPaletteHSV(len(self))
     self.connect(self, SIGNAL("columnsInserted(QModelIndex, int, int)"), self.updateColors)
     self.connect(self, SIGNAL("columnsRemoved(QModelIndex, int, int)"), self.updateColors)
示例#20
0
class OWRScript(OWWidget):
    settingsList = ["scriptLibraryList", "selectedScriptIndex", "lastDir"]
    def __init__(self, parent=None, signalManager=None, name="R Script"):
        OWWidget.__init__(self, parent, signalManager, name)
        
        self.inputs = [("in_data", ExampleTable, self.setData), ("in_distance", orange.SymMatrix, self.setDistance)]
        self.outputs = [("out_data", ExampleTable), ("out_distance", orange.SymMatrix), ("out_learner", orange.Learner), ("out_classifier", orange.Classifier)]
        
        self.in_data, self.in_distance = None, None
        self.scriptLibraryList = [RScript("New script", "x <- c(1,2,5)\ny <- c(2,1 6)\nplot(x,y)\n")]
        self.selectedScriptIndex = 0
        self.selectedGrDev = "PNG"
        
        self.lastDir = os.path.expanduser("~/script.R")
        
        self.loadSettings()
        
        self.defaultFont = QFont("Monaco") if sys.platform == "darwin" else QFont("Courier")
        
        self.splitter = QSplitter(Qt.Vertical, self.mainArea)
        self.mainArea.layout().addWidget(self.splitter)
        self.scriptEdit = RScriptEditor()
        self.splitter.addWidget(self.scriptEdit)
        self.console = RPy2Console({}, self)
        self.splitter.addWidget(self.console)
        self.splitter.setSizes([2,1])
        
        self.libraryModel = PyListModel([], self, Qt.ItemIsEnabled | Qt.ItemIsSelectable | Qt.ItemIsEditable)
        self.libraryModel.wrap(self.scriptLibraryList)
        
        self.infoBox = OWGUI.widgetLabel(OWGUI.widgetBox(self.controlArea, "Info", addSpace=True), "")
        self.infoBox.setText("<p>Execute R script</p>Input variables<li><ul>in_data</ul><ul>in_distance</ul></li>Output variables:<li><ul>out_data</ul></p/>")
        
        box = OWGUI.widgetBox(self.controlArea, "Library", addSpace=True)
        
        self.libraryWidget = LibraryWidget()
        self.libraryView = self.libraryWidget.view
        box.layout().addWidget(self.libraryWidget)
        
        self.libraryWidget.view.setItemDelegate(ScriptItemDelegate(self))
        self.libraryWidget.setScriptModel(self.libraryModel)
        self.libraryWidget.setDocumentEditor(self.scriptEdit)
        
        box = OWGUI.widgetBox(self.controlArea, "Run")
        OWGUI.button(box, self, "Execute", callback=self.runScript, tooltip="Execute the script")
        
        OWGUI.rubber(self.controlArea)
        
        
        self.connect(self.libraryWidget.addScriptAction, SIGNAL("triggered()"), self.onAddNewScript)
        self.connect(self.libraryWidget.updateScriptAction, SIGNAL("triggered()"), self.onUpdateScript)
        self.connect(self.libraryWidget.removeScriptAction, SIGNAL("triggered()"), self.onRemoveScript)
        self.connect(self.libraryWidget.addScriptFromFile, SIGNAL("triggered()"), self.onAddScriptFromFile)
        self.connect(self.libraryWidget.saveScriptToFile, SIGNAL("triggered()"), self.onSaveScriptToFile)
        
        self.connect(self.libraryView.selectionModel(), SIGNAL("selectionChanged(QItemSelection, QItemSelection)"), self.onScriptSelection)
        
        self._cachedDocuments = {}
        
        self.grView = QLabel()
        
        self.resize(800, 600)
        QTimer.singleShot(30, self.initGrDevice)
        
    def initGrDevice(self):
        import tempfile
        self.grDevFile = tempfile.NamedTemporaryFile("rwb", prefix="orange-rscript-grDev", suffix=".png", delete=False)
        self.grDevFile.close()
        robjects.r('png("%s", width=512, height=512)' % self.grDevFile.name)
        self.fileWatcher = QFileSystemWatcher(self)
        self.fileWatcher.addPath(self.grDevFile.name)
        self.connect(self.fileWatcher, SIGNAL("fileChanged(QString)"), self.updateGraphicsView)
        
    def updateGraphicsView(self, filename):
        self.grView.setPixmap(QPixmap(filename))
        self.grView.show()
        if self.grDevFile.name not in list(self.fileWatcher.files()):
            # The file can be removed and recreated by R, in which case we need to re-add it
            self.fileWatcher.addPath(self.grDevFile.name)

    def selectScript(self, index):
        index = self.libraryModel.index(index)
        self.libraryView.selectionModel().select(index, QItemSelectionModel.ClearAndSelect)
        
    def selectedScript(self):
        rows = self.libraryView.selectionModel().selectedRows()
        rows = [index.row() for index in rows]
        if rows:
            return rows[0]
        else:
            return None
        
    def onAddNewScript(self):
        self.libraryModel.append(RScript("New Script", ""))
        self.selectScript(len(self.libraryModel) - 1)
        
    def onRemoveScript(self):
        row = self.selectedScript()
        if row is not None:
            del self.libraryModel[row]
        
    def onUpdateScript(self):
        row = self.selectedScript()
        if row is not None:
            self.libraryModel[row].script = str(self.scriptEdit.toPlainText())
            self.scriptEdit.document().setModified(False)
            self.libraryModel.emitDataChanged([row])   
        
    def onAddScriptFromFile(self):
        filename = str(QFileDialog.getOpenFileName(self, "Open script", self.lastDir))
        if filename:
            script = open(filename, "rb").read()
            self.lastDir, name = os.path.split(filename)
            self.libraryModel.append(RScript(name, script, sourceFileName=filename))
            self.selectScript(len(self.libraryModel) - 1)   
            
    def onSaveScriptToFile(self):
        row = self.selectedScript()
        if row is not None:
            script = self.libraryModel[row]
            filename = str(QFileDialog.getSaveFileName(self, "Save Script As", script.sourceFileName or self.lastDir))
            if filename:
                self.lastDir, name = os.path.split(filename)
                script.sourceFileName = filename
                script.flags = 0
                open(filename, "wb").write(script.script)
                       
    def onScriptSelection(self, *args):
        row = self.selectedScript()
        if row is not None:
            self.scriptEdit.setDocument(self.documentForScript(row))
                       
    def documentForScript(self, script=0):
        if type(script) != RScript:
            script = self.libraryModel[script]
        if script not in self._cachedDocuments:
            doc = QTextDocument(self)
            doc.setDocumentLayout(QPlainTextDocumentLayout(doc))
            doc.setPlainText(script.script)
            doc.setDefaultFont(QFont(self.defaultFont))
            doc.highlighter = RSyntaxHighlighter(doc)
            self.connect(doc, SIGNAL("modificationChanged(bool)"), self.onModificationChanged)
            doc.setModified(False)
            self._cachedDocuments[script] = doc
        return self._cachedDocuments[script]
    
    def onModificationChanged(self, changed):
        row = self.selectedScript()
        if row is not None:
            self.libraryModel[row].flags = RScript.Modified if changed else 0
            self.libraryModel.emitDataChanged([row]) 
                             
    def setData(self, data):
        self.in_data = data
        self.console.setLocals(self.getLocals())

    def setDistance(self, matrix):
        self.in_distance = matrix
        self.console.setLocals(self.getLocals())

    def getLocals(self):
        return {"in_data": self.in_data,
                "in_distance": self.in_distance,
               }
        
    def runScript(self):
        self.console.push('png("%s", width=512, height=512)\n' % self.grDevFile.name)
        self.console.push(str(self.scriptEdit.toPlainText()))
        self.console.new_prompt(">>> ")
        robjects.r("dev.off()\n")
示例#21
0
 def data(self, index, role=Qt.DisplayRole):
     if role == Qt.DecorationRole:
         i = index.row()
         return QVariant(self.itemQIcon(i))
     else:
         return PyListModel.data(self, index, role)
示例#22
0
 def __init__(self, parent=None, signalManager=None, name="R Script"):
     OWWidget.__init__(self, parent, signalManager, name)
     
     self.inputs = [("in_data", ExampleTable, self.setData), ("in_distance", orange.SymMatrix, self.setDistance)]
     self.outputs = [("out_data", ExampleTable), ("out_distance", orange.SymMatrix), ("out_learner", orange.Learner), ("out_classifier", orange.Classifier)]
     
     self.in_data, self.in_distance = None, None
     self.scriptLibraryList = [RScript("New script", "x <- c(1,2,5)\ny <- c(2,1 6)\nplot(x,y)\n")]
     self.selectedScriptIndex = 0
     self.selectedGrDev = "PNG"
     
     self.lastDir = os.path.expanduser("~/script.R")
     
     self.loadSettings()
     
     self.defaultFont = QFont("Monaco") if sys.platform == "darwin" else QFont("Courier")
     
     self.splitter = QSplitter(Qt.Vertical, self.mainArea)
     self.mainArea.layout().addWidget(self.splitter)
     self.scriptEdit = RScriptEditor()
     self.splitter.addWidget(self.scriptEdit)
     self.console = RPy2Console({}, self)
     self.splitter.addWidget(self.console)
     self.splitter.setSizes([2,1])
     
     self.libraryModel = PyListModel([], self, Qt.ItemIsEnabled | Qt.ItemIsSelectable | Qt.ItemIsEditable)
     self.libraryModel.wrap(self.scriptLibraryList)
     
     self.infoBox = OWGUI.widgetLabel(OWGUI.widgetBox(self.controlArea, "Info", addSpace=True), "")
     self.infoBox.setText("<p>Execute R script</p>Input variables<li><ul>in_data</ul><ul>in_distance</ul></li>Output variables:<li><ul>out_data</ul></p/>")
     
     box = OWGUI.widgetBox(self.controlArea, "Library", addSpace=True)
     
     self.libraryWidget = LibraryWidget()
     self.libraryView = self.libraryWidget.view
     box.layout().addWidget(self.libraryWidget)
     
     self.libraryWidget.view.setItemDelegate(ScriptItemDelegate(self))
     self.libraryWidget.setScriptModel(self.libraryModel)
     self.libraryWidget.setDocumentEditor(self.scriptEdit)
     
     box = OWGUI.widgetBox(self.controlArea, "Run")
     OWGUI.button(box, self, "Execute", callback=self.runScript, tooltip="Execute the script")
     
     OWGUI.rubber(self.controlArea)
     
     
     self.connect(self.libraryWidget.addScriptAction, SIGNAL("triggered()"), self.onAddNewScript)
     self.connect(self.libraryWidget.updateScriptAction, SIGNAL("triggered()"), self.onUpdateScript)
     self.connect(self.libraryWidget.removeScriptAction, SIGNAL("triggered()"), self.onRemoveScript)
     self.connect(self.libraryWidget.addScriptFromFile, SIGNAL("triggered()"), self.onAddScriptFromFile)
     self.connect(self.libraryWidget.saveScriptToFile, SIGNAL("triggered()"), self.onSaveScriptToFile)
     
     self.connect(self.libraryView.selectionModel(), SIGNAL("selectionChanged(QItemSelection, QItemSelection)"), self.onScriptSelection)
     
     self._cachedDocuments = {}
     
     self.grView = QLabel()
     
     self.resize(800, 600)
     QTimer.singleShot(30, self.initGrDevice)