我希望能够从我的python应用程序中调出一个交互式python终端.我的程序中的一些(但不是全部)变量需要暴露给解释器.
目前我使用子类和修改QPlainTextEdit并将所有"命令"路由到eval或exec,并在dict中跟踪单独的命名空间.然而,必须有一个更优雅和健壮的方式!怎么样?
这是一个做我想要的例子,但它是用IPython和pyGTK ... http://ipython.scipy.org/moin/Cookbook/EmbeddingInGTK
以下是我目前的情况.但是有太多的角落案例我可能错过了一些.这是非常慢,尝试一个大的打印循环...它必须是一个更简单,更少漏洞的方式,...我希望!
这个def runCommand(self)功能是理解我的问题的关键.理想情况下,我不想改进它,我宁愿用更简单,更聪明的东西来替换它的内容.
console.updateNamespace({'myVar1' : app, 'myVar2' : 1234})"main"中语句的功能也很重要.
import sys, os
import traceback
from PyQt4 import QtCore
from PyQt4 import QtGui
class Console(QtGui.QPlainTextEdit):
def __init__(self, prompt='$> ', startup_message='', parent=None):
QtGui.QPlainTextEdit.__init__(self, parent)
self.prompt = prompt
self.history = []
self.namespace = {}
self.construct = []
self.setGeometry(50, 75, 600, 400)
self.setWordWrapMode(QtGui.QTextOption.WrapAnywhere)
self.setUndoRedoEnabled(False)
self.document().setDefaultFont(QtGui.QFont("monospace", 10, QtGui.QFont.Normal))
self.showMessage(startup_message)
def updateNamespace(self, namespace):
self.namespace.update(namespace)
def showMessage(self, message):
self.appendPlainText(message)
self.newPrompt()
def newPrompt(self):
if …Run Code Online (Sandbox Code Playgroud) 我正在为我的实验室开发PyQt软件.在这个软件中,我正在加载不同类型的RAW并分析来自mySQL数据库的数据(通常是在数组中).
我想在Widget中集成一个Iython控制台,这样我就可以轻松地与这些数据进行交互.
我在使用Ipython 0.13时遇到了一些困难.
这是我已经拥有的(整个代码很长,所以我只显示包含小部件的部分,Ipython控制台和相应的导入行,如果你需要更多,请告诉我):
##I load everything useful to my application, including the following line
from IPython.frontend.qt.console.qtconsoleapp import IPythonQtConsoleApp
##then is my whole software
##here is a class containing the Graphical User Interface elements. A button call the following function. self.Shell_Widget is the widget containing the Ipython console, self.MainWindow is the application mainwindow
def EmbeddedIpython(self):
"""
This function should launch an Ipython console
"""
self.Shell_Widget = QtGui.QDockWidget(self.MainWindow) #Widget creation
self.MainWindow.addDockWidget(4,self.Shell_Widget)
self.Shell_Widget.setMinimumSize(400,420)
console = IPythonQtConsoleApp() #Console Creation
console.initialize()
console.start()
self.Shell_Widget.show() …Run Code Online (Sandbox Code Playgroud) 我希望在我的应用程序中使用RichJupyterWidget. 关于如何设置控制台,我似乎有两个选择:
QtInProcessKernelManager(如下)。在这种情况下,内核在执行不理想的代码时会阻塞,因为我希望用户运行的某些命令需要长达一分钟的时间。QtKernelManager(如本GitHub 示例中所示)创建作为子进程启动的普通 IPython 内核。在这种情况下,我无法将名称空间从主进程传递到内核,内核也无法与主应用程序通信。这两个都是要求。是否有可能在这里两全其美?我想要一个非阻塞控制台,它包含与我的主进程相同的命名空间,并且可以向主应用程序发送信号。waszil在此处的评论中提出了类似的问题。使用QThreadwithQtInProcessKernelManager是一种可能性,但我不确定我应该使用哪种方法。
from qtconsole.qt import QtGui
from qtconsole.rich_jupyter_widget import RichJupyterWidget
from qtconsole.inprocess import QtInProcessKernelManager
class ConsoleWidget(RichJupyterWidget):
def __init__(self, namespace={}, customBanner=None, *args, **kwargs):
super(ConsoleWidget, self).__init__(*args, **kwargs)
if customBanner is not None:
self.banner = customBanner
self.font_size = 6
self.kernel_manager = kernel_manager = QtInProcessKernelManager()
kernel_manager.start_kernel(show_banner=False)
kernel_manager.kernel.gui = 'qt'
self.kernel_client = kernel_client = self._kernel_manager.client()
kernel_client.start_channels()
self.push_vars(namespace)
def stop():
kernel_client.stop_channels()
kernel_manager.shutdown_kernel()
guisupport.get_app_qt().exit()
self.exit_requested.connect(stop) …Run Code Online (Sandbox Code Playgroud) 我正在尝试将一个iPython Qtconsole嵌入到PyQt5应用程序中.嵌入式控制台工作正常,但当我尝试退出应用程序时(通过单击"退出",使用Cmd-Q),Python进程挂起,我必须强制退出以解除旋转的死亡沙滩球.这是在OS X 10.10.2,Python 2.7.9,iPython 3.0.0和PyQt5 5.3.1上.有关如何正常戒烟的任何想法?
最小的例子,改编自iPython示例:
#!/usr/bin/env python
from PyQt5 import Qt
from internal_ipkernel import InternalIPKernel
class SimpleWindow(Qt.QWidget, InternalIPKernel):
def __init__(self, app):
Qt.QWidget.__init__(self)
self.app = app
self.add_widgets()
self.init_ipkernel('qt')
def add_widgets(self):
self.setGeometry(300, 300, 400, 70)
self.setWindowTitle('IPython in your app')
# Add simple buttons:
self.console = Qt.QPushButton('Qt Console', self)
self.console.setGeometry(10, 10, 100, 35)
self.console.clicked.connect(self.new_qt_console)
self.namespace = Qt.QPushButton('Namespace', self)
self.namespace.setGeometry(120, 10, 100, 35)
self.namespace.clicked.connect(self.print_namespace)
self.count_button = Qt.QPushButton('Count++', self)
self.count_button.setGeometry(230, 10, 80, 35)
self.count_button.clicked.connect(self.count)
# Quit and cleanup
self.quit_button = …Run Code Online (Sandbox Code Playgroud)