Qt源码分享–gif动画按钮,素材+源码

Qt源码分享--gif动画按钮,素材+源码

关注微信号:cpp手艺人,获取源码

好,废话不说,先看看效果怎么样。

1.四态绘制,normal,hover,press,disabled

2.gif 动画

Qt源码分享--gif动画按钮,素材+源码

说下思路:

使用QMovie播放Gif动画,每播放一次,就是图片缓存下来。在paintEvent绘制,这样就形成了动画的效果,是不是很简单。

这里我贴出主要的代码:

GifButton::GifButton(QWidget *parent, 
           const QString &gifPath) :
          QPushButton(parent), 
          mGifPath(gifPath),
          mGif(nullptr) {


  mGifFrame = QPixmap();

  mNormalBK  = QPixmap(kRESOURCE1K.arg("btn_login.png"));
  mHoverBK  = QPixmap(kRESOURCE1K.arg("btn_login_hover.png"));
  mPressBK  = QPixmap(kRESOURCE1K.arg("btn_login_push.png"));
  mDisabledBK = QPixmap(kRESOURCE1K.arg("btn_login_disabled.png"));
  mBtnStatus  = Normal;
  mTextColor  = Qt::black;

  if(! mGifPath.isEmpty()) {
    mGif = new QMovie(mGifPath, QByteArray(), this);
    connect(mGif, SIGNAL(frameChanged(int)), this, SLOT(OnIconChanged(int)));
    mGif->start();
  }

}
GifButton::~GifButton() {
  if (nullptr != mGif) {
    mGif->stop();
    delete mGif;
    mGif = nullptr;
  }
}

void GifButton::Stop() {
  mGifFrame = QPixmap();

  if (nullptr != mGif) {
    mGif->stop();
  }
  update();
}

void GifButton::Start() {
  if (nullptr != mGif) {
    mGif->start();
  }
  update();
}

void GifButton::SetText(const QString &text) {
  this->setText(text);
  update();
}

void GifButton::SetGifPath(const QString &path) {
  mGifPath = path;

  if (nullptr != mGif) {
    mGif->stop();
    delete mGif;
  }

  mGif = new QMovie(mGifPath, QByteArray(), this);
  connect(mGif, SIGNAL(frameChanged(int)), this, SLOT(OnIconChanged(int)));
}

QString GifButton::GifPath() const {
  return mGifPath;
}

void GifButton::SetEnabled(bool enable) {
  this->setEnabled(enable);
  update();
}

void GifButton::SetTextColor(QColor textColor) {
  mTextColor = textColor;
  update();
}

void GifButton::paintEvent(QPaintEvent *paintEvent) {
  const QRect rect = this->rect();

  QPainter painter(this);

  if (! this->isEnabled()) {
    painter.drawPixmap(rect, mDisabledBK);
  } else {
    if (Normal == mBtnStatus) {
      painter.drawPixmap(rect, mNormalBK);
    } else if (Hover == mBtnStatus) {
      painter.drawPixmap(rect, mHoverBK);
    } else if (Press == mBtnStatus) {
      painter.drawPixmap(rect, mPressBK);
    }
  }

  QString text = this->text();

    QFontMetrics fontWidth(this->font());  
    int width = fontWidth.width(text);
  int total_width = width;

  if (! mGifFrame.isNull()) {
    total_width += mGifFrame.width();
  }

  int text_distance = (rect.width()-total_width)/2;

  QRect text_rect(text_distance, 0, width, rect.height());
  
  QPen pen(mTextColor); 
  painter.setPen(pen);
  painter.drawText(text_rect, Qt::AlignHCenter | Qt::AlignVCenter, text);

  if (! mGifFrame.isNull()) {
    painter.drawPixmap(text_distance+width+2, 
               (rect.height()-mGifFrame.height())/2, 
               mGifFrame);
  }
}

void GifButton::enterEvent(QEvent *event) {
  mBtnStatus = Hover;
  update();
  QPushButton::enterEvent(event);
}

void GifButton::leaveEvent(QEvent *event) {
  mBtnStatus = Normal;
  update();
  QPushButton::leaveEvent(event);
}

void GifButton::mousePressEvent(QMouseEvent *event) {
  mBtnStatus = Press;
  update();
  QPushButton::mousePressEvent(event);
}

void GifButton::OnIconChanged(int) {
  QPixmap currFrame = mGif->currentPixmap();
  mGifFrame = QPixmap(currFrame.width(), currFrame.height());
  mGifFrame.fill(Qt::transparent);
  QPainter painter(&mGifFrame);
  painter.drawPixmap((mGifFrame.width()-currFrame.width()) / 2  ,
             (mGifFrame.height()-currFrame.height()) / 2, currFrame);
  update();
}

源码参考:https://github.com/MingYueRuYa/QtDemoStydy.git GifButton 项目下。

原文链接:http://lsxcpp.com/2020/08/20/Qt%E6%BA%90%E7%A0%81%E5%88%86%E4%BA%AB%EF%BC%88%E4%BA%94%EF%BC%89-gif%E5%8A%A8%E7%94%BB%E6%8C%89%E9%92%AE/

原文出处:微信公众号【刘世雄 cpp手艺人】

原文链接:https://mp.weixin.qq.com/s/8xFkEcK_KXVnHK7UzuOQ2g

本文观点不代表Dotnet9立场,转载请联系原作者。

发表评论

登录后才能评论