1 需求描述
- 使用Qt實現彈幕效果;
- 支持全屏置頂顯示;
- 實現過程簡單,拒絕復雜。
2 設計思路
- 使用QLabel顯示彈幕文字;
- 通過QDesktopWidget獲取屏幕尺寸,來確定QLabel動畫起點;
- 使用QPropertyAnimation動畫循環顯示QLabel;
- 每次循環隨機獲取顯示內容和字體顏色。
3 代碼實現
- 首先初始化顯示文字列表,可以通過加載文件方式獲取,也可以在程序里寫死,例如寫點情話:
void Widget::initMessage()
{
m_messageList.append(QStringLiteral("愛你一萬年"));
m_messageList.append(QStringLiteral("老婆我愛你"));
m_messageList.append(QStringLiteral("愛你么么噠"));
m_messageList.append(QStringLiteral("老婆最漂亮"));
m_messageList.append(QStringLiteral("老婆最可愛"));
m_messageList.append(QStringLiteral("老婆最溫柔"));
m_messageList.append(QStringLiteral("老婆最美麗"));
m_messageList.append(QStringLiteral("老婆最體貼"));
m_messageList.append(QStringLiteral("愛你愛你愛你么么噠"));
m_messageList.append(QStringLiteral("老婆萌萌噠"));
m_messageList.append(QStringLiteral("老婆最賢惠"));
m_messageList.append(QStringLiteral("老婆棒棒噠"));
m_messageList.append(QStringLiteral("愛你一輩子"));
m_messageList.append(QStringLiteral("快樂與你隨行"));
m_messageList.append(QStringLiteral("天空中最亮的星"));
m_messageList.append(QStringLiteral("回眸一笑勝星華"));
m_messageList.append(QStringLiteral("你是花叢中的蝴蝶"));
m_messageList.append(QStringLiteral("讓人久久難以忘懷"));
m_messageList.append(QStringLiteral("我眼中最美的偶象"));
m_messageList.append(QStringLiteral("你如此美麗可人"));
m_messageList.append(QStringLiteral("你的美點綴了這一切"));
m_messageList.append(QStringLiteral("老婆乃我心中唯一"));
m_messageList.append(QStringLiteral("你如此美麗可人"));
m_messageList.append(QStringLiteral("老婆最善解人意"));
m_messageList.append(QStringLiteral("我眼中最美的偶象"));
m_messageList.append(QStringLiteral("愛你愛你愛你么么噠"));
m_messageList.append(QStringLiteral("你是花叢中的蝴蝶"));
m_messageList.append(QStringLiteral("愛你愛你愛你么么噠"));
}
- 文字初始化后,初始化QLabel再設置動畫進行顯示,代碼如下:
void Widget::onTimeOut()
{
initMessage();
for (int i = 0; i < m_messageList.count(); ++i) {
QLabel *label = new QLabel(this);
label->setMinimumWidth(500);
label->setAttribute(Qt::WA_TranslucentBackground);
label->setWindowFlags(label->windowFlags() | Qt::FramelessWindowHint | Qt::Dialog | Qt::WindowStaysOnTopHint);
label->setStyleSheet(QString("color:%1;")
.arg(QColor::colorNames().at(QRandomGenerator::global()->bounded(QColor::colorNames().count()))));
QFont font;
font.setBold(true);
font.setFamily(QStringLiteral("幼圓"));
font.setPixelSize(50);
label->setFont(font);
label->setText(m_messageList.at(QRandomGenerator::global()->bounded(m_messageList.count())));
label->move(QDesktopWidget().width() + QRandomGenerator::global()->bounded(1000) , i * 50 + 10);
label->show();
QPropertyAnimation *animation = new QPropertyAnimation(label, "pos", this);
//每循環一次重新設置字體顏色以及顯示內容
connect(animation, &QAbstractAnimation::currentLoopChanged, [=]() {
label->setText(m_messageList.at(QRandomGenerator::global()->bounded(m_messageList.count())));
label->setStyleSheet(QString("color:%1;")
.arg(QColor::colorNames().at(QRandomGenerator::global()->bounded(QColor::colorNames().count()))));
});
animation->setStartValue(QPoint(label->x(), label->y()));
animation->setEndValue(QPoint(-400, label->y()));
animation->setDuration(QRandomGenerator::global()->bounded(3500, 5000));
animation->setLoopCount(-1);
animation->start();
}
}
到此,彈幕效果就做好了。
4 總結
實現非常簡單,僅僅用到QLabel、QPropertyAnimation就完成了彈幕效果,這里需要注意QLabel的設置:
label->setAttribute(Qt::WA_TranslucentBackground); 設置背景透明
label->setWindowFlags(label->windowFlags() | Qt::FramelessWindowHint | Qt::Dialog | Qt::WindowStaysOnTopHint); 設置無邊框、對話框、置頂顯示
這樣才能達到預期效果,然后每次循環完成后設置隨機內容和字體顏色進入下一次循環。