当前位置: 首页 > news >正文

解决Qt重绘事件中进行了耗时的图片操作导致卡顿问题

先简单描述一下我出现的问题,我是在写一个聊天界面,然后对于图片消息来说,一旦图片比较大时,滑动聊天界面就会出现了明显卡顿情况,原因是和我在写这个ImageMessage时直接在paintEvent中就进行了耗时的图片操作,也是我对于重绘事件的不够了解导致的
在c++ - Stabilize QWidget::paintEvent() calls frequency - Stack Overflow

QWidget Class | Qt Widgets | Qt 6.9.1中可以看到.大致告诉我们在paintEvent中不要进行一些其他的操作,他只负责绘制.

image-20250823102156915

我这个MessageImage就是左下角这个长矩形,有点难度的地方在这个如何计算图片放置的位置,需要用到父元素来计算,我在解决卡顿时把updateUi从paintEvent直接提出来就出现了父元素为NULL,因为我使用MessageImage没有直接传父元素给构造函数,而是先创建在放入layout中,也就导致了更新ui时出现父元素为空的情况,然后我采用的是新增一个字段表示是否完成ui更新,updateUI将state设置为false__updateUi在父元素为空时会直接返回没有更新图片和state,然后让showEvent去再判断是否成功了,没成功再执行 一次 updateUi,这样就将原本卡顿的显示解决了.

class MessageImage : public QWidget {Q_OBJECT
public:MessageImage(const QString& fileId,const QByteArray& content, bool isLeft);void updateUI(const QString& fileId, const QByteArray& content);protected:void paintEvent(QPaintEvent* event) override;void showEvent(QShowEvent* event) override;
private:void __updateUi();
private:QPushButton* image;QString fileId;QPixmap image_pixmap;bool isLeft;bool state; // 0 -- 未更新 
};
//==========================================================================================
MessageImage::MessageImage(const QString& fileId, const QByteArray& content, bool isLeft):isLeft(isLeft),fileId(fileId),state(false)
{this->setSizePolicy(QSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding));this->setStyleSheet("QPushButton{border:none;} QWidget{background-color:red}");image = new QPushButton(this);if (content.isEmpty()) {model::DataCenter* dataCenter = model::DataCenter::getInstance();connect(dataCenter, &model::DataCenter::getSingleFileDone, this,&MessageImage::updateUI,Qt::UniqueConnection);dataCenter->getSingleFileAsync(fileId);}else {updateUI(fileId, content);}
}
void MessageImage::updateUI(const QString& fileId, const QByteArray& content)
{if (this->fileId.isEmpty() || content.isEmpty()) {return;}this->fileId = fileId;__scaledImageToWidth(content, image_pixmap);this->state = false;__updateUi();this->update();}
void MessageImage::showEvent(QShowEvent* event)
{QWidget::showEvent(event);if (!state) {__updateUi();  }
}
void MessageImage::paintEvent(QPaintEvent* event)
{Q_UNUSED(event);QWidget::paintEvent(event);
}
void __scaledImageToWidth(const QByteArray& body,__out QPixmap& pixmap) {pixmap.loadFromData(body);pixmap = pixmap.scaledToWidth(120, Qt::SmoothTransformation);
}
void MessageImage::__updateUi() {QObject* obj = this->parent();if (obj == nullptr || !obj->isWidgetType()) {return;}QWidget* parent = dynamic_cast<QWidget*> (obj);if (image_pixmap.isNull()) {image_pixmap.load(":/resource/images/xiaoju.jpg");}QRect r = image_pixmap.rect();qDebug() << "image rect " << r;parent->setMinimumHeight(r.height() + 30);image->setIconSize(QSize(r.width(), r.height()));image->setIcon(QIcon(image_pixmap));if (isLeft) {image->setGeometry(0, 0, r.width(), r.height());}else {image->setGeometry(parent->width() - r.width() - 65, 0, r.width(), r.height());}this->state = true;
}
http://www.sczhlp.com/news/30363/

相关文章:

  • 青岛响应式网站建设nba排名最新
  • 网站建设福州新营销模式有哪些
  • 做淘宝详情页的网站服务推广软文
  • 杠杆 止盈 对冲
  • 上饶市住房和城乡建设网站关键词什么意思
  • 什么网站百度收录好网络营销组合策略
  • 备案之后怎样把 放到网站上百度知道官网登录入口
  • 做app还是网站如何提升网站搜索排名
  • 使用QQ做网站客服电话销售怎么找客户渠道
  • 寄生虫网站排名代做友情链接
  • 用手机做免费自助网站seo数据优化教程
  • 做零食的网站西安网站外包
  • 稷山做网站百度开户联系方式
  • 做php网站前端价格91关键词排名
  • 中山门户网站制作在哪里买网站建设与维护
  • 宝坻网站建设软文的概念是什么
  • 政府网站建设运维可口可乐营销策划方案
  • 自己给网站做logo客服系统网页源码2022免费
  • 怎么在门户网站上发布网店代运营十大排名
  • 广州 网站制作我是做推广的怎么找客户
  • 网站建设哪里最好数字化营销怎么做
  • 网站制作技术有哪些广州信息流推广公司
  • 个人网站可以做咨询吗磁力帝
  • 厦门网站设计公司推荐旅游网站网页设计
  • JBoltAI的AI-Chat:生成式AI大模型的无缝对接与多样化应用 - 那年-冬季
  • 网站建设站点无法发布最近的头条新闻
  • 邯郸网站优化公司什么是企业营销型网站
  • 精品网站制作公司买了500元黑科技引流靠谱吗
  • wordpress 所有标签页六年级上册数学优化设计答案
  • 文章类型的网站模版sem推广计划