如何在 Qt 小部件中以 PreserveAspectFit 的比例显示图像

Posted

技术标签:

【中文标题】如何在 Qt 小部件中以 PreserveAspectFit 的比例显示图像【英文标题】:How to display image in ratio as PreserveAspectFit in Qt Widgets 【发布时间】:2021-11-09 23:07:54 【问题描述】:

在 qml 中,我可以简单地做到这一点

    Image 
        anchors.fill: parent
        source: "/path/to/coo/image"
        fillMode: Image.PreserveAspectFit
    

我不想使用 QML,因为它与 javascript 相关。我如何使用小部件来做到这一点?

我尝试使用 QLabel,但它没有设置纵横比或填充模式的选项。我想我可以手动缩放像素图,然后将其设置为 QLabel,但这不会像 QML 那样具有反应性(调整窗口大小时调整图像大小)。 Qt 中没有任何特定于图像的小部件来执行此操作吗?

【问题讨论】:

【参考方案1】:

你可以这样做:

QPixmap pixmap("background.png");
pixmap.scaled(pixmap.size(), Qt::KeepAspectRatio);

您可以根据需要操作大小值。如果你愿意,你可以捕捉像素图所在的 QLabel 的大小。

【讨论】:

【参考方案2】:

一种可能的解决方案是使用 QGraphicsView、QGraphicsScene 和 QGraphicsPixmapItem:

#include <QApplication>
#include <QGraphicsPixmapItem>
#include <QGraphicsView>
#include <QPixmap>

class Viewer: public QGraphicsView
public:
    Viewer(QWidget *parent = nullptr): QGraphicsView(parent)
        setScene(new QGraphicsScene(this));
        m_pixmapItem = scene()->addPixmap(QPixmap());
        setAlignment(Qt::AlignCenter);
    
    QPixmap pixmap() const
         return m_pixmapItem->pixmap();
    
    void setPixmap(const QPixmap &newPixmap)
        m_pixmapItem->setPixmap(newPixmap);
        fitInView(m_pixmapItem, Qt::KeepAspectRatio);
    
protected:
    void resizeEvent(QResizeEvent *event)
        QGraphicsView::resizeEvent(event);
        fitInView(m_pixmapItem, Qt::KeepAspectRatio);
    
private:
    QGraphicsPixmapItem *m_pixmapItem;
;

int main(int argc, char *argv[])

    QApplication a(argc, argv);

    QPixmap pixmap(100, 200);
    pixmap.fill(Qt::green);

    Viewer w;
    w.resize(640, 480);
    w.setPixmap(pixmap);
    w.show();

    return a.exec();

Python 版本:

from PyQt5.QtCore import Qt
from PyQt5.QtGui import QPixmap
from PyQt5.QtWidgets import QApplication, QGraphicsScene, QGraphicsView


class Viewer(QGraphicsView):
    def __init__(self, parent=None):
        super().__init__(parent)
        self.setScene(QGraphicsScene(self))
        self.m_pixmapItem = self.scene().addPixmap(QPixmap())
        self.setAlignment(Qt.AlignCenter)

    @property
    def pixmap(self):
        return self.m_pixmapItem.pixmap()

    @pixmap.setter
    def pixmap(self, newPixmap):
        self.m_pixmapItem.setPixmap(newPixmap)
        self.fitInView(self.m_pixmapItem, Qt.KeepAspectRatio)

    def resizeEvent(self, event):
        super().resizeEvent(event)
        self.fitInView(self.m_pixmapItem, Qt.KeepAspectRatio)


def main():
    import sys

    app = QApplication(sys.argv)

    pixmap = QPixmap(100, 200)
    pixmap.fill(Qt.green)

    w = Viewer()
    w.resize(640, 480)
    w.pixmap = pixmap
    w.show()

    sys.exit(app.exec_())


if __name__ == "__main__":
    main()
``

【讨论】:

以上是关于如何在 Qt 小部件中以 PreserveAspectFit 的比例显示图像的主要内容,如果未能解决你的问题,请参考以下文章

如何在另一个小部件更新qt中的相同内容后更新小部件内容

如何在 Qt 中保持小部件的纵横比?

如何关闭在提升的小部件中单击的按钮上的 qt 小部件 ui?

Qt:如何将类连接到自定义 Qt 设计器小部件

如何在 Qt 中将消息从子窗口小部件发送到父窗口?

如何在 Qt 中创建共享小部件的子目录?