#include "alertwidget.h" #include #include #include #include #include #include "MabiWeather.h" // Begin shadow methods (http://labs.trolltech.com/page/Graphics/Examples) // Exponential blur, Jani Huhtanen, 2006 // template static inline void blurinner(unsigned char* bptr, int &zR, int &zG, int &zB, int &zA, int alpha); template static inline void blurrow(QImage &im, int line, int alpha); template static inline void blurcol(QImage &im, int col, int alpha); /* * expblur(QImage &img, int radius) * * In-place blur of image 'img' with kernel * of approximate radius 'radius'. * * Blurs with two sided exponential impulse * response. * * aprec = precision of alpha parameter * in fixed-point format 0.aprec * * zprec = precision of state parameters * zR,zG,zB and zA in fp format 8.zprec */ template void expblur(QImage &img, int radius) { if(radius < 1) { return; } /* Calculate the alpha such that 90% of the kernel is within the radius. (Kernel extends to infinity) */ int alpha = (int)((1<(img, row, alpha); } for(int col = 0; col < img.width(); col++) { blurcol(img, col, alpha); } return; } template static inline void blurinner(unsigned char *bptr, int &zR, int &zG, int &zB, int &zA, int alpha) { int R; int G; int B; int A; R = *(bptr + 0); G = *(bptr + 1); B = *(bptr + 2); A = *(bptr + 3); zR += (alpha * ((R << zprec) - zR)) >> aprec; zG += (alpha * ((G << zprec) - zG)) >> aprec; zB += (alpha * ((B << zprec) - zB)) >> aprec; zA += (alpha * ((A << zprec) - zA)) >> aprec; *(bptr + 0) = zR >> zprec; *(bptr + 1) = zG >> zprec; *(bptr + 2) = zB >> zprec; *(bptr + 3) = zA >> zprec; } template static inline void blurrow(QImage &im, int line, int alpha) { int zR; int zG; int zB; int zA; QRgb *ptr = (QRgb*)im.scanLine(line); zR = *((unsigned char*)ptr + 0) << zprec; zG = *((unsigned char*)ptr + 1) << zprec; zB = *((unsigned char*)ptr + 2) << zprec; zA = *((unsigned char*)ptr + 3) << zprec; for(int index = 1; index < im.width(); index++) { blurinner((unsigned char*)&ptr[index], zR, zG, zB, zA, alpha); } for(int index = im.width() - 2; index >= 0; index--) { blurinner((unsigned char*)&ptr[index], zR, zG, zB, zA, alpha); } } template static inline void blurcol(QImage &im, int col, int alpha) { int zR; int zG; int zB; int zA; QRgb *ptr = (QRgb*)im.bits(); ptr += col; zR = *((unsigned char*)ptr + 0) << zprec; zG = *((unsigned char*)ptr + 1) << zprec; zB = *((unsigned char*)ptr + 2) << zprec; zA = *((unsigned char*)ptr + 3) << zprec; for(int index = im.width(); index < (im.height() - 1) * im.width(); index += im.width()) { blurinner((unsigned char*)&ptr[index], zR, zG, zB, zA, alpha); } for(int index = (im.height() - 2) * im.width(); index >= 0; index -= im.width()) { blurinner((unsigned char*)&ptr[index], zR, zG, zB, zA, alpha); } } // End of shadow methods AlertWidget::AlertWidget(QWidget *parent) : QWidget(parent) { setWindowFlags( Qt::SubWindow | Qt::FramelessWindowHint | Qt::WindowStaysOnTopHint); setAttribute(Qt::WA_TranslucentBackground, true); _glass = new Glass(); _glass->SetTransparent(winId(), true, true); _radius = 0; _timerAlpha = false; _currentAlpha = 0; _duration = 333; _delay = 8000; } AlertWidget::~AlertWidget() { delete _glass; } void AlertWidget::setRadius(int radius) { _radius = radius; } void AlertWidget::setMessage(QString &message) { _message = message; _timerAlpha = false; _timer.stop(); _timer.start(_delay, this); update(); setWindowOpacity(1.0); } void AlertWidget::setColor(QColor &text, QColor &shadow) { QPalette palette = this->palette(); palette.setColor(QPalette::Text, text); palette.setColor(QPalette::Shadow, shadow); setPalette(palette); update(); } void AlertWidget::paintEvent(QPaintEvent*) { QFontMetrics fm(font()); QRect fontRect = fm.boundingRect(_message); QRect available = QDesktopWidget().availableGeometry(); setGeometry(available.width() / 2 - fontRect.width() / 2, available.height() / 2 - fontRect.height(), fontRect.width() + _radius * 2, fontRect.height() + _radius * 2); QImage img(fontRect.width() + _radius * 2, fontRect.height() + _radius * 2, QImage::Format_ARGB32_Premultiplied); img.fill(qRgba(0, 0, 0, 0)); QPainter p(this); QPainter pimg(&img); pimg.setFont(font()); pimg.setPen(palette().shadow().color()); pimg.drawText(-fontRect.left() + _radius, -fontRect.top() + _radius, _message); expblur<16, 7>(img, _radius); p.drawImage(QPoint(0, 0), img); //p.drawImage(QPoint(0, 0), img); p.setFont(font()); p.setPen(palette().text().color()); p.drawText(-fontRect.left() + _radius, -fontRect.top() + _radius, _message); } void AlertWidget::timerEvent(QTimerEvent*) { if(_timerAlpha) { _currentAlpha -= 255 * 33 / _duration; if(_currentAlpha <= 0) { setWindowOpacity(0.0f); _timer.stop(); _timerAlpha = false; } else if(_currentAlpha < 255) { setWindowOpacity(_currentAlpha / 255.0f); } } else { _timer.stop(); _timer.start(33, this); _timerAlpha = true; _currentAlpha = 255; } }