pyqt骚操作之使用print

今天学习opencv和pyqt的结合,从国外一篇博客看到可以使用print函数,直接在pyqt控件上输出。觉得很有意思,仔细研究了一下原理,发现其实也不是很难。

思想

当我们调用print函数,比如

print("hello")

其实调用了

sys.stdout.write()
sys.stdout.flush()

因此,希望print输出到一个控件上,在上面两个函数上进行重写即可。

例1

我们直接改写sys.stdout下的write和flush函数即可

import sys
from PyQt5.QtWidgets import QApplication, QMainWindow, QTextEdit, QWidget


class MyWindow(QMainWindow):
    def __init__(self, parent=None):
        # ------------------------------
        # Set the UI
        QMainWindow.__init__(self, parent)
        self.central = QWidget(self)
        self.textbox = QTextEdit(self.central)
        self.textbox.setMinimumSize(300, 100)
        self.setCentralWidget(self.central)

        # ------------------------------
        # Set print
        # 连接sys.stdout
        sys.stdout = self
        print("hello")
        print("world", end="")
        print(",every body")

    # ------------------------------
    #   sys.stdout模块下的write 和 flush在此重写
    def write(self, text):
        self.textbox.insertPlainText(text)

    def flush(self):
        pass


if __name__ == '__main__':
    app = QApplication(sys.argv)
    win = MyWindow()
    win.show()

    sys.exit(app.exec_())

# EOF

总结

直接改写子类中的write和flush函数,easy!

例2 使用信号与槽

使用信号机制,信号与槽的初高级玩法网上有不少介绍 ,使用这种方法,不用去担心它们在哪个线程。

import sys
from PyQt5.QtCore import pyqtSignal
from PyQt5.QtWidgets import QApplication, QMainWindow, QTextEdit, QWidget
from PyQt5.QtGui import QTextCursor


class MyWindow(QMainWindow):
    # 信号必须在此声明
    # 1.声明一个带str的信号
    text_update = pyqtSignal(str)

    # Create main window
    def __init__(self, parent=None):

        # ------------------------------
        # Set UI
        QMainWindow.__init__(self, parent)
        self.central = QWidget(self)
        self.textbox = QTextEdit(self.central)
        self.textbox.setMinimumSize(300, 100)
        self.setCentralWidget(self.central)

        # ------------------------------
        # 2.连接信号的槽函数,信号若发出,运行槽函数
        self.text_update.connect(self.append_text)
        # 3.连接sys.stdout
        sys.stdout = self
        print("hello")

    # ------------------------------
    # 4 sys.stdout模块下的write 和 flush在此重写
    #   用信号机制触发函数,操作控件
    def write(self, text):
        self.text_update.emit(str(text))

    def flush(self):
        pass

    # ------------------------------
    # 5.槽函数
    def append_text(self, text):
        cur = self.textbox.textCursor()  # Move cursor to end of text
        cur.movePosition(QTextCursor.End)
        s = str(text)
        while s:
            head, sep, s = s.partition("\n")  # Split line at LF
            cur.insertText(head)  # Insert text at cursor
            if sep:  # New line if LF
                cur.insertBlock()
        self.textbox.setTextCursor(cur)  # Update visible cursor


if __name__ == '__main__':
    app = QApplication(sys.argv)
    win = MyWindow()
    win.show()

    sys.exit(app.exec_())

# EOF

可见,print函数调用经过以下流程

print --> sys.stdout.write --> text_update.emit(text) --> append_text(text)

总结

例2步骤稍显麻烦,其实分两路:

一路是信号触发机制,信号触发时,调用控件修改函数

另一路是如何调整信号呢?在 sys.stdout的write和flush函数

参考

https://iosoft.blog/2019/07/31/rpi-camera-display-pyqt-opencv/

  • 1
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值