zoukankan      html  css  js  c++  java
  • 一个 Qt 显示图片的控件(继承QWidget,使用QPixmap记录图像,最后在paintEvent进行绘制,可缩放)

    Qt 中没有专门显示图片的控件,通常我们会使用QLabel来显示图片。但是QLabel 显示图片的能力还是有点弱。比如不支持图像的缩放一类的功能,使用起来不是很方便。因此我就自己写了个简单的类。

    我这个类支持三种图像显示模式,我分别称之为:FIXED_SIZE, CENTRED,AUTO_ZOOM, AUTO_SIZE。

    • FIXED_SIZE 模式下,显示的图像大小等于图像尺寸乘以缩放因子,如果控件的尺寸小于这个大小则多出的部分被裁切掉。
    • FIX_SIZE_CENTRED模式与FIXED_SIZE 模式类似,但是,显示的图像居于窗口正中。
    • AUTO_ZOOM 模式下,显示的图像大小自动适应控件窗口大小。
    • AUTO_SIZE 模式下,这个控件的尺寸等于图像尺寸乘以缩放因子。

    下面是代码:

    [cpp] view plain copy
     
    1. #ifndef PICTUREBOX_H  
    2. #define PICTUREBOX_H  
    3.   
    4. #include <QWidget>  
    5. #include <QImage>  
    6. #include <QPixmap>  
    7.   
    8.   
    9. class PictureBox : public QWidget  
    10. {      
    11.     Q_OBJECT  
    12. public:  
    13.     enum PB_MODE {FIXED_SIZE, FIX_SIZE_CENTRED, AUTO_ZOOM, AUTO_SIZE};  
    14.     explicit PictureBox(QWidget *parent = 0);  
    15.     void setMode(PB_MODE mode);  
    16.     ~PictureBox();  
    17. private:  
    18.     QPixmap m_pixmap;  
    19.     double m_scale;  
    20.     PB_MODE m_mode;  
    21.     QBrush m_brush;  
    22. protected:  
    23.     void paintEvent(QPaintEvent * event);  
    24. signals:  
    25.   
    26. public slots:  
    27.     bool setImage(QImage &image, double scale = 1.0);  
    28.     void setBackground(QBrush brush);  
    29. };  
    30.   
    31. #endif // PICTUREBOX_H  
    [cpp] view plain copy
     
    1. #include "picturebox.h"  
    2. #include <QPainter>  
    3. #include <QDebug>  
    4. static const int IMAGE_WIDTH = 160;  
    5. static const int IMAGE_HEIGHT = 120;  
    6. static const QSize IMAGE_SIZE = QSize(IMAGE_WIDTH, IMAGE_HEIGHT);  
    7.   
    8. PictureBox::PictureBox(QWidget *parent) : QWidget(parent)  
    9. {  
    10.     m_pixmap = QPixmap(IMAGE_SIZE);  
    11.     m_pixmap.fill();  
    12.     m_scale = 1.0;  
    13.     m_mode = FIXED_SIZE;  
    14.     m_brush = QBrush(Qt::white);  
    15. }  
    16.   
    17. void PictureBox::setBackground(QBrush brush)  
    18. {  
    19.     m_brush = brush;  
    20.     update();  
    21. }  
    22.   
    23. void PictureBox::setMode(PB_MODE mode)  
    24. {  
    25.     m_mode = mode;  
    26.     if(m_mode == AUTO_SIZE)  
    27.     {  
    28.         setFixedSize(m_pixmap.size() * m_scale);  
    29.     }  
    30.     else  
    31.     {  
    32.         setMaximumSize(QWIDGETSIZE_MAX, QWIDGETSIZE_MAX);  
    33.         setMinimumSize(0, 0);  
    34.     }  
    35.     update();  
    36. }  
    37.   
    38. bool PictureBox::setImage(QImage &image, double scale)  
    39. {  
    40.     if(image.isNull())  
    41.     {  
    42.         return false;  
    43.     }  
    44.     m_pixmap = QPixmap::fromImage(image);  
    45.     m_scale = qBound(0.01, scale, 100.0);  
    46.     if(m_mode == AUTO_SIZE)  
    47.     {  
    48.         setFixedSize(m_pixmap.size() * m_scale);  
    49.     }  
    50.     update();  
    51.     return true;  
    52. }  
    53.   
    54. void PictureBox::paintEvent(QPaintEvent * event)  
    55. {  
    56.     Q_UNUSED(event);  
    57.     QPainter painter(this);  
    58.     painter.setBackground(m_brush);  
    59.     painter.eraseRect(rect());  
    60.   
    61.     double window_width, window_height;  
    62.     double image_width, image_height;  
    63.     double r1, r2, r;  
    64.     int offset_x, offset_y;  
    65.     switch (m_mode)  
    66.     {  
    67.     case FIXED_SIZE:  
    68.     case AUTO_SIZE:  
    69.         painter.scale(m_scale, m_scale);  
    70.         painter.drawPixmap(0, 0, m_pixmap);  
    71.         break;  
    72.     case FIX_SIZE_CENTRED:  
    73.         window_width = width();  
    74.         window_height = height();  
    75.         image_width = m_pixmap.width();  
    76.         image_height = m_pixmap.height();  
    77.         offset_x = (window_width - m_scale * image_width) / 2;  
    78.         offset_y = (window_height - m_scale * image_height) / 2;  
    79.         painter.translate(offset_x, offset_y);  
    80.         painter.scale(m_scale, m_scale);  
    81.         painter.drawPixmap(0, 0, m_pixmap);  
    82.         break;  
    83.     case AUTO_ZOOM:  
    84.         window_width = width();  
    85.         window_height = height();  
    86.         image_width = m_pixmap.width();  
    87.         image_height = m_pixmap.height();  
    88.         r1 = window_width / image_width;  
    89.         r2 = window_height / image_height;  
    90.         r = qMin(r1, r2);  
    91.         offset_x = (window_width - r * image_width) / 2;  
    92.         offset_y = (window_height - r * image_height) / 2;  
    93.         painter.translate(offset_x, offset_y);  
    94.         painter.scale(r, r);  
    95.         painter.drawPixmap(0, 0, m_pixmap);  
    96.         break;  
    97.     }  
    98. }  
    99.   
    100. PictureBox::~PictureBox()  
    101. {  
    102.   
    103. }  

    AUTO_ZOOM 模式下显示例子如下:

    FIXED_SIZE 模式下的例子如下:

    FIX_SIZE_CENTRED 模式下的例子如下:

    http://blog.csdn.net/liyuanbhu/article/details/46687495

  • 相关阅读:
    【Azure 应用服务】由 Azure Functions runtime is unreachable 的错误消息推导出 ASYNC(异步)和 SYNC(同步)混用而引起ThreadPool耗尽问题
    【Azure API 管理】是否可以将Swagger 的API定义导入导Azure API Management中
    【Azure 应用服务】Azure Function 不能被触发
    【Azure 环境】Azure Key Vault (密钥保管库)中所保管的Keys, Secrets,Certificates是否可以实现数据粒度的权限控制呢?
    【Azure 事件中心】为应用程序网关(Application Gateway with WAF) 配置诊断日志,发送到事件中心
    【Azure 事件中心】azure-spring-cloud-stream-binder-eventhubs客户端组件问题, 实践消息非顺序可达
    【Azure API 管理】Azure API Management通过请求中的Path来限定其被访问的频率(如1秒一次)
    【Azure 环境】前端Web通过Azure AD获取Token时发生跨域问题(CORS Error)
    【Azure 应用服务】记一次Azure Spring Cloud 的部署错误 (az spring-cloud app deploy -g dev -s testdemo -n demo -p ./hellospring-0.0.1-SNAPSHOT.jar --->>> Failed to wait for deployment instances to be ready)
    【Azure 应用服务】App Service中抓取 Web Job 的 DUMP 办法
  • 原文地址:https://www.cnblogs.com/findumars/p/6546096.html
Copyright © 2011-2022 走看看