简述

前面几节中我们介绍了关于动画的基本使用,有属性动画、串行动画组、并行动画组。这节我们来实现一些特效,让交互更顺畅。
**

示例

下面,我们以geometry、pos、windowOpacity属性为例,来实现窗体的下坠、抖动、透明度效果。

效果

2021-02-24-10-41-38.gif

代码

  1. #ifndef WIDGET_H
  2. #define WIDGET_H
  3. #include <QWidget>
  4. QT_BEGIN_NAMESPACE
  5. namespace Ui {
  6. class Widget;
  7. }
  8. QT_END_NAMESPACE
  9. class Widget : public QWidget {
  10. Q_OBJECT
  11. public:
  12. Widget(QWidget* parent = nullptr);
  13. ~Widget();
  14. protected slots:
  15. void onDropWindow();
  16. void onShakeWindow();
  17. void onOpacityWindow();
  18. private:
  19. Ui::Widget* ui;
  20. };
  21. #endif // WIDGET_H
  1. #include "widget.h"
  2. #include "ui_widget.h"
  3. #include <QDebug>
  4. #include <QDesktopWidget>
  5. #include <QPropertyAnimation>
  6. #include <QSequentialAnimationGroup>
  7. Widget::Widget(QWidget* parent)
  8. : QWidget(parent)
  9. , ui(new Ui::Widget)
  10. {
  11. ui->setupUi(this);
  12. connect(ui->pushButton, &QPushButton::clicked, this, &Widget::onDropWindow);
  13. connect(ui->pushButton_2, &QPushButton::clicked, this, &Widget::onShakeWindow);
  14. connect(ui->pushButton_3, &QPushButton::clicked, this, &Widget::onOpacityWindow);
  15. }
  16. // 通过计算桌面的宽度、高度,来设置动画的起始值和结束值。
  17. void Widget::onDropWindow()
  18. {
  19. QPropertyAnimation* pAnimation = new QPropertyAnimation(this, "geometry");
  20. QDesktopWidget* pDesktopWidget = QApplication::desktop();
  21. int x = (pDesktopWidget->availableGeometry().width() - width()) / 2;
  22. int y = (pDesktopWidget->availableGeometry().height() - height()) / 2;
  23. pAnimation->setDuration(1000);
  24. pAnimation->setStartValue(QRect(x, 0, width(), height()));
  25. pAnimation->setEndValue(QRect(x, y, width(), height()));
  26. pAnimation->setEasingCurve(QEasingCurve::OutElastic);
  27. pAnimation->start(QAbstractAnimation::DeleteWhenStopped);
  28. }
  29. // 获取界面的坐标,然后进行上、下、左、右坐标浮动,通过setKeyValueAt()来设置每一时刻的位置,实现抖动效果。
  30. void Widget::onShakeWindow()
  31. {
  32. QPropertyAnimation* pAnimation = new QPropertyAnimation(this, "pos");
  33. pAnimation->setDuration(500);
  34. pAnimation->setLoopCount(2);
  35. pAnimation->setKeyValueAt(0, QPoint(geometry().x() - 3, geometry().y() - 3));
  36. pAnimation->setKeyValueAt(0.1, QPoint(geometry().x() + 6, geometry().y() + 6));
  37. pAnimation->setKeyValueAt(0.2, QPoint(geometry().x() - 6, geometry().y() + 6));
  38. pAnimation->setKeyValueAt(0.3, QPoint(geometry().x() + 6, geometry().y() - 6));
  39. pAnimation->setKeyValueAt(0.4, QPoint(geometry().x() - 6, geometry().y() - 6));
  40. pAnimation->setKeyValueAt(0.5, QPoint(geometry().x() + 6, geometry().y() + 6));
  41. pAnimation->setKeyValueAt(0.6, QPoint(geometry().x() - 6, geometry().y() + 6));
  42. pAnimation->setKeyValueAt(0.7, QPoint(geometry().x() + 6, geometry().y() - 6));
  43. pAnimation->setKeyValueAt(0.8, QPoint(geometry().x() - 6, geometry().y() - 6));
  44. pAnimation->setKeyValueAt(0.9, QPoint(geometry().x() + 6, geometry().y() + 6));
  45. pAnimation->setKeyValueAt(1, QPoint(geometry().x() - 3, geometry().y() - 3));
  46. pAnimation->start(QAbstractAnimation::DeleteWhenStopped);
  47. }
  48. // 设置每一时刻的透明度值,动画结束时界面还原(透明度再为1)。
  49. void Widget::onOpacityWindow()
  50. {
  51. QPropertyAnimation* pAnimation = new QPropertyAnimation(this, "windowOpacity");
  52. pAnimation->setDuration(1000);
  53. pAnimation->setKeyValueAt(0, 1);
  54. pAnimation->setKeyValueAt(0.5, 0);
  55. pAnimation->setKeyValueAt(1, 1);
  56. pAnimation->start(QAbstractAnimation::DeleteWhenStopped);
  57. }
  58. Widget::~Widget()
  59. {
  60. delete ui;
  61. }