У меня есть программа на Python с PyQt, предназначенная для работы в Windows. Эта программа делает много операций и печатает много информации. Но поскольку я хочу заморозить его и не хочу, чтобы экран подсказки отображался, я хочу, чтобы вся эта информация отображалась в основном приложении в QTextEdit или так. Как я могу заставить программу работать, чтобы она получала выходные данные от интерпретатора и одновременно отображала ее на текстовом элементе, как это делается на реальном интерпретаторе?
Как захватить вывод интерпретатора Python и показать в текстовом виджете?
Ответ 1
Я предполагаю, что с "выходом из интерпретатора" вы имеете в виду вывод, записанный в консоль или окно терминала, например, вывод, полученный с помощью print()
.
Все выходные данные консоли, созданные Python, записываются в выходные потоки программы sys.stdout
(нормальный вывод) и sys.stderr
(вывод ошибок, например трассировки исключений). Это файловые объекты.
Вы можете заменить эти потоки своим файлоподобным объектом. Вся ваша пользовательская реализация должна предоставить функцию write(text)
. Предоставляя свою собственную реализацию, вы можете перенаправить весь вывод на ваш виджет:
class MyStream(object):
def write(self, text):
# Add text to a QTextEdit...
sys.stdout = MyStream()
sys.stderr = MyStream()
Если вам понадобится reset эти потоки, они по-прежнему доступны как sys.__stdout__
и sys.__stderr__
:
sys.stdout = sys.__stdout__
sys.stderr = sys.__stderr__
Обновление
Вот какой рабочий код для PyQt4. Сначала определите поток, который сообщает данные, записанные ему с сигналом Qt:
from PyQt4 import QtCore
class EmittingStream(QtCore.QObject):
textWritten = QtCore.pyqtSignal(str)
def write(self, text):
self.textWritten.emit(str(text))
Теперь в вашем графическом интерфейсе установите экземпляр этого потока в sys.stdout
и подключите сигнал textWritten
к слоту, который записывает текст в QTextEdit
:
# Within your main window class...
def __init__(self, parent=None, **kwargs):
# ...
# Install the custom output stream
sys.stdout = EmittingStream(textWritten=self.normalOutputWritten)
def __del__(self):
# Restore sys.stdout
sys.stdout = sys.__stdout__
def normalOutputWritten(self, text):
"""Append text to the QTextEdit."""
# Maybe QTextEdit.append() works as well, but this is how I do it:
cursor = self.textEdit.textCursor()
cursor.movePosition(QtGui.QTextCursor.End)
cursor.insertText(text)
self.textEdit.setTextCursor(cursor)
self.textEdit.ensureCursorVisible()
Ответ 2
Я предлагаю вам использовать библиотеку регистрации. http://docs.python.org/library/logging.html Вы можете написать свой собственный обработчик журналов для связи с QTextEdit. Вот хороший учебник, который поможет вам начать: http://pantburk.info/?blog=77
Ответ 3
К сожалению, пример не работает с PySide. Он дает следующую ошибку:
sys.stdout = EmittingStream(textWritten=self.write2Console)
AttributeError: 'textWritten()' is not a Qt property or a signal
Нам нужно сделать следующие изменения для работы с PySide:
sys.stdout = EmittingStream()
self.connect(sys.stdout,QtCore.SIGNAL('textWritten(QString)'),self.write2Console)
Ответ 4
Я разместил некоторое приложение для терминала для PySide на этом некоторое время назад Terminal как приложение в PySide. Если вы смотрите на PyQt, проверьте также PySide. Они в основном одни и те же, кроме лицензирования и несколько различий в синтаксисе.