自定义控件 QOpenGLWidget并实现缩放(纯代码)
QScrollArea+QOpenGLWidget 实现缩放,用于显示QImage。
先自定义QOpenGLWidget ,然后自定义QWidget(上图)
glwidget.h
#ifndef GLWIDGET_H #define GLWIDGET_H #include <QOpenGLWidget> class GLWidget : public QOpenGLWidget { Q_OBJECT public: explicit GLWidget(QWidget *parent = nullptr); void setImageData(const QImage& img); protected: //重写事件 void paintEvent(QPaintEvent* e) override; private: QImage mImg; }; #endif // GLWIDGET_H
glwidget.cpp
#include "glwidget.h" #include <QPainter> GLWidget::GLWidget(QWidget *parent) : QOpenGLWidget{parent} { } void GLWidget::setImageData(const QImage& img) { if (!img.isNull()) { mImg = img; update(); } } void GLWidget::paintEvent(QPaintEvent* e) { QPainter p; p.begin(this); p.drawImage(rect(), mImg); p.end(); }
viewwidget.h
#ifndef VIEWWIDGET_H #define VIEWWIDGET_H #include <QWidget> #include "glwidget.h" #include <QScrollArea> class ViewWidget : public QWidget { Q_OBJECT public: explicit ViewWidget(QWidget *parent = nullptr); signals: public: GLWidget *glWidget; QScrollArea *scrollArea; float scaleFactor; private slots: void buttonClicked(int id); }; #endif // VIEWWIDGET_H
viewwidget.cpp
#include "viewwidget.h" #include <QVBoxLayout> #include <QHBoxLayout> #include <QPushButton> #include <QButtonGroup> #pragma execution_character_set("utf-8") ViewWidget::ViewWidget(QWidget *parent) : QWidget{parent} ,glWidget{new GLWidget} ,scrollArea{new QScrollArea} { //! [1] //上下布局,上方为QOpenGLWidget,下方为3个按钮(放大、缩小、适应窗口) QVBoxLayout *centralLayout=new QVBoxLayout; setLayout(centralLayout); centralLayout->setSpacing(0); centralLayout->setMargin(0); centralLayout->addWidget(scrollArea); scrollArea->setBackgroundRole(QPalette::Dark); scrollArea->setWidgetResizable(true); scrollArea->setWidget(glWidget); //下方的3个按钮+1个弹簧,水平布局 QHBoxLayout* toolboxLayout = new QHBoxLayout; centralLayout->addLayout(toolboxLayout); toolboxLayout->setSpacing(0); toolboxLayout->setMargin(0); QPushButton* buttonPlus = new QPushButton(QIcon("://icons/zoom_in.png"), QString(""), this); buttonPlus->setMaximumWidth(32); toolboxLayout->addWidget(buttonPlus); QPushButton* buttonMinus = new QPushButton(QIcon("://icons/zoom_out.png"), QString(""), this); buttonMinus->setMaximumWidth(32); toolboxLayout->addWidget(buttonMinus); QPushButton* buttonFit = new QPushButton(QIcon("://icons/zoom_fit.png"), QString(""), this); buttonFit->setMaximumWidth(32); toolboxLayout->addWidget(buttonFit); toolboxLayout->addStretch(); //按钮组,方便多按钮调用一个函数 QButtonGroup *toolbox=new QButtonGroup; toolbox->addButton(buttonPlus, 0); toolbox->addButton(buttonMinus, 1); toolbox->addButton(buttonFit, 2); connect(toolbox, SIGNAL(buttonClicked(int)), this, SLOT(buttonClicked(int))); //! [1] //初始化缩放系数 scaleFactor = 1.0; } void ViewWidget::buttonClicked(int id) { switch (id) { case 0: //plus scaleFactor *= 1.25; glWidget->setFixedSize(scrollArea->width() * scaleFactor, scrollArea->height() * scaleFactor); break; case 1: //minus scaleFactor *= 0.8; glWidget->setFixedSize(scrollArea->width() * scaleFactor, scrollArea->height() * scaleFactor); break; case 2: //fit scaleFactor = 1.0; glWidget->setMinimumSize(0, 0); glWidget->setMaximumSize(QSize(QWIDGETSIZE_MAX, QWIDGETSIZE_MAX)); glWidget->resized(); break; default: break; } }
【参考】
QT学习笔记之QT代码编写控件不显示的问题 - sgggr - 博客园 (cnblogs.com)
【画圆、文字,以及随图缩放】
void GLWidget::paintEvent(QPaintEvent* e) { QPainter p; p.begin(this); p.drawImage(rect(), m_qImg); float factorX = 1.0*rect().width() / m_qImg.width(); float factorY = 1.0*rect().height() / m_qImg.height(); p.setFont(QFont("Arial", 14)); for (int i = 0; i < m_vCircle.length(); i++) { //画圆 int x = factorX*m_vCircle[i].x(); //矩形左上角 int y= factorY*m_vCircle[i].y(); p.drawEllipse(x + 50 * factorX / 2, y + 50 * factorY / 2, 50 * factorX, 50 * factorX); //在圆附近显示文字 QString txt = QString("清晰度:%1").arg(m_vSharpness[i]); p.drawText(QPointF(x + 50 * factorX / 2, y + 50 * factorY / 2), txt); } p.end(); }