Skip to content

Instantly share code, notes, and snippets.

@ialexpovad
Created June 2, 2023 08:47
Show Gist options
  • Save ialexpovad/4ff08002b37f2d0883ab2f36ee5978b2 to your computer and use it in GitHub Desktop.
Save ialexpovad/4ff08002b37f2d0883ab2f36ee5978b2 to your computer and use it in GitHub Desktop.
#include "notify.h"
#include <QPixmapCache>
#include <QApplication>
#include <QDesktopWidget>
#include <QPainter>
#include <QTimer>
Notify::Notify(QWidget* parent) :
QWidget(parent)
{
QPixmapCache::insert("success.png", QPixmap(":/success.png").scaledToHeight(80, Qt::SmoothTransformation));
QPixmapCache::insert("error.png", QPixmap(":/error.png").scaledToHeight(80, Qt::SmoothTransformation));
QPixmapCache::insert("warning.png", QPixmap(":/warning.png").scaledToHeight(80, Qt::SmoothTransformation));
animation = new QPropertyAnimation(this, "geometry");
connect(animation, SIGNAL(finished()), SLOT(onFinished()));
// defaults
w = 300;
x = qApp->desktop()->availableGeometry().width() - (w + 50);
y = 50;
setGeometry(x, y, w, 100);
showingNow = false;
}
Notify::~Notify()
{
QPixmapCache::clear();
}
void Notify::setPosition(QPoint p)
{
x = p.x();
y = p.y();
setGeometry(x, y, w, 100);
repaint();
}
void Notify::setDialogWidth(int width)
{
w = width;
setGeometry(x, y, w, 100);
repaint();
}
void Notify::adjustInViewport()
{
x = qApp->desktop()->availableGeometry().width() - (w + 50);
y = 50;
}
void Notify::notify(QString text, NotificationType type, int duration)
{
msgText = text;
notifType = type;
keepDuration = duration;
repaint();
animation->setDuration(500);
animation->setStartValue(QRect(x, -100, w, 100));
animation->setEndValue(QRect(x, y, w, 100));
showingNow = true;
animation->start();
show();
}
void Notify::onFinished()
{
if (showingNow) {
animation->setStartValue(QRect(x, y, w, 100));
animation->setEndValue(QRect(x, -100, w, 100));
QTimer::singleShot(keepDuration, animation, SLOT(start()));
showingNow = false;
}
else {
showingNow = false;
hide();
}
}
void Notify::paintEvent(QPaintEvent*)
{
QPainter painter(this);
painter.setRenderHints(QPainter::HighQualityAntialiasing | QPainter::Qt4CompatiblePainting);
painter.setBrush(Qt::white);
painter.setPen(Qt::NoPen);
painter.drawRoundedRect(0, 0, width(), height(), 5.0, 5.0);
QString key;
if (notifType == Notify::SUCCESS) {
key = "success.png";
}
else if (notifType == Notify::ERROR) {
key = "error.png";
}
else if (notifType == Notify::WARNING) {
key = "warning.png";
}
int proposedCoord = height() / 2 - QPixmapCache::find(key)->height() / 2;
painter.drawPixmap(10, proposedCoord, *QPixmapCache::find(key));
painter.setPen(Qt::black);
int remainingWidth = width() - 120;
painter.drawText(120, 10, remainingWidth, height() - 20, Qt::AlignCenter | Qt::TextWordWrap, msgText);
}
void Notify::mousePressEvent(QMouseEvent* mouseEvent)
{
if (mouseEvent->buttons() == Qt::LeftButton) {
animation->setStartValue(QRect(x, y, w, 100));
animation->setEndValue(QRect(x, -100, w, 100));
animation->start();
showingNow = false;
}
}
#pragma once
#include <QWidget>
#include <QPropertyAnimation>
#include <QMouseEvent>
class Notify : public QWidget
{
Q_OBJECT
public:
enum NotificationType {
SUCCESS,
ERROR,
WARNING
};
explicit Notify(QWidget* parent);
~Notify();
void setPosition(QPoint p);
void setDialogWidth(int width);
void adjustInViewport();
void notify(QString text, NotificationType type, int duration = 1000);
private slots:
void onFinished();
protected:
virtual void paintEvent(QPaintEvent*);
virtual void mousePressEvent(QMouseEvent* mouseEvent);
private:
QPropertyAnimation* animation;
int x;
int y;
int w;
bool showingNow;
QString msgText;
NotificationType notifType;
int keepDuration;
};
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment