src/gui/styles/qwindowsvistastyle.cpp
changeset 3 41300fa6a67c
parent 0 1918ee327afb
child 4 3b1da2848fc7
equal deleted inserted replaced
2:56cd8111b7f7 3:41300fa6a67c
   157     : QWindowsXPStyle(*new QWindowsVistaStylePrivate)
   157     : QWindowsXPStyle(*new QWindowsVistaStylePrivate)
   158 {
   158 {
   159 }
   159 }
   160 
   160 
   161 //convert Qt state flags to uxtheme button states
   161 //convert Qt state flags to uxtheme button states
   162 int buttonStateId(int flags, int partId)
   162 static int buttonStateId(int flags, int partId)
   163 {
   163 {
   164     int stateId = 0;
   164     int stateId = 0;
   165     if (partId == BP_RADIOBUTTON || partId == BP_CHECKBOX) {
   165     if (partId == BP_RADIOBUTTON || partId == BP_CHECKBOX) {
   166         if (!(flags & QStyle::State_Enabled))
   166         if (!(flags & QStyle::State_Enabled))
   167             stateId = RBS_UNCHECKEDDISABLED;
   167             stateId = RBS_UNCHECKEDDISABLED;
   188         Q_ASSERT(1);
   188         Q_ASSERT(1);
   189     }
   189     }
   190     return stateId;
   190     return stateId;
   191 }
   191 }
   192 
   192 
   193 void Animation::paint(QPainter *painter, const QStyleOption *option)
   193 void QWindowsVistaAnimation::paint(QPainter *painter, const QStyleOption *option)
   194 {
   194 {
   195     Q_UNUSED(option);
   195     Q_UNUSED(option);
   196     Q_UNUSED(painter);
   196     Q_UNUSED(painter);
   197 }
   197 }
   198 
   198 
   203 
   203 
   204   The result is a blended image consisting of ((alpha)*_primaryImage)
   204   The result is a blended image consisting of ((alpha)*_primaryImage)
   205   + ((1-alpha)*_secondaryImage)
   205   + ((1-alpha)*_secondaryImage)
   206 
   206 
   207 */
   207 */
   208 void Animation::drawBlendedImage(QPainter *painter, QRect rect, float alpha) {
   208 void QWindowsVistaAnimation::drawBlendedImage(QPainter *painter, QRect rect, float alpha) {
   209     if (_secondaryImage.isNull() || _primaryImage.isNull())
   209     if (_secondaryImage.isNull() || _primaryImage.isNull())
   210         return;
   210         return;
   211 
   211 
   212     if (_tempImage.isNull())
   212     if (_tempImage.isNull())
   213         _tempImage = _secondaryImage;
   213         _tempImage = _secondaryImage;
   249 /*! \internal
   249 /*! \internal
   250   Paints a transition state. The result will be a mix between the
   250   Paints a transition state. The result will be a mix between the
   251   initial and final state of the transition, depending on the time
   251   initial and final state of the transition, depending on the time
   252   difference between _startTime and current time.
   252   difference between _startTime and current time.
   253 */
   253 */
   254 void Transition::paint(QPainter *painter, const QStyleOption *option)
   254 void QWindowsVistaTransition::paint(QPainter *painter, const QStyleOption *option)
   255 {
   255 {
   256     float alpha = 1.0;
   256     float alpha = 1.0;
   257     if (_duration > 0) {
   257     if (_duration > 0) {
   258         QTime current = QTime::currentTime();
   258         QTime current = QTime::currentTime();
   259 
   259 
   276 /*! \internal
   276 /*! \internal
   277   Paints a pulse. The result will be a mix between the primary and
   277   Paints a pulse. The result will be a mix between the primary and
   278   secondary pulse images depending on the time difference between
   278   secondary pulse images depending on the time difference between
   279   _startTime and current time.
   279   _startTime and current time.
   280 */
   280 */
   281 void Pulse::paint(QPainter *painter, const QStyleOption *option)
   281 void QWindowsVistaPulse::paint(QPainter *painter, const QStyleOption *option)
   282 {
   282 {
   283     float alpha = 1.0;
   283     float alpha = 1.0;
   284     if (_duration > 0) {
   284     if (_duration > 0) {
   285         QTime current = QTime::currentTime();
   285         QTime current = QTime::currentTime();
   286 
   286 
   391                 opt.rect.setRect(0, 0, option->rect.width(), option->rect.height());
   391                 opt.rect.setRect(0, 0, option->rect.width(), option->rect.height());
   392                 opt.state = (QStyle::State)oldState;
   392                 opt.state = (QStyle::State)oldState;
   393                 startImage.fill(0);
   393                 startImage.fill(0);
   394                 QPainter startPainter(&startImage);
   394                 QPainter startPainter(&startImage);
   395 
   395 
   396                 Animation *anim = d->widgetAnimation(widget);
   396                 QWindowsVistaAnimation *anim = d->widgetAnimation(widget);
   397                 Transition *t = new Transition;
   397                 QWindowsVistaTransition *t = new QWindowsVistaTransition;
   398                 t->setWidget(w);
   398                 t->setWidget(w);
   399 
   399 
   400                 // If we have a running animation on the widget already, we will use that to paint the initial
   400                 // If we have a running animation on the widget already, we will use that to paint the initial
   401                 // state of the new transition, this ensures a smooth transition from a current animation such as a
   401                 // state of the new transition, this ensures a smooth transition from a current animation such as a
   402                 // pulsating default button into the intended target state.
   402                 // pulsating default button into the intended target state.
   529 
   529 
   530     case PE_PanelButtonBevel:
   530     case PE_PanelButtonBevel:
   531     case PE_IndicatorCheckBox:
   531     case PE_IndicatorCheckBox:
   532     case PE_IndicatorRadioButton:
   532     case PE_IndicatorRadioButton:
   533         {
   533         {
   534             if (Animation *a = d->widgetAnimation(widget)) {
   534             if (QWindowsVistaAnimation *a = d->widgetAnimation(widget)) {
   535                 a->paint(painter, option);
   535                 a->paint(painter, option);
   536             } else {
   536             } else {
   537                 QWindowsXPStyle::drawPrimitive(element, option, painter, widget);
   537                 QWindowsXPStyle::drawPrimitive(element, option, painter, widget);
   538             }
   538             }
   539         }
   539         }
   642             return;
   642             return;
   643         }
   643         }
   644         break;
   644         break;
   645 
   645 
   646     case PE_FrameLineEdit:
   646     case PE_FrameLineEdit:
   647         if (Animation *anim = d->widgetAnimation(widget)) {
   647         if (QWindowsVistaAnimation *anim = d->widgetAnimation(widget)) {
   648             anim->paint(painter, option);
   648             anim->paint(painter, option);
   649         } else {
   649         } else {
   650             QPainter *p = painter;
   650             QPainter *p = painter;
   651             QWidget *parentWidget = 0;
   651             QWidget *parentWidget = 0;
   652             if (widget) {
   652             if (widget) {
   927                 }
   927                 }
   928 
   928 
   929                 if (doTransition) {
   929                 if (doTransition) {
   930                     QImage startImage(option->rect.size(), QImage::Format_ARGB32_Premultiplied);
   930                     QImage startImage(option->rect.size(), QImage::Format_ARGB32_Premultiplied);
   931                     QImage endImage(option->rect.size(), QImage::Format_ARGB32_Premultiplied);
   931                     QImage endImage(option->rect.size(), QImage::Format_ARGB32_Premultiplied);
   932                     Animation *anim = d->widgetAnimation(widget);
   932                     QWindowsVistaAnimation *anim = d->widgetAnimation(widget);
   933 
   933 
   934                     QStyleOptionButton opt = *button;
   934                     QStyleOptionButton opt = *button;
   935                     opt.state = (QStyle::State)oldState;
   935                     opt.state = (QStyle::State)oldState;
   936 
   936 
   937                     startImage.fill(0);
   937                     startImage.fill(0);
   938                     Transition *t = new Transition;
   938                     QWindowsVistaTransition *t = new QWindowsVistaTransition;
   939                     t->setWidget(w);
   939                     t->setWidget(w);
   940                     QPainter startPainter(&startImage);
   940                     QPainter startPainter(&startImage);
   941 
   941 
   942                     if (!anim) {
   942                     if (!anim) {
   943                         proxy()->drawControl(element, &opt, &startPainter, 0 /* Intentional */);
   943                         proxy()->drawControl(element, &opt, &startPainter, 0 /* Intentional */);
   970     switch (element) {
   970     switch (element) {
   971     case CE_PushButtonBevel:
   971     case CE_PushButtonBevel:
   972         if (const QStyleOptionButton *btn = qstyleoption_cast<const QStyleOptionButton *>(option))
   972         if (const QStyleOptionButton *btn = qstyleoption_cast<const QStyleOptionButton *>(option))
   973         {
   973         {
   974 
   974 
   975             if (Animation *anim = d->widgetAnimation(widget)) {
   975             if (QWindowsVistaAnimation *anim = d->widgetAnimation(widget)) {
   976                 anim->paint(painter, option);
   976                 anim->paint(painter, option);
   977             } else {
   977             } else {
   978                 name = QLatin1String("BUTTON");
   978                 name = QLatin1String("BUTTON");
   979                 partId = BP_PUSHBUTTON;
   979                 partId = BP_PUSHBUTTON;
   980                 if (btn->features & QStyleOptionButton::CommandLinkButton)
   980                 if (btn->features & QStyleOptionButton::CommandLinkButton)
   997 
   997 
   998                     if (widget && d->transitionsEnabled() && (btn->features & QStyleOptionButton::DefaultButton) &&
   998                     if (widget && d->transitionsEnabled() && (btn->features & QStyleOptionButton::DefaultButton) &&
   999                         !(state & (State_Sunken | State_On)) && !(state & State_MouseOver) &&
   999                         !(state & (State_Sunken | State_On)) && !(state & State_MouseOver) &&
  1000                          (state & State_Enabled) && (state & State_Active))
  1000                          (state & State_Enabled) && (state & State_Active))
  1001                         {
  1001                         {
  1002                         Animation *anim = d->widgetAnimation(widget);
  1002                         QWindowsVistaAnimation *anim = d->widgetAnimation(widget);
  1003                         if (!anim && widget) {
  1003                         if (!anim && widget) {
  1004                             QImage startImage(option->rect.size(), QImage::Format_ARGB32_Premultiplied);
  1004                             QImage startImage(option->rect.size(), QImage::Format_ARGB32_Premultiplied);
  1005                             startImage.fill(0);
  1005                             startImage.fill(0);
  1006                             QImage alternateImage(option->rect.size(), QImage::Format_ARGB32_Premultiplied);
  1006                             QImage alternateImage(option->rect.size(), QImage::Format_ARGB32_Premultiplied);
  1007                             alternateImage.fill(0);
  1007                             alternateImage.fill(0);
  1008 
  1008 
  1009                             Pulse *pulse = new Pulse;
  1009                             QWindowsVistaPulse *pulse = new QWindowsVistaPulse;
  1010                             pulse->setWidget(const_cast<QWidget*>(widget));
  1010                             pulse->setWidget(const_cast<QWidget*>(widget));
  1011 
  1011 
  1012                             QPainter startPainter(&startImage);
  1012                             QPainter startPainter(&startImage);
  1013                             stateId = PBS_DEFAULTED;
  1013                             stateId = PBS_DEFAULTED;
  1014                             XPThemeData theme(widget, &startPainter, name, partId, stateId, rect);
  1014                             XPThemeData theme(widget, &startPainter, name, partId, stateId, rect);
  1077             }
  1077             }
  1078 
  1078 
  1079             if (const QProgressBar *progressbar = qobject_cast<const QProgressBar *>(widget)) {
  1079             if (const QProgressBar *progressbar = qobject_cast<const QProgressBar *>(widget)) {
  1080                 if (((progressbar->value() > 0  && d->transitionsEnabled()) || isIndeterminate)) {
  1080                 if (((progressbar->value() > 0  && d->transitionsEnabled()) || isIndeterminate)) {
  1081                     if (!d->widgetAnimation(progressbar) && progressbar->value() < progressbar->maximum()) {
  1081                     if (!d->widgetAnimation(progressbar) && progressbar->value() < progressbar->maximum()) {
  1082                         Animation *a = new Animation;
  1082                         QWindowsVistaAnimation *a = new QWindowsVistaAnimation;
  1083                         a->setWidget(const_cast<QWidget*>(widget));
  1083                         a->setWidget(const_cast<QWidget*>(widget));
  1084                         a->setStartTime(QTime::currentTime());
  1084                         a->setStartTime(QTime::currentTime());
  1085                         d->startAnimation(a);
  1085                         d->startAnimation(a);
  1086                     }
  1086                     }
  1087                 } else {
  1087                 } else {
  1093             theme.rect = option->rect;
  1093             theme.rect = option->rect;
  1094             bool reverse = (bar->direction == Qt::LeftToRight && inverted) || (bar->direction == Qt::RightToLeft && !inverted);
  1094             bool reverse = (bar->direction == Qt::LeftToRight && inverted) || (bar->direction == Qt::RightToLeft && !inverted);
  1095             QTime current = QTime::currentTime();
  1095             QTime current = QTime::currentTime();
  1096 
  1096 
  1097             if (isIndeterminate) {
  1097             if (isIndeterminate) {
  1098                 if (Animation *a = d->widgetAnimation(widget)) {
  1098                 if (QWindowsVistaAnimation *a = d->widgetAnimation(widget)) {
  1099                     int glowSize = 120;
  1099                     int glowSize = 120;
  1100                     int animationWidth = glowSize * 2 + (vertical ? theme.rect.height() : theme.rect.width());
  1100                     int animationWidth = glowSize * 2 + (vertical ? theme.rect.height() : theme.rect.width());
  1101                     int animOffset = a->startTime().msecsTo(current) / 4;
  1101                     int animOffset = a->startTime().msecsTo(current) / 4;
  1102                     if (animOffset > animationWidth)
  1102                     if (animOffset > animationWidth)
  1103                         a->setStartTime(QTime::currentTime());
  1103                         a->setStartTime(QTime::currentTime());
  1163                     theme.rect = QStyle::visualRect(reverse ? Qt::RightToLeft : Qt::LeftToRight, 
  1163                     theme.rect = QStyle::visualRect(reverse ? Qt::RightToLeft : Qt::LeftToRight, 
  1164                                                               option->rect, theme.rect);
  1164                                                               option->rect, theme.rect);
  1165                 }
  1165                 }
  1166                 d->drawBackground(theme);
  1166                 d->drawBackground(theme);
  1167 
  1167 
  1168                 if (Animation *a = d->widgetAnimation(widget)) {
  1168                 if (QWindowsVistaAnimation *a = d->widgetAnimation(widget)) {
  1169                     int glowSize = 140;
  1169                     int glowSize = 140;
  1170                     int animationWidth = glowSize * 2 + (vertical ? theme.rect.height() : theme.rect.width());
  1170                     int animationWidth = glowSize * 2 + (vertical ? theme.rect.height() : theme.rect.width());
  1171                     int animOffset = a->startTime().msecsTo(current) / 4;
  1171                     int animOffset = a->startTime().msecsTo(current) / 4;
  1172                     theme.partId = vertical ? PP_MOVEOVERLAYVERT : PP_MOVEOVERLAY;
  1172                     theme.partId = vertical ? PP_MOVEOVERLAYVERT : PP_MOVEOVERLAY;
  1173                     if (animOffset > animationWidth) {
  1173                     if (animOffset > animationWidth) {
  1601             }
  1601             }
  1602 
  1602 
  1603             if (doTransition) {
  1603             if (doTransition) {
  1604                 QImage startImage(option->rect.size(), QImage::Format_ARGB32_Premultiplied);
  1604                 QImage startImage(option->rect.size(), QImage::Format_ARGB32_Premultiplied);
  1605                 QImage endImage(option->rect.size(), QImage::Format_ARGB32_Premultiplied);
  1605                 QImage endImage(option->rect.size(), QImage::Format_ARGB32_Premultiplied);
  1606                 Animation *anim = d->widgetAnimation(widget);
  1606                 QWindowsVistaAnimation *anim = d->widgetAnimation(widget);
  1607                 Transition *t = new Transition;
  1607                 QWindowsVistaTransition *t = new QWindowsVistaTransition;
  1608                 t->setWidget(w);
  1608                 t->setWidget(w);
  1609                 if (!anim) {
  1609                 if (!anim) {
  1610                     if (const QStyleOptionComboBox *combo = qstyleoption_cast<const QStyleOptionComboBox*>(option)) {
  1610                     if (const QStyleOptionComboBox *combo = qstyleoption_cast<const QStyleOptionComboBox*>(option)) {
  1611                         //Combo boxes are special cased to avoid cleartype issues
  1611                         //Combo boxes are special cased to avoid cleartype issues
  1612                         startImage.fill(0);
  1612                         startImage.fill(0);
  1649                     t->setDuration(150);
  1649                     t->setDuration(150);
  1650                 else
  1650                 else
  1651                     t->setDuration(500);
  1651                     t->setDuration(500);
  1652             }
  1652             }
  1653 
  1653 
  1654             if (Animation *anim = d->widgetAnimation(widget)) {
  1654             if (QWindowsVistaAnimation *anim = d->widgetAnimation(widget)) {
  1655                 anim->paint(painter, option);
  1655                 anim->paint(painter, option);
  1656                 return;
  1656                 return;
  1657             }
  1657             }
  1658 
  1658 
  1659         }
  1659         }
  2215                 wi = cb->rect.width(),
  2215                 wi = cb->rect.width(),
  2216                 he = cb->rect.height();
  2216                 he = cb->rect.height();
  2217             int xpos = x;
  2217             int xpos = x;
  2218             int margin = cb->frame ? 3 : 0;
  2218             int margin = cb->frame ? 3 : 0;
  2219             int bmarg = cb->frame ? 2 : 0;
  2219             int bmarg = cb->frame ? 2 : 0;
  2220             xpos += wi - bmarg - 16;
  2220             int arrowButtonWidth = bmarg + 16;
       
  2221             xpos += wi - arrowButtonWidth;
  2221 
  2222 
  2222             switch (subControl) {
  2223             switch (subControl) {
  2223             case SC_ComboBoxFrame:
  2224             case SC_ComboBoxFrame:
  2224                 rect = cb->rect;
  2225                 rect = cb->rect;
  2225                 break;
  2226                 break;
  2226             case SC_ComboBoxArrow:
  2227             case SC_ComboBoxArrow:
  2227                 rect.setRect(xpos, y , wi - xpos, he);
  2228                 rect.setRect(xpos, y , arrowButtonWidth, he);
  2228                 break;
  2229                 break;
  2229             case SC_ComboBoxEditField:
  2230             case SC_ComboBoxEditField:
  2230                 rect.setRect(x + margin, y + margin, wi - 2 * margin - 16, he - 2 * margin);
  2231                 rect.setRect(x + margin, y + margin, wi - 2 * margin - 16, he - 2 * margin);
  2231                 break;
  2232                 break;
  2232             case SC_ComboBoxListBoxPopup:
  2233             case SC_ComboBoxListBoxPopup:
  2531             !animations[i]->widget()->isVisible() ||
  2532             !animations[i]->widget()->isVisible() ||
  2532             animations[i]->widget()->window()->isMinimized() ||
  2533             animations[i]->widget()->window()->isMinimized() ||
  2533             !animations[i]->running() ||
  2534             !animations[i]->running() ||
  2534             !QWindowsVistaStylePrivate::useVista())
  2535             !QWindowsVistaStylePrivate::useVista())
  2535         {
  2536         {
  2536             Animation *a = animations.takeAt(i);
  2537             QWindowsVistaAnimation *a = animations.takeAt(i);
  2537             delete a;
  2538             delete a;
  2538         }
  2539         }
  2539     }
  2540     }
  2540     if (animations.size() == 0 && animationTimer.isActive()) {
  2541     if (animations.size() == 0 && animationTimer.isActive()) {
  2541         animationTimer.stop();
  2542         animationTimer.stop();
  2544 
  2545 
  2545 void QWindowsVistaStylePrivate::stopAnimation(const QWidget *w)
  2546 void QWindowsVistaStylePrivate::stopAnimation(const QWidget *w)
  2546 {
  2547 {
  2547     for (int i = animations.size() - 1 ; i >= 0 ; --i) {
  2548     for (int i = animations.size() - 1 ; i >= 0 ; --i) {
  2548         if (animations[i]->widget() == w) {
  2549         if (animations[i]->widget() == w) {
  2549             Animation *a = animations.takeAt(i);
  2550             QWindowsVistaAnimation *a = animations.takeAt(i);
  2550             delete a;
  2551             delete a;
  2551             break;
  2552             break;
  2552         }
  2553         }
  2553     }
  2554     }
  2554 }
  2555 }
  2555 
  2556 
  2556 void QWindowsVistaStylePrivate::startAnimation(Animation *t)
  2557 void QWindowsVistaStylePrivate::startAnimation(QWindowsVistaAnimation *t)
  2557 {
  2558 {
  2558     Q_Q(QWindowsVistaStyle);
  2559     Q_Q(QWindowsVistaStyle);
  2559     stopAnimation(t->widget());
  2560     stopAnimation(t->widget());
  2560     animations.append(t);
  2561     animations.append(t);
  2561     if (animations.size() > 0 && !animationTimer.isActive()) {
  2562     if (animations.size() > 0 && !animationTimer.isActive()) {
  2573     }
  2574     }
  2574     return false;
  2575     return false;
  2575 }
  2576 }
  2576 
  2577 
  2577 
  2578 
  2578 Animation * QWindowsVistaStylePrivate::widgetAnimation(const QWidget *widget) const
  2579 QWindowsVistaAnimation * QWindowsVistaStylePrivate::widgetAnimation(const QWidget *widget) const
  2579 {
  2580 {
  2580     if (!widget)
  2581     if (!widget)
  2581         return 0;
  2582         return 0;
  2582     foreach (Animation *a, animations) {
  2583     foreach (QWindowsVistaAnimation *a, animations) {
  2583         if (a->widget() == widget)
  2584         if (a->widget() == widget)
  2584             return a;
  2585             return a;
  2585     }
  2586     }
  2586     return 0;
  2587     return 0;
  2587 }
  2588 }