Exemple #1
0
    def complete(self, content):
        if content is None:
            logging.debug('Content should not be None...')
            content = []

        # cache content
        self.content = content

        # make model
        if isinstance(content, QAbstractItemModel):
            model = content
        else:
            model = QStringListModel()
            model.setStringList([str(c) for c in content])

        self.model = model

        if self.empty:
            # no suggestion, hide
            self.hide_popup()
        else:
            #self.popup.setFocus()
            self._resize_popup()
            self.select_first_item()
            self.popup.show()
Exemple #2
0
    def update(self, result):
        if isinstance(result, QAbstractItemModel):
            model = result
        else:
            model = QStringListModel()
            model.setStringList([str(r) for r in result])

        self.setModel(model)
        self.setCompletionPrefix('')
        self.complete()
        first_index = self.popup().model().index(0, 0)
        self.popup().selectionModel().setCurrentIndex(
            first_index,
            QItemSelectionModel.Select | QItemSelectionModel.Rows
        )
        self.popup().scrollTo(first_index, QAbstractItemView.PositionAtCenter)
Exemple #3
0
class Suggest(QWidget):

    activated = pyqtSignal(QModelIndex)

    def __init__(self, parent):
        QObject.__init__(self, parent)
        self.editor = parent
        self.popup = None
        self.set_popup(CenterListView())
        self.content = None

    def set_popup(self, popup):
        if self.popup:
            self.popup.removeEventFilter(self)

        self.popup = popup
        popup.setWindowFlags(Qt.Popup)
        popup.setFocusPolicy(Qt.NoFocus)
        #popup.setFocusProxy(self.editor)
        popup.setMouseTracking(True)

        popup.installEventFilter(self)

        popup.clicked.connect(self.activated)
        self.activated.connect(popup.hide)

    def completionModel(self):
        return self.model

    def done(self, index):
        if index.isValid():
            self.activated.emit(index)

    def eventFilter(self, o, e):
        #if e.type() == QEvent.MouseButtonPress:
            ##self.popup.hide()
            #self.editor.setFocus()
            #return True

        if o == self.popup:
            if not self.popup.underMouse() and e.type() in (
                QEvent.MouseButtonPress,
                #QEvent.MouseButtonRelease,
                #QEvent.MouseButtonDblClick,
                #QEvent.MouseMove
            ):
                self.popup.hide()
                #self.editor.setFocus()
                #QApplication.sendEvent(self.editor, e)
                return False
            elif e.type() == QEvent.KeyPress:
                key = e.key()
                if e.key() == Qt.Key_Tab or e.key() == Qt.Key_J and e.modifiers() & Qt.ControlModifier:
                    ne = QKeyEvent(
                        QEvent.KeyPress,
                        Qt.Key_Down,
                        e.modifiers(),
                        ''
                    )
                    QApplication.sendEvent(o, ne)
                    return True
                elif e.key() == Qt.Key_Tab or e.key() == Qt.Key_K and e.modifiers() & Qt.ControlModifier:
                    ne = QKeyEvent(
                        QEvent.KeyPress,
                        Qt.Key_Up,
                        e.modifiers(),
                        e.text(),
                        e.isAutoRepeat(),
                        e.count()
                    )
                    QApplication.sendEvent(o, ne)
                    return True
                elif e.key() == Qt.Key_Up and self.attop:
                    ne = QKeyEvent(
                        QEvent.KeyPress,
                        Qt.Key_End,
                        Qt.ControlModifier
                    )
                    QApplication.sendEvent(o, ne)
                    return True
                elif e.key() == Qt.Key_Down and self.atbottom:
                    ne = QKeyEvent(
                        QEvent.KeyPress,
                        Qt.Key_Home,
                        Qt.ControlModifier
                    )
                    QApplication.sendEvent(o, ne)
                    return True
                elif key in (Qt.Key_Enter, Qt.Key_Return):
                    self.done(self.popup.currentIndex())
                    return True
                #elif key in (Qt.Key_Escape, ):
                    #self.editor.setFocus()
                    #self.popup.hide()
                    #return True
                #elif key in (
                    #Qt.Key_Home,
                    #Qt.Key_End,
                #):
                    #QApplication.sendEvent(self.editor, e)
                    #return True
                #elif key in (
                        #Qt.Key_Up,
                        #Qt.Key_Down,
                        #Qt.Key_Home,
                        #Qt.Key_End,
                        #Qt.Key_PageUp,
                        #Qt.Key_PageDown
                        #):
                    #pass
                else:
                    #self.editor.setFocus()
                    #self.editor.event(e)
                    #TODO: why HOME and END not processed by editor?
                    QApplication.sendEvent(self.editor, e)
                    #self.popup.hide()

        return self.super.eventFilter(o, e)

    @property
    def atbottom(self):
        p = self.popup
        return p.currentIndex().row() + 1 == p.model().rowCount(QModelIndex())

    @property
    def attop(self):
        return self.popup.currentIndex().row() == 0

    @property
    def popuped(self):
        return self.popup.isVisible()

    @property
    def super(self):
        return super(QWidget, self)

    @property
    def model(self):
        return self.popup.model() if self.popup else None

    @model.setter
    def model(self, value):
        self.popup.setModel(value)

    def hide_popup(self):
        self.popup.hide()

    def reset(self):
        """Reset model and hide popup."""
        self.model = QStringListModel()
        self.hide_popup()

    def select_first_item(self):
        first_index = self.popup.model().index(0, 0)
        self.popup.selectionModel().setCurrentIndex(
            first_index,
            QItemSelectionModel.Select | QItemSelectionModel.Rows
        )
        self.popup.scrollTo(first_index, QAbstractItemView.PositionAtCenter)

    def _resize_popup(self):
        h = sum([
            self.popup.sizeHintForRow(0) * min(MAX_ITEM, self.row_count),
            self.popup.contentsMargins().top(),
            self.popup.contentsMargins().bottom()
        ])
        self.popup.resize(self.editor.width(), h)
        #self.popup._adjust_popup_height()
        #hsb = self.popup.horizontalScrollBar()
        #if hsb and hsb.isVisible():
            #h += hsb.sizeHint().height()
        self.popup.move(self.editor.mapToGlobal(QPoint(0, self.editor.height())))

    @property
    def row_count(self):
        return self.model.rowCount(QModelIndex())

    @property
    def empty(self):
        return self.row_count == 0

    def complete(self, content):
        if content is None:
            logging.debug('Content should not be None...')
            content = []

        # cache content
        self.content = content

        # make model
        if isinstance(content, QAbstractItemModel):
            model = content
        else:
            model = QStringListModel()
            model.setStringList([str(c) for c in content])

        self.model = model

        if self.empty:
            # no suggestion, hide
            self.hide_popup()
        else:
            #self.popup.setFocus()
            self._resize_popup()
            self.select_first_item()
            self.popup.show()
            #self._continues_update()

    def _update_popup(self):
        model = self.model
        self.model = None
        self.model = model

    def _continues_update(self):
        if self.popuped:
            self._update_popup()
            QTimer.singleShot(1000, self._continues_update)
Exemple #4
0
 def reset(self):
     """Reset model and hide popup."""
     self.model = QStringListModel()
     self.hide_popup()