如何使用 pixmap 和 Qlabel 使图像可选择?

Posted

技术标签:

【中文标题】如何使用 pixmap 和 Qlabel 使图像可选择?【英文标题】:How to make an image selectable using pixmap and Qlabel? 【发布时间】:2021-11-07 04:16:45 【问题描述】:

我正在尝试使用Pyqt5 显示多个图像。最好在 GUI 中使图像可选择,以便用户可以立即轻松地选择和复制该图像。

“可选择”是指用户可以右键单击图像,然后将其复制,然后可能将其粘贴到 GUI 之外的其他位置。就像保存在 Word 中的普通图像一样。用户可以在 Word 中选择/复制图像,然后将其粘贴到其他位置。

我知道Qlabel 中的文本可以通过使用self.my_label.setTextInteractionFlags(QtCore.Qt.TextSelectableByMouse) 轻松实现。但是,对于图像,似乎没有这样的方法来处理它。有什么办法可以解决图片问题?

import sys
import PyQt5
from PyQt5.QtWidgets import (
    QLabel,
    QVBoxLayout,
    QWidget
)
from PyQt5 import QtCore
from PyQt5.QtGui import QPixmap
from PyQt5.QtCore import QSize


class Display_Window(QWidget):
    def __init__(self):
        super().__init__()
        self.setMinimumSize(QSize(980,700))
        self.layout = QVBoxLayout(self)
        self.label1 = QLabel(self)
        self.pixmap = QPixmap(path_to_my_image)
        self.pixmap = self.pixmap.scaled(900, 900, QtCore.Qt.KeepAspectRatio)
        self.label1.setPixmap(self.pixmap)
        self.label1.resize(self.pixmap.width(), self.pixmap.height())



# Run if Script
if __name__ == "__main__":
    app = PyQt5.QtWidgets.QApplication(sys.argv)
    MainWindow = Display_Window()                                                   # Initialize GUI
    MainWindow.show()                                                                       # Show Window
    app.exec_()      

【问题讨论】:

你能解释一下你所说的“可选择”是什么意思吗?您想用鼠标选择图像的部分吗? 谢谢@musicamante。可选择的意思是用户可以右键单击图像,然后将其复制,然后可能将其粘贴到 GUI 之外的其他位置。就像保存在 Word 中的普通图像一样。 【参考方案1】:

只要标签具有有效的像素图,您就可以对标签进行子类化并创建一个菜单,然后使用系统剪贴板复制它。

class CopiableLabel(QLabel):
    def contextMenuEvent(self, event):
        pixmap = self.pixmap()
        if not pixmap.isNull():
            menu = QMenu()
            copyAction = menu.addAction('Copy image to clipboard')
            if menu.exec_(event.globalPos()) == copyAction:
                QApplication.clipboard().setPixmap(pixmap)
            return
        super().contextMenuEvent(event)


class Display_Window(QWidget):
    def __init__(self):
        super().__init__()
        self.layout = QVBoxLayout(self)
        self.label1 = CopiableLabel(self)
        self.layout.addWidget(self.label1)
        self.pixmap = QPixmap(path_to_my_image)
        self.pixmap = self.pixmap.scaled(900, 900, Qt.KeepAspectRatio)
        self.label1.setPixmap(self.pixmap)

请注意,在 QLabel 上设置像素图会自动调整其大小(除非将 scaledContents 属性设置为 True。 您还应该将标签添加到布局中,就像我在上述修改中所做的那样。

【讨论】:

谢谢。这完美地工作。我有点惊讶,虽然对于图像这必须创建一个子类来实现,而对于文本它只是一行代码。 @whj123 QLabel 是一个非常基本的小部件,它提供了预期的标准 功能。对于文本控件,选择/复制菜单操作几乎在任何地方都是标准的:用户期望可以复制用户界面中的可选文本。图像是不同的,因为它们可以用于许多不同的目的,所以没有关于它们在 UI 环境中的行为的“约定”。提供很多可能性对于一个工具包来说是没有意义的,只提供一个是没用的,而且考虑到这很容易实现,所以不需要 API。 感谢您的解释!

以上是关于如何使用 pixmap 和 Qlabel 使图像可选择?的主要内容,如果未能解决你的问题,请参考以下文章

从 QLabel 获取 QPixmap

使用 QPainter 和 paintEvent 在 PYQT5 中的 QLabel 中包含的 Pixmap 上绘制圆圈

QLabel 在图像上的映射位置

混淆QLabel和QPixmap

qt编程为什么不能显示图片:qt 为了让QLabel显示图片,用如下语句:

Qt 之 QPixmap