可以在不使用QCompleter的情况下具有类似QCompleter的外观



长话短说,我已经在列表中有需要显示的内容(对于qlineedit(。但是我需要在自动完成框中显示一些额外的信息,这弄乱了QCompleter,因为我使用它的setModel方法来更新它显示的内容(所以我放入setModel方法的附加信息与QCompleter的完成规则混淆了QCompleter(所以我需要在QLineEdit下面有一个类似QCompleter的显示。无论如何,我能做到这一点吗?

#The method TopProducts(text) -> returns a list of strings with the format 
#"manufacturer - model number - description" (picks three products based on the given text)
#in __init__ somewhere:
self.nameEdit = QLineEdit()
self.completer = QCompleter()
self.nameEdit.setCompleter(self.completer)
self.nameEdit.textEdited.connect(self.suggest)
self.model = QStringListModel()
def suggest(self,text):
    stringList = TopProducts(text)
    self.model.setStringList(stringList)
    self.completer.setModel(self.model)

合适的解决方案是创建一个自定义模型,该模型具有每个制造商的角色、型号和说明,因此您可以使用 QCompletercompletionRole 属性并仅按型号对其进行筛选。

默认情况下,将显示选定的角色文本,因此我们不会有这种不当行为,我们将覆盖pathFromIndex()以返回Qt::DisplayRole角色:

class ProductModel(QAbstractListModel):
    ManufacturerRole, ModelNumberRole, DescriptionRole = range(Qt.UserRole, Qt.UserRole + 3)
    def __init__(self, parent=None):
        QAbstractListModel.__init__(self, parent)
        self._products = []
    def addProduct(self, product):
        self.beginInsertRows(QModelIndex(), self.rowCount(), self.rowCount())
        self._products.append(product)
        self.endInsertRows()
    def removeProduct(self, model_number, manufacturer):
        selecteds = filter(lambda product: product['manufacturer'] == manufacturer and product["modelNumber"] == model_number, 
            self._products)
        for selected in selecteds:
            row = self._products.index(selected)
            self.beginRemoveRows(QModelIndex(), row, row)
            self._products.pop(row)
            self.endRemoveRows()
    def rowCount(self, parent=QModelIndex()):
        return len(self._products)
    def data(self, index, role=Qt.DisplayRole):
        if 0 <= index.row() < self.rowCount():
            product = self._products[index.row()]
            if role == ProductModel.ManufacturerRole:
                return product["manufacturer"]
            elif role == ProductModel.ModelNumberRole:
                return product["modelNumber"]
            elif role == ProductModel.DescriptionRole:
                return product["description"]
            elif role == Qt.DisplayRole:
                return "{} {} {}".format(*product.values())
class ProductCompler(QCompleter):
    def pathFromIndex(self, index):
        return index.data()
if __name__ == '__main__':
    app = QApplication(sys.argv)
    le = QLineEdit()
    completer = ProductCompler(le)
    le.setCompleter(completer)
    model = ProductModel()
    completer.setModel(model)
    completer.setCompletionRole(ProductModel.ModelNumberRole)
    model.addProduct({"manufacturer": "StarTech", "modelNumber": "STANDOFF122", "description": "description"})
    model.addProduct({"manufacturer": "StarTrek", "modelNumber": "STANDOFF111", "description": "description"})
    model.addProduct({"manufacturer": "StackOverFlow", "modelNumber": "STANDOFF100", "description": "description"})
    model.addProduct({"manufacturer": "StarTech", "modelNumber": "ABCSTANDOFF122", "description": "description"})
    model.addProduct({"manufacturer": "StarTrek", "modelNumber": "ABCSTANDOFF111", "description": "description"})
    model.addProduct({"manufacturer": "StackOverFlow", "modelNumber": "DFSTANDOFF100", "description": "description"})
    model.removeProduct("STANDOFF111", "StarTrek")
    le.show()
    sys.exit(app.exec_())

相关内容

  • 没有找到相关文章

最新更新