问题描述
有没有办法让 QCompleter 的 pyside 工作更类似于 StackOverflow 上的标签编辑器的工作方式?用户可以在哪里输入单词,然后如果有空格,它允许自动完成显示匹配的单词?
这篇文章似乎符合我的要求,但它是用 C++ 编写的
导入操作系统导入系统导入json从 PySide 导入 QtCore、QtGui类 ExampleWindow(QtGui.QMainWindow):def __init__(self, parent=None):super(ExampleWindow, self).__init__(parent)self.resize(300, 200)self.strings_model = QtGui.QStringListModel()self.get_data(self.strings_model)完成者 = QtGui.QCompleter()completer.setCaseSensitivity(QtCore.Qt.CaseInsensitive)completer.setModel(self.strings_model)self.ui_input = QtGui.QLineEdit()self.ui_input.setCompleter(完成者)self.ui_input.setPlaceholderText('输入描述...')self.ui_tags_list = QtGui.QListView()self.ui_tags_list.setEditTriggers(QtGui.QAbstractItemView.NoEditTriggers)self.ui_tags_list.setSelectionMode(QtGui.QAbstractItemView.ExtendedSelection)self.ui_tags_list.setModel(self.strings_model)# 主要布局main_layout = QtGui.QVBoxLayout()main_layout.setContentsMargins(5,5,5,5)main_layout.setSpacing(5)main_layout.addWidget(self.ui_input)main_layout.addWidget(self.ui_tags_list)main_widget = QtGui.QWidget()main_widget.setLayout(main_layout)self.setCentralWidget(main_widget)# 连接self.ui_input.returnPressed.connect(self.input_entered)def get_data(自我,模型):model.setStringList(["Animals", "Dogs", "Birds", "Cats", "Elephant", "Zebra"])def append_tag(self, val):如果不是 val:返回错误如果 val.lower() 在 [x.lower() for x in self.strings_model.stringList()]:返回错误self.strings_model.insertRow(self.strings_model.rowCount())index = self.strings_model.index(self.strings_model.rowCount()-1)self.strings_model.setData(index, val)def input_entered(self):打印从下拉列表中选择的单词应添加到 lineEdit"定义主():app = QtGui.QApplication(sys.argv)ex = ExampleWindow()例如.show()sys.exit(app.exec_())如果 __name__ == '__main__':主要的()
你必须实现一个获取最后一个字符串的逻辑,这将是在 QComplete
到 中制作过滤器的词>setCompletionPrefix()
:
class LineEdit(QtGui.QLineEdit):def __init__(self, *args, **kwargs):QtGui.QLineEdit.__init__(self, *args, **kwargs)self.multipleCompleter = 无def keyPressEvent(self, event):QtGui.QLineEdit.keyPressEvent(self, event)如果不是 self.multipleCompleter:返回c = self.multipleCompleter如果 self.text() == "":返回c.setCompletionPrefix(self.cursorWord(self.text()))如果 len(c.completionPrefix())
Is there a way to make the QCompleter for pyside work more similar to how the Tag editor here on StackOverflow works? Where a user can type a word and then if there is a space it allows the autocomplete to display matching words?
This post seems like it does what i want but it's in C++How to force QCompleter to check second word in QLineEdit
import os
import sys
import json
from PySide import QtCore, QtGui
class ExampleWindow(QtGui.QMainWindow):
def __init__(self, parent=None):
super(ExampleWindow, self).__init__(parent)
self.resize(300, 200)
self.strings_model = QtGui.QStringListModel()
self.get_data(self.strings_model)
completer = QtGui.QCompleter()
completer.setCaseSensitivity(QtCore.Qt.CaseInsensitive)
completer.setModel(self.strings_model)
self.ui_input = QtGui.QLineEdit()
self.ui_input.setCompleter(completer)
self.ui_input.setPlaceholderText('enter description...')
self.ui_tags_list = QtGui.QListView()
self.ui_tags_list.setEditTriggers(QtGui.QAbstractItemView.NoEditTriggers)
self.ui_tags_list.setSelectionMode(QtGui.QAbstractItemView.ExtendedSelection)
self.ui_tags_list.setModel(self.strings_model)
# main layout
main_layout = QtGui.QVBoxLayout()
main_layout.setContentsMargins(5,5,5,5)
main_layout.setSpacing(5)
main_layout.addWidget(self.ui_input)
main_layout.addWidget(self.ui_tags_list)
main_widget = QtGui.QWidget()
main_widget.setLayout(main_layout)
self.setCentralWidget(main_widget)
# connections
self.ui_input.returnPressed.connect(self.input_entered)
def get_data(self, model):
model.setStringList(["Animals", "Dogs", "Birds", "Cats", "Elephant", "Zebra"])
def append_tag(self, val):
if not val:
return False
if val.lower() in [x.lower() for x in self.strings_model.stringList()]:
return False
self.strings_model.insertRow(self.strings_model.rowCount())
index = self.strings_model.index(self.strings_model.rowCount()-1)
self.strings_model.setData(index, val)
def input_entered(self):
print 'selected word from drop down should be added to lineEdit'
def main():
app = QtGui.QApplication(sys.argv)
ex = ExampleWindow()
ex.show()
sys.exit(app.exec_())
if __name__ == '__main__':
main()
You must implement a logic that gets the last string, this will be the word to make the filter in the QComplete
through setCompletionPrefix()
:
class LineEdit(QtGui.QLineEdit):
def __init__(self, *args, **kwargs):
QtGui.QLineEdit.__init__(self, *args, **kwargs)
self.multipleCompleter = None
def keyPressEvent(self, event):
QtGui.QLineEdit.keyPressEvent(self, event)
if not self.multipleCompleter:
return
c = self.multipleCompleter
if self.text() == "":
return
c.setCompletionPrefix(self.cursorWord(self.text()))
if len(c.completionPrefix()) < 1:
c.popup().hide()
return
c.complete()
def cursorWord(self, sentence):
p = sentence.rfind(" ")
if p == -1:
return sentence
return sentence[p + 1:]
def insertCompletion(self, text):
p = self.text().rfind(" ")
if p == -1:
self.setText(text)
else:
self.setText(self.text()[:p+1]+ text)
def setMultipleCompleter(self, completer):
self.multipleCompleter = completer
self.multipleCompleter.setWidget(self)
completer.activated.connect(self.insertCompletion)
def main():
app = QtGui.QApplication(sys.argv)
w = LineEdit()
completer = QtGui.QCompleter(["Animals", "Dogs", "Birds", "Cats", "Elephant", "Zebra"])
completer.setCaseSensitivity(QtCore.Qt.CaseInsensitive)
w.setMultipleCompleter(completer)
w.show()
sys.exit(app.exec_())
if __name__ == '__main__':
main()
这篇关于QCompleter 支持多个项目,如 stackoverflow 标签字段的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!