示例#1
0
class PipeLine(PipeLineDock):
    
    error_detected =  QtCore.pyqtSignal(object, object, object)
    
    def __init__(self, parent):

        super(PipeLine, self).__init__(parent)
        self._tree = Tree()
        
        # Root branches
        self._branch_map = None
        self._items = []
        
        # Test data picker
        self._test_data_picker = TestDataPicker(self)
        self._test_data_picker.setModal(True)
        self._active_thread = None
                
        self._init_title()
        
        return
        
    def _init_title(self):
        
        self.setWindowTitle("Pipeline")
        self.treeWidget.setSortingEnabled(False)
        self.treeWidget.headerItem().setText(0, "Waiting...")

        return
        
    def _set_branch_map(self, branch_map):
        
        self._branch_map = branch_map
        
        return
        
    def _set_title(self, title):
        
        self.treeWidget.headerItem().setText(0, title)
        
        return
        
    def _draw(self, shell):
        
        self._clear()
        
        for branch_dict in self._branch_map:
            
            HubCls = branch_dict["hub"]
            args = []
            if "args" in branch_dict: args.extend(branch_dict["args"])
            
            new_item = HubCls(self.treeWidget,
                              branch_dict["name"],
                              *args)
            new_item._activate(shell)
            self._items.append(new_item)
            
        return
        
    def _expand(self, shell):
        
        for item in self._items:
            item._expand(shell)
        
        return
    
    def _refresh(self, shell, expand=True):
        
        self._draw(shell)
        if expand: self._expand(shell)
        
        return        
        
    def _clear(self):
        
        root = self.treeWidget.invisibleRootItem()
        
        for widget in self._items:
            
            widget._clear()
            
            if not isinstance(widget, HiddenHub):
                root.removeChild(widget)
            
        self._items = []

        return
        
    def _find_item(self, item_title, item_class=None, root_item=None):
        
        if root_item is None: root_item = self

        for item in root_item._items:
            
            if item._title == item_title:
                if item_class is None or isinstance(item, item_class):
                    return item
                    
            result = self._find_item(item_title, item_class, item)
            
            if result is not None: return result

        return None
        
    def _make_menus(self, shell, position):
                
        item = self.treeWidget.currentItem()

        if isinstance(item, InputBranchItem):
            
            # Set the widget action
            self._test_data_picker.buttonBox.button(
                         QtGui.QDialogButtonBox.Ok).clicked.disconnect()
            self._test_data_picker.buttonBox.button(
                         QtGui.QDialogButtonBox.Ok).clicked.connect(
                             lambda: self._read_test_data(shell, item))
            self._test_data_picker.buttonBox.button(
                         QtGui.QDialogButtonBox.Ok).clicked.connect(
                             self._test_data_picker.close)
            
            # Build module and theme context menu
            if item._hub_title in ["Modules", "Assessment"]:
                
                menu = QtGui.QMenu()
                
                if item._hub_title == "Modules":
                    menu.addAction('Inspect', lambda: item._inspect(shell))
                    menu.addAction('Reset', lambda: item._reset(shell))
                    
                menu.addAction('Load test data...', 
                               self._test_data_picker.show)            
                menu.exec_(self.treeWidget.mapToGlobal(position))
            
        elif isinstance(item, OutputBranchItem):
            
            # Build module context menu
            if item._hub_title == "Modules":
                
                menu = QtGui.QMenu()
                menu.addAction('Inspect', lambda: item._inspect(shell))
                menu.exec_(self.treeWidget.mapToGlobal(position))
     
        return
        
    def _set_top_item(self):
        
        self.treeWidget.itemClicked.emit(self.treeWidget.topLevelItem(0), -1)
        
        return
    
    def _read_auto(self, shell):
        
        self._tree.read_auto(shell.core,
                             shell.project)
                             
        return
    
    @QtCore.pyqtSlot(object, object)
    def _read_test_data(self, shell, item):
        
        self._active_thread = ThreadReadTest(
                             item,
                             shell,
                             str(self._test_data_picker.pathLineEdit.text()),
                             self._test_data_picker.overwriteBox.isChecked())
        self._active_thread.start()
        self._active_thread.error_detected.connect(self._emit_error)
        self._active_thread.finished.connect(self._clear_active_thread)
        
        return
        
    @QtCore.pyqtSlot()
    def _clear_active_thread(self):
        
        self._active_thread = None 
        
        return
        
    @QtCore.pyqtSlot(object, object, object)
    def _emit_error(self, etype, evalue, etraceback):
        
        self.error_detected.emit(etype, evalue, etraceback)
        
        return
示例#2
0
class PipeLine(PipeLineDock):

    error_detected = QtCore.pyqtSignal(object, object, object)

    def __init__(self, parent):

        super(PipeLine, self).__init__(parent)
        self._tree = Tree()
        self._model = None
        self._proxy = None

        # Root branches
        self._branch_map = None
        self._controls = []

        # Test data picker
        self._test_data_picker = TestDataPicker(self)
        self._test_data_picker.setModal(True)

        self._init_model()
        self._init_title()

        return

    def _init_model(self):

        self._model = QtGui.QStandardItemModel()
        self._model.setColumnCount(1)
        self._proxy = PipelineFilterProxyModel()
        self._proxy.setSourceModel(self._model)
        self._proxy.setDynamicSortFilter(True)
        self.treeView.setModel(self._proxy)

        self.filterLineEdit.textChanged.connect(self._update_filter)
        self.clearButton.clicked.connect(self._clear_filter)

        return

    def _init_title(self):

        self.setWindowTitle("Pipeline")
        self.treeView.setSortingEnabled(False)
        self._model.setHeaderData(0, QtCore.Qt.Horizontal, "Waiting...")

        return

    def _set_branch_map(self, branch_map):

        self._branch_map = branch_map

        return

    def _set_title(self, title):

        self._model.setHeaderData(0, QtCore.Qt.Horizontal, title)

        return

    def _draw(self, shell):

        self._clear()
        section_address = ""

        for branch_dict in self._branch_map:

            HubCls = branch_dict["hub"]
            args = []
            if "args" in branch_dict: args.extend(branch_dict["args"])

            # Model item
            if HubCls == SectionControl:
                section_address = branch_dict["name"]
                address = section_address
                section = "section"
            else:
                address = section_address + "." + branch_dict["name"]
                section = "hub"

            user_dict = {
                "address": address,
                "visible": True,
                "section": section,
                "status": None
            }

            name_item = QtGui.QStandardItem(branch_dict["name"])
            name_item.setData(address, QtCore.Qt.UserRole)
            name_item.setData((user_dict, ), 33)
            self._model.appendRow(name_item)

            # Controller
            new_control = HubCls(address, branch_dict["name"], self.treeView,
                                 self._model, self._proxy, *args)
            new_control._init_ui(name_item)
            new_control._activate(shell, name_item)

            self._controls.append(new_control)

        return

    def _expand(self, shell):

        for controller in self._controls:
            controller._expand(shell)

        return

    def _refresh(self, shell, expand=True):

        self._draw(shell)
        if expand: self._expand(shell)

        return

    def _clear(self):

        root = self._model.invisibleRootItem()
        root.removeRows(0, root.rowCount())

        self._controls = []

        return

    def _find_controller(self,
                         proxy_index=None,
                         controller_title=None,
                         controller_class=None,
                         root=None):

        if proxy_index is None and controller_title is None:
            err_str = ("Either argument 'proxy_index' or 'controller_title' "
                       "must be provided and 'proxy_index' will take "
                       "precedence")
            raise ValueError(err_str)

        if root is None: root = self

        if proxy_index is not None:
            match = self._proxy.data(proxy_index, QtCore.Qt.UserRole)
            search_attr = "_address"
        else:
            match = controller_title
            search_attr = "_title"

        for controller in root._controls:

            if getattr(controller, search_attr) == match:
                if (controller_class is None
                        or isinstance(controller, controller_class)):
                    return controller

            result = self._find_controller(proxy_index, controller_title,
                                           controller_class, controller)

            if result is not None: return result

        return None

    def _make_menus(self, shell, position):

        proxy_indexes = self.treeView.selectedIndexes()
        proxy_index = proxy_indexes[0]
        controller = self._find_controller(proxy_index)

        if isinstance(controller, InputBranchControl):

            # Set the widget action
            self._test_data_picker.buttonBox.button(
                QtGui.QDialogButtonBox.Ok).clicked.disconnect()
            self._test_data_picker.buttonBox.button(
                QtGui.QDialogButtonBox.Ok).clicked.connect(
                    lambda: self._read_test_data(shell, controller))
            self._test_data_picker.buttonBox.button(
                QtGui.QDialogButtonBox.Ok).clicked.connect(
                    self._test_data_picker.close)

            # Build module and theme context menu
            if controller._hub_title in ["Modules", "Assessment"]:

                menu = QtGui.QMenu()

                # Enable tooltips
                tips = lambda action: QtGui.QToolTip.showText(
                    QtGui.QCursor.pos(), action.toolTip(), menu,
                    menu.actionGeometry(action))
                menu.hovered.connect(tips)

                if controller._hub_title == "Modules":

                    # Can't reset or insepct unless the interface has executed
                    connector = _get_connector(shell.project, "modules")

                    active = connector.is_interface_completed(
                        shell.core, shell.project, controller._title)

                    action = menu.addAction('Inspect',
                                            lambda: controller._inspect(shell))
                    action.setToolTip('Inspect results following '
                                      'execution of this module')
                    action.setEnabled(active)

                    action = menu.addAction('Reset',
                                            lambda: controller._reset(shell))
                    action.setToolTip('Reset simulation prior to '
                                      'execution of this module')
                    action.setEnabled(active)

                menu.addAction('Load test data...',
                               self._test_data_picker.show)
                menu.exec_(self.treeView.mapToGlobal(position))

        elif isinstance(controller, OutputBranchControl):

            # Build module context menu
            if controller._hub_title == "Modules":

                menu = QtGui.QMenu()
                menu.addAction('Inspect', lambda: controller._inspect(shell))
                menu.exec_(self.treeView.mapToGlobal(position))

        return

    def _set_top_item(self):

        index = self._controls[0]._get_index_from_address()
        proxy_index = self._proxy.mapFromSource(index)
        self.treeView.clicked.emit(proxy_index)

        return

    def _read_auto(self, shell):

        self._tree.read_auto(shell.core, shell.project)

        return

    @QtCore.pyqtSlot(str)
    def _update_filter(self, text):

        search = QtCore.QRegExp(text, QtCore.Qt.CaseInsensitive,
                                QtCore.QRegExp.RegExp)

        self._proxy.setFilterRegExp(search)

        return

    @QtCore.pyqtSlot(str)
    def _repeat_filter(self):

        text = self.filterLineEdit.text()

        search = QtCore.QRegExp(text, QtCore.Qt.CaseInsensitive,
                                QtCore.QRegExp.RegExp)

        self._proxy.setFilterRegExp(search)

        return

    @QtCore.pyqtSlot()
    def _clear_filter(self):

        self.filterLineEdit.clear()
        self._update_filter("")

        return

    @QtCore.pyqtSlot(object, object)
    def _read_test_data(self, shell, controller):

        if shell._active_thread is not None: shell._active_thread.wait()

        shell.read_test_data(controller,
                             str(self._test_data_picker.pathLineEdit.text()),
                             self._test_data_picker.overwriteBox.isChecked())

        shell._active_thread.error_detected.connect(self._emit_error)

        return

    @QtCore.pyqtSlot(object, object, object)
    def _emit_error(self, etype, evalue, etraceback):

        self.error_detected.emit(etype, evalue, etraceback)

        return