Files
cbh/ElaWidgetTools/DeveloperComponents/ElaPivotView.cpp
2025-09-20 01:41:33 +08:00

116 lines
4.9 KiB
C++

#include "ElaPivotView.h"
#include <QMouseEvent>
#include <QPainter>
#include <QPropertyAnimation>
#include "ElaPivotStyle.h"
#include "ElaScrollBar.h"
ElaPivotView::ElaPivotView(QWidget *parent) : QListView(parent) {
_pMarkX = 0;
_pMarkWidth = 40;
_pMarkAnimationWidth = 0;
_pCurrentIndex = QModelIndex();
_pCurrentIndexRect = QRect();
_pIsAnimationFinished = true;
setObjectName("ElaPivotView");
setStyleSheet("#ElaPivotView{background-color:transparent;}");
setMouseTracking(true);
setVerticalScrollBar(new ElaScrollBar(this));
setHorizontalScrollBar(new ElaScrollBar(this));
setHorizontalScrollMode(QAbstractItemView::ScrollPerPixel);
setVerticalScrollMode(QAbstractItemView::ScrollPerPixel);
}
ElaPivotView::~ElaPivotView() {}
void ElaPivotView::doCurrentIndexChangedAnimation(const QModelIndex &index) {
int xOffset = visualRect(_pCurrentIndex).x() - _pCurrentIndexRect.x();
if (index.row() >= 0) {
_pCurrentIndexRect = visualRect(index);
QPropertyAnimation *markAnimation = new QPropertyAnimation(this, "pMarkX");
connect(markAnimation, &QPropertyAnimation::valueChanged, this, [=]() { update(); });
connect(markAnimation, &QPropertyAnimation::finished, this, [=]() {
_pIsAnimationFinished = true;
update();
});
markAnimation->setDuration(300);
markAnimation->setEasingCurve(QEasingCurve::InOutSine);
if (_pPivotStyle->getCurrentIndex() >= 0) {
markAnimation->setStartValue(_pMarkX + xOffset);
markAnimation->setEndValue(_pCurrentIndexRect.center().x() - _pMarkWidth / 2);
} else {
markAnimation->setStartValue(_pCurrentIndexRect.center().x());
markAnimation->setEndValue(_pCurrentIndexRect.center().x() - _pMarkWidth / 2);
QPropertyAnimation *markWidthAnimation = new QPropertyAnimation(this, "pMarkAnimationWidth");
markWidthAnimation->setDuration(300);
markWidthAnimation->setEasingCurve(QEasingCurve::InOutSine);
markWidthAnimation->setStartValue(0);
markWidthAnimation->setEndValue(_pMarkWidth);
markWidthAnimation->start(QAbstractAnimation::DeleteWhenStopped);
}
markAnimation->start(QAbstractAnimation::DeleteWhenStopped);
} else {
_pCurrentIndexRect = visualRect(model()->index(_pPivotStyle->getCurrentIndex(), 0));
QPropertyAnimation *markAnimation = new QPropertyAnimation(this, "pMarkX");
connect(markAnimation, &QPropertyAnimation::valueChanged, this, [=]() { update(); });
connect(markAnimation, &QPropertyAnimation::finished, this, [=]() {
_pIsAnimationFinished = true;
update();
});
markAnimation->setDuration(300);
markAnimation->setEasingCurve(QEasingCurve::InOutSine);
markAnimation->setStartValue(_pCurrentIndexRect.center().x() - _pMarkWidth / 2);
markAnimation->setEndValue(_pCurrentIndexRect.center().x());
markAnimation->start(QAbstractAnimation::DeleteWhenStopped);
QPropertyAnimation *markWidthAnimation = new QPropertyAnimation(this, "pMarkAnimationWidth");
markWidthAnimation->setDuration(300);
markWidthAnimation->setEasingCurve(QEasingCurve::InOutSine);
markWidthAnimation->setStartValue(_pMarkAnimationWidth);
markWidthAnimation->setEndValue(0);
markWidthAnimation->start(QAbstractAnimation::DeleteWhenStopped);
}
_pCurrentIndex = index;
_pIsAnimationFinished = false;
setCurrentIndex(index);
}
void ElaPivotView::mouseDoubleClickEvent(QMouseEvent *event) {
_pPivotStyle->setPressIndex(indexAt(event->pos()));
viewport()->update();
QListView::mouseDoubleClickEvent(event);
}
void ElaPivotView::mouseReleaseEvent(QMouseEvent *event) {
if (event->button() == Qt::LeftButton) {
_pPivotStyle->setPressIndex(QModelIndex());
viewport()->update();
}
QListView::mouseReleaseEvent(event);
}
void ElaPivotView::wheelEvent(QWheelEvent *event) {
QListView::wheelEvent(event);
event->accept();
}
void ElaPivotView::paintEvent(QPaintEvent *event) {
QPainter painter(viewport());
QRect viewPortRect = viewport()->rect();
painter.save();
painter.setRenderHint(QPainter::Antialiasing);
painter.setPen(Qt::NoPen);
painter.setBrush(_pPivotStyle->getMarkColor());
QRect currentIndexRect = visualRect(_pCurrentIndex);
if (_pIsAnimationFinished) {
painter.drawRoundedRect(QRect(currentIndexRect.center().x() - _pMarkWidth / 2, viewPortRect.bottom() - 4, _pMarkAnimationWidth, 3), 3, 3);
} else {
int xOffset = currentIndexRect.x() - _pCurrentIndexRect.x();
painter.drawRoundedRect(QRect(_pMarkX + xOffset, viewPortRect.bottom() - 4, _pMarkAnimationWidth, 3), 3, 3);
}
painter.restore();
QListView::paintEvent(event);
}