Notification.zip
大小:12.29KB
价格:30积分
下载量:0
评分:
5.0
上传者:u012959478
更新日期:2025-09-22

QT实现带动态弹出动画的自定义通知提示框

资源文件列表(大概)

文件名
大小
Notification/
-
Notification/main.cpp
172B
Notification/mainwindow.cpp
1.96KB
Notification/mainwindow.h
323B
Notification/mainwindow.ui
692B
Notification/notification.cpp
15.23KB
Notification/notification.h
2.97KB
Notification/Notification.pro
1.11KB
Notification/Notification.qrc
335B
Notification/skin/
-
Notification/skin/notification_close.png
343B
Notification/skin/notification_close_hover.png
338B
Notification/skin/type_error.png
664B
Notification/skin/type_information.png
743B
Notification/skin/type_success.png
807B
Notification/skin/type_warning.png
729B

资源内容介绍

Qt中经常会用到提示框,用于交互操作!QMessageBox是被大多数人用到的,用起来是很方便,但是控件类型、大小、布局、样式、往往不是开发者想要的。本实例实现的Notification控件,是一种悬浮在角落的通知提醒框
#include "notification.h"#include <QPainter>#include <QStyleOption>#include <QGraphicsDropShadowEffect>#include <QScrollBar>#include <QPropertyAnimation>#include <QApplication>#include <QScreen>static int nAppearTime = 200; // 出现的时间200msstatic int nDisappearTime = 200; // 消失的时间200msNotification::Notification(QObject *parent) : QObject(parent){ QWidget* pWidget = qobject_cast<QWidget*>(parent); if(pWidget == nullptr) throw std::runtime_error("parent of notification error!"); m_size = pWidget->size(); m_vecItem.reserve(30);}Notification::~Notification(){}void Notification::Push(NotifyType type, NotifyPosition pos, QString title, QString content, int nLive){ std::lock_guard<std::mutex> lck(m_vecMtx); NotificationItem* pItem = new NotificationItem(qobject_cast<QWidget*>(parent()), type, pos, title, content, nLive); connect(pItem, &NotificationItem::itemRemoved, this, &Notification::itemRemoved); int currentHeight = 0; int currentX = 0; if(pos == NotifyPosition::Pos_Top_Right) { currentX = m_size.width(); currentHeight = nMargin; } else if(pos == NotifyPosition::Pos_Top_Left) { currentX = -pItem->width(); currentHeight = nMargin; } else if(pos == NotifyPosition::Pos_Bottom_Left) { currentX = -pItem->width(); currentHeight = m_size.height() - nMargin - pItem->height(); } else { currentX = m_size.width(); currentHeight = m_size.height() - nMargin - pItem->height(); } for_each(m_vecItem.begin(), m_vecItem.end(), [&](NotificationItem* item) { if(item->GetPosType() == pos) { if(pos == NotifyPosition::Pos_Top_Right) { currentHeight += (item->height() + nMargin); } else if(pos == NotifyPosition::Pos_Top_Left) { currentHeight += (item->height() + nMargin); } else if(pos == NotifyPosition::Pos_Bottom_Left) { currentHeight -= (item->height() + nMargin); } else { currentHeight -= (item->height() + nMargin); } } }); pItem->move(currentX, currentHeight); m_vecItem.emplace_back(pItem); pItem->Show();}void Notification::itemRemoved(NotificationItem *pRemoved){ std::unique_lock<std::mutex> lck(m_vecMtx); int currentY = 0; bool bFirst = true; NotifyPosition pos = pRemoved->GetPosType(); for(auto itr = m_vecItem.begin(); itr != m_vecItem.end();) { if(*itr == pRemoved) { m_vecItem.erase(itr); break; } else ++itr; } for_each(m_vecItem.begin(), m_vecItem.end(), [&, pos, bFirst, currentY](NotificationItem* item) mutable { if(item->GetPosType() == pos) { if(bFirst) { if(pos == NotifyPosition::Pos_Top_Right) { currentY = nMargin; } else if(pos == NotifyPosition::Pos_Top_Left) { currentY = nMargin; } else if(pos == NotifyPosition::Pos_Bottom_Left) { currentY = m_size.height() - nMargin - item->height(); } else { currentY = m_size.height() - nMargin - item->height(); } bFirst = false; } else { if(item->IsAppearEnd()) { if(pos == NotifyPosition::Pos_Top_Right) { currentY += (item->height() + nMargin); } else if(pos == NotifyPosition::Pos_Top_Left) { currentY += (item->height() + nMargin); } else if(pos == NotifyPosition::Pos_Bottom_Left) { currentY -= (item->height() + nMargin); } else { currentY -= (item->height() + nMargin); } } } if(item->IsAppearEnd()) { QPropertyAnimation* pAnimation1 = new QPropertyAnimation(item, "geometry", this); pAnimation1->setDuration(nDisappearTime); pAnimation1->setStartValue(QRect(item->pos().x(), item->pos().y(), item->width(), item->height())); pAnimation1->setEndValue(QRect(item->pos().x(), currentY, item->width(), item->height())); pAnimation1->start(QAbstractAnimation::DeletionPolicy::DeleteWhenStopped); } } });}///////////////////////////////////////////////////////////////NotificationItem::NotificationItem(QWidget *parent, NotifyType type, NotifyPosition pos, QString title, QString content, int nLife) : QWidget(parent), m_enPos(pos), m_bAppearEnd(false){ setObjectName(QStringLiteral("notification_item")); QLabel* pTitle = new QLabel(title, this); pTitle->setObjectName(QStringLiteral("label_title")); NotificationLabel* pContent = new NotificationLabel(this, nFixedWidth - 10, content); QFont font; font.setPointSize(11); font.setFamily(QStringLiteral("Microsoft Yahei")); pContent->setFont(font); QPushButton* pClose = new QPushButton(this); pClose->setFixedSize(16, 16); pClose->setObjectName(QStringLiteral("btn_close")); pClose->setCursor(QCursor(Qt::PointingHandCursor)); setStyleSheet(QStringLiteral("QWidget#notification_item{border:none;border-radius:8px;background-color:white;}" "QLabel#label_title{border:none;background-color:white;font-family:Microsoft Yahei;font-size:20px;font-weight:700;color:#303133;}" "QPushButton#btn_close{border:none;background-color:white;background-position:center;border-image:url(:/skin/notification_close.png);}" "QPushButton:hover#btn_close{border-image:url(:/skin/notification_close_hover.png);}")); // 标题设置 pTitle->setAlignment(Qt::AlignLeft | Qt::AlignTop); QFontMetrics fontWidth(pTitle->font()); QString elideNote = fontWidth.elidedText(pTitle->text(), Qt::ElideRight, 120); pTitle->setText(elideNote); pTitle->setToolTip(title); pTitle->adjustSize(); // 内容设置 pContent->Adjust(); // 布局 if(type != NotifyType::Notify_Type_None) { QLabel* pIcon = new QLabel(this); pIcon->setStyleSheet(QStringLiteral("QLabel{border:none;background-color:white;}")); if(type == NotifyType::Notify_Type_Success) { pIcon->setPixmap(QPixmap(":/skin/type_success.png")); } else if(type == NotifyType::Notify_Type_Error) { pIcon->setPixmap(QPixmap(":/s

用户评论 (0)

发表评论

captcha

相关资源

等价类划分方法等价类划分法 是一种基于规格说明的测试,经典的软件测试技术之一,属于黑盒测试的技术范畴 等价类划分法只

等价类划分法 是一种基于规格说明的测试,经典的软件测试技术之一,属于黑盒测试的技术范畴。 等价类划分法只是根据软件或程序的功能规格说明(需求)来进行测试用例设计,并对输入要求和输出要求做出不同的对待与处理。 等价类划分法在测试实践中的应用极其广泛,可用于任何测试级别,如组件测试、集成测试、系统测试和验收测试,只要被测试对象的输入和输出参数可以根据规格说明进行等价类的划分,都能运用这项测试技术。

2.26MB10积分

NLP-机器学习文本分类源代码+数据集

建立基于Logistics Regression算法的文本分类模型,其完整流程包括:数据预处理、特征工程、构建分类器、最优参数选择、模型评估与保存等。

2.36MB27积分

SPI通信协议(包含主机发送从机接收)及其验证(Verilog)

使用Verilog代码,本次代码采用SPI的工作模式为CPOL=1,CPHA=1(即在总线空闲时为高电平,在上升沿采样)SPI_M_transmitter.v为主机发送模块SPI_S_receive.v为从机接收模块SPI_MT_SR.v为调用收发模块,以便进行验证SPI_MT_SR_TB.v为验证模块,验证了收发数据,及来连续收发数据注意:本代码近用于学习熟悉SPI协议,无法工程应用或不完善,由于时间关系,逐步完善注释与pdf文档

2.26KB45积分

职场人摸鱼神器,背景动态可调的阅读器

优点:可以动态根据背景的图层进行屏幕取色,并设置阅读器的背景色和字体颜色、字体大小等,各种老板键也是十分方便适用人群:非常适合办公室的人放在文档或者IDE的一角处,没事看看小说或者看备考书籍,十分隐蔽,我已经用了两个多月了

1.62MB35积分