用Python(PyQt)创建二维码

用Python(PyQt)创建二维码,python,pyqt,python-imaging-library,qr-code,qpixmap,Python,Pyqt,Python Imaging Library,Qr Code,Qpixmap,我目前正在使用PyQt4和 正如您所见,在屏幕上显示图像之前,有几个障碍需要克服。QR码从RGBA PIL图像开始,转换为RGB,然后转换为PIL ImageQt对象,然后转换为QPixmap,然后将其放置在具有缩放固定的QLabel上 如果您没有显式地存储imgQt引用,那么在加载小部件时就会收到垃圾 我的问题:我能做些什么来改进这一点吗,因为似乎涉及到这么多转换。从qrcode文档中,您可以创建自己的图像工厂,这可能会让您简化流程 您只需要对qrcode.image.base.BaseIma

我目前正在使用PyQt4和

正如您所见,在屏幕上显示图像之前,有几个障碍需要克服。QR码从RGBA PIL图像开始,转换为RGB,然后转换为PIL ImageQt对象,然后转换为QPixmap,然后将其放置在具有缩放固定的QLabel上

如果您没有显式地存储imgQt引用,那么在加载小部件时就会收到垃圾


我的问题:我能做些什么来改进这一点吗,因为似乎涉及到这么多转换。

从qrcode文档中,您可以创建自己的
图像工厂
,这可能会让您简化流程

您只需要对
qrcode.image.base.BaseImage
进行子类化,然后重新实现
new\u image
drawrect
save
方法。这个子类可以包装一个QImage,因此不需要PIL转换步骤

更新

下面是一个消除PIL依赖性的演示(这也很好,因为我发现某些输入会导致PIL崩溃):


您还可以使用PNG作为中间格式,并使用StringIO将其存储在内存中

import qrcode
import StringIO

def set_qr_label(label, text):
    """
    set qrcode image on QLabel

    @param label: QLabel
    @param text: text for the QR code
    """
    buf = StringIO.StringIO()
    img = qrcode.make(text)
    img.save(buf, "PNG")
    label.setText("")
    qt_pixmap = QtGui.QPixmap()
    qt_pixmap.loadFromData(buf.getvalue(), "PNG")
    label.setPixmap(qt_pixmap)

mgmax给出了很好的答案,但仅限于Python2。对于Python3,请使用:

import qrcode
from io import BytesIO

def set_qr_label(label, text):
    """
    set qrcode image on QLabel

    @param label: QLabel
    @param text: text for the QR code
    """
    buf = BytesIO()
    img = qrcode.make(text)
    img.save(buf, "PNG")
    label.setText("")
    qt_pixmap = QtGui.QPixmap()
    qt_pixmap.loadFromData(buf.getvalue(), "PNG")
    label.setPixmap(qt_pixmap)

这是ekhumoro在python3的pyqt5中工作的答案 希望它能帮助其他人

from PyQt5 import QtWidgets, QtCore, QtGui
import qrcode

class Image(qrcode.image.base.BaseImage):
    def __init__(self, border, width, box_size):
        self.border = border
        self.width = width
        self.box_size = box_size
        size = (width + border * 2) * box_size
        self._image = QtGui.QImage(
            size, size, QtGui.QImage.Format_RGB16)
        self._image.fill(QtCore.Qt.white)

    def pixmap(self):
        return QtGui.QPixmap.fromImage(self._image)

    def drawrect(self, row, col):
        painter = QtGui.QPainter(self._image)
        painter.fillRect(
            (col + self.border) * self.box_size,
            (row + self.border) * self.box_size,
            self.box_size, self.box_size,
            QtCore.Qt.black)

    def save(self, stream, kind=None):
        pass

class Window(QtWidgets.QWidget):
    def __init__(self):
        QtWidgets.QWidget.__init__(self)
        self.label = QtWidgets.QLabel(self)
        self.edit = QtWidgets.QLineEdit(self)
        self.edit.returnPressed.connect(self.handleTextEntered)
        layout = QtWidgets.QVBoxLayout(self)
        layout.addWidget(self.label)
        layout.addWidget(self.edit)

    def handleTextEntered(self):
        text = self.edit.text()#text = unicode(self.edit.text())
        self.label.setPixmap(
            qrcode.make(text, image_factory=Image).pixmap())

if __name__ == '__main__':

    import sys
    app = QtWidgets.QApplication(sys.argv)
    window = Window()
    window.setGeometry(500, 300, 200, 200)
    window.show()
    sys.exit(app.exec_())


不要提及用户名,插入该用户对python2的答案的链接。虽然这段代码可以解决这个问题,但如何以及为什么解决这个问题将真正有助于提高您的帖子质量,并可能导致更多的投票。请记住,你是在将来回答读者的问题,而不仅仅是现在提问的人。请在回答中添加解释,并说明适用的限制和假设。
import qrcode
from io import BytesIO

def set_qr_label(label, text):
    """
    set qrcode image on QLabel

    @param label: QLabel
    @param text: text for the QR code
    """
    buf = BytesIO()
    img = qrcode.make(text)
    img.save(buf, "PNG")
    label.setText("")
    qt_pixmap = QtGui.QPixmap()
    qt_pixmap.loadFromData(buf.getvalue(), "PNG")
    label.setPixmap(qt_pixmap)
from PyQt5 import QtWidgets, QtCore, QtGui
import qrcode

class Image(qrcode.image.base.BaseImage):
    def __init__(self, border, width, box_size):
        self.border = border
        self.width = width
        self.box_size = box_size
        size = (width + border * 2) * box_size
        self._image = QtGui.QImage(
            size, size, QtGui.QImage.Format_RGB16)
        self._image.fill(QtCore.Qt.white)

    def pixmap(self):
        return QtGui.QPixmap.fromImage(self._image)

    def drawrect(self, row, col):
        painter = QtGui.QPainter(self._image)
        painter.fillRect(
            (col + self.border) * self.box_size,
            (row + self.border) * self.box_size,
            self.box_size, self.box_size,
            QtCore.Qt.black)

    def save(self, stream, kind=None):
        pass

class Window(QtWidgets.QWidget):
    def __init__(self):
        QtWidgets.QWidget.__init__(self)
        self.label = QtWidgets.QLabel(self)
        self.edit = QtWidgets.QLineEdit(self)
        self.edit.returnPressed.connect(self.handleTextEntered)
        layout = QtWidgets.QVBoxLayout(self)
        layout.addWidget(self.label)
        layout.addWidget(self.edit)

    def handleTextEntered(self):
        text = self.edit.text()#text = unicode(self.edit.text())
        self.label.setPixmap(
            qrcode.make(text, image_factory=Image).pixmap())

if __name__ == '__main__':

    import sys
    app = QtWidgets.QApplication(sys.argv)
    window = Window()
    window.setGeometry(500, 300, 200, 200)
    window.show()
    sys.exit(app.exec_())