我正在尝试使用jedi在PyQt应用程序中完成python代码,使用QCompleter
和QStringListModel
来存储可能的完成。
这是一个简单的工作演示:
#!/usr/bin/env python3
from PyQt5.QtCore import *
from PyQt5.QtWidgets import *
import jedi
import sys
class JediEdit(QLineEdit):
def __init__(self, parent=None):
super().__init__(parent)
self._model = QStringListModel()
self._compl = QCompleter()
self._compl.setModel(self._model)
self.setCompleter(self._compl)
self.textEdited.connect(self.update_model)
def update_model(self, cur_text):
script = jedi.Script(cur_text)
compl = script.completions()
strings = list(cur_text + c.complete for c in compl)
self._model.setStringList(strings)
if __name__ == '__main__':
app = QApplication(sys.argv)
line = JediEdit()
line.show()
sys.exit(app.exec_())
如果您运行应用程序并编写未完成任何操作的代码(例如或
foo =
),则完成将实际显示可以进入该位置的所有可能令牌。
所以,如果我在字段中运行并写一个空格,会弹出很多东西,从abs
到__version__
。
我想阻止这种情况:是否可以查询jedi.Script
以了解令牌是否正在完成,或者是否有一个全新的令牌?
编辑:另一个小问题:说我正在运行一个与jedi当前状态分离的解释器。如何向jedi.Script
提供本地和全局变量,以便考虑那些而不是自己的完成?
答案 0 :(得分:1)
Jedi的自动完成将始终显示所有可能的令牌。这是自动完成的重点。
如果您不想要这种行为,只需扫描最后几个字符的空格和某些其他字符,如=
或:
,这将是一个非常简单的正则表达式命令。 (您也可以尝试查看Jedi的内部结构并使用Jedi对此背景的了解方式。但我不会告诉您,因为它不是公共API和IMHO正则表达式电话就够了。)
将来可能会出现类似的情况。 (见https://github.com/davidhalter/jedi/issues/253)。
现在我想到了,可能还有另一种方法可以试验:您可以尝试使用Completion.name
和Completion.complete
。后者只给你在当前令牌之后可能出现的内容,而名称将是完整的。所以你可以比较,如果它们相等,你可能不想显示任何东西。
玩API时玩得很开心: - )
如果您正在运行解释器,则可以使用jedi.Interpreter
将代码与实际的Python对象组合在一起。它非常灵活。但请注意,目前的口译员(0.8.1)非常错误。请使用Github(0.9.0)中的主分支。