Showing preview only (580K chars total). Download the full file or copy to clipboard to get everything.
Repository: daishuboluo/Anime_carousel
Branch: main
Commit: d4a4037fba56
Files: 145
Total size: 528.6 KB
Directory structure:
gitextract_vx1aefsx/
├── Anime_Template_Project/
│ ├── Accordion/
│ │ ├── AccordionCard.cpp
│ │ ├── AccordionCard.h
│ │ ├── CMakeLists.txt
│ │ ├── accordionwidget.cpp
│ │ ├── accordionwidget.h
│ │ ├── img.qrc
│ │ └── main.cpp
│ ├── Adaptive_Carousel/
│ │ ├── daen_no_kado.cpp
│ │ ├── daen_no_kado.h
│ │ ├── latticed_circle_button.cpp
│ │ └── latticed_circle_button.h
│ ├── Blur_Text/
│ │ ├── fuzzytextwidget.cpp
│ │ └── fuzzytextwidget.h
│ ├── Carousel_card/
│ │ ├── card_button.cpp
│ │ ├── card_button.h
│ │ ├── card_text.cpp
│ │ ├── card_text.h
│ │ ├── carousel_card.cpp
│ │ ├── carousel_card.h
│ │ ├── carrier_card.cpp
│ │ └── carrier_card.h
│ ├── Eye_of_Cthulhu/
│ │ ├── JellyfishWidget.cpp
│ │ └── JellyfishWidget.h
│ ├── Flowing_Gradient_Font/
│ │ ├── widget.cpp
│ │ └── widget.h
│ ├── FractalWidget/
│ │ ├── CMakeLists.txt
│ │ ├── fractalwidget.cpp
│ │ ├── fractalwidget.h
│ │ ├── fractalworker.cpp
│ │ ├── fractalworker.h
│ │ ├── main.cpp
│ │ ├── mainwindow.cpp
│ │ └── mainwindow.h
│ ├── Generative_Lines/
│ │ ├── widget.cpp
│ │ └── widget.h
│ ├── Glitch_Text/
│ │ ├── GlitchTextWidget.cpp
│ │ └── GlitchTextWidget.h
│ ├── Honeycomb_Grid/
│ │ ├── hexagonwidget.cpp
│ │ ├── hexagonwidget.h
│ │ ├── mainwindow.cpp
│ │ └── mainwindow.h
│ ├── Letter_Glitch/
│ │ ├── CMakeLists.txt
│ │ ├── GlitchEffectWidget.cpp
│ │ ├── GlitchEffectWidget.h
│ │ └── main.cpp
│ ├── Liquid/
│ │ ├── image_processing.cpp
│ │ ├── image_processing.h
│ │ ├── liquid_button.cpp
│ │ ├── liquid_button.h
│ │ ├── widget.cpp
│ │ └── widget.h
│ ├── LoadingAnime/
│ │ ├── Bouncing_Ball_Loading.h
│ │ ├── CMakeLists.txt
│ │ ├── Rectangle_Loading.h
│ │ ├── Square_Pseudo_Bounce_Loading.cpp
│ │ ├── Square_Pseudo_Bounce_Loading.h
│ │ ├── black_white_ball_loading.cpp
│ │ ├── black_white_ball_loading.h
│ │ ├── bouncing_ball_loading.cpp
│ │ ├── hexagonloaderwidget.cpp
│ │ ├── hexagonloaderwidget.h
│ │ ├── line_loading.cpp
│ │ ├── line_loading.h
│ │ ├── line_rotating_along_rectangular_border.cpp
│ │ ├── line_rotating_along_rectangular_border.h
│ │ ├── main.cpp
│ │ ├── rectangle_loading.cpp
│ │ ├── regular_loading.cpp
│ │ ├── regular_loading.h
│ │ ├── ring_loading.cpp
│ │ ├── ring_loading.h
│ │ ├── widget.cpp
│ │ └── widget.h
│ ├── Login_interface/
│ │ ├── hollow_button.cpp
│ │ ├── hollow_button.h
│ │ ├── input_box.cpp
│ │ ├── input_box.h
│ │ ├── login_button.cpp
│ │ ├── login_button.h
│ │ ├── login_form.cpp
│ │ ├── login_form.h
│ │ ├── other_login_buttons.cpp
│ │ ├── other_login_buttons.h
│ │ ├── registration_form.cpp
│ │ ├── registration_form.h
│ │ ├── responsive_form.cpp
│ │ ├── responsive_form.h
│ │ ├── scroll_bar.cpp
│ │ ├── scroll_bar.h
│ │ ├── transparent_transition_interface.cpp
│ │ └── transparent_transition_interface.h
│ ├── Magnet_Lines/
│ │ ├── CMakeLists.txt
│ │ ├── RotatableLinesWidget.cpp
│ │ ├── RotatableLinesWidget.h
│ │ └── main.cpp
│ ├── Mimic_Button/
│ │ ├── depressed_button.cpp
│ │ ├── depressed_button.h
│ │ ├── img.qrc
│ │ ├── widget.cpp
│ │ └── widget.h
│ ├── Particle_Generation/
│ │ ├── CMakeLists.txt
│ │ ├── ParticleWidget.h
│ │ ├── main.cpp
│ │ ├── mainwindow.cpp
│ │ ├── mainwindow.h
│ │ └── particlewidget.cpp
│ ├── Physical_Text/
│ │ ├── DraggableElasticObject.cpp
│ │ ├── draggableelasticobject.h
│ │ └── main.cpp
│ ├── PixelTransition/
│ │ ├── pixel_transition.cpp
│ │ ├── pixel_transition.h
│ │ ├── widget.cpp
│ │ └── widget.h
│ ├── Point_Wave/
│ │ ├── widget.cpp
│ │ └── widget.h
│ ├── Pressure_Block/
│ │ ├── squarepressurewidget.cpp
│ │ └── squarepressurewidget.h
│ ├── SplitText/
│ │ ├── Single_Text.cpp
│ │ ├── Single_Text.h
│ │ ├── SplitText.cpp
│ │ └── SplitText.h
│ ├── Star_Sky_Connection/
│ │ ├── MovingPointsWidget.cpp
│ │ └── MovingPointsWidget.h
│ ├── TreeScene/
│ │ ├── TreeScene.cpp
│ │ └── TreeScene.h
│ ├── Wave/
│ │ ├── waveswidget.cpp
│ │ └── waveswidget.h
│ ├── Zipper_Slider/
│ │ ├── pathwidget.cpp
│ │ └── pathwidget.h
│ ├── button_class/
│ │ ├── diffusion_button.cpp
│ │ ├── diffusion_button.h
│ │ ├── wave_button.cpp
│ │ └── wave_button.h
│ ├── dial_class/
│ │ ├── knob_page.cpp
│ │ ├── knob_page.h
│ │ ├── temperature_dial.cpp
│ │ └── temperature_dial.h
│ ├── json/
│ │ └── Anime_care_attributes.json
│ ├── src.qrc
│ └── utility_class/
│ ├── timer_animation.cpp
│ ├── timer_animation.h
│ ├── timer_animationgroup.cpp
│ └── timer_animationgroup.h
├── LICENSE
└── README.md
================================================
FILE CONTENTS
================================================
================================================
FILE: Anime_Template_Project/Accordion/AccordionCard.cpp
================================================
#include "AccordionCard.h"
#include <QDebug>
#include <QPalette>
#include <QVariant>
#include <QPainter>
#include <QResizeEvent>
AccordionCard::AccordionCard(const QString &text, const QString &imagePath, QWidget *parent)
: QWidget(parent),
m_currentStretch(1.0)
{
m_label = new QLabel(text, this);
m_label->setAlignment(Qt::AlignCenter);
m_label->hide();
QVBoxLayout *layout = new QVBoxLayout(this);
layout->addWidget(m_label);
setLayout(layout);
setMinimumWidth(50);
m_stretchAnimation = new QPropertyAnimation(this, "currentStretch", this);
m_stretchAnimation->setDuration(280);
m_stretchAnimation->setEasingCurve(QEasingCurve::OutQuad);
connect(m_stretchAnimation, &QPropertyAnimation::valueChanged,
[this](const QVariant &value){
emit stretchChanged(this, value.toReal());
});
m_originalImage.load(imagePath);
if (m_originalImage.isNull()) {
qWarning() << "Failed to load image for AccordionCard from path:" << imagePath;
}
m_cachedScaledImage = QPixmap();
m_cachedImageSize = QSize(0,0);
}
qreal AccordionCard::currentStretch() const
{
return m_currentStretch;
}
void AccordionCard::setCurrentStretch(qreal stretch)
{
if (qFuzzyCompare(m_currentStretch, stretch))
return;
m_currentStretch = stretch;
updateGeometry();
}
void AccordionCard::setTargetStretch(qreal targetStretch)
{
if (m_stretchAnimation->state() == QAbstractAnimation::Running) {
m_stretchAnimation->stop();
}
m_stretchAnimation->setStartValue(m_currentStretch);
m_stretchAnimation->setEndValue(targetStretch);
m_stretchAnimation->start();
}
void AccordionCard::enterEvent(QEnterEvent *event)
{
emit hovered(this);
QWidget::enterEvent(event);
}
void AccordionCard::leaveEvent(QEvent *event)
{
emit left(this);
QWidget::leaveEvent(event);
}
void AccordionCard::paintEvent(QPaintEvent *event)
{
QPainter painter(this);
painter.setRenderHint(QPainter::Antialiasing, true);
int w = width();
int h = height();
int cornerRadius = 5;
QPainterPath path;
path.addRoundedRect(0, 0, w, h, cornerRadius, cornerRadius);
painter.setClipPath(path);
painter.fillRect(rect(), QColor(100, 100, 100, 255));
if (!m_originalImage.isNull())
{
if (m_cachedImageSize != QSize(w, h))
{
QSize imageSize = m_originalImage.size();
qreal imageAspectRatio = (qreal)imageSize.width() / imageSize.height();
qreal cardAspectRatio = (qreal)w / h;
QSize scaledTargetSize;
if (imageAspectRatio > cardAspectRatio)
{
scaledTargetSize = QSize(qRound(h * imageAspectRatio), h);
}
else
{
scaledTargetSize = QSize(w, qRound(w / imageAspectRatio));
}
m_cachedScaledImage = m_originalImage.scaled(scaledTargetSize,
Qt::KeepAspectRatio,
Qt::SmoothTransformation);
m_cachedImageSize = QSize(w, h);
}
int imageX = (w - m_cachedScaledImage.width()) / 2;
int imageY = (h - m_cachedScaledImage.height()) / 2;
painter.drawPixmap(imageX, imageY, m_cachedScaledImage);
}
}
void AccordionCard::resizeEvent(QResizeEvent *event)
{
if (event->oldSize() != event->size()) {
m_cachedScaledImage = QPixmap();
m_cachedImageSize = QSize(0,0);
}
QWidget::resizeEvent(event);
}
================================================
FILE: Anime_Template_Project/Accordion/AccordionCard.h
================================================
#ifndef ACCORDIONCARD_H
#define ACCORDIONCARD_H
#include <QWidget>
#include <QLabel>
#include <QVBoxLayout>
#include <QPropertyAnimation>
#include <QPixmap>
#include <QPainter>
#include <QPainterPath>
#include <QEnterEvent>
class AccordionCard : public QWidget
{
Q_OBJECT
Q_PROPERTY(qreal currentStretch READ currentStretch WRITE setCurrentStretch)
public:
explicit AccordionCard(const QString &text, const QString &imagePath, QWidget *parent = nullptr);
qreal currentStretch() const;
void setCurrentStretch(qreal stretch);
void setTargetStretch(qreal targetStretch);
protected:
void enterEvent(QEnterEvent *event) override;
void leaveEvent(QEvent *event) override;
void paintEvent(QPaintEvent *event) override;
// 添加 resizeEvent 以便在部件大小改变时清除缓存
void resizeEvent(QResizeEvent *event) override;
signals:
void hovered(AccordionCard *card);
void left(AccordionCard *card);
void stretchChanged(AccordionCard *card, qreal stretchValue);
private:
QLabel *m_label;
qreal m_currentStretch;
QPropertyAnimation *m_stretchAnimation;
QPixmap m_originalImage;
QPixmap m_cachedScaledImage;
QSize m_cachedImageSize;
};
#endif // ACCORDIONCARD_H
================================================
FILE: Anime_Template_Project/Accordion/CMakeLists.txt
================================================
cmake_minimum_required(VERSION 3.16)
project(untitled4 VERSION 0.1 LANGUAGES CXX)
set(CMAKE_AUTOUIC ON)
set(CMAKE_AUTOMOC ON)
set(CMAKE_AUTORCC ON)
set(CMAKE_CXX_STANDARD 17)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
find_package(QT NAMES Qt6 Qt5 REQUIRED COMPONENTS Widgets)
find_package(Qt${QT_VERSION_MAJOR} REQUIRED COMPONENTS Widgets)
set(PROJECT_SOURCES
main.cpp
AccordionCard.cpp
AccordionCard.h
)
if(${QT_VERSION_MAJOR} GREATER_EQUAL 6)
qt_add_executable(untitled4
MANUAL_FINALIZATION
${PROJECT_SOURCES}
AccordionWidget.h AccordionWidget.cpp
img.qrc
)
# Define target properties for Android with Qt 6 as:
# set_property(TARGET untitled4 APPEND PROPERTY QT_ANDROID_PACKAGE_SOURCE_DIR
# ${CMAKE_CURRENT_SOURCE_DIR}/android)
# For more information, see https://doc.qt.io/qt-6/qt-add-executable.html#target-creation
else()
if(ANDROID)
add_library(untitled4 SHARED
${PROJECT_SOURCES}
)
# Define properties for Android with Qt 5 after find_package() calls as:
# set(ANDROID_PACKAGE_SOURCE_DIR "${CMAKE_CURRENT_SOURCE_DIR}/android")
else()
add_executable(untitled4
${PROJECT_SOURCES}
)
endif()
endif()
target_link_libraries(untitled4 PRIVATE Qt${QT_VERSION_MAJOR}::Widgets)
# Qt for iOS sets MACOSX_BUNDLE_GUI_IDENTIFIER automatically since Qt 6.1.
# If you are developing for iOS or macOS you should consider setting an
# explicit, fixed bundle identifier manually though.
if(${QT_VERSION} VERSION_LESS 6.1.0)
set(BUNDLE_ID_OPTION MACOSX_BUNDLE_GUI_IDENTIFIER com.example.untitled4)
endif()
set_target_properties(untitled4 PROPERTIES
${BUNDLE_ID_OPTION}
MACOSX_BUNDLE_BUNDLE_VERSION ${PROJECT_VERSION}
MACOSX_BUNDLE_SHORT_VERSION_STRING ${PROJECT_VERSION_MAJOR}.${PROJECT_VERSION_MINOR}
MACOSX_BUNDLE TRUE
WIN32_EXECUTABLE TRUE
)
include(GNUInstallDirs)
install(TARGETS untitled4
BUNDLE DESTINATION .
LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR}
RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR}
)
if(QT_VERSION_MAJOR EQUAL 6)
qt_finalize_executable(untitled4)
endif()
================================================
FILE: Anime_Template_Project/Accordion/accordionwidget.cpp
================================================
#include "AccordionWidget.h"
#include <QDebug>
AccordionWidget::AccordionWidget(QWidget *parent)
: QWidget(parent)
{
m_layout = new QHBoxLayout(this);
m_layout->setSpacing(5);
setLayout(m_layout);
}
void AccordionWidget::addCard(AccordionCard *card)
{
m_cards.append(card);
m_layout->addWidget(card);
card->setCurrentStretch(1.0);
m_cardCurrentStretches.insert(card, 1.0);
connect(card, &AccordionCard::hovered, this, &AccordionWidget::onCardHovered);
connect(card, &AccordionCard::left, this, &AccordionWidget::onCardLeft);
connect(card, &AccordionCard::stretchChanged, this, &AccordionWidget::onCardStretchChanged);
updateLayoutStretches();
}
void AccordionWidget::onCardHovered(AccordionCard *hoveredCard)
{
qreal expandedStretch = 5.0;
qreal defaultStretch = 1.0;
for (AccordionCard *card : m_cards)
{
if (card == hoveredCard)
{
card->setTargetStretch(expandedStretch);
}
else
{
card->setTargetStretch(defaultStretch);
}
}
}
void AccordionWidget::onCardLeft(AccordionCard *leftCard)
{
Q_UNUSED(leftCard);
qreal defaultStretch = 1.0;
for (AccordionCard *card : m_cards)
{
card->setTargetStretch(defaultStretch);
}
}
void AccordionWidget::onCardStretchChanged(AccordionCard *card, qreal stretchValue)
{
m_cardCurrentStretches.insert(card, stretchValue);
updateLayoutStretches();
}
void AccordionWidget::updateLayoutStretches()
{
if (m_cards.isEmpty()) return;
for (int i = 0; i < m_cards.size(); ++i)
{
AccordionCard *card = m_cards.at(i);
int layoutStretch = static_cast<int>(m_cardCurrentStretches.value(card, 1.0) * 1000);
qDebug() << "Card" << i << "current stretch:" << m_cardCurrentStretches.value(card, 1.0)
<< "layout stretch factor:" << layoutStretch;
m_layout->setStretch(i, layoutStretch);
}
}
================================================
FILE: Anime_Template_Project/Accordion/accordionwidget.h
================================================
#ifndef ACCORDIONWIDGET_H
#define ACCORDIONWIDGET_H
#include <QWidget>
#include <QHBoxLayout>
#include <QList>
#include <QMap>
#include "AccordionCard.h"
class AccordionWidget : public QWidget
{
Q_OBJECT
public:
explicit AccordionWidget(QWidget *parent = nullptr);
void addCard(AccordionCard *card);
private slots:
void onCardHovered(AccordionCard *hoveredCard);
void onCardLeft(AccordionCard *leftCard);
void onCardStretchChanged(AccordionCard *card, qreal stretchValue);
private:
QHBoxLayout *m_layout;
QList<AccordionCard *> m_cards;
QMap<AccordionCard *, qreal> m_cardCurrentStretches;
void updateLayoutStretches();
};
#endif // ACCORDIONWIDGET_H // 预处理指令:结束条件编译块
================================================
FILE: Anime_Template_Project/Accordion/img.qrc
================================================
<RCC>
<qresource prefix="/">
<file>img/FvCpS5naYAA06ej.jpg</file>
<file>img/GaznbVDaMAAp7pf.jpg</file>
<file>img/GCPNMbRbMAAsh0_.jpg</file>
<file>img/GGE5u19acAAa7OA.jpg</file>
<file>img/GGIv8piaUAA_myh.jpg</file>
<file>img/GmGE-x0asAAuc9A.jpg</file>
<file>img/GniQBbrbUAAq-HX.jpg</file>
<file>img/GnkSUY9aMAAtOuY.jpg</file>
<file>img/GWN1xIIbAAA50xM.jpg</file>
<file>img/GS6v-JebIAIMmNY.jpg</file>
</qresource>
</RCC>
================================================
FILE: Anime_Template_Project/Accordion/main.cpp
================================================
#include <QApplication>
#include <QMainWindow>
#include "AccordionWidget.h"
#include "AccordionCard.h"
int main(int argc, char *argv[])
{
QApplication a(argc, argv);
QMainWindow window;
window.setWindowTitle("手风琴");
window.setMinimumSize(800, 300);
AccordionWidget *accordion = new AccordionWidget(&window);
accordion->addCard(new AccordionCard("卡片 1", "://img/FvCpS5naYAA06ej.jpg"));
accordion->addCard(new AccordionCard("卡片 2", "://img/GS6v-JebIAIMmNY.jpg"));
accordion->addCard(new AccordionCard("卡片 3", "://img/GniQBbrbUAAq-HX.jpg"));
accordion->addCard(new AccordionCard("卡片 4", "://img/GGE5u19acAAa7OA.jpg"));
accordion->addCard(new AccordionCard("卡片 5", "://img/GGIv8piaUAA_myh.jpg"));
window.setCentralWidget(accordion);
window.show();
return a.exec();
}
================================================
FILE: Anime_Template_Project/Adaptive_Carousel/daen_no_kado.cpp
================================================
#include "daen_no_kado.h"
Daen_no_Kado::Daen_no_Kado(QWidget *parent)
: QWidget{parent}
{
this->resize(1200, 606);
recta = QRect(0, 0, 1200, 606);
QPalette pal(this->palette());
pal.setColor(QPalette::Window, QColor(243, 246, 253));
this->setPalette(pal);
button = new Latticed_Circle_Button(this);
button2 = new Latticed_Circle_Button(this);
button->Shikisai_no_joutai = true;
connect(button, &Latticed_Circle_Button::Latticed_Circle_Click_Signal, this, &Daen_no_Kado::Move_Left);
connect(button2, &Latticed_Circle_Button::Latticed_Circle_Click_Signal, this, &Daen_no_Kado::Move_Right);
this->Get_Image();
this->Kiso_Deta_Kouchiku();
this->Gazou_wo_nabebae_ru();
connect(&timerA, &QTimer::timeout, this, &Daen_no_Kado::koushin_suru);
timerA.setInterval(16);
connect(&timerB, &QTimer::timeout, this, &Daen_no_Kado::Progress_Bar_Data_Update);
timerB.setInterval(16);
timerB.start();
this->animations();
}
void Daen_no_Kado::animations()
{
animation = new QPropertyAnimation(this->button, "geometry");
animation->setDuration(300);
animation->setStartValue(this->button->geometry());
animation->setEndValue(QRect(this->button->pos().x() - zoom_rate / 2, this->button->pos().y() - zoom_rate / 2, button->width() + zoom_rate, button->height() + zoom_rate));
animation->setEasingCurve(QEasingCurve::Linear);
animation2 = new QPropertyAnimation(this->button2, "geometry");
animation2->setDuration(300);
animation2->setStartValue(this->button2->geometry());
animation2->setEndValue(QRect(this->button2->pos().x() - zoom_rate / 2, this->button2->pos().y() - zoom_rate / 2, button2->width() + zoom_rate, button2->height() + zoom_rate));
animation2->setEasingCurve(QEasingCurve::Linear);
connect(button, &Latticed_Circle_Button::execute_animation_signal, this, [this](Latticed_Circle_Button::AnimationState state) {
if (state == Latticed_Circle_Button::Execute)
{
animation->setDirection(QAbstractAnimation::Forward);
animation->start();
}
else if (state == Latticed_Circle_Button::Restore)
{
animation->setDirection(QAbstractAnimation::Backward);
animation->start();
}
});
connect(button2, &Latticed_Circle_Button::execute_animation_signal, this, [this](Latticed_Circle_Button::AnimationState state) {
if (state == Latticed_Circle_Button::Execute)
{
animation2->setDirection(QAbstractAnimation::Forward);
animation2->start();
}
else if (state == Latticed_Circle_Button::Restore)
{
animation2->setDirection(QAbstractAnimation::Backward);
animation2->start();
}
});
animation3 = new QPropertyAnimation(this, "Expand_Collapse_Height");
animation3->setDuration(360);
animation3->setStartValue(m_Expand_Collapse_Height);
animation3->setEndValue(recta.height());
animation3->setEasingCurve(QEasingCurve::Linear);
animation4 = new QPropertyAnimation(this, "Expand_Collapse_Opacity");
animation4->setDuration(360);
animation4->setStartValue(m_Expand_Collapse_Opacity);
animation4->setEndValue(0);
animation4->setEasingCurve(QEasingCurve::Linear);
}
void Daen_no_Kado::Get_Image()
{
qreal x = 0;
for (int i = 1; i < 99; i++)
{
QPixmap pixmap(QString("://img/card_image%1.jpg").arg(i));
if (pixmap.isNull()) return;
Gazou_Shuu.append(pixmap);
}
}
void Daen_no_Kado::Kiso_Deta_Kouchiku()
{
leftBound = recta.width() * 0.3750;
Jouhan_Daen_no_Chuushin = QPointF(recta.width() / 2.0, 0);
Jouhan_Daen_no_X_Hankei = recta.width() * 0.56;
Jouhan_Daen_no_Y_Hankei = recta.height() * 0.2215;
Kahan_Daen_no_Chuushin = QPointF(recta.width() / 2.0, recta.height());
Kahan_Daen_no_X_Hankei = recta.width() * 0.656;
Kahan_Daen_no_Y_Hankei = recta.height() * 0.3261;
int i = recta.width() / 30;
button->resize(i, i);
button2->resize(i, i);
button->move(recta.width() * 0.45, recta.height() * 0.8);
button2->move(recta.width() * 0.50, recta.height() * 0.8);
Progress_Bar_Step = qreal(recta.width()) / qreal(recta.height()) * 1.6;
m_Expand_Collapse_Height = recta.height() * 0.98;
qDebug() << "进度条步长" << Progress_Bar_Step;
qDebug() << "展开高度" << m_Expand_Collapse_Height;
Kado_Suu.clear();
this->Gazou_wo_nabebae_ru();
this->animations();
}
void Daen_no_Kado::Gazou_wo_nabebae_ru()
{
qreal x = Ratio_Position * recta.width();
for (int i = 0; i < Gazou_Shuu.size(); i++)
{
if (i == 0)
Left_Limit_Margin = x + -leftBound * 0.4444;
else if (i == Gazou_Shuu.size() - 1)
Right_Limit_Margin = x + leftBound * 0.3333;
Kado_Suu.append(qMakePair(x, leftBound * 0.6666 + x));
x += leftBound * 0.6888;
}
kankaku = Kado_Suu[3].second - Kado_Suu[3].first;
}
void Daen_no_Kado::resizeEvent(QResizeEvent* event)
{
recta = QRect(0, 0, event->size().width(), event->size().height());
this->Kiso_Deta_Kouchiku();
m_Progress_Bar_X = (m_Progress_Bar_X / event->oldSize().width()) * event->size().width();
m_Progress_Bar_Width = (m_Progress_Bar_Width / event->oldSize().width()) * event->size().width();
QWidget::resizeEvent(event);
}
void Daen_no_Kado::mousePressEvent(QMouseEvent* event)
{
if (event->button() == Qt::LeftButton)
{
if (!Ima_no_joutai) return;
this->setCursor(Qt::PointingHandCursor);
mousePressed = true;
startX = event->pos().x();
accumulatedDistance = 0;
}
QWidget::mousePressEvent(event);
}
void Daen_no_Kado::mouseMoveEvent(QMouseEvent* event)
{
if (mousePressed)
{
int currentX = event->pos().x();
int deltaX = currentX - startX;
if (deltaX > 0) Execution_Direction = true;
else if (deltaX <= 0) Execution_Direction = false;
accumulatedDistance += qAbs(deltaX);
if (accumulatedDistance >= 9) {
this->koushin_suru();
accumulatedDistance -= 9;
}
startX = currentX;
}
QWidget::mouseMoveEvent(event);
}
void Daen_no_Kado::mouseReleaseEvent(QMouseEvent* event)
{
if (event->button() == Qt::LeftButton)
{
this->setCursor(Qt::ArrowCursor);
mousePressed = false;
accumulatedDistance = 0;
}
QWidget::mouseReleaseEvent(event);
}
bool Daen_no_Kado::event(QEvent* e)
{
if (e->type() == QEvent::Enter)
{
timerB.stop();
animation3->setDirection(QAbstractAnimation::Forward);
animation3->start();
animation4->setDirection(QAbstractAnimation::Forward);
animation4->start();
}
else if (e->type() == QEvent::Leave)
{
timerB.start();
animation3->setDirection(QAbstractAnimation::Backward);
animation3->start();
animation4->setDirection(QAbstractAnimation::Backward);
animation4->start();
}
return QWidget::event(e);
}
void Daen_no_Kado::wheelEvent(QWheelEvent *event)
{
if (event->angleDelta().y() > 0)
this->Card_Move_Left_Behavior();
else if (event->angleDelta().y() < 0)
this->Card_Move_Right_Behavior();
}
void Daen_no_Kado::paintEvent(QPaintEvent *event)
{
QPainter painter(this);
painter.setRenderHints(QPainter::Antialiasing | QPainter::LosslessImageRendering);
for (int i = 0; i < Kado_Suu.size(); i++)
Byouga_Ryouiki(Kado_Suu[i].first, Kado_Suu[i].second, Gazou_Shuu[i]);
this->draw_text();
this->Draw_Progress_Bar();
}
void Daen_no_Kado::Byouga_Ryouiki(qreal& Gazou_Zen_XJiku, qreal& Gazou_Go_XJiku, QPixmap& Ehon)
{
QPainter painter(this);
painter.setRenderHints(QPainter::Antialiasing | QPainter::LosslessImageRendering);
if (Gazou_Zen_XJiku > recta.width() || Gazou_Go_XJiku < 0) return;
qreal Haba = Gazou_Go_XJiku - Gazou_Zen_XJiku;
QRectF Kari_no_saizu(Gazou_Zen_XJiku, 0, Haba, recta.height());
QPainterPath targetPath1;
targetPath1.addEllipse(Kahan_Daen_no_Chuushin, Kahan_Daen_no_X_Hankei, Kahan_Daen_no_Y_Hankei);
QPainterPath targetPath2;
targetPath2.addEllipse(Jouhan_Daen_no_Chuushin, Jouhan_Daen_no_X_Hankei, Jouhan_Daen_no_Y_Hankei);
QPainterPath mergedTargetPath = targetPath1.united(targetPath2);
QPainterPath entireArea;
entireArea.addRect(recta);
QPainterPath clipPath = entireArea.subtracted(mergedTargetPath);
QPainterPath targetPath3;
targetPath3.addRect(Kari_no_saizu);
QPainterPath targetPath4 = clipPath.intersected(targetPath3);
painter.setClipPath(targetPath4);
qreal targetHeight = Kari_no_saizu.height() * Keisan_suru_shukusetsu_no_takasa(Gazou_Zen_XJiku);
qreal aspectRatio = Ehon.width() / qreal(Ehon.height());
qreal targetWidth = targetHeight * aspectRatio;
QRectF targetRect;
targetRect.setSize(QSizeF(targetWidth, targetHeight));
targetRect.moveCenter(QPointF(Kari_no_saizu.center().rx(), Kari_no_saizu.height() * 0.45));
QTransform transform;
QPointF center = targetRect.center();
transform.translate(center.x(), center.y());
transform.rotate(calculateRectRotation(Gazou_Zen_XJiku), Qt::YAxis, 2048.0);
transform.translate(-center.x(), -center.y());
painter.setWorldTransform(transform);
painter.drawPixmap(targetRect, Ehon, Ehon.rect());
QRect rect1(0, 0, recta.width(), recta.height());
QFont font1;
font1.setPixelSize(recta.width() / 45);
font1.setBold(true);
font1.setWordSpacing(4);
font1.setStyleHint(QFont::Decorative);
painter.setFont(font1);
QColor semiTransparent(255, 177, 248, 255);
painter.setPen(semiTransparent);
painter.drawText(Kari_no_saizu, Qt::AlignCenter, QString("夹心假面"));
}
void Daen_no_Kado::draw_text()
{
QPainter painter(this);
painter.setRenderHints(QPainter::Antialiasing | QPainter::TextAntialiasing);
painter.setViewport(recta);
painter.setWindow(recta);
QRect rect1(0, 0, recta.width(), recta.height());
QFont font1;
font1.setPixelSize(recta.width() / 35);
font1.setBold(true);
font1.setWordSpacing(4);
font1.setStyleHint(QFont::Decorative);
painter.setFont(font1);
QColor semiTransparent(0, 0, 0, 255);
painter.setPen(semiTransparent);
QRect actualRect = painter.boundingRect(rect1, Qt::AlignCenter, QString("Hello_World"));
rect1.setHeight(actualRect.height());
rect1.setWidth(actualRect.width());
rect1.moveCenter(QPoint(width() / 2, height() / 10));
painter.drawText(rect1, QString("Hello_World"));
}
void Daen_no_Kado::Draw_Progress_Bar()
{
QPainter painter(this);
painter.setRenderHints(QPainter::Antialiasing | QPainter::TextAntialiasing);
painter.setViewport(recta);
painter.setWindow(recta);
painter.setPen(Qt::NoPen);
QBrush brush;
brush.setColor(QColor(129, 249, 255, m_Expand_Collapse_Opacity));
brush.setStyle(Qt::SolidPattern);
painter.setBrush(brush);
painter.drawRect(QRectF(m_Progress_Bar_X, m_Expand_Collapse_Height, m_Progress_Bar_Width, recta.height() * 0.04));
}
void Daen_no_Kado::Progress_Bar_Data_Update()
{
if (Is_Execution_Step_Width)
{
m_Progress_Bar_Width += Progress_Bar_Step;
m_Progress_Bar_X = 0;
if (m_Progress_Bar_Width >= recta.width())
{
Is_Execution_Step_Width = false;
Is_Execution_Step_X = true;
this->Card_Move_Right_Behavior();
}
}
else if (Is_Execution_Step_X)
{
m_Progress_Bar_X += Progress_Bar_Step;
m_Progress_Bar_Width -= Progress_Bar_Step;
if (m_Progress_Bar_X >= recta.width())
{
m_Progress_Bar_Width = recta.width();
Is_Execution_Step_X = false;
this->Card_Move_Right_Behavior();
}
}
else if (m_Progress_Bar_X > 0)
{
m_Progress_Bar_X -= Progress_Bar_Step;
if (m_Progress_Bar_X <= 0)
{
m_Progress_Bar_X = 0;
this->Card_Move_Right_Behavior();
}
}
else
{
m_Progress_Bar_Width -= Progress_Bar_Step;
if (m_Progress_Bar_Width <= 0)
{
m_Progress_Bar_Width = 0;
Is_Execution_Step_Width = true;
this->Card_Move_Right_Behavior();
}
}
update();
}
void Daen_no_Kado::koushin_suru()
{
for (auto& pair : Kado_Suu)
{
if (Execution_Direction == false)
{
pair.first -= Time_Step;
pair.second -= Time_Step;
}
else if (Execution_Direction == true)
{
pair.first += Time_Step;
pair.second += Time_Step;
}
}
if (Kado_Suu[0].first < Left_Limit_Margin)
{
Kado_Suu.append(Kado_Suu.takeFirst());
Gazou_Shuu.append(Gazou_Shuu.takeFirst());
Kado_Suu[Kado_Suu.size() - 1].first = Kado_Suu[Kado_Suu.size() - 2].first + leftBound * 0.6888;
Kado_Suu[Kado_Suu.size() - 1].second = Kado_Suu[Kado_Suu.size() - 2].second + leftBound * 0.6888;
}
else if (Kado_Suu[Kado_Suu.size() - 1].first > Right_Limit_Margin)
{
Kado_Suu.prepend(Kado_Suu.takeLast());
Gazou_Shuu.prepend(Gazou_Shuu.takeLast());
Kado_Suu[0].first = Kado_Suu[1].first - leftBound * 0.6888;
Kado_Suu[0].second = Kado_Suu[1].second - leftBound * 0.6888;
}
if (mousePressed == true)
{
timerA.stop();
Ratio_Position = Kado_Suu[0].first / recta.width();
update();
return;
}
Kari_no_kankaku += Time_Step;
if (Kari_no_kankaku >= leftBound * 0.6888)
{
timerA.stop();
Ima_no_joutai = true;
Ratio_Position = Kado_Suu[0].first / recta.width();
}
update();
}
qreal Daen_no_Kado::Keisan_suru_shukusetsu_no_takasa(qreal& xLeft)
{
if (xLeft < leftBound)
{
qreal overflow = leftBound - xLeft;
return overflow / leftBound / 4 + maxRadians;
}
else if (xLeft > leftBound)
{
qreal overflow = xLeft - leftBound;
return overflow / leftBound / 4 + maxRadians;
}
else
{
return maxRadians;
}
}
qreal Daen_no_Kado::calculateRectRotation(qreal& xLeft)
{
// 计算左侧影响
if (xLeft < leftBound)
{
qreal overflow = leftBound - xLeft;
return -maxRadians2 * (overflow / leftBound);
}
else if (xLeft > leftBound)
{
qreal overflow = xLeft - leftBound;
return maxRadians2 * (overflow / leftBound);
}
else return 0.0;
}
void Daen_no_Kado::Move_Left()
{
if (Ima_no_joutai != true) return;
this->Card_Move_Left_Behavior();
}
void Daen_no_Kado::Move_Right()
{
if (Ima_no_joutai != true) return;
this->Card_Move_Right_Behavior();
}
void Daen_no_Kado::Card_Move_Right_Behavior()
{
Ima_no_joutai = false;
timerA.start();
Kari_no_kankaku = 0;
Execution_Direction = true;
}
void Daen_no_Kado::Card_Move_Left_Behavior()
{
Ima_no_joutai = false;
timerA.start();
Kari_no_kankaku = 0;
Execution_Direction = false;
}
qreal Daen_no_Kado::Progress_Bar_X() const
{
return m_Progress_Bar_X;
}
void Daen_no_Kado::setProgress_Bar_X(qreal newProgress_Bar_X)
{
if (m_Progress_Bar_X == newProgress_Bar_X)
return;
m_Progress_Bar_X = newProgress_Bar_X;
}
qreal Daen_no_Kado::Progress_Bar_Width() const
{
return m_Progress_Bar_Width;
}
void Daen_no_Kado::setProgress_Bar_Width(qreal newProgress_Bar_Width)
{
if (m_Progress_Bar_Width == newProgress_Bar_Width)
return;
m_Progress_Bar_Width = newProgress_Bar_Width;
}
qreal Daen_no_Kado::Expand_Collapse_Height() const
{
return m_Expand_Collapse_Height;
}
void Daen_no_Kado::setExpand_Collapse_Height(qreal newExpand_Collapse_Height)
{
if (qFuzzyCompare(m_Expand_Collapse_Height, newExpand_Collapse_Height))
return;
m_Expand_Collapse_Height = newExpand_Collapse_Height;
update();
}
int Daen_no_Kado::Expand_Collapse_Opacity() const
{
return m_Expand_Collapse_Opacity;
}
void Daen_no_Kado::setExpand_Collapse_Opacity(int newExpand_Collapse_Opacity)
{
if (m_Expand_Collapse_Opacity == newExpand_Collapse_Opacity)
return;
m_Expand_Collapse_Opacity = newExpand_Collapse_Opacity;
update();
}
================================================
FILE: Anime_Template_Project/Adaptive_Carousel/daen_no_kado.h
================================================
#ifndef DAEN_NO_KADO_H
#define DAEN_NO_KADO_H
#include <QWidget>
#include <QPainter>
#include <QPainterPath>
#include <QVector>
#include <QPixmap>
#include <QResizeEvent>
#include <QTimer>
#include "latticed_circle_button.h"
class Daen_no_Kado : public QWidget
{
Q_OBJECT
Q_PROPERTY(qreal Progress_Bar_X READ Progress_Bar_X WRITE setProgress_Bar_X FINAL)
Q_PROPERTY(qreal Progress_Bar_Width READ Progress_Bar_Width WRITE setProgress_Bar_Width FINAL)
Q_PROPERTY(qreal Expand_Collapse_Height READ Expand_Collapse_Height WRITE setExpand_Collapse_Height FINAL)
Q_PROPERTY(int Expand_Collapse_Opacity READ Expand_Collapse_Opacity WRITE setExpand_Collapse_Opacity FINAL)
public:
explicit Daen_no_Kado(QWidget* parent = nullptr);
void Get_Image();
void Kiso_Deta_Kouchiku();
void Gazou_wo_nabebae_ru();
void Byouga_Ryouiki(qreal& Gazou_Zen_XJiku, qreal& Gazou_Go_XJiku, QPixmap& Ehon);
void draw_text();
void Draw_Progress_Bar();
qreal calculateRectRotation(qreal& xLeft);
qreal Keisan_suru_shukusetsu_no_takasa(qreal& xLeft);
void animations();
QPropertyAnimation* animation;
QPropertyAnimation* animation2;
QPropertyAnimation* animation3;
QPropertyAnimation* animation4;
int zoom_rate = 10;
Latticed_Circle_Button* button;
Latticed_Circle_Button* button2;
QTimer timerA;
QTimer timerB;
void Card_Move_Left_Behavior();
void Card_Move_Right_Behavior();
public:
qreal Progress_Bar_X() const;
void setProgress_Bar_X(qreal newProgress_Bar_X);
qreal Progress_Bar_Width() const;
void setProgress_Bar_Width(qreal newProgress_Bar_Width);
qreal Expand_Collapse_Height() const;
void setExpand_Collapse_Height(qreal newExpand_Collapse_Height);
int Expand_Collapse_Opacity() const;
void setExpand_Collapse_Opacity(int newExpand_Collapse_Opacity);
public slots:
void Move_Left();
void Move_Right();
void koushin_suru();
void Progress_Bar_Data_Update();
protected:
void paintEvent(QPaintEvent* event);
void resizeEvent(QResizeEvent* event);
void mousePressEvent(QMouseEvent* event);
void mouseMoveEvent(QMouseEvent* event);
void mouseReleaseEvent(QMouseEvent* event);
bool event(QEvent* e);
void wheelEvent(QWheelEvent* event);
private:
QVector<QPixmap> Gazou_Shuu;
QVector<QPair<qreal, qreal>> Kado_Suu;
qreal kankaku;
qreal Kari_no_kankaku;
qreal Left_Limit_Margin;
qreal Right_Limit_Margin;
qreal Substitute_Required_Spacing;
bool Ima_no_joutai = true;
bool Execution_Direction = false;
QRect recta;
qreal maxRadians = 0.5;
qreal maxRadians2 = 28.0;
qreal leftBound = 0.0;
qreal Ratio_Position = -0.375;
qreal Time_Step = 15.000;
QPointF Jouhan_Daen_no_Chuushin;
double Jouhan_Daen_no_Y_Hankei;
double Jouhan_Daen_no_X_Hankei;
QPointF Kahan_Daen_no_Chuushin;
double Kahan_Daen_no_Y_Hankei;
double Kahan_Daen_no_X_Hankei;
bool mousePressed = false;
int startX = 0;
int accumulatedDistance = 0;
qreal m_Progress_Bar_X = 0;
qreal m_Progress_Bar_Width = 0;
qreal Progress_Bar_Step = 1;
bool Is_Execution_Step_Width = true;
bool Is_Execution_Step_X = false;
qreal m_Expand_Collapse_Height;
int m_Expand_Collapse_Opacity = 255;
};
#endif // DAEN_NO_KADO_H
================================================
FILE: Anime_Template_Project/Adaptive_Carousel/latticed_circle_button.cpp
================================================
#include "latticed_circle_button.h"
Latticed_Circle_Button::Latticed_Circle_Button(QWidget* parent) : QPushButton{ parent }
{
this->resize(50, 50);
this->setCursor(Qt::PointingHandCursor);
QGraphicsDropShadowEffect* shadow = new QGraphicsDropShadowEffect(this);
shadow->setOffset(0, 13);
shadow->setBlurRadius(30);
shadow->setColor(QColor(0, 0, 0, 100));
this->setGraphicsEffect(shadow);
animation1 = new QPropertyAnimation(this, "Tomeido");
animation1->setDuration(300);
animation1->setStartValue(m_Tomeido);
animation1->setEndValue(255);
animation1->setEasingCurve(QEasingCurve::Linear);
animation2 = new QPropertyAnimation(this, "Current_Color");
animation2->setDuration(300);
animation2->setStartValue(m_Current_Color);
animation2->setEndValue(QColor(255, 255, 255, 255));
animation2->setEasingCurve(QEasingCurve::Linear);
}
void Latticed_Circle_Button::paintEvent(QPaintEvent* event)
{
QPainter painter(this);
painter.setRenderHints(QPainter::Antialiasing);
painter.setViewport(0, 0, width(), width());
painter.setWindow(0, 0, 50, 50);
QPen pen;
pen.setWidth(2.00);
pen.setColor(Qt::black);
painter.setPen(pen);
QBrush brush;
brush.setColor(QColor(0, 0, 0, m_Tomeido));
brush.setStyle(Qt::SolidPattern);
painter.setBrush(brush);
painter.drawEllipse(3, 3, 44, 44 );
QPen pen1;
pen1.setWidth(4);
pen1.setColor(m_Current_Color);
pen1.setStyle(Qt::SolidLine);
pen1.setCapStyle(Qt::FlatCap);
pen1.setJoinStyle(Qt::MiterJoin);
painter.setPen(pen1);
if (Shikisai_no_joutai == true)
{
QPoint points[] = {
QPoint(28, 15),
QPoint(18, 25),
QPoint(28, 35),
};
painter.drawPolyline(points, 3);
}
else
{
QPoint points[] = {
QPoint(23, 15),
QPoint(33, 25),
QPoint(23, 35),
};
painter.drawPolyline(points, 3);
}
}
bool Latticed_Circle_Button::event(QEvent* e)
{
if (e->type() == QEvent::Enter)
{
animation1->setDirection(QPropertyAnimation::Forward);
animation1->start();
animation2->setDirection(QPropertyAnimation::Forward);
animation2->start();
emit execute_animation_signal(AnimationState::Execute);
update();
}
else if (e->type() == QEvent::Leave)
{
animation1->setDirection(QPropertyAnimation::Backward);
animation1->start();
animation2->setDirection(QPropertyAnimation::Backward);
animation2->start();
emit execute_animation_signal(AnimationState::Restore);
update();
}
return QPushButton::event(e);
}
void Latticed_Circle_Button::mousePressEvent(QMouseEvent* event)
{
if (event->button() == Qt::LeftButton) emit Latticed_Circle_Click_Signal();
}
int Latticed_Circle_Button::Tomeido() const
{
return m_Tomeido;
}
void Latticed_Circle_Button::setTomeido(int newTomeido)
{
if (m_Tomeido == newTomeido)
return;
m_Tomeido = newTomeido;
update();
}
QColor Latticed_Circle_Button::Current_Color() const
{
return m_Current_Color;
}
void Latticed_Circle_Button::setCurrent_Color(const QColor &newCurrent_Color)
{
if (m_Current_Color == newCurrent_Color)
return;
m_Current_Color = newCurrent_Color;
update();
}
================================================
FILE: Anime_Template_Project/Adaptive_Carousel/latticed_circle_button.h
================================================
#ifndef LATTICED_CIRCLE_BUTTON_H
#define LATTICED_CIRCLE_BUTTON_H
#include <QPushButton>
#include <QPainter>
#include <QGraphicsDropShadowEffect>
#include <QPropertyAnimation>
#include <QMouseEvent>
class Latticed_Circle_Button : public QPushButton
{
Q_OBJECT
Q_PROPERTY(int Tomeido READ Tomeido WRITE setTomeido FINAL)
Q_PROPERTY(QColor Current_Color READ Current_Color WRITE setCurrent_Color FINAL)
public:
explicit Latticed_Circle_Button(QWidget* parent = nullptr);
enum AnimationState {
Execute,
Restore
};
QPropertyAnimation *animation1;
QPropertyAnimation* animation2;
bool Shikisai_no_joutai = false;
int Tomeido() const;
void setTomeido(int newTomeido);
QColor Current_Color() const;
void setCurrent_Color(const QColor &newCurrent_Color);
signals:
void Latticed_Circle_Click_Signal();
void execute_animation_signal(Latticed_Circle_Button::AnimationState state);
protected:
void paintEvent(QPaintEvent *event);
void mousePressEvent(QMouseEvent *event);
bool event(QEvent* e);
private:
int m_Tomeido = 0;
QColor m_Current_Color = QColor(0, 0, 0, 255);
};
#endif // LATTICED_CIRCLE_BUTTON_H
================================================
FILE: Anime_Template_Project/Blur_Text/fuzzytextwidget.cpp
================================================
#include "FuzzyTextWidget.h"
#include <QPainter>
#include <QPaintEvent>
#include <QMouseEvent>
#include <QDebug>
#include <QScreen>
#include <QApplication>
#include <QFontMetricsF>
#include <QRandomGenerator>
FuzzyTextWidget::FuzzyTextWidget(QWidget *parent)
: QWidget(parent),
m_text("Hello, Qt!"),
m_fontSizeStr("clamp(2rem, 10vw, 10rem)"),
m_fontWeight(QFont::Black),
m_fontFamily("Arial"),
m_color(Qt::white),
m_enableHover(true),
m_baseIntensity(0.18),
m_hoverIntensity(0.5),
m_isHovering(false),
m_numericFontSize(0.0)
{
setAttribute(Qt::WA_TranslucentBackground);
setMouseTracking(true);
m_animationTimer = new QTimer(this);
connect(m_animationTimer, &QTimer::timeout, this, &FuzzyTextWidget::updateFuzzyEffect);
m_animationTimer->start(16);
updateTextMetrics();
initializeOffscreenBuffer();
setMinimumSize(m_offscreenPixmap.size() + QSize(100, 0));
}
FuzzyTextWidget::~FuzzyTextWidget()
{
m_animationTimer->stop();
delete m_animationTimer;
}
void FuzzyTextWidget::setText(const QString &text)
{
if (m_text != text) {
m_text = text;
updateTextMetrics();
initializeOffscreenBuffer();
update();
}
}
void FuzzyTextWidget::setFontSize(const QString &fontSize)
{
if (m_fontSizeStr != fontSize)
{
m_fontSizeStr = fontSize;
updateTextMetrics();
initializeOffscreenBuffer();
update();
}
}
void FuzzyTextWidget::setFontWeight(QFont::Weight fontWeight)
{
if (m_fontWeight != fontWeight)
{
m_fontWeight = fontWeight;
updateTextMetrics();
initializeOffscreenBuffer();
update();
}
}
void FuzzyTextWidget::setFontFamily(const QString &fontFamily)
{
if (m_fontFamily != fontFamily)
{
m_fontFamily = fontFamily;
updateTextMetrics();
initializeOffscreenBuffer();
update();
}
}
void FuzzyTextWidget::setColor(const QColor &color)
{
if (m_color != color)
{
m_color = color;
initializeOffscreenBuffer();
update();
}
}
void FuzzyTextWidget::setEnableHover(bool enable)
{
m_enableHover = enable;
if (!m_enableHover) {
m_isHovering = false;
update();
}
}
void FuzzyTextWidget::setBaseIntensity(double intensity)
{
m_baseIntensity = intensity;
}
void FuzzyTextWidget::setHoverIntensity(double intensity)
{
m_hoverIntensity = intensity;
}
double FuzzyTextWidget::parseFontSize(const QString &fontSizeStr, double defaultSize)
{
if (fontSizeStr.endsWith("px", Qt::CaseInsensitive))
{
return fontSizeStr.chopped(2).toDouble();
}
else if (fontSizeStr.endsWith("rem", Qt::CaseInsensitive))
{
return fontSizeStr.chopped(3).toDouble() * 16.0;
}
else if (fontSizeStr.endsWith("vw", Qt::CaseInsensitive))
{
QScreen *screen = QGuiApplication::primaryScreen();
if (screen)
{
return fontSizeStr.chopped(2).toDouble() / 100.0 * screen->geometry().width();
}
return defaultSize;
}
else if (fontSizeStr.startsWith("clamp(", Qt::CaseInsensitive) && fontSizeStr.endsWith(")"))
{
QString content = fontSizeStr.mid(6, fontSizeStr.length() - 7);
QStringList parts = content.split(",", Qt::SkipEmptyParts);
if (parts.size() == 3) {
double minVal = parseFontSize(parts[0].trimmed(), defaultSize);
double preferredVal = parseFontSize(parts[1].trimmed(), defaultSize);
double maxVal = parseFontSize(parts[2].trimmed(), defaultSize);
return qBound(minVal, preferredVal, maxVal);
}
}
return defaultSize;
}
void FuzzyTextWidget::updateTextMetrics()
{
QFont font;
font.setFamily(m_fontFamily);
font.setWeight(m_fontWeight);
m_numericFontSize = parseFontSize(m_fontSizeStr, 48.0);
font.setPixelSize(static_cast<int>(m_numericFontSize));
QFontMetricsF metrics(font);
m_textBoundingRect = metrics.boundingRect(m_text).toRect();
int extraWidthBuffer = 10;
int horizontalMargin = 50;
int verticalMargin = 0;
int offscreenWidth = m_textBoundingRect.width() + extraWidthBuffer;
int tightHeight = m_textBoundingRect.height();
setFixedSize(offscreenWidth + horizontalMargin * 2, tightHeight + verticalMargin * 2);
qDebug() << "Calculated font size:" << m_numericFontSize;
qDebug() << "Text bounding rect:" << m_textBoundingRect;
qDebug() << "Widget fixed size:" << size();
}
void FuzzyTextWidget::initializeOffscreenBuffer()
{
if (m_text.isEmpty())
{
m_offscreenPixmap = QPixmap();
return;
}
updateTextMetrics();
int offscreenWidth = m_textBoundingRect.width() + 10;
int offscreenHeight = m_textBoundingRect.height();
m_offscreenPixmap = QPixmap(offscreenWidth, offscreenHeight);
m_offscreenPixmap.fill(Qt::transparent);
QPainter painter(&m_offscreenPixmap);
painter.setRenderHint(QPainter::Antialiasing);
QFont font;
font.setFamily(m_fontFamily);
font.setWeight(m_fontWeight);
font.setPixelSize(static_cast<int>(m_numericFontSize));
painter.setFont(font);
painter.setPen(m_color);
painter.drawText(5 - m_textBoundingRect.left(), -m_textBoundingRect.top(), m_text);
}
void FuzzyTextWidget::paintEvent(QPaintEvent *event)
{
QPainter painter(this);
painter.setRenderHint(QPainter::Antialiasing);
if (m_offscreenPixmap.isNull() || m_text.isEmpty())
{
return;
}
const int fuzzRange = 30;
double intensity = m_isHovering ? m_hoverIntensity : m_baseIntensity;
for (int j = 0; j < m_offscreenPixmap.height(); j++)
{
int dx = static_cast<int>(intensity * (QRandomGenerator::global()->generateDouble() - 0.5) * fuzzRange);
painter.drawPixmap(dx + 50,
j + 0,
m_offscreenPixmap,
0,
j,
m_offscreenPixmap.width(),
1);
}
}
void FuzzyTextWidget::mouseMoveEvent(QMouseEvent *event)
{
if (m_enableHover)
{
QRect interactiveArea(55, 0, m_textBoundingRect.width(), m_textBoundingRect.height());
bool nowHovering = interactiveArea.contains(event->pos());
if (nowHovering != m_isHovering)
{
m_isHovering = nowHovering;
update();
}
}
QWidget::mouseMoveEvent(event);
}
void FuzzyTextWidget::leaveEvent(QEvent *event)
{
if (m_enableHover && m_isHovering)
{
m_isHovering = false;
update();
}
QWidget::leaveEvent(event);
}
void FuzzyTextWidget::resizeEvent(QResizeEvent *event)
{
updateTextMetrics();
initializeOffscreenBuffer();
QWidget::resizeEvent(event);
}
void FuzzyTextWidget::updateFuzzyEffect()
{
update();
}
================================================
FILE: Anime_Template_Project/Blur_Text/fuzzytextwidget.h
================================================
#ifndef FUZZYTEXTWIDGET_H
#define FUZZYTEXTWIDGET_H
#include <QWidget>
#include <QTimer>
#include <QColor>
#include <QFont>
class FuzzyTextWidget : public QWidget
{
Q_OBJECT
public:
explicit FuzzyTextWidget(QWidget *parent = nullptr);
~FuzzyTextWidget();
void setText(const QString &text);
void setFontSize(const QString &fontSize);
void setFontWeight(QFont::Weight fontWeight);
void setFontFamily(const QString &fontFamily);
void setColor(const QColor &color);
void setEnableHover(bool enable);
void setBaseIntensity(double intensity);
void setHoverIntensity(double intensity);
protected:
void paintEvent(QPaintEvent *event) override;
void mouseMoveEvent(QMouseEvent *event) override;
void leaveEvent(QEvent *event) override;
void resizeEvent(QResizeEvent *event) override;
private slots:
void updateFuzzyEffect();
private:
void initializeOffscreenBuffer();
void updateTextMetrics();
double parseFontSize(const QString &fontSizeStr, double defaultSize);
QString m_text;
QString m_fontSizeStr;
QFont::Weight m_fontWeight;
QString m_fontFamily;
QColor m_color;
bool m_enableHover;
double m_baseIntensity;
double m_hoverIntensity;
QTimer *m_animationTimer;
QPixmap m_offscreenPixmap;
bool m_isHovering;
QRect m_textBoundingRect;
double m_numericFontSize;
};
#endif // FUZZYTEXTWIDGET_H
================================================
FILE: Anime_Template_Project/Carousel_card/card_button.cpp
================================================
#include "card_button.h"
Card_button::Card_button(QString text, QColor button_color, QWidget* parent) : QPushButton{ parent }
{
this->btntext = text;
this->m_button_color = button_color;
this->resize(122, 32);
this->color_control();
animation = new QPropertyAnimation(this, "color_opacity");
animation->setDuration(100);
animation->setStartValue(this->color_opacity());
animation->setEndValue(0);
connect(this, &Card_button::pressed, this, &Card_button::openWebsite);
}
void Card_button::openWebsite()
{
QDesktopServices::openUrl(QUrl(website_url));
}
void Card_button::setWebsite_url(QString url)
{
this->website_url = url;
}
void Card_button::paintEvent(QPaintEvent* event)
{
QPainter painter(this);
painter.setRenderHint(QPainter::Antialiasing);
painter.setViewport(0, 0, width(), height());
painter.setWindow(0, 0, 122, 32);
QPainterPath path;
path.addRoundedRect(0, 0, 122, 32, 10, 10);
painter.setClipPath(path);
painter.setPen(Qt::NoPen);
QBrush Brush(color1);
painter.setBrush(Brush);
painter.drawRoundedRect(0, 0, 122, 32, 8, 8);
color2.setAlpha(m_color_opacity);
QBrush Brush1(color2);
painter.setBrush(Brush1);
painter.drawRoundedRect(0, -3, 122, 32, 8, 8);
QPen pen;
pen.setWidth(1);
pen.setColor(Qt::white);
pen.setStyle(Qt::SolidLine);
pen.setCapStyle(Qt::FlatCap);
pen.setJoinStyle(Qt::BevelJoin);
painter.setPen(pen);
QPoint points[] = {
QPoint(28, 10),
QPoint(33, 15),
QPoint(28, 20),
};
painter.drawPolyline(points, 3);
painter.setPen(Qt::white);
QFont font("Microsoft YaHei", 10, QFont::Normal);
painter.setFont(font);
painter.drawText(45, 21, btntext);
}
bool Card_button::event(QEvent* e)
{
if (e->type() == QEvent::Enter)
{
animation->setDirection(QPropertyAnimation::Forward);
animation->start();
qDebug() << "鼠标进入";
}
else if (e->type() == QEvent::Leave)
{
animation->setDirection(QPropertyAnimation::Backward);
animation->start();
qDebug() << "鼠标离开";
update();
}
return QPushButton::event(e);
}
QColor Card_button::getbutton_color() const
{
return m_button_color;
}
void Card_button::setButton_color(const QColor &newButton_color)
{
if (m_button_color == newButton_color)
return;
m_button_color = newButton_color;
update();
}
void Card_button::color_control()
{
m_button_color.setAlpha(255);
color1 = m_button_color;
color2 = QColor(m_button_color.red() * 0.8, m_button_color.green() * 0.8, m_button_color.blue() * 0.8);
}
int Card_button::color_opacity() const
{
return m_color_opacity;
}
void Card_button::setcolor_opacity(int newColor_opacity)
{
if (m_color_opacity == newColor_opacity)
return;
m_color_opacity = newColor_opacity;
update();
}
================================================
FILE: Anime_Template_Project/Carousel_card/card_button.h
================================================
#ifndef CARD_BUTTON_H
#define CARD_BUTTON_H
#include <QPushButton>
#include <QPainter>
#include <QPainterPath>
#include <QMouseEvent>
#include <QPropertyAnimation>
#include <QDesktopServices>
#include <QUrl>
class Card_button : public QPushButton
{
Q_OBJECT
Q_PROPERTY(QColor button_color READ getbutton_color WRITE setButton_color FINAL)
Q_PROPERTY(int color_opacity READ color_opacity WRITE setcolor_opacity FINAL)
public:
explicit Card_button(QString text, QColor button_color, QWidget* parent = nullptr);
QColor getbutton_color() const;
void setButton_color(const QColor &newButton_color);
public:
QString btntext;
void color_control();
QColor color1;
QColor color2;
int color_opacity() const;
void setcolor_opacity(int newColor_opacity);
void openWebsite();
void setWebsite_url(QString url);
protected:
void paintEvent(QPaintEvent* event);
bool event(QEvent* e);
private:
QPropertyAnimation* animation;
QString website_url;
QColor m_button_color;
int m_color_opacity = 255;
};
#endif // CARD_BUTTON_H
================================================
FILE: Anime_Template_Project/Carousel_card/card_text.cpp
================================================
#include "card_text.h"
Card_text::Card_text(QString text, QString text1, QWidget *parent)
: QWidget{parent}
{
this->text_main = text;
this->text_sub = text1;
}
void Card_text::paintEvent(QPaintEvent *event)
{
QPainter painter(this);
QRect rect(0, 0, width(), height());
painter.setViewport(rect);
painter.setWindow(0, 0, m_shrink_width, height());
painter.setRenderHint(QPainter::Antialiasing);
painter.setRenderHint(QPainter::TextAntialiasing);
QRect rect1(0, 0, m_shrink_width, 0);
QFont font1;
font1.setPointSize(m_font_size);
font1.setBold(true);
painter.setFont(font1);
QColor semiTransparent(255, 255, 255, 255);
painter.setPen(semiTransparent);
QRect actualRect = painter.boundingRect(rect1, Qt::TextWordWrap | Qt::AlignLeft | Qt::AlignBottom, text_main);
rect1.setHeight(actualRect.height());
painter.drawText(rect1, text_main);
QRect rect2(2, actualRect.height() + 7, width() - width()/4, 0);
QFont font;
font.setPointSize(m_font_size2);
font.setBold(true);
painter.setFont(font);
QColor semiTransparent1(255, 255, 255, m_enlarge_width);
painter.setPen(semiTransparent1);
QRect actualRect1 = painter.boundingRect(rect2, Qt::TextWordWrap | Qt::AlignLeft | Qt::AlignBottom, text_sub);
rect2.setHeight(actualRect1.height());
painter.drawText(rect2, text_sub);
this->resize(m_shrink_width, actualRect1.height() + actualRect.height() + 7);
this->move(38, 480 - actualRect1.height() - actualRect.height() - m_top_margin);
}
void Card_text::start_animation(int animation_duration)
{
QPropertyAnimation *animation = new QPropertyAnimation(this, "shrink_width");
animation->setDuration(animation_duration);
animation->setStartValue(this->m_shrink_width);
animation->setEndValue(280);
animation->setEasingCurve(QEasingCurve::Linear);
animation->start(QAbstractAnimation::DeleteWhenStopped);
QPropertyAnimation* animation1 = new QPropertyAnimation(this, "enlarge_width");
animation1->setDuration(animation_duration);
animation1->setStartValue(this->m_enlarge_width);
animation1->setEndValue(255);
animation1->setEasingCurve(QEasingCurve::Linear);
animation1->start(QAbstractAnimation::DeleteWhenStopped);
QPropertyAnimation* animation2 = new QPropertyAnimation(this, "font_size");
animation2->setDuration(animation_duration);
animation2->setStartValue(this->m_font_size);
animation2->setEndValue(23);
animation2->setEasingCurve(QEasingCurve::Linear);
animation2->start(QAbstractAnimation::DeleteWhenStopped);
QPropertyAnimation* animation3 = new QPropertyAnimation(this, "font_size2");
animation3->setDuration(animation_duration);
animation3->setStartValue(this->m_font_size2);
animation3->setEndValue(10);
animation3->setEasingCurve(QEasingCurve::Linear);
animation3->start(QAbstractAnimation::DeleteWhenStopped);
QPropertyAnimation* animation4 = new QPropertyAnimation(this, "top_margin");
animation4->setDuration(animation_duration);
animation4->setStartValue(this->m_top_margin);
animation4->setEndValue(232);
animation4->setEasingCurve(QEasingCurve::Linear);
animation4->start(QAbstractAnimation::DeleteWhenStopped);
}
void Card_text::reset_animation(int animation_duration)
{
QPropertyAnimation *animation = new QPropertyAnimation(this, "shrink_width");
animation->setDuration(animation_duration);
animation->setStartValue(this->m_shrink_width);
animation->setEndValue(200);
animation->setEasingCurve(QEasingCurve::Linear);
animation->start(QAbstractAnimation::DeleteWhenStopped);
QPropertyAnimation* animation1 = new QPropertyAnimation(this, "enlarge_width");
animation1->setDuration(animation_duration);
animation1->setStartValue(this->m_enlarge_width);
animation1->setEndValue(0);
animation1->setEasingCurve(QEasingCurve::Linear);
animation1->start(QAbstractAnimation::DeleteWhenStopped);
QPropertyAnimation* animation2 = new QPropertyAnimation(this, "font_size");
animation2->setDuration(animation_duration);
animation2->setStartValue(this->m_font_size);
animation2->setEndValue(15);
animation2->setEasingCurve(QEasingCurve::Linear);
animation2->start(QAbstractAnimation::DeleteWhenStopped);
QPropertyAnimation* animation3 = new QPropertyAnimation(this, "font_size2");
animation3->setDuration(animation_duration);
animation3->setStartValue(this->m_font_size2);
animation3->setEndValue(1);
animation3->setEasingCurve(QEasingCurve::Linear);
animation3->start(QAbstractAnimation::DeleteWhenStopped);
QPropertyAnimation* animation4 = new QPropertyAnimation(this, "top_margin");
animation4->setDuration(animation_duration);
animation4->setStartValue(this->m_top_margin);
animation4->setEndValue(210);
animation4->setEasingCurve(QEasingCurve::Linear);
animation4->start(QAbstractAnimation::DeleteWhenStopped);
}
int Card_text::shrink_width() const
{
return m_shrink_width;
}
void Card_text::setShrink_width(int newShrink_width)
{
m_shrink_width = newShrink_width;
update();
}
int Card_text::enlarge_width() const
{
return m_enlarge_width;
}
void Card_text::setEnlarge_width(int newEnlarge_width)
{
m_enlarge_width = newEnlarge_width;
update();
}
int Card_text::font_size() const
{
return m_font_size;
}
void Card_text::setFont_size(int newFont_size)
{
m_font_size = newFont_size;
update();
}
int Card_text::font_size2() const
{
return m_font_size2;
}
void Card_text::setFont_size2(int newFont_size2)
{
m_font_size2 = newFont_size2;
update();
}
int Card_text::top_margin() const
{
return m_top_margin;
}
void Card_text::setTop_margin(int newTop_margin)
{
m_top_margin = newTop_margin;
update();
}
================================================
FILE: Anime_Template_Project/Carousel_card/card_text.h
================================================
#ifndef CARD_TEXT_H
#define CARD_TEXT_H
#include <QWidget>
#include <QPainter>
#include <QTextDocument>
#include <QPropertyAnimation>
#include <QMouseEvent>
class Card_text : public QWidget
{
Q_OBJECT
Q_PROPERTY(int shrink_width READ shrink_width WRITE setShrink_width FINAL)
Q_PROPERTY(int enlarge_width READ enlarge_width WRITE setEnlarge_width FINAL)
Q_PROPERTY(int font_size READ font_size WRITE setFont_size FINAL)
Q_PROPERTY(int font_size2 READ font_size2 WRITE setFont_size2 FINAL)
Q_PROPERTY(int top_margin READ top_margin WRITE setTop_margin FINAL)
public:
explicit Card_text(QString text, QString text1, QWidget *parent = nullptr);
QString text_main;
QString text_sub;
void start_animation(int animation_duration);
void reset_animation(int animation_duration);
int shrink_width() const;
void setShrink_width(int newShrink_width);
int enlarge_width() const;
void setEnlarge_width(int newEnlarge_width);
int font_size() const;
void setFont_size(int newFont_size);
int font_size2() const;
void setFont_size2(int newFont_size2);
int top_margin() const;
void setTop_margin(int newTop_margin);
protected:
void paintEvent(QPaintEvent *event);
private:
int m_shrink_width = 200;
int m_enlarge_width = 0;
int m_font_size = 15;
int m_font_size2 = 1;
int m_top_margin = 210;
};
#endif // CARD_TEXT_H
================================================
FILE: Anime_Template_Project/Carousel_card/carousel_card.cpp
================================================
#include "carousel_card.h"
Carousel_card::Carousel_card(QWidget *parent)
: QWidget{parent}
{
this->setMaximumSize(1900, 530);
this->setMinimumSize(1300, 530);
this->Anime_basic_information();
this->Anime_cards_sorting(Anime_seven_cards_list,
Anime_cards_startX,
Anime_cards_cardWidth,
Anime_cards_spacing);
}
void Carousel_card::Anime_card_position_update(int m_carrier_card_id)
{
qDebug() << "m_carrier_card_id" << m_carrier_card_id;
int timeA = animation_duration;
if (m_carrier_card_id > 2)
{
int x = m_carrier_card_id - 2;
int j = x;
for (int i = 0; i < x; i++)
{
timeA = timeA - 70;
Anime_seven_cards_list.append(Anime_seven_cards_list.takeFirst());
for (Carrier_card* Anime_cards : Anime_seven_cards_list)
{
if (Anime_cards == nullptr) continue;
int j = Anime_seven_cards_list.indexOf(Anime_cards);
Anime_cards->setcarrier_card_id(j);
if (Anime_seven_cards_list.length() - 1 == j) Anime_cards->move(Anime_seven_cards_zasyo_list[j]);
this->Anime_Anima_set(Anime_cards, Anime_seven_cards_zasyo_list[j], timeA);
}
}
j--;
}
else if (m_carrier_card_id < 2)
{
int x = 2 - m_carrier_card_id;
Anime_seven_cards_list.prepend(Anime_seven_cards_list.takeLast());
for (Carrier_card* Anime_cards : Anime_seven_cards_list)
{
if (Anime_cards == nullptr) continue;
int j = Anime_seven_cards_list.indexOf(Anime_cards);
Anime_cards->setcarrier_card_id(j);
if (Anime_cards->carrier_card_id() == 0) Anime_cards->move(Anime_seven_cards_zasyo_list.first());
if (Anime_seven_cards_list.length() - 1 == j) Anime_cards->move(Anime_seven_cards_zasyo_list[j]);
this->Anime_Anima_set(Anime_cards, Anime_seven_cards_zasyo_list[j], timeA);
}
}
}
void Carousel_card::onwheel_TimerTimeout()
{
clickTimer.stop();
}
void Carousel_card::Anime_Anima_set(Carrier_card* Anime_cards,QPoint Anime_zasyo, int Anime_time)
{
Anime_cards->raise();
Anime_cards->Anime_card_transformation(Anime_time);
QPropertyAnimation* Anime_anima = new QPropertyAnimation(Anime_cards, "pos");
Anime_anima->setDuration(Anime_time);
Anime_anima->setStartValue(Anime_cards->pos());
Anime_anima->setEndValue(Anime_zasyo);
Anime_anima->setEasingCurve(QEasingCurve::Linear);
Anime_anima->start(QAbstractAnimation::DeleteWhenStopped);
}
void Carousel_card::Anime_basic_information()
{
QFile file(":/json/json/Anime_care_attributes.json");
if (!file.open(QIODevice::ReadOnly))
{
qDebug() << "打开文件失败";
return;
}
QByteArray jsonData = file.readAll();
file.close();
QJsonDocument document = QJsonDocument::fromJson(jsonData);
if (document.isNull() && !document.isObject())
{
qDebug() << "解析JSON失败";
return;
}
QJsonObject rootObject = document.object();
QJsonArray hobbiesArray = rootObject["Anime_img_str_list"].toArray();
for (const QJsonValue& value : hobbiesArray)
{
QJsonObject addressObject = value.toObject();
if (!QFile::exists(addressObject["img"].toString()))
{
qDebug() << "图片资源文件不存在";
continue;
}
Carrier_card* Anime_cards = new Carrier_card(QPixmap(addressObject["img"].toString()),
addressObject["str_1"].toString(),
addressObject["str_2"].toString(),
this);
Anime_cards->Anime_button->setWebsite_url(addressObject["anime_url"].toString());
connect(Anime_cards, &Carrier_card::carrier_card_idChanged, this, &Carousel_card::Anime_card_position_update);
QGraphicsDropShadowEffect* shadow = new QGraphicsDropShadowEffect(Anime_cards);
shadow->setOffset(0, 0);
shadow->setBlurRadius(80);
shadow->setColor(Anime_cards->m_color3);
Anime_cards->setGraphicsEffect(shadow);
Anime_seven_cards_list.append(Anime_cards);
}
connect(this, &Carousel_card::wheel_signalChanged, this, &Carousel_card::Anime_card_position_update);
connect(&clickTimer, &QTimer::timeout, this, &Carousel_card::onwheel_TimerTimeout);
}
void Carousel_card::Anime_cards_sorting(QList<Carrier_card *> &Anime_seven_cards_list,
int Anime_cards_startX,
int Anime_cards_cardWidth,
int Anime_cards_spacing)
{
int currentX = Anime_cards_startX;
for (Carrier_card* Anime_cards : Anime_seven_cards_list)
{
if (Anime_cards == nullptr)
{
continue;
}
Anime_cards->setcarrier_card_id(Anime_seven_cards_list.indexOf(Anime_cards));
if (Anime_cards->carrier_card_id() == 2)
{
Anime_cards->Anime_card_1();
}
if (Anime_cards->carrier_card_id() == 3)
{
currentX += 540;
}
Anime_cards->move(currentX, 13);
Anime_seven_cards_zasyo_list.append(QPoint(currentX, 13));
currentX += Anime_cards_cardWidth + Anime_cards_spacing;
}
}
void Carousel_card::mousePressEvent(QMouseEvent* event)
{
if (event->button() == Qt::RightButton)
{
emit wheel_signalChanged(San);
}
QWidget::mousePressEvent(event);
}
void Carousel_card::wheelEvent(QWheelEvent* event)
{
if (event->angleDelta().y() > 0)
{
if (!clickTimer.isActive())
{
emit wheel_signalChanged(Yizi);
clickTimer.start(310);
}
}
else if (event->angleDelta().y() < 0)
{
if (!clickTimer.isActive())
{
emit wheel_signalChanged(San);
clickTimer.start(170);
}
}
}
================================================
FILE: Anime_Template_Project/Carousel_card/carousel_card.h
================================================
#ifndef CAROUSEL_CARD_H
#define CAROUSEL_CARD_H
#include <QWidget>
#include "carrier_card.h"
#include <QList>
#include <QPropertyAnimation>
#include <QTimer>
#include <QGraphicsDropShadowEffect>
#include <QFile>
#include <QJsonDocument>
#include <QJsonObject>
#include <QJsonArray>
class Carousel_card : public QWidget
{
Q_OBJECT
public:
explicit Carousel_card(QWidget *parent = nullptr);
public:
QList<Carrier_card*> Anime_seven_cards_list;
QList<QPoint> Anime_seven_cards_zasyo_list;
void Anime_basic_information();
void Anime_cards_sorting(QList<Carrier_card*>& Anime_seven_cards_list,
int Anime_cards_startX,
int Anime_cards_cardWidth,
int Anime_cards_spacing);
void Anime_Anima_set(Carrier_card* Anime_cards, QPoint Anime_zasyo, int Anime_time);
public slots:
void Anime_card_position_update(int m_carrier_card_id);
void onwheel_TimerTimeout();
signals:
void wheel_signalChanged(int wheel_signal);
protected:
void mousePressEvent(QMouseEvent *event);
void wheelEvent(QWheelEvent *event);
private:
QTimer clickTimer;
int Yizi = 1;
int San = 3;
int Anime_cards_startX = -628;
int Anime_cards_cardWidth = 320;
int Anime_cards_spacing = 13;
int animation_duration = 410;
};
#endif // CAROUSEL_CARD_H
================================================
FILE: Anime_Template_Project/Carousel_card/carrier_card.cpp
================================================
#include "carrier_card.h"
Carrier_card::Carrier_card(QPixmap m_carrier_card, QString main_title, QString sub_title,QWidget *parent)
: QWidget{parent}
{
this->setMaximumSize(860, 480);
this->resize(320, 480);
this->m_carrier_card = m_carrier_card;
this->font_related_construction(main_title, sub_title);
this->set_gradient_color();
setMouseTracking(true);
connect(&m_clickTimer, &QTimer::timeout, this, &Carrier_card::onClickTimerTimeout);
connect(&timer4s, &QTimer::timeout, this, &Carrier_card::circle_reset);
shadow = new QGraphicsDropShadowEffect(Anime_button);
shadow->setOffset(0, 0);
shadow->setBlurRadius(150);
shadow->setColor(Qt::black);
Anime_button->setGraphicsEffect(shadow);
}
void Carrier_card::font_related_construction(QString main_title, QString sub_title)
{
Anime_small_text = new Card_text(main_title, sub_title,this);
Anime_small_text->reset_animation(0);
qDebug() << "Card_text::" << Anime_small_text->height();
}
void Carrier_card::mousePressEvent(QMouseEvent* event)
{
if (event->button() == Qt::LeftButton)
{
if (!m_clickTimer.isActive())
{
emit carrier_card_idChanged(this->m_carrier_card_id);
m_clickTimer.start(500);
}
}
QWidget::mousePressEvent(event);
}
void Carrier_card::mouseMoveEvent(QMouseEvent* event)
{
if (this->isClicked == true)
{
mousePos = event->pos();
update();
}
}
bool Carrier_card::event(QEvent* e)
{
if (e->type() == QEvent::Enter)
{
this->isClicked = true;
if (this->m_carrier_card_id == 2) timer4s.stop();
}
else if (e->type() == QEvent::Leave)
{
this->isClicked = false;
if (this->m_carrier_card_id == 2) timer4s.start(100);
update();
}
return QWidget::event(e);
}
void Carrier_card::draw_radial_gradient_circle()
{
QPainter painter(this);
painter.setRenderHint(QPainter::Antialiasing);
QRadialGradient gradient1(mousePos.rx(), mousePos.ry(), qMax(width() , height() ) / 2);
gradient1.setColorAt(0.0, QColor(255, 255, 255, 15));
gradient1.setColorAt(0.8, QColor(255, 255, 255, 0));
gradient1.setColorAt(1.0, QColor(255, 255, 255, 0));
painter.setBrush(gradient1);
painter.setPen(Qt::NoPen);
painter.drawRect(rect());
}
void Carrier_card::paintEvent(QPaintEvent* event)
{
QPainter painter(this);
painter.setRenderHint(QPainter::Antialiasing);
painter.setRenderHint(QPainter::SmoothPixmapTransform);
painter.setRenderHint(QPainter::LosslessImageRendering);
QPainterPath path;
path.addRoundedRect(0, 0, this->width(), this->height(), 10, 10);
painter.setClipPath(path);
int windowWidth = width();
int windowHeight = height();
double aspectRatio = static_cast<double>(m_carrier_card.width()) / m_carrier_card.height();
int newWidth = static_cast<int>(windowHeight * aspectRatio);
int newHeight = windowHeight;
int posX = (windowWidth - newWidth) / 2;
int posY = 0;
painter.drawPixmap(posX, posY, newWidth, newHeight, m_carrier_card, 0, 0, m_carrier_card.width(), m_carrier_card.height());
QLinearGradient gradient(0, 480, 860, 480);
gradient.setColorAt(0, m_color1);
gradient.setColorAt(0.35, m_color2);
gradient.setColorAt(0.55, QColor(0, 0, 0, 0));
gradient.setColorAt(1, QColor(0, 0, 0, 0));
gradient.setSpread(QGradient::PadSpread);
painter.setBrush(gradient);
painter.setPen(Qt::NoPen);
painter.drawRect(0, 0, width(), height());
QColor semiTransparentRed(0, 0, 0, m_opacity);
painter.setBrush(semiTransparentRed);
painter.drawRect(0, 0, width(), height());
if (isClicked == true) this->draw_radial_gradient_circle();
if (m_carrier_card_id == 2 && display_circle == true) draw_sector_circle();
}
void Carrier_card::draw_sector_circle()
{
QPainter painter(this);
painter.setRenderHint(QPainter::Antialiasing);
painter.setPen(Qt::NoPen);
painter.setBrush(QColor(255, 255, 255, 140));
QRect rect(20, 450, 15, 15);
int startAngle = 0 * 16;
int spanAngle = m_circle_degrees * 16;
painter.drawPie(rect, startAngle, spanAngle);
}
void Carrier_card::circle_reset()
{
TimerTimeout++;
update();
if (TimerTimeout == 15)
{
display_circle = true;
}
if (TimerTimeout < 87 && display_circle == true)
{
m_circle_degrees -= 5;
}
if (TimerTimeout == 87)
{
restore_disc();
emit carrier_card_idChanged(3);
}
}
void Carrier_card::set_gradient_color()
{
QColor clr = this->getMostFrequentColor(m_carrier_card);
Anime_button = new Card_button(QString("查看详情"), clr, this);
Anime_button->move(38, 315);
clr.setAlpha(100);
m_color1 = clr;
clr.setAlpha(68);
m_color2 = clr;
clr.setAlpha(255);
m_color3 = clr;
}
QColor Carrier_card::getMostFrequentColor(const QPixmap& pixmap)
{
QImage image = pixmap.toImage();
if (image.isNull()) {
return QColor();
}
image = image.convertToFormat(QImage::Format_RGB32);
QHash<QRgb, int> colorCounts;
const uchar* bits = image.constBits();
const int width = image.width();
const int height = image.height();
const int bytesPerLine = image.bytesPerLine();
const qreal minSaturation = 8.1;
const qreal maxLightnessForWhite = 0.99;
for (int y = 0; y < height; ++y) {
const QRgb* line = reinterpret_cast<const QRgb*>(bits + y * bytesPerLine);
for (int x = 0; x < width; ++x) {
QRgb rgb = line[x];
QColor color = QColor::fromRgb(rgb);
float h, s, l;
color.getHslF(&h, &s, &l);
if (s < minSaturation && l > maxLightnessForWhite) {
continue;
}
colorCounts[rgb]++;
}
}
if (colorCounts.isEmpty()) {
return QColor();
}
QHashIterator<QRgb, int> it(colorCounts);
QRgb maxColor = it.peekNext().key();
int maxCount = it.peekNext().value();
while (it.hasNext()) {
it.next();
if (it.value() > maxCount) {
maxCount = it.value();
maxColor = it.key();
}
}
return QColor::fromRgb(maxColor);
}
void Carrier_card::Anime_card_transformation(int animation_duration)
{
if (m_carrier_card_id != 2)
{
timer4s.stop();
restore_disc();
Anime_small_text->reset_animation(animation_duration);
QPropertyAnimation* animation1 = new QPropertyAnimation(this, "size");
animation1->setDuration(animation_duration);
animation1->setStartValue(this->size());
animation1->setEndValue(QSize(320, 480));
animation1->setEasingCurve(QEasingCurve::Linear);
QPropertyAnimation* animation3 = new QPropertyAnimation(this, "opacity");
animation3->setDuration(animation_duration);
animation3->setStartValue(this->opacity());
animation3->setEndValue(90);
animation3->setEasingCurve(QEasingCurve::Linear);
animation1->start(QAbstractAnimation::DeleteWhenStopped);
animation3->start(QAbstractAnimation::DeleteWhenStopped);
}
else
{
timer4s.start(100);
Anime_small_text->start_animation(animation_duration);
QPropertyAnimation* animation1 = new QPropertyAnimation(this, "size");
animation1->setDuration(animation_duration);
animation1->setStartValue(this->size());
animation1->setEndValue(QSize(860, 480));
animation1->setEasingCurve(QEasingCurve::Linear);
QPropertyAnimation* animation3 = new QPropertyAnimation(this, "opacity");
animation3->setDuration(animation_duration);
animation3->setStartValue(this->opacity());
animation3->setEndValue(0);
animation3->setEasingCurve(QEasingCurve::Linear);
animation1->start(QAbstractAnimation::DeleteWhenStopped);
animation3->start(QAbstractAnimation::DeleteWhenStopped);
}
}
void Carrier_card::Anime_card_1()
{
this->resize(860, 480);
Anime_small_text->start_animation(0);
this->setOpacity(0);
timer4s.start(100);
}
void Carrier_card::onClickTimerTimeout()
{
m_clickTimer.stop();
}
void Carrier_card::restore_disc()
{
display_circle = false;
TimerTimeout = 0;
m_circle_degrees = 360;
}
int Carrier_card::carrier_card_id() const
{
return m_carrier_card_id;
}
void Carrier_card::setcarrier_card_id(int newCarrier_card_id)
{
if (m_carrier_card_id == newCarrier_card_id)
return;
m_carrier_card_id = newCarrier_card_id;
update();
}
int Carrier_card::opacity() const
{
return m_opacity;
}
void Carrier_card::setOpacity(int newOpacity)
{
m_opacity = newOpacity;
update();
}
int Carrier_card::circle_degrees() const
{
return m_circle_degrees;
}
void Carrier_card::setCircle_degrees(int newCircle_degrees)
{
if (m_circle_degrees == newCircle_degrees)
return;
m_circle_degrees = newCircle_degrees;
qDebug() << "circle_degrees changed to:" << m_circle_degrees;
update();
}
================================================
FILE: Anime_Template_Project/Carousel_card/carrier_card.h
================================================
#ifndef CARRIER_CARD_H
#define CARRIER_CARD_H
#include <QWidget>
#include <QPainter>
#include <QPropertyAnimation>
#include <QMouseEvent>
#include <QPainterPath>
#include <QTimer>
#include <QFile>
#include <QGraphicsDropShadowEffect>
#include <QLabel>
#include "card_text.h"
#include "Card_button.h"
class Carrier_card : public QWidget
{
Q_OBJECT
Q_PROPERTY(int carrier_card_id READ carrier_card_id WRITE setcarrier_card_id NOTIFY carrier_card_idChanged FINAL)
Q_PROPERTY(int opacity READ opacity WRITE setOpacity FINAL)
Q_PROPERTY(int circle_degrees READ circle_degrees WRITE setCircle_degrees FINAL)
public:
explicit Carrier_card(QPixmap m_carrier_card, QString main_title, QString sub_title, QWidget *parent = nullptr);
protected:
void paintEvent(QPaintEvent *event);
void mousePressEvent(QMouseEvent *event);
void mouseMoveEvent(QMouseEvent *event);
bool event(QEvent* e);
public:
QTimer m_clickTimer;
QTimer timer4s;
int TimerTimeout = 0;
bool display_circle = false;
void restore_disc();
void onClickTimerTimeout();
void circle_reset();
QPoint mousePos;
bool isClicked = false;
void draw_radial_gradient_circle();
public:
Card_text* Anime_small_text;
int position_small_after_enlargement = 267;
int basic_small_position = 245;
void font_related_construction(QString main_title, QString sub_title);
Card_button* Anime_button;
public:
int carrier_card_id() const;
QColor m_color1;
QColor m_color2;
QColor m_color3;
int opacity() const;
void setOpacity(int newOpacity);
int circle_degrees() const;
void setCircle_degrees(int newCircle_degrees);
void Anime_card_1();
void setcarrier_card_id(int newCarrier_card_id);
QColor getMostFrequentColor(const QPixmap& pixmap);
void set_gradient_color();
void draw_sector_circle();
public slots:
void Anime_card_transformation(int animation_duration);
signals:
void carrier_card_idChanged(int m_carrier_card_id);
private:
QGraphicsDropShadowEffect* shadow;
QPixmap m_carrier_card;
int m_carrier_card_id = 0;
int m_opacity = 90;
int m_circle_degrees = 360;
};
#endif // CARRIER_CARD_H
================================================
FILE: Anime_Template_Project/Eye_of_Cthulhu/JellyfishWidget.cpp
================================================
#include "jellyfishwidget.h"
#include <QtMath>
#include <QDebug>
#include <QRandomGenerator>
#include <QMouseEvent>
#include <QEvent>
JellyfishWidget::JellyfishWidget(QWidget *parent)
: QWidget(parent),
x_input(0.0),
y_input(0.0),
t_current(0.0),
mousePosition(width() / 2.0, height() / 2.0),
smoothedPupilTarget(0.0, 0.0),
mouseIsInWindow(false),
blinkProgress(0.0),
isBlinking(false),
pulseScale(1.0),
m_targetPupilScaleFactor(1.0),
m_currentPupilScaleFactor(1.0)
{
setWindowTitle("眼球克苏鲁");
resize(800, 600);
setMouseTracking(true);
animationTimer = new QTimer(this);
connect(animationTimer, &QTimer::timeout, this, &JellyfishWidget::updateAnimation);
animationTimer->start(15);
for (int i = 0; i < 3; ++i) {
TentacleShadow shadow;
shadow.opacity = QRandomGenerator::global()->generateDouble() * 0.1 + 0.05;
shadow.phaseOffset = QRandomGenerator::global()->generateDouble() * 100.0;
shadow.thickness = QRandomGenerator::global()->bounded(50, 150);
for (int j = 0; j < 5; ++j) {
shadow.points.append(QPointF(
QRandomGenerator::global()->bounded(-100, width() + 100),
QRandomGenerator::global()->bounded(height() / 2, height() + 100)
));
}
backgroundTentacleShadows.append(shadow);
}
}
JellyfishWidget::~JellyfishWidget()
{
}
QPointF JellyfishWidget::calculateJellyfishPoint(double local_x, double local_y, double current_t)
{
double x_formula = local_x;
double y_formula = local_y;
double t = current_t;
double k = 5.0 * qCos(x_formula / 14.0) * qCos(y_formula / 30.0);
double e = y_formula / 8.0 - 13.0;
double d = (k * k + e * e) / 59.0 + 4.0;
double a = qAtan2(e, k);
double d_safe = (d < 0.001 && d >= 0) ? 0.001 : d;
double q = 60.0 - qSin(a * e) + k * (3.0 + (4.0 / d_safe) * qSin(d * d - 2.0 * t));
double c = d / 2.0 + e / 99.0 - t / 18.0;
double X_result = q * qSin(c);
double Y_result = (q + 9.0 * d) * qCos(c);
return QPointF(X_result, Y_result);
}
void JellyfishWidget::paintEvent(QPaintEvent *event)
{
Q_UNUSED(event);
QPainter painter(this);
painter.setRenderHint(QPainter::Antialiasing);
painter.fillRect(rect(), QColor(20, 0, 0));
drawBackgroundTentacleShadows(&painter);
QPointF cthulhuCenter = QPointF(width() / 2.0, height() / 2.0);
QPointF currentCthulhuPosition = calculateJellyfishPoint(x_input, y_input, t_current) + cthulhuCenter;
double currentEyeballRadius = 80.0 * pulseScale;
double currentEyeballHeight = 40.0 * pulseScale;
drawEyeball(&painter, currentCthulhuPosition, currentEyeballRadius, currentEyeballHeight);
drawGoreTendrils(&painter, currentCthulhuPosition, currentEyeballRadius * 0.9, 15, t_current);
drawFallingGoreAndBlood(&painter);
drawAcidDrips(&painter);
}
void JellyfishWidget::mouseMoveEvent(QMouseEvent *event)
{
mousePosition = event->pos();
mouseIsInWindow = true;
}
void JellyfishWidget::leaveEvent(QEvent *event)
{
Q_UNUSED(event);
mousePosition = QPointF(width() / 2.0, height() / 2.0);
mouseIsInWindow = false;
}
void JellyfishWidget::updateAnimation()
{
t_current += 0.02;
QPointF cthulhuCenter = QPointF(width() / 2.0, height() / 2.0);
QPointF currentCthulhuPosition = calculateJellyfishPoint(x_input, y_input, t_current) + cthulhuCenter;
double eyeball_radius = 80.0;
double maxPupilTravel = eyeball_radius * 0.4;
QPointF targetPupilOffset;
double basePupilRatio = 0.3;
double minPupilScale = 0.8;
double maxPupilScale = 1.2;
double influenceDistance = 200.0;
if (mouseIsInWindow) {
QPointF vecToMouse = mousePosition - currentCthulhuPosition;
double distToMouse = qSqrt(vecToMouse.x() * vecToMouse.x() + vecToMouse.y() * vecToMouse.y());
if (distToMouse > 0) {
targetPupilOffset = vecToMouse / distToMouse * qMin(distToMouse, maxPupilTravel);
} else {
targetPupilOffset = QPointF(0, 0);
}
double normalizedDist = qMin(distToMouse, influenceDistance) / influenceDistance;
m_targetPupilScaleFactor = minPupilScale + (1.0 - normalizedDist) * (maxPupilScale - minPupilScale);
} else {
QPointF wanderOffset(qSin(t_current * 0.7) * 20, qCos(t_current * 0.9) * 15);
double wander_magnitude = qSqrt(wanderOffset.x()*wanderOffset.x() + wanderOffset.y()*wanderOffset.y());
if (wander_magnitude > maxPupilTravel) {
wanderOffset = wanderOffset / wander_magnitude * maxPupilTravel;
}
targetPupilOffset = wanderOffset;
m_targetPupilScaleFactor = 1.0;
}
double smoothness_factor = 0.05;
smoothedPupilTarget = smoothedPupilTarget * (1.0 - smoothness_factor) + targetPupilOffset * smoothness_factor;
double pupil_smoothness = 0.1;
m_currentPupilScaleFactor += (m_targetPupilScaleFactor - m_currentPupilScaleFactor) * pupil_smoothness;
if (isBlinking) {
blinkProgress += 0.06;
if (blinkProgress >= 1.0) {
isBlinking = false;
blinkProgress = 0.0;
}
} else {
if (QRandomGenerator::global()->generateDouble() < 0.003) {
isBlinking = true;
blinkProgress = 0.0;
}
}
double targetPulse = 1.0 + qSin(t_current * 5.0) * 0.02;
pulseScale += (targetPulse - pulseScale) * 0.1;
ParticleUpdateRunnable *runnable = new ParticleUpdateRunnable(
t_current, height(), width(), currentCthulhuPosition, 80.0,
fallingGoreParticles, acidDrips, backgroundTentacleShadows
);
connect(runnable, &ParticleUpdateRunnable::particlesUpdated,
this, &JellyfishWidget::handleParticlesUpdated, Qt::QueuedConnection);
QThreadPool::globalInstance()->start(runnable);
update();
}
void JellyfishWidget::handleParticlesUpdated(QVector<GoreParticle> newGore,
QVector<AcidDrip> newAcid,
QVector<TentacleShadow> newShadows)
{
fallingGoreParticles = newGore;
acidDrips = newAcid;
backgroundTentacleShadows = newShadows;
}
void JellyfishWidget::drawEyeball(QPainter *painter, const QPointF& center, double radius, double bell_height)
{
QRadialGradient eyeballGradient(center.x(), center.y() - bell_height / 2, radius * 1.5, center.x(), center.y());
eyeballGradient.setColorAt(0.0, QColor(255, 50, 50, 200));
eyeballGradient.setColorAt(0.4, QColor(180, 0, 0, 180));
eyeballGradient.setColorAt(0.8, QColor(80, 0, 0, 150));
eyeballGradient.setColorAt(1.0, QColor(30, 0, 0, 100));
painter->setBrush(eyeballGradient);
painter->setPen(QPen(QColor(50, 0, 0, 180), 3));
painter->drawEllipse(QRectF(center.x() - radius, center.y() - bell_height, radius * 2, bell_height * 2));
painter->setPen(Qt::NoPen);
for (int i = 0; i < 20; ++i) {
double angle_start = QRandomGenerator::global()->generateDouble() * 2 * M_PI;
double vein_start_radius = radius * (0.8 + QRandomGenerator::global()->generateDouble() * 0.1);
QPointF veinStart = center + QPointF(qCos(angle_start) * vein_start_radius, qSin(angle_start) * vein_start_radius * (bell_height / radius));
double angle_end = angle_start + (QRandomGenerator::global()->generateDouble() * 0.5 - 0.25) * M_PI;
double vein_end_radius = radius * (0.3 + QRandomGenerator::global()->generateDouble() * 0.3);
QPointF veinEnd = center + QPointF(qCos(angle_end) * vein_end_radius, qSin(angle_end) * vein_end_radius * (bell_height / radius));
QColor veinColor(QRandomGenerator::global()->bounded(100, 201), 0, 0, QRandomGenerator::global()->bounded(100, 201));
int veinThickness = QRandomGenerator::global()->bounded(1, 3);
painter->setPen(QPen(veinColor, veinThickness));
painter->drawLine(veinStart, veinEnd);
}
painter->save();
QPainterPath eyeballOutline;
eyeballOutline.addEllipse(QRectF(center.x() - radius, center.y() - bell_height, radius * 2, bell_height * 2));
painter->setClipPath(eyeballOutline);
double iris_radius = radius * 0.6;
QPointF irisCenter = center + smoothedPupilTarget;
QRadialGradient irisGradient(irisCenter, iris_radius);
irisGradient.setColorAt(0.0, QColor(80, 150, 80, 200));
irisGradient.setColorAt(0.5, QColor(30, 80, 30, 220));
irisGradient.setColorAt(1.0, QColor(10, 40, 10, 255));
painter->setBrush(irisGradient);
painter->setPen(QPen(QColor(0, 0, 0, 150), 2));
painter->drawEllipse(irisCenter, iris_radius, iris_radius);
painter->setPen(QPen(QColor(0, 0, 0, 100), 1));
for (int i = 0; i < 8; ++i) {
double angle = i * M_PI / 4.0 + t_current * 0.1;
QPointF crackStart = irisCenter + QPointF(qCos(angle) * iris_radius * 0.5, qSin(angle) * iris_radius * 0.5);
QPointF crackEnd = irisCenter + QPointF(qCos(angle) * iris_radius * 0.9, qSin(angle) * iris_radius * 0.9);
painter->drawLine(crackStart, crackEnd);
}
double pupil_base_radius = radius * 0.3;
double pupil_radius_adjusted = pupil_base_radius * m_currentPupilScaleFactor;
QPointF pupilOffsetFinal = smoothedPupilTarget;
pupilOffsetFinal.setX(pupilOffsetFinal.x() + qSin(t_current * 2.5) * 2);
pupilOffsetFinal.setY(pupilOffsetFinal.y() + qCos(t_current * 2.8) * 2);
QPointF pupilCenter = center + pupilOffsetFinal;
double pupil_width = pupil_radius_adjusted * (1.0 + qSin(t_current * 1.5) * 0.05);
double pupil_height = pupil_radius_adjusted * (1.0 + qCos(t_current * 1.7) * 0.05);
painter->setBrush(QColor(0, 0, 0, 255));
painter->setPen(QPen(QColor(20, 0, 0, 200), 2));
painter->drawEllipse(QRectF(pupilCenter.x() - pupil_width / 2, pupilCenter.y() - pupil_height / 2, pupil_width, pupil_height));
painter->restore();
if (blinkProgress > 0.0) {
double closure_amount;
if (blinkProgress <= 0.5) {
closure_amount = blinkProgress * 2.0;
} else {
closure_amount = (1.0 - blinkProgress) * 2.0;
}
closure_amount = qMax(0.0, qMin(1.0, closure_amount));
double eyelid_vertical_coverage = bell_height * closure_amount;
painter->setBrush(QColor(20, 0, 0));
painter->setPen(Qt::NoPen);
painter->drawRect(QRectF(center.x() - radius, center.y() - bell_height, radius * 2, eyelid_vertical_coverage));
painter->drawRect(QRectF(center.x() - radius, center.y() + bell_height - eyelid_vertical_coverage, radius * 2, eyelid_vertical_coverage));
}
}
void JellyfishWidget::drawGoreTendrils(QPainter *painter, const QPointF& center, double radius, int num_tendrils, double current_t)
{
for (int i = 0; i < num_tendrils; ++i) {
double base_angle = i * 2 * M_PI / num_tendrils;
QPointF startPoint(center.x() + radius * qCos(base_angle + qSin(current_t * 0.7 + i * 0.3) * 0.05),
center.y() + radius * qSin(base_angle + qCos(current_t * 0.7 + i * 0.3) * 0.05));
int segments = 12;
double tendril_length = 100.0 + 80.0 * qSin(current_t * 1.0 + i * 0.6);
QPointF prevPoint = startPoint;
for (int j = 1; j <= segments; ++j) {
double segment_progress = (double)j / segments;
double current_segment_length_factor = 0.5 + 0.5 * qCos(current_t * 2.0 + j * 0.9 + i * 0.4);
double current_segment_length = tendril_length * segment_progress * current_segment_length_factor;
double wave_amplitude = 25.0 * qSin(current_t * 2.5 + j * 1.0 + i * 0.3) * (1.0 - segment_progress * 0.5);
double wave_angle_offset = qCos(base_angle + M_PI / 2.0 + qSin(current_t * 1.8));
QPointF dir(qCos(base_angle), qSin(base_angle));
QPointF normal_dir(-dir.y(), dir.x());
QPointF nextPoint(startPoint.x() + dir.x() * current_segment_length + normal_dir.x() * wave_amplitude,
startPoint.y() + dir.y() * current_segment_length + normal_dir.y() * wave_amplitude);
int alpha = 200 - j * 15;
int pen_thickness = 2 + (segments - j) * 0.2;
painter->setPen(QPen(QColor(180, 20, 20, qMax(0, alpha)), pen_thickness));
painter->drawLine(prevPoint, nextPoint);
prevPoint = nextPoint;
if (j % 3 == 0) {
painter->setBrush(QColor(100, 0, 0, qMax(0, alpha - 50)));
painter->setPen(Qt::NoPen);
painter->drawEllipse(nextPoint, pen_thickness + 1, pen_thickness + 1);
painter->setBrush(Qt::NoBrush);
}
}
}
}
void JellyfishWidget::drawFallingGoreAndBlood(QPainter *painter) {
for (const GoreParticle &p : fallingGoreParticles) {
QColor particleColor = p.color;
particleColor.setAlphaF(p.opacity);
painter->setBrush(particleColor);
painter->setPen(Qt::NoPen);
painter->drawEllipse(p.position, p.size, p.size);
}
}
void JellyfishWidget::drawAcidDrips(QPainter *painter) {
for (const AcidDrip &d : acidDrips) {
QColor dripColor = d.color;
dripColor.setAlphaF(d.opacity);
painter->setBrush(dripColor);
painter->setPen(Qt::NoPen);
painter->drawEllipse(d.position, d.size, d.size);
if (d.trailOpacity > 0.01) {
QColor trailColor = d.color;
trailColor.setAlphaF(d.trailOpacity * 0.5);
QPen trailPen(trailColor, d.size / 2.0, Qt::SolidLine, Qt::RoundCap, Qt::RoundJoin);
painter->setPen(trailPen);
painter->drawLine(d.position - d.velocity * 3.0, d.position);
painter->setPen(Qt::NoPen);
}
}
}
void JellyfishWidget::drawBackgroundTentacleShadows(QPainter *painter) {
for (const TentacleShadow &shadow : backgroundTentacleShadows) {
if (shadow.points.size() < 2) continue;
QColor shadowColor = QColor(10, 0, 0, static_cast<int>(shadow.opacity * 255));
QPen shadowPen(shadowColor, shadow.thickness, Qt::SolidLine, Qt::RoundCap, Qt::RoundJoin);
painter->setPen(shadowPen);
painter->setBrush(Qt::NoBrush);
QPainterPath path;
path.moveTo(shadow.points.first());
for (int i = 1; i < shadow.points.size(); ++i) {
path.lineTo(shadow.points[i]);
}
painter->drawPath(path);
}
}
================================================
FILE: Anime_Template_Project/Eye_of_Cthulhu/JellyfishWidget.h
================================================
#ifndef JELLYFISHWIDGET_H
#define JELLYFISHWIDGET_H
#include <QWidget>
#include <QTimer>
#include <QPainter>
#include <QDateTime>
#include <QPointF>
#include <QVector>
#include <QColor>
#include <QMouseEvent>
#include <QEvent>
#include <QPainterPath>
#include <QThreadPool>
#include <QRunnable>
#include <QRandomGenerator>
struct GoreParticle {
QPointF position;
QPointF velocity;
double size;
double opacity;
QColor color;
bool active;
};
struct AcidDrip {
QPointF position;
QPointF velocity;
double size;
double opacity;
double trailOpacity;
QColor color;
bool active;
};
struct TentacleShadow {
QVector<QPointF> points;
double opacity;
double phaseOffset;
double thickness;
};
class ParticleUpdateRunnable : public QObject, public QRunnable {
Q_OBJECT
public:
ParticleUpdateRunnable(double t_current, int widgetHeight, int widgetWidth,
const QPointF& cthulhuCenter, double eyeball_radius_base,
QVector<GoreParticle> currentGore,
QVector<AcidDrip> currentAcid,
QVector<TentacleShadow> currentShadows)
: m_t_current(t_current),
m_widgetHeight(widgetHeight),
m_widgetWidth(widgetWidth),
m_cthulhuCenter(cthulhuCenter),
m_eyeball_radius_base(eyeball_radius_base),
m_goreParticles(currentGore),
m_acidDrips(currentAcid),
m_tentacleShadows(currentShadows) {
setAutoDelete(true);
}
void run() override {
for (int i = 0; i < m_goreParticles.size(); ) {
GoreParticle &p = m_goreParticles[i];
p.position += p.velocity;
p.velocity.setY(p.velocity.y() + 0.2);
p.opacity -= 0.01;
p.size *= 0.99;
if (p.position.y() > m_widgetHeight + 50 || p.opacity <= 0.01) {
m_goreParticles.removeAt(i);
} else {
++i;
}
}
if (QRandomGenerator::global()->generateDouble() < 0.2) {
GoreParticle newParticle;
newParticle.position = QPointF(m_cthulhuCenter.x() + QRandomGenerator::global()->bounded(-50, 51),
m_cthulhuCenter.y() + m_eyeball_radius_base + QRandomGenerator::global()->bounded(10, 31));
newParticle.velocity = QPointF(QRandomGenerator::global()->generateDouble() * 2.0 - 1.0,
QRandomGenerator::global()->generateDouble() * 3.0 + 1.0);
newParticle.size = QRandomGenerator::global()->bounded(3, 11);
newParticle.opacity = QRandomGenerator::global()->generateDouble() * 0.2 + 0.8;
if (QRandomGenerator::global()->generateDouble() < 0.7) {
newParticle.color = QColor(150, 0, 0);
} else {
newParticle.color = QColor(80, 20, 20);
}
m_goreParticles.append(newParticle);
}
for (int i = 0; i < m_acidDrips.size(); ) {
AcidDrip &d = m_acidDrips[i];
d.position += d.velocity;
d.velocity.setY(d.velocity.y() + 0.1);
d.opacity -= 0.008;
d.trailOpacity -= 0.012;
d.size *= 0.995;
if (d.position.y() > m_widgetHeight + 50 || d.opacity <= 0.01) {
m_acidDrips.removeAt(i);
} else {
++i;
}
}
if (QRandomGenerator::global()->generateDouble() < 0.05) {
AcidDrip newDrip;
newDrip.position = QPointF(m_cthulhuCenter.x() + QRandomGenerator::global()->bounded(-60, 61),
m_cthulhuCenter.y() + m_eyeball_radius_base * 0.8 + QRandomGenerator::global()->bounded(0, 20));
newDrip.velocity = QPointF(QRandomGenerator::global()->generateDouble() * 1.0 - 0.5,
QRandomGenerator::global()->generateDouble() * 1.5 + 0.5);
newDrip.size = QRandomGenerator::global()->bounded(4, 8);
newDrip.opacity = QRandomGenerator::global()->generateDouble() * 0.3 + 0.7;
newDrip.trailOpacity = 0.5;
newDrip.color = QColor(50, 150, 50, 255);
m_acidDrips.append(newDrip);
}
for (TentacleShadow &shadow : m_tentacleShadows) {
for (int i = 0; i < shadow.points.size(); ++i) {
shadow.points[i].setX(shadow.points[i].x() + qSin(m_t_current * 0.1 + shadow.phaseOffset + i * 0.5) * 0.5);
shadow.points[i].setY(shadow.points[i].y() + qCos(m_t_current * 0.08 + shadow.phaseOffset + i * 0.7) * 0.5);
if (shadow.points[i].x() < -200) shadow.points[i].setX(m_widgetWidth + 200);
else if (shadow.points[i].x() > m_widgetWidth + 200) shadow.points[i].setX(-200);
if (shadow.points[i].y() < -200) shadow.points[i].setY(m_widgetHeight + 200);
else if (shadow.points[i].y() > m_widgetHeight + 200) shadow.points[i].setY(-200);
}
}
emit particlesUpdated(m_goreParticles, m_acidDrips, m_tentacleShadows);
}
signals:
void particlesUpdated(QVector<GoreParticle> newGore, QVector<AcidDrip> newAcid, QVector<TentacleShadow> newShadows);
private:
double m_t_current;
int m_widgetHeight;
int m_widgetWidth;
QPointF m_cthulhuCenter;
double m_eyeball_radius_base;
QVector<GoreParticle> m_goreParticles;
QVector<AcidDrip> m_acidDrips;
QVector<TentacleShadow> m_tentacleShadows;
};
class JellyfishWidget : public QWidget
{
Q_OBJECT
public:
explicit JellyfishWidget(QWidget *parent = nullptr);
~JellyfishWidget();
protected:
void paintEvent(QPaintEvent *event) override;
void mouseMoveEvent(QMouseEvent *event) override;
void leaveEvent(QEvent *event) override;
private slots:
void updateAnimation();
void handleParticlesUpdated(QVector<GoreParticle> newGore,
QVector<AcidDrip> newAcid,
QVector<TentacleShadow> newShadows);
private:
double x_input;
double y_input;
double t_current;
QTimer *animationTimer;
QPointF mousePosition;
QPointF smoothedPupilTarget;
bool mouseIsInWindow;
double blinkProgress;
bool isBlinking;
QVector<GoreParticle> fallingGoreParticles;
QVector<AcidDrip> acidDrips;
QVector<TentacleShadow> backgroundTentacleShadows;
double pulseScale;
double m_targetPupilScaleFactor;
double m_currentPupilScaleFactor;
QPen eyeballBorderPen;
QBrush eyeballGradientBrush;
QPen irisBorderPen;
QBrush irisGradientBrush;
QPen pupilPen;
QBrush pupilBrush;
QBrush eyelidBrush;
QPen goreTendrilPen;
QBrush goreTendrilBrush;
QPen fallingGorePen;
QBrush fallingGoreBrush;
QPen acidDripPen;
QBrush acidDripBrush;
QPen acidDripTrailPen;
QPen backgroundShadowPen;
QPointF calculateJellyfishPoint(double local_x, double local_y, double current_t);
void drawEyeball(QPainter *painter, const QPointF& center, double radius, double eyeball_height);
void drawGoreTendrils(QPainter *painter, const QPointF& center, double radius, int num_tentacles, double current_t);
void drawFallingGoreAndBlood(QPainter *painter);
void drawAcidDrips(QPainter *painter);
void drawBackgroundTentacleShadows(QPainter *painter);
};
#endif
================================================
FILE: Anime_Template_Project/Flowing_Gradient_Font/widget.cpp
================================================
#include "widget.h"
Widget::Widget(QWidget *parent)
: QWidget(parent) {
this->resize(1440, 880);
animation = new QPropertyAnimation(this, "Gradient_Position");
animation->setDuration(5000);
animation->setStartValue(0);
animation->setEndValue(360);
animation->start();
connect(animation, &QPropertyAnimation::finished, this, [this] {
animation->start();
});
animation2 = new QPropertyAnimation(this, "Circle_Ratio");
animation2->setDuration(1000);
animation2->setStartValue(m_Circle_Ratio);
animation2->setEndValue(1.0);
button = new QPushButton(this);
button->setText("更改背景颜色");
button->setGeometry(20, 20, 100, 30);
lineEdit = new QLineEdit(this);
lineEdit->setGeometry(130, 20, 100, 30);
connect(lineEdit, &QLineEdit::textChanged, this, [this](const QString &text) {
color_str = text;
update();
});
connect(button, &QPushButton::clicked, this, [this] {
if (m_isForward) {
this->forward();
m_isForward = false;
} else {
this->backward();
m_isForward = true;
}
});
}
Widget::~Widget() {}
void Widget::paintEvent(QPaintEvent *event) {
QPainter painter(this);
int w = this->width();
int h = this->height();
int sum = w + h;
painter.setRenderHints(QPainter::Antialiasing | QPainter::SmoothPixmapTransform | QPainter::TextAntialiasing);
painter.setPen(Qt::NoPen);
painter.setBrush(QBrush(QColor(255, 255, 255, 255)));
painter.drawRect(0, 0, w, h);
painter.setBrush(QBrush(QColor(0, 0, 0, 255)));
painter.drawEllipse(button->rect().bottomRight(), int(sum * m_Circle_Ratio), int(sum * m_Circle_Ratio));
QConicalGradient gradient(w / 2, h, m_Gradient_Position);
gradient.setColorAt(0, QColor(255, 167, 69, 255));
gradient.setColorAt(0.125, QColor(254, 134, 159, 255));
gradient.setColorAt(0.25, QColor(239, 122, 200, 255));
gradient.setColorAt(0.375, QColor(160, 131, 237, 255));
gradient.setColorAt(0.5, QColor(67, 174, 255, 255));
gradient.setColorAt(0.625, QColor(160, 131, 237, 255));
gradient.setColorAt(0.75, QColor(239, 122, 200, 255));
gradient.setColorAt(0.875, QColor(254, 134, 159, 255));
gradient.setColorAt(1, QColor(255, 167, 69, 255));
painter.setBrush(gradient);
QFont font;
font.setPixelSize(h / 5);
font.setFamily("微软雅黑");
font.setBold(true);
painter.setFont(font);
painter.setPen(QPen(QBrush(gradient), 2));
painter.drawText(QRect(0, 0, w, h), Qt::AlignCenter, color_str);
}
void Widget::resizeEvent(QResizeEvent *event) {}
void Widget::forward() {
animation2->setDirection(QAbstractAnimation::Forward);
animation2->start();
}
void Widget::backward() {
animation2->setDirection(QAbstractAnimation::Backward);
animation2->start();
}
int Widget::Gradient_Position() const {
return m_Gradient_Position;
}
void Widget::setGradient_Position(const int &value) {
if (m_Gradient_Position == value)
return;
m_Gradient_Position = value;
update();
}
qreal Widget::Circle_Ratio() const {
return m_Circle_Ratio;
}
void Widget::setCircle_Ratio(const qreal &value) {
if (m_Circle_Ratio == value)
return;
m_Circle_Ratio = value;
update();
}
================================================
FILE: Anime_Template_Project/Flowing_Gradient_Font/widget.h
================================================
#ifndef WIDGET_H
#define WIDGET_H
#include <QWidget>
#include <QPainter>
#include <QPropertyAnimation>
#include <QPushButton>
#include <QLineEdit>
class Widget : public QWidget
{
Q_OBJECT
Q_PROPERTY(int Gradient_Position READ Gradient_Position WRITE setGradient_Position)
Q_PROPERTY(qreal Circle_Ratio READ Circle_Ratio WRITE setCircle_Ratio)
public:
Widget(QWidget *parent = nullptr);
~Widget();
QPropertyAnimation *animation;
QPropertyAnimation* animation2;
QPushButton *button;
QLineEdit *lineEdit;
void forward();
void backward();
int Gradient_Position() const;
void setGradient_Position(const int&value);
qreal Circle_Ratio() const;
void setCircle_Ratio(const qreal&value);
protected:
void paintEvent(QPaintEvent *event);
void resizeEvent(QResizeEvent *event);
private:
int m_Gradient_Position;
QColor Global_Color = QColor(255, 255, 255 , 255);
QString color_str;
qreal m_Circle_Ratio = 0.0;
bool m_isForward = true;
};
#endif // WIDGET_H
================================================
FILE: Anime_Template_Project/FractalWidget/CMakeLists.txt
================================================
cmake_minimum_required(VERSION 3.16)
project(FractalWidget VERSION 0.1 LANGUAGES CXX)
set(CMAKE_AUTOUIC ON)
set(CMAKE_AUTOMOC ON)
set(CMAKE_AUTORCC ON)
set(CMAKE_CXX_STANDARD 17)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
find_package(QT NAMES Qt6 Qt5 REQUIRED COMPONENTS Widgets)
find_package(Qt${QT_VERSION_MAJOR} REQUIRED COMPONENTS Widgets)
set(PROJECT_SOURCES
main.cpp
fractalwidget.cpp
fractalwidget.h
)
if(${QT_VERSION_MAJOR} GREATER_EQUAL 6)
qt_add_executable(FractalWidget
MANUAL_FINALIZATION
${PROJECT_SOURCES}
mainwindow.h mainwindow.cpp
fractalworker.h fractalworker.cpp
)
# Define target properties for Android with Qt 6 as:
# set_property(TARGET FractalWidget APPEND PROPERTY QT_ANDROID_PACKAGE_SOURCE_DIR
# ${CMAKE_CURRENT_SOURCE_DIR}/android)
# For more information, see https://doc.qt.io/qt-6/qt-add-executable.html#target-creation
else()
if(ANDROID)
add_library(FractalWidget SHARED
${PROJECT_SOURCES}
)
# Define properties for Android with Qt 5 after find_package() calls as:
# set(ANDROID_PACKAGE_SOURCE_DIR "${CMAKE_CURRENT_SOURCE_DIR}/android")
else()
add_executable(FractalWidget
${PROJECT_SOURCES}
)
endif()
endif()
target_link_libraries(FractalWidget PRIVATE Qt${QT_VERSION_MAJOR}::Widgets)
# Qt for iOS sets MACOSX_BUNDLE_GUI_IDENTIFIER automatically since Qt 6.1.
# If you are developing for iOS or macOS you should consider setting an
# explicit, fixed bundle identifier manually though.
if(${QT_VERSION} VERSION_LESS 6.1.0)
set(BUNDLE_ID_OPTION MACOSX_BUNDLE_GUI_IDENTIFIER com.example.FractalWidget)
endif()
set_target_properties(FractalWidget PROPERTIES
${BUNDLE_ID_OPTION}
MACOSX_BUNDLE_BUNDLE_VERSION ${PROJECT_VERSION}
MACOSX_BUNDLE_SHORT_VERSION_STRING ${PROJECT_VERSION_MAJOR}.${PROJECT_VERSION_MINOR}
MACOSX_BUNDLE TRUE
WIN32_EXECUTABLE TRUE
)
include(GNUInstallDirs)
install(TARGETS FractalWidget
BUNDLE DESTINATION .
LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR}
RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR}
)
if(QT_VERSION_MAJOR EQUAL 6)
qt_finalize_executable(FractalWidget)
endif()
================================================
FILE: Anime_Template_Project/FractalWidget/fractalwidget.cpp
================================================
#include "fractalwidget.h"
#include <QPainter>
#include <QDebug>
#include <cmath>
#include <algorithm>
#include <QRandomGenerator>
#include <QWheelEvent>
#include <QMouseEvent>
#include <QElapsedTimer>
FractalWidget::FractalWidget(QWidget *parent)
: QWidget(parent),
m_currentFractalType(Mandelbrot),
m_juliaCr(-0.7),
m_juliaCi(0.27015),
m_animationTimer(new QTimer(this)),
m_animationStep(0),
m_maxAnimationSteps(500),
m_centerX(0.0),
m_centerY(0.0),
m_scale(2.0),
m_defaultCenterX(0.0),
m_defaultCenterY(0.0),
m_defaultScale(2.0),
m_lineFractalOrder(1),
m_defaultLineFractalOrder(1),
m_workerThread(new QThread(this)),
m_fractalWorker(new FractalWorker()),
m_isCalculating(false),
m_isDragging(false),
m_accumulatedDragDelta(0, 0),
m_imageTopLeft(0, 0)
{
resize(600, 600);
connect(m_animationTimer, &QTimer::timeout, this, &FractalWidget::animateFractal);
m_fractalWorker->moveToThread(m_workerThread);
connect(m_fractalWorker, &FractalWorker::imageReady, this, &FractalWidget::onImageReady);
connect(m_workerThread, &QThread::finished, m_fractalWorker, &QObject::deleteLater);
connect(m_workerThread, &QThread::finished, m_workerThread, &QObject::deleteLater);
connect(m_fractalWorker, &FractalWorker::finished, this, &FractalWidget::onWorkerFinished);
m_workerThread->start();
}
FractalWidget::~FractalWidget()
{
if (m_workerThread->isRunning())
{
m_workerThread->quit();
m_workerThread->wait();
}
}
void FractalWidget::setFractalType(FractalType type)
{
bool typeChanged = (m_currentFractalType != type);
m_currentFractalType = type;
m_imageTopLeft = QPointF(0, 0);
if (m_currentFractalType == Mandelbrot ||
m_currentFractalType == Julia ||
m_currentFractalType == BurningShip ||
m_currentFractalType == Newton ||
m_currentFractalType == Tricorn ||
m_currentFractalType == BurningShipJulia ||
m_currentFractalType == Spider) {
if (typeChanged || (std::abs(m_centerX - m_defaultCenterX) > 1e-9 ||
std::abs(m_centerY - m_defaultCenterY) > 1e-9 ||
std::abs(m_scale - m_defaultScale) > 1e-9)) {
m_centerX = m_defaultCenterX;
m_centerY = m_defaultCenterY;
m_scale = m_defaultScale;
qDebug() << "迭代型分形视图已重置到默认。";
}
}
else
{
if (typeChanged || m_lineFractalOrder != m_defaultLineFractalOrder)
{
m_lineFractalOrder = m_defaultLineFractalOrder;
qDebug() << "线条分形阶数已重置到默认。";
}
}
startAnimation();
}
void FractalWidget::setJuliaC(double cr, double ci)
{
m_juliaCr = cr;
m_juliaCi = ci;
if (m_currentFractalType == Julia || m_currentFractalType == BurningShipJulia)
{
startAnimation();
}
}
void FractalWidget::paintEvent(QPaintEvent *event)
{
Q_UNUSED(event);
QPainter painter(this);
painter.fillRect(rect(), Qt::black);
if (!m_image.isNull() && (m_currentFractalType == Mandelbrot ||
m_currentFractalType == Julia ||
m_currentFractalType == BurningShip ||
m_currentFractalType == Newton ||
m_currentFractalType == Tricorn ||
m_currentFractalType == BurningShipJulia ||
m_currentFractalType == Spider)) {
if (m_isDragging)
{
painter.drawImage(m_imageTopLeft, m_image);
}
else
{
painter.drawImage(0, 0, m_image);
}
}
else if (m_currentFractalType == KochSnowflake ||
m_currentFractalType == SierpinskiCurve)
{
painter.setRenderHint(QPainter::Antialiasing, true);
painter.setPen(Qt::white);
qreal minSide = std::min(width(), height()) * 0.8;
if (m_currentFractalType == KochSnowflake)
{
QPointF p1(width() / 2.0 - minSide / 2.0, height() / 2.0 + minSide * std::sqrt(3.0) / 6.0);
QPointF p2(width() / 2.0 + minSide / 2.0, height() / 2.0 + minSide * std::sqrt(3.0) / 6.0);
QPointF p3(width() / 2.0, height() / 2.0 - minSide * std::sqrt(3.0) / 3.0);
generateKochSnowflake(painter, m_animationStep, p1, p2);
generateKochSnowflake(painter, m_animationStep, p2, p3);
generateKochSnowflake(painter, m_animationStep, p3, p1);
} else if (m_currentFractalType == SierpinskiCurve)
{
qreal side = minSide * 0.8;
QPointF p1(width() / 2.0 - side / 2.0, height() / 2.0 + side * std::sqrt(3.0) / 6.0);
QPointF p2(width() / 2.0 + side / 2.0, height() / 2.0 + side * std::sqrt(3.0) / 6.0);
QPointF p3(width() / 2.0, height() / 2.0 - side * std::sqrt(3.0) / 3.0);
generateSierpinskiCurve(painter, m_animationStep, p1, p2, p3);
}
}
if (m_isCalculating && (m_currentFractalType == Mandelbrot ||
m_currentFractalType == Julia ||
m_currentFractalType == BurningShip ||
m_currentFractalType == Newton ||
m_currentFractalType == Tricorn ||
m_currentFractalType == BurningShipJulia ||
m_currentFractalType == Spider)) {
painter.setPen(Qt::white);
painter.setFont(QFont("Arial", 24));
painter.drawText(rect(), Qt::AlignCenter, "计算中...");
}
}
void FractalWidget::resizeEvent(QResizeEvent *event)
{
Q_UNUSED(event);
setFractalType(m_currentFractalType);
}
void FractalWidget::wheelEvent(QWheelEvent *event)
{
if (!(m_currentFractalType == Mandelbrot ||
m_currentFractalType == Julia ||
m_currentFractalType == BurningShip ||
m_currentFractalType == Newton ||
m_currentFractalType == Tricorn ||
m_currentFractalType == BurningShipJulia ||
m_currentFractalType == Spider))
{
event->ignore();
return;
}
QPoint numPixels = event->pixelDelta();
QPoint numDegrees = event->angleDelta() / 4;
qreal zoomFactor = 1.0;
if (!numPixels.isNull())
{
zoomFactor = std::pow(1.0015, numPixels.y());
} else if (!numDegrees.isNull())
{
zoomFactor = std::pow(1.1, numDegrees.y() / 15.0);
}
if (zoomFactor == 1.0)
{
event->ignore();
return;
}
QPoint mousePos = event->position().toPoint();
double mouseX = mousePos.x();
double mouseY = mousePos.y();
double oldReal = (mouseX - width() / 2.0) * m_scale / width() + m_centerX;
double oldImag = (mouseY - height() / 2.0) * m_scale / height() + m_centerY;
m_scale /= zoomFactor;
m_centerX = oldReal - (mouseX - width() / 2.0) * m_scale / width();
m_centerY = oldImag - (mouseY - height() / 2.0) * m_scale / height();
m_scale = std::max(1e-10, std::min(1000.0, m_scale));
startAnimation();
event->accept();
}
void FractalWidget::mousePressEvent(QMouseEvent *event)
{
if (!(m_currentFractalType == Mandelbrot ||
m_currentFractalType == Julia ||
m_currentFractalType == BurningShip ||
m_currentFractalType == Newton ||
m_currentFractalType == Tricorn ||
m_currentFractalType == BurningShipJulia ||
m_currentFractalType == Spider)) {
event->ignore();
return;
}
if (event->button() == Qt::LeftButton) {
m_isDragging = true;
m_lastMousePos = event->position().toPoint();
m_accumulatedDragDelta = QPoint(0, 0);
m_imageTopLeft = QPointF(0, 0);
updateLoadingState(true);
event->accept();
}
else
{
event->ignore();
}
}
void FractalWidget::mouseMoveEvent(QMouseEvent *event)
{
if (m_isDragging && (m_currentFractalType == Mandelbrot ||
m_currentFractalType == Julia ||
m_currentFractalType == BurningShip ||
m_currentFractalType == Newton ||
m_currentFractalType == Tricorn ||
m_currentFractalType == BurningShipJulia ||
m_currentFractalType == Spider)) {
QPoint currentMousePos = event->position().toPoint();
QPoint delta = currentMousePos - m_lastMousePos;
m_imageTopLeft += delta;
m_centerX -= delta.x() * m_scale / width();
m_centerY -= delta.y() * m_scale / height();
m_lastMousePos = currentMousePos;
m_accumulatedDragDelta += delta;
if (std::abs(m_accumulatedDragDelta.x()) >= 5 || std::abs(m_accumulatedDragDelta.y()) >= 5) {
update();
m_accumulatedDragDelta = QPoint(0, 0);
}
event->accept();
} else {
event->ignore();
}
}
void FractalWidget::mouseReleaseEvent(QMouseEvent *event)
{
if (event->button() == Qt::LeftButton) {
if (m_isDragging) {
m_isDragging = false;
startAnimation();
}
event->accept();
} else {
event->ignore();
}
}
void FractalWidget::startAnimation()
{
stopAnimation();
m_animationStep = 0;
if (m_currentFractalType == Mandelbrot ||
m_currentFractalType == Julia ||
m_currentFractalType == BurningShip ||
m_currentFractalType == Newton ||
m_currentFractalType == Tricorn ||
m_currentFractalType == BurningShipJulia ||
m_currentFractalType == Spider) {
m_maxAnimationSteps = 500;
m_animationTimer->start(25);
} else {
int orderVariation = QRandomGenerator::global()->bounded(-2, 3);
m_maxAnimationSteps = m_lineFractalOrder + orderVariation;
m_maxAnimationSteps = std::max(4, m_maxAnimationSteps);
m_animationTimer->start(1);
}
}
void FractalWidget::stopAnimation()
{
if (m_animationTimer->isActive()) {
m_animationTimer->stop();
}
if (m_isCalculating) {
qDebug() << "动画停止,但分形计算仍在进行中。当前帧将完成。";
}
updateLoadingState(false);
}
void FractalWidget::animateFractal()
{
if (m_animationStep > m_maxAnimationSteps) {
stopAnimation();
return;
}
QElapsedTimer timer;
timer.start();
if (m_currentFractalType == Mandelbrot ||
m_currentFractalType == Julia ||
m_currentFractalType == BurningShip ||
m_currentFractalType == Newton ||
m_currentFractalType == Tricorn ||
m_currentFractalType == BurningShipJulia ||
m_currentFractalType == Spider) {
if (!m_isCalculating) {
updateLoadingState(true);
startFractalCalculationThread(m_animationStep);
}
} else {
update();
qDebug() << "线条分形 动画步进:" << m_animationStep << "耗时:" << timer.elapsed() << "ms";
}
if (m_currentFractalType == KochSnowflake ||
m_currentFractalType == SierpinskiCurve) {
m_animationStep += 1;
} else {
m_animationStep += 10;
}
m_animationStep = std::min(m_animationStep, m_maxAnimationSteps + 1);
}
void FractalWidget::onImageReady(const QImage &image)
{
m_image = image;
update();
qDebug() << "收到工作线程图像。更新UI。";
updateLoadingState(false);
}
void FractalWidget::onWorkerFinished()
{
}
void FractalWidget::startFractalCalculationThread(int currentMaxIterations)
{
QMetaObject::invokeMethod(m_fractalWorker, "doWork",
Qt::QueuedConnection,
Q_ARG(FractalWorker::FractalType, (FractalWorker::FractalType)m_currentFractalType),
Q_ARG(int, currentMaxIterations),
Q_ARG(double, m_juliaCr),
Q_ARG(double, m_juliaCi),
Q_ARG(double, m_centerX),
Q_ARG(double, m_centerY),
Q_ARG(double, m_scale),
Q_ARG(int, width()),
Q_ARG(int, height()),
Q_ARG(int, m_maxAnimationSteps));
m_isCalculating = true;
}
void FractalWidget::updateLoadingState(bool loading) {
m_isCalculating = loading;
update();
}
void FractalWidget::generateKochSnowflake(QPainter &painter, int order, QPointF p1, QPointF p2)
{
if (order == 0) {
painter.drawLine(p1, p2);
return;
}
QPointF p_a = p1;
QPointF p_b(p1.x() + (p2.x() - p1.x()) / 3.0, p1.y() + (p2.y() - p1.y()) / 3.0);
QPointF p_c(p1.x() + 2.0 * (p2.x() - p1.x()) / 3.0, p1.y() + 2.0 * (p2.y() - p1.y()) / 3.0);
QPointF p_d = p2;
qreal dx = p2.x() - p1.x();
qreal dy = p2.y() - p1.y();
QPointF p_e(p_b.x() + dx * std::cos(M_PI / 3.0) - dy * std::sin(M_PI / 3.0),
p_b.y() + dx * std::sin(M_PI / 3.0) + dy * std::cos(M_PI / 3.0));
generateKochSnowflake(painter, order - 1, p_a, p_b);
generateKochSnowflake(painter, order - 1, p_b, p_e);
generateKochSnowflake(painter, order - 1, p_e, p_c);
generateKochSnowflake(painter, order - 1, p_c, p_d);
}
void FractalWidget::generateSierpinskiCurve(QPainter &painter, int order, QPointF p1, QPointF p2, QPointF p3)
{
if (order == 0) {
painter.drawLine(p1, p2);
painter.drawLine(p2, p3);
painter.drawLine(p3, p1);
return;
}
QPointF p12((p1.x() + p2.x()) / 2.0, (p1.y() + p2.y()) / 2.0);
QPointF p23((p2.x() + p3.x()) / 2.0, (p2.y() + p3.y()) / 2.0);
QPointF p31((p3.x() + p1.x()) / 2.0, (p1.y() + p3.y()) / 2.0);
generateSierpinskiCurve(painter, order - 1, p1, p12, p31);
generateSierpinskiCurve(painter, order - 1, p12, p2, p23);
generateSierpinskiCurve(painter, order - 1, p31, p23, p3);
}
================================================
FILE: Anime_Template_Project/FractalWidget/fractalwidget.h
================================================
#ifndef FRACTALWIDGET_H
#define FRACTALWIDGET_H
#include <QWidget>
#include <QImage>
#include <QTimer>
#include <QThread>
#include <QPoint>
#include <QPointF>
#include "fractalworker.h"
class FractalWidget : public QWidget
{
Q_OBJECT
public:
explicit FractalWidget(QWidget *parent = nullptr);
~FractalWidget();
enum FractalType {
Mandelbrot,
Julia,
BurningShip,
Newton,
Tricorn,
BurningShipJulia,
Spider,
SierpinskiCurve,
KochSnowflake
};
Q_ENUM(FractalType)
void setFractalType(FractalType type);
void setJuliaC(double cr, double ci);
protected:
void paintEvent(QPaintEvent *event) override;
void resizeEvent(QResizeEvent *event) override;
void wheelEvent(QWheelEvent *event) override;
void mousePressEvent(QMouseEvent *event) override;
void mouseMoveEvent(QMouseEvent *event) override;
void mouseReleaseEvent(QMouseEvent *event) override;
private slots:
void animateFractal();
void onImageReady(const QImage &image);
void onWorkerFinished();
private:
FractalType m_currentFractalType;
double m_juliaCr;
double m_juliaCi;
QTimer *m_animationTimer;
int m_animationStep;
int m_maxAnimationSteps;
double m_centerX;
double m_centerY;
double m_scale;
double m_defaultCenterX;
double m_defaultCenterY;
double m_defaultScale;
int m_lineFractalOrder;
int m_defaultLineFractalOrder;
QThread *m_workerThread;
FractalWorker *m_fractalWorker;
QImage m_image;
bool m_isCalculating;
bool m_isDragging;
QPoint m_lastMousePos;
QPoint m_accumulatedDragDelta;
QPointF m_imageTopLeft;
void startAnimation();
void stopAnimation();
void startFractalCalculationThread(int currentMaxIterations);
void updateLoadingState(bool loading);
void generateKochSnowflake(QPainter &painter, int order, QPointF p1, QPointF p2);
void generateSierpinskiCurve(QPainter &painter, int order, QPointF p1, QPointF p2, QPointF p3);
};
#endif // FRACTALWIDGET_H
================================================
FILE: Anime_Template_Project/FractalWidget/fractalworker.cpp
================================================
#include "fractalworker.h"
#include <cmath>
#include <complex>
#include <QVector>
#include <QThreadPool>
#include <QElapsedTimer>
#include <QDebug>
FractalWorker::FractalWorker(QObject *parent)
: QObject(parent)
{
}
void FractalWorker::doWork(FractalType type, int currentMaxIterations, double juliaCr, double juliaCi,
double centerX, double centerY, double scale,
int imageWidth, int imageHeight, int maxAnimationSteps)
{
m_juliaCr = juliaCr;
m_juliaCi = juliaCi;
m_centerX = centerX;
m_centerY = centerY;
m_scale = scale;
m_maxAnimationSteps = maxAnimationSteps;
if (!(type == Mandelbrot || type == Julia || type == BurningShip || type == Newton || type == Tricorn || type == BurningShipJulia || type == Spider)) {
emit finished();
return;
}
QElapsedTimer timer;
timer.start();
int numThreads = QThreadPool::globalInstance()->maxThreadCount();
if (numThreads == 0) {
numThreads = QThread::idealThreadCount();
}
if (numThreads <= 0) numThreads = 1;
QVector<FractalChunkData> chunks;
int rowsPerChunk = imageHeight / numThreads;
int remainderRows = imageHeight % numThreads;
for (int i = 0; i < numThreads; ++i) {
FractalChunkData data;
data.type = type;
data.currentMaxIterations = currentMaxIterations;
data.juliaCr = juliaCr;
data.juliaCi = juliaCi;
data.centerX = centerX;
data.centerY = centerY;
data.scale = scale;
data.imageWidth = imageWidth;
data.imageHeight = imageHeight;
data.maxAnimationSteps = maxAnimationSteps;
data.startY = i * rowsPerChunk;
data.endY = data.startY + rowsPerChunk;
if (i == numThreads - 1) {
data.endY += remainderRows;
}
chunks.append(data);
}
QVector<QFuture<QImage>> futures;
futures.reserve(chunks.size());
for (const FractalChunkData& data : chunks) {
futures.append(QtConcurrent::run(FractalWorker::computeFractalChunk, data));
}
for (QFuture<QImage>& future : futures) {
future.waitForFinished();
}
QImage finalImage(imageWidth, imageHeight, QImage::Format_ARGB32);
for (int i = 0; i < futures.size(); ++i) {
const QImage &chunkImage = futures.at(i).result();
const FractalChunkData &chunkData = chunks.at(i);
for (int y = 0; y < chunkImage.height(); ++y) {
for (int x = 0; x < chunkImage.width(); ++x) {
finalImage.setPixel(x, chunkData.startY + y, chunkImage.pixel(x, y));
}
}
}
qDebug() << "分形计算完成,耗时" << timer.elapsed() << "ms,使用" << numThreads << "个线程。";
emit imageReady(finalImage);
emit finished();
}
QImage FractalWorker::computeFractalChunk(const FractalChunkData &data)
{
QImage chunkImage(data.imageWidth, data.endY - data.startY, QImage::Format_ARGB32);
for (int y = 0; y < (data.endY - data.startY); ++y) {
for (int x = 0; x < data.imageWidth; ++x) {
double globalY = data.startY + y;
double real = (x - data.imageWidth / 2.0) * data.scale / data.imageWidth + data.centerX;
double imag = (globalY - data.imageHeight / 2.0) * data.scale / data.imageHeight + data.centerY;
int iterations = 0;
QRgb pixelColor = qRgb(0, 0, 0);
if (data.type == Mandelbrot) {
double zr = 0.0;
double zi = 0.0;
while (zr * zr + zi * zi < 4.0 && iterations < data.currentMaxIterations) {
double tempZr = zr * zr - zi * zi + real;
zi = 2.0 * zr * zi + imag;
zr = tempZr;
iterations++;
}
pixelColor = getColor(iterations, data.maxAnimationSteps);
} else if (data.type == Julia) {
double zr = real;
double zi = imag;
while (zr * zr + zi * zi < 4.0 && iterations < data.currentMaxIterations) {
double tempZr = zr * zr - zi * zi + data.juliaCr;
zi = 2.0 * zr * zi + data.juliaCi;
zr = tempZr;
iterations++;
}
pixelColor = getColor(iterations, data.maxAnimationSteps);
} else if (data.type == BurningShip) {
double zr = 0.0;
double zi = 0.0;
while (zr * zr + zi * zi < 4.0 && iterations < data.currentMaxIterations) {
double absZr = std::abs(zr);
double absZi = std::abs(zi);
double tempZr = absZr * absZr - absZi * absZi + real;
zi = 2.0 * absZr * absZi + imag;
zr = tempZr;
iterations++;
}
pixelColor = getColor(iterations, data.maxAnimationSteps);
} else if (data.type == Newton) {
std::complex<double> root1(1.0, 0.0);
std::complex<double> root2(-0.5, std::sqrt(3.0) / 2.0);
std::complex<double> root3(-0.5, -std::sqrt(3.0) / 2.0);
const double tolerance = 1e-6;
std::complex<double> z(real, imag);
std::complex<double> finalZ = z;
while (iterations < data.currentMaxIterations) {
std::complex<double> f_z = z * z * z - 1.0;
std::complex<double> f_prime_z = 3.0 * z * z;
if (std::abs(f_prime_z) < 1e-10) {
iterations = data.currentMaxIterations;
break;
}
std::complex<double> z_next = z - f_z / f_prime_z;
if (std::abs(z_next - z) < tolerance) {
finalZ = z_next;
break;
}
z = z_next;
iterations++;
}
pixelColor = getNewtonColor(iterations, data.maxAnimationSteps, finalZ.real(), finalZ.imag());
} else if (data.type == Tricorn) {
double zr = 0.0;
double zi = 0.0;
while (zr * zr + zi * zi < 4.0 && iterations < data.currentMaxIterations) {
double tempZr = zr * zr - zi * zi + real;
zi = -2.0 * zr * zi + imag;
zr = tempZr;
iterations++;
}
pixelColor = getColor(iterations, data.maxAnimationSteps);
} else if (data.type == BurningShipJulia) {
double zr = real;
double zi = imag;
while (zr * zr + zi * zi < 4.0 && iterations < data.currentMaxIterations) {
double absZr = std::abs(zr);
double absZi = std::abs(zi);
double tempZr = absZr * absZi - absZi * absZi + data.juliaCr;
zi = 2.0 * absZr * absZi + data.juliaCi;
zr = tempZr;
iterations++;
}
pixelColor = getColor(iterations, data.maxAnimationSteps);
} else if (data.type == Spider) {
double zr = 0.0;
double zi = 0.0;
double cr = real;
double ci = imag;
while (zr * zr + zi * zi < 4.0 && iterations < data.currentMaxIterations) {
double tempZr = zr * zr - zi * zi + cr;
double tempZi = 2.0 * zr * zi + ci;
cr = zr;
ci = zi;
zr = tempZr;
zi = tempZi;
iterations++;
}
pixelColor = getColor(iterations, data.maxAnimationSteps);
}
chunkImage.setPixel(x, y, pixelColor);
}
}
return chunkImage;
}
QRgb FractalWorker::getColor(int iterations, int maxIterationsUsed)
{
if (iterations == maxIterationsUsed) {
return qRgb(0, 0, 0);
}
double t = (double)iterations / maxIterationsUsed;
int r = (int)(9 * (1 - t) * t * t * t * 255);
int g = (int)(15 * (1 - t) * (1 - t) * t * t * 255);
int b = (int)(8.5 * (1 - t) * (1 - t) * (1 - t) * t * 255);
return qRgb(r, g, b);
}
QRgb FractalWorker::getNewtonColor(int iterations, int maxIterationsUsed, double finalZr, double finalZi)
{
if (iterations == maxIterationsUsed) {
return qRgb(0, 0, 0);
}
QRgb baseColor;
std::complex<double> finalZ(finalZr, finalZi);
std::complex<double> root1(1.0, 0.0);
std::complex<double> root2(-0.5, std::sqrt(3.0) / 2.0);
std::complex<double> root3(-0.5, -std::sqrt(3.0) / 2.0);
if (std::abs(finalZ - root1) < 1e-5) {
baseColor = qRgb(255, 0, 0);
} else if (std::abs(finalZ - root2) < 1e-5) {
baseColor = qRgb(0, 255, 0);
} else if (std::abs(finalZ - root3) < 1e-5) {
baseColor = qRgb(0, 0, 255);
} else {
baseColor = qRgb(128, 128, 128);
}
double brightness = 1.0 - (double)iterations / maxIterationsUsed;
int r = qRed(baseColor) * brightness;
int g = qGreen(baseColor) * brightness;
int b = qBlue(baseColor) * brightness;
return qRgb(r, g, b);
}
================================================
FILE: Anime_Template_Project/FractalWidget/fractalworker.h
================================================
#ifndef FRACTALWORKER_H
#define FRACTALWORKER_H
#include <QObject>
#include <QImage>
#include <QtConcurrent/QtConcurrent>
#include <QFuture>
class FractalWorker : public QObject
{
Q_OBJECT
public:
explicit FractalWorker(QObject *parent = nullptr);
enum FractalType {
Mandelbrot,
Julia,
BurningShip,
Newton,
Tricorn,
BurningShipJulia,
Spider,
SierpinskiCurve,
KochSnowflake
};
signals:
void imageReady(const QImage &image);
void finished();
public slots:
void doWork(FractalType type, int currentMaxIterations, double juliaCr, double juliaCi,
double centerX, double centerY, double scale,
int imageWidth, int imageHeight, int maxAnimationSteps);
private:
struct FractalChunkData {
FractalType type;
int currentMaxIterations;
double juliaCr;
double juliaCi;
double centerX;
double centerY;
double scale;
int imageWidth;
int imageHeight;
int maxAnimationSteps;
int startY;
int endY;
};
static QImage computeFractalChunk(const FractalChunkData &data);
static QRgb getColor(int iterations, int maxIterationsUsed);
static QRgb getNewtonColor(int iterations, int maxIterationsUsed, double finalZr, double finalZi);
double m_juliaCr;
double m_juliaCi;
double m_centerX;
double m_centerY;
double m_scale;
int m_maxAnimationSteps;
};
#endif // FRACTALWORKER_H
================================================
FILE: Anime_Template_Project/FractalWidget/main.cpp
================================================
#include "mainwindow.h"
#include <QApplication>
int main(int argc, char *argv[])
{
QApplication a(argc, argv);
MainWindow w;
w.show();
return a.exec();
}
================================================
FILE: Anime_Template_Project/FractalWidget/mainwindow.cpp
================================================
#include "mainwindow.h"
#include <QVBoxLayout>
#include <QHBoxLayout>
#include <QWidget>
#include <QDebug>
MainWindow::MainWindow(QWidget *parent)
: QMainWindow(parent)
{
setupUi();
setWindowTitle("Qt 分形生成器 - She Chen Zhi Ma");
setMinimumSize(800, 700);
}
MainWindow::~MainWindow()
{
}
void MainWindow::setupUi()
{
QWidget *centralWidget = new QWidget(this);
setCentralWidget(centralWidget);
QHBoxLayout *mainHorizontalLayout = new QHBoxLayout(centralWidget);
QGroupBox *controlGroup = new QGroupBox("控制", this);
controlGroup->setMaximumWidth(250);
QVBoxLayout *controlLayout = new QVBoxLayout(controlGroup);
m_fractalTypeComboBox = new QComboBox(this);
m_fractalTypeComboBox->addItem("曼德布罗集", FractalWidget::Mandelbrot);
m_fractalTypeComboBox->addItem("朱利亚集", FractalWidget::Julia);
m_fractalTypeComboBox->addItem("燃烧船分形", FractalWidget::BurningShip);
m_fractalTypeComboBox->addItem("牛顿分形", FractalWidget::Newton);
m_fractalTypeComboBox->addItem("Tricorn", FractalWidget::Tricorn);
m_fractalTypeComboBox->addItem("燃烧船朱利亚集", FractalWidget::BurningShipJulia);
m_fractalTypeComboBox->addItem("蜘蛛分形", FractalWidget::Spider);
m_fractalTypeComboBox->addItem("谢尔宾斯基曲线", FractalWidget::SierpinskiCurve);
m_fractalTypeComboBox->addItem("科赫雪花", FractalWidget::KochSnowflake);
connect(m_fractalTypeComboBox, QOverload<int>::of(&QComboBox::currentIndexChanged),
this, &MainWindow::onFractalTypeChanged);
controlLayout->addWidget(new QLabel("选择分形类型:"));
controlLayout->addWidget(m_fractalTypeComboBox);
m_juliaCrLineEdit = new QLineEdit(this);
m_juliaCrLineEdit->setValidator(new QDoubleValidator(-1000.0, 1000.0, 5, this));
m_juliaCrLineEdit->setText("-0.7");
m_juliaCiLineEdit = new QLineEdit(this);
m_juliaCiLineEdit->setValidator(new QDoubleValidator(-1000.0, 1000.0, 5, this));
m_juliaCiLineEdit->setText("0.27015");
m_applyJuliaButton = new QPushButton("应用朱利亚参数", this);
connect(m_applyJuliaButton, &QPushButton::clicked, this, &MainWindow::onApplyJuliaParams);
QHBoxLayout *juliaCrLayout = new QHBoxLayout();
juliaCrLayout->addWidget(new QLabel("Julia Cr:"));
juliaCrLayout->addWidget(m_juliaCrLineEdit);
QHBoxLayout *juliaCiLayout = new QHBoxLayout();
juliaCiLayout->addWidget(new QLabel("Julia Ci:"));
juliaCiLayout->addWidget(m_juliaCiLineEdit);
controlLayout->addLayout(juliaCrLayout);
controlLayout->addLayout(juliaCiLayout);
controlLayout->addWidget(m_applyJuliaButton);
controlLayout->addStretch();
mainHorizontalLayout->addWidget(controlGroup);
m_fractalWidget = new FractalWidget(this);
mainHorizontalLayout->addWidget(m_fractalWidget);
m_fractalTypeComboBox->setCurrentIndex(0);
}
void MainWindow::onFractalTypeChanged(int index)
{
Q_UNUSED(index);
FractalWidget::FractalType type = static_cast<FractalWidget::FractalType>(
m_fractalTypeComboBox->currentData().toInt());
m_fractalWidget->setFractalType(type);
bool isJuliaRelated = (type == FractalWidget::Julia || type == FractalWidget::BurningShipJulia);
m_juliaCrLineEdit->setVisible(isJuliaRelated);
m_juliaCiLineEdit->setVisible(isJuliaRelated);
m_applyJuliaButton->setVisible(isJuliaRelated);
if (type == FractalWidget::BurningShipJulia) {
m_juliaCrLineEdit->setText("-0.1");
m_juliaCiLineEdit->setText("0.29015");
m_fractalWidget->setJuliaC(-0.1, 0.29015);
} else if (type == FractalWidget::Julia) {
m_juliaCrLineEdit->setText("-0.7");
m_juliaCiLineEdit->setText("0.27015");
m_fractalWidget->setJuliaC(-0.7, 0.27015);
}
}
void MainWindow::onApplyJuliaParams()
{
double cr = m_juliaCrLineEdit->text().toDouble();
double ci = m_juliaCiLineEdit->text().toDouble();
m_fractalWidget->setJuliaC(cr, ci);
}
================================================
FILE: Anime_Template_Project/FractalWidget/mainwindow.h
================================================
#ifndef MAINWINDOW_H
#define MAINWINDOW_H
#include <QMainWindow>
#include "fractalwidget.h"
#include <QComboBox>
#include <QLabel>
#include <QLineEdit>
#include <QPushButton>
#include <QDoubleValidator>
#include <QVBoxLayout>
#include <QHBoxLayout>
#include <QGroupBox>
#include <QDebug>
class MainWindow : public QMainWindow
{
Q_OBJECT
public:
explicit MainWindow(QWidget *parent = nullptr);
~MainWindow();
private slots:
void onFractalTypeChanged(int index);
void onApplyJuliaParams();
private:
FractalWidget *m_fractalWidget;
QComboBox *m_fractalTypeComboBox;
QLineEdit *m_juliaCrLineEdit;
QLineEdit *m_juliaCiLineEdit;
QPushButton *m_applyJuliaButton;
void setupUi();
};
#endif // MAINWINDOW_H
================================================
FILE: Anime_Template_Project/Generative_Lines/widget.cpp
================================================
#include "widget.h"
Widget::Widget(QWidget *parent)
: QWidget(parent)
{
// 设置窗口大小
resize(600, 600);
// 初始化半径和角度步长
outerRadius = 200.0;
innerRadius = 200.0;
angleStep = 15; // 每15度一个点
animation = new QPropertyAnimation(this, "innerRadius");
animation->setDuration(700); // 动画持续时间为5秒
animation->setEasingCurve(QEasingCurve::InOutCirc); // 使用缓动曲线
animation2 = new QPropertyAnimation(this, "angleStep");
animation2->setDuration(700); // 动画持续时间为5秒
animation2->setEasingCurve(QEasingCurve::InOutCirc); // 使用缓动曲线
timer = new QTimer(this);
connect(timer, &QTimer::timeout, this,[this]{
count += 1;
switch (count)
{
case 1:
startangleStepAnimation(5,15);
startAnimation(200,100);
break;
case 2:
startAnimation(100,220);
break;
case 3:
startAnimation(220,200);
break;
case 4:
startangleStepAnimation(15,120);
startAnimation(200,150);
break;
case 5:
startangleStepAnimation(120,15);
startAnimation(150,180);
break;
case 6:
startangleStepAnimation(15,90);
startAnimation(180,60);
break;
case 7:
startAnimation(60,200);
startangleStepAnimation(90,15);
break;
case 8:
startAnimation(200,100);
startangleStepAnimation(15,5);
break;
case 9:
startAnimation(100,170);
startangleStepAnimation(5,180);
break;
case 10:
startAnimation(170,200);
startangleStepAnimation(180,5);
count = 0; // 重置计数器
break;
}
}); // 每次定时器超时更新界面
connect(animation, &QPropertyAnimation::valueChanged, this, [=]{
timer->start(100); // 启动定时器,每100毫秒触发一次
}); // 当动画值变化时更新界面
timer->start(100); // 启动定时器,每100毫秒触发一次
}
Widget::~Widget() {}
void Widget::startAnimation(qreal Start, qreal End)
{
timer->stop();
// 设置动画的起始和结束值
animation->setStartValue(Start);
animation->setEndValue(End);
// 启动动画
animation->start();
}
void Widget::startangleStepAnimation(qreal Start, qreal End)
{
// 设置动画的起始和结束值
animation2->setStartValue(Start);
animation2->setEndValue(End);
// 启动动画
animation2->start();
}
void Widget::paintEvent(QPaintEvent *event)
{
Q_UNUSED(event);
QPainter painter(this);
painter.setRenderHint(QPainter::Antialiasing); // 开启抗锯齿,使线条更平滑
// 将原点移动到窗口中心
painter.translate(width() / 2, height() / 2);
QPen pen(QColor(115,236,206), 2); // 设置画笔颜色为蓝色,线宽为2
painter.setPen(pen);
painter.setBrush(Qt::NoBrush);
QPolygonF polygon;
// 计算多边形的顶点
for (qreal angle = 0; angle < 360; angle += angleStep) {
// 计算外半径上的点
qreal xOuter = outerRadius * qCos(qDegreesToRadians(angle));
qreal yOuter = outerRadius * qSin(qDegreesToRadians(angle));
polygon << QPointF(xOuter, yOuter);
// 计算内半径上的点
// 注意:下一个点是内半径上的点,角度与外半径点相同
// 这样可以确保内外半径点交替出现,形成星形或锯齿状
qreal xInner = innerRadius * qCos(qDegreesToRadians(angle + angleStep / 2)); // 调整内半径点的角度,使其在内外点之间
qreal yInner = innerRadius * qSin(qDegreesToRadians(angle + angleStep / 2));
polygon << QPointF(xInner, yInner);
}
// 绘制多边形
painter.drawPolygon(polygon);
}
qreal Widget::getOuterRadius() const
{
return outerRadius;
}
void Widget::setOuterRadius(qreal newOuterRadius)
{
outerRadius = newOuterRadius;
update(); // 更新界面以反映新的外半径
}
qreal Widget::getInnerRadius() const
{
return innerRadius;
}
void Widget::setInnerRadius(qreal newInnerRadius)
{
innerRadius = newInnerRadius;
update(); // 更新界面以反映新的内半径
}
qreal Widget::getAngleStep() const
{
return angleStep;
}
void Widget::setAngleStep(qreal newAngleStep)
{
angleStep = newAngleStep;
update(); // 更新界面以反映新的角度步长
}
================================================
FILE: Anime_Template_Project/Generative_Lines/widget.h
================================================
#ifndef WIDGET_H
#define WIDGET_H
#include <QWidget>
#include <QMetaType> // 引入 QMetaType
#include <QPainter>
#include <QPolygonF>
#include <QtMath> // For qDegreesToRadians
#include <QPropertyAnimation>
//动画组
#include <QParallelAnimationGroup>
//定时器
#include <QTimer>
class Widget : public QWidget
{
Q_OBJECT
Q_PROPERTY(qreal outerRadius READ getOuterRadius WRITE setOuterRadius)
Q_PROPERTY(qreal innerRadius READ getInnerRadius WRITE setInnerRadius)
Q_PROPERTY(qreal angleStep READ getAngleStep WRITE setAngleStep)
public:
Widget(QWidget *parent = nullptr);
~Widget();
qreal getOuterRadius() const;
void setOuterRadius(qreal newOuterRadius);
qreal getInnerRadius() const;
void setInnerRadius(qreal newInnerRadius);
qreal getAngleStep() const;
void setAngleStep(qreal newAngleStep);
public:
void startAnimation(qreal Start, qreal End);
void startangleStepAnimation(qreal Start, qreal End);
//计算边数量
protected:
void paintEvent(QPaintEvent *event) override;
private:
qreal outerRadius;
qreal innerRadius;
qreal angleStep; // 角度步长
QTimer *timer; // 定时器
// 计数
int count = 0;;
QPropertyAnimation *animation; // 属性动画
QPropertyAnimation *animation2; // 属性动画
};
#endif // WIDGET_H
================================================
FILE: Anime_Template_Project/Glitch_Text/GlitchTextWidget.cpp
================================================
#include "GlitchTextWidget.h"
#include <QDebug>
#include <QMouseEvent>
#include <QEnterEvent>
#include <QAbstractAnimation>
GlitchTextWidget::GlitchTextWidget(const QString& text, QWidget *parent)
: QWidget(parent),
m_text(text),
m_speed(1.0),
m_enableShadows(true),
m_enableOnHover(false),
m_glitchFrameIndex(0),
m_isMouseOver(false)
{
QFontDatabase::addApplicationFont("://Cyberpunk.ttf");
setFont(QFont("Cyberpunk", 72, QFont::Black));
setMouseTracking(true);
m_animationAfter = new QPropertyAnimation(this, "clipRectAfter");
m_animationBefore = new QPropertyAnimation(this, "clipRectBefore");
m_animationAfter->setLoopCount(-1);
m_animationBefore->setLoopCount(-1);
m_animationAfter->setEasingCurve(QEasingCurve::Linear);
m_animationBefore->setEasingCurve(QEasingCurve::Linear);
m_glitchTimer = new QTimer(this);
connect(m_glitchTimer, &QTimer::timeout, this, [this](){
if (m_clipKeyframes.isEmpty()) {
updateClipKeyframes();
}
if (!m_clipKeyframes.isEmpty()) {
QMargins margins = m_clipKeyframes[m_glitchFrameIndex];
int clipY = (height() * margins.top()) / 100;
int clipHeight = height() - clipY - (height() * margins.bottom()) / 100;
m_clipRectAfter = QRect(0, clipY, width(), clipHeight);
m_clipRectBefore = QRect(0, clipY, width(), clipHeight);
m_glitchFrameIndex = (m_glitchFrameIndex + 1) % m_clipKeyframes.size();
update();
}
});
setupAnimations();
if (!m_enableOnHover) {
startGlitchAnimation();
}
}
void GlitchTextWidget::setText(const QString& text) {
if (m_text != text) {
m_text = text;
update();
updateGeometry();
}
}
void GlitchTextWidget::setSpeed(qreal speed) {
if (m_speed != speed) {
m_speed = speed;
setupAnimations();
if (!m_enableOnHover && m_glitchTimer->isActive()) {
startGlitchAnimation();
} else if (m_enableOnHover && m_isMouseOver) {
startGlitchAnimation();
}
}
}
void GlitchTextWidget::setEnableShadows(bool enable) {
if (m_enableShadows != enable) {
m_enableShadows = enable;
update();
}
}
void GlitchTextWidget::setEnableOnHover(bool enable) {
if (m_enableOnHover != enable) {
m_enableOnHover = enable;
if (m_enableOnHover) {
stopGlitchAnimation();
} else {
startGlitchAnimation();
}
update();
}
}
void GlitchTextWidget::setCustomClassName(const QString& className) {
m_customClassName = className;
}
void GlitchTextWidget::updateClipKeyframes() {
m_clipKeyframes.clear();
m_clipKeyframes.append(QMargins(0, 20, 0, 50));
m_clipKeyframes.append(QMargins(0, 10, 0, 60));
m_clipKeyframes.append(QMargins(0, 15, 0, 55));
m_clipKeyframes.append(QMargins(0, 25, 0, 35));
m_clipKeyframes.append(QMargins(0, 30, 0, 40));
m_clipKeyframes.append(QMargins(0, 40, 0, 20));
m_clipKeyframes.append(QMargins(0, 10, 0, 60));
m_clipKeyframes.append(QMargins(0, 15, 0, 55));
m_clipKeyframes.append(QMargins(0, 25, 0, 35));
m_clipKeyframes.append(QMargins(0, 00, 0, 40));
m_clipKeyframes.append(QMargins(0, 20, 0, 50));
m_clipKeyframes.append(QMargins(0, 10, 0, 60));
m_clipKeyframes.append(QMargins(0, 15, 0, 55));
m_clipKeyframes.append(QMargins(0, 25, 0, 35));
m_clipKeyframes.append(QMargins(0, 30, 0, 111));
m_clipKeyframes.append(QMargins(0, 40, 0, 20));
m_clipKeyframes.append(QMargins(0, 20, 0, 50));
m_clipKeyframes.append(QMargins(0, 10, 0, 60));
m_clipKeyframes.append(QMargins(0, 15, 0, 55));
m_clipKeyframes.append(QMargins(0, 25, 0, 35));
m_clipKeyframes.append(QMargins(0, 30, 0, 40));
}
void GlitchTextWidget::setupAnimations() {
updateClipKeyframes();
int totalAfterDurationMs = static_cast<int>(m_speed * 3000);
int totalBeforeDurationMs = static_cast<int>(m_speed * 2000);
if (m_clipKeyframes.isEmpty()) {
m_glitchTimer->setInterval(30);
} else {
m_glitchTimer->setInterval(totalAfterDurationMs / m_clipKeyframes.size());
}
m_animationAfter->setDuration(totalAfterDurationMs);
m_animationBefore->setDuration(totalBeforeDurationMs);
}
void GlitchTextWidget::startGlitchAnimation() {
if (!m_glitchTimer->isActive()) {
m_glitchFrameIndex = 0;
m_glitchTimer->start();
}
}
void GlitchTextWidget::stopGlitchAnimation() {
if (m_glitchTimer->isActive()) {
m_glitchTimer->stop();
m_clipRectAfter = rect();
m_clipRectBefore = rect();
update();
}
}
void GlitchTextWidget::paintEvent(QPaintEvent *event) {
Q_UNUSED(event);
QPainter painter(this);
painter.setRenderHint(QPainter::Antialiasing);
painter.setFont(font());
painter.fillRect(rect(), QColor("#060606"));
QFontMetrics fm(font());
int textWidth = fm.horizontalAdvance(m_text);
int textHeight = fm.height();
int textX = (width() - textWidth) / 2;
int textY = (height() - textHeight) / 2 + fm.ascent();
painter.setPen(QColor(Qt::white));
painter.drawText(textX, textY, m_text);
if (!m_enableOnHover || (m_enableOnHover && m_isMouseOver)) {
painter.save();
painter.setPen(QColor(Qt::red));
painter.setClipRect(m_clipRectAfter);
painter.drawText(textX - 10, textY, m_text);
painter.restore();
painter.save();
painter.setPen(QColor(Qt::cyan));
painter.setClipRect(m_clipRectBefore);
painter.drawText(textX + 10, textY, m_text);
painter.restore();
}
}
void GlitchTextWidget::enterEvent(QEnterEvent *event) {
m_isMouseOver = true;
if (m_enableOnHover) {
startGlitchAnimation();
}
QWidget::enterEvent(event);
}
void GlitchTextWidget::leaveEvent(QEvent *event) {
m_isMouseOver = false;
if (m_enableOnHover) {
stopGlitchAnimation();
}
QWidget::leaveEvent(event);
}
QSize GlitchTextWidget::sizeHint() const {
QFontMetrics fm(font());
int widthHint = fm.horizontalAdvance(m_text) + 20;
int heightHint = fm.height() + 20;
return QSize(widthHint, heightHint);
}
QRect GlitchTextWidget::clipRectAfter() const { return m_clipRectAfter; }
void GlitchTextWidget::setClipRectAfter(const QRect& rect) { m_clipRectAfter = rect; update(); }
QRect GlitchTextWidget::clipRectBefore() const { return m_clipRectBefore; }
void GlitchTextWidget::setClipRectBefore(const QRect& rect) { m_clipRectBefore = rect; update(); }
================================================
FILE: Anime_Template_Project/Glitch_Text/GlitchTextWidget.h
================================================
#ifndef GLITCHTEXTWIDGET_H
#define GLITCHTEXTWIDGET_H
#include <QWidget>
#include <QPropertyAnimation>
#include <QPainter>
#include <QTimer>
#include <QFontMetrics>
#include <QEnterEvent>
#include <QAbstractAnimation>
#include <QFontDatabase>
#include <QDebug>
class GlitchTextWidget : public QWidget
{
Q_OBJECT
Q_PROPERTY(QRect clipRectAfter READ clipRectAfter WRITE setClipRectAfter)
Q_PROPERTY(QRect clipRectBefore READ clipRectBefore WRITE setClipRectBefore)
public:
explicit GlitchTextWidget(const QString& text, QWidget *parent = nullptr);
void setText(const QString& text);
void setSpeed(qreal speed);
void setEnableShadows(bool enable);
void setEnableOnHover(bool enable);
void setCustomClassName(const QString& className);
protected:
void paintEvent(QPaintEvent *event) override;
void enterEvent(QEnterEvent *event) override;
void leaveEvent(QEvent *event) override;
QSize sizeHint() const override;
private:
QString m_text;
qreal m_speed;
bool m_enableShadows;
bool m_enableOnHover;
QString m_customClassName;
QPropertyAnimation *m_animationAfter;
QPropertyAnimation *m_animationBefore;
QTimer *m_glitchTimer;
int m_glitchFrameIndex;
QList<QMargins> m_clipKeyframes;
bool m_isMouseOver;
QRect m_clipRectAfter;
QRect m_clipRectBefore;
QRect clipRectAfter() const;
void setClipRectAfter(const QRect& rect);
QRect clipRectBefore() const;
void setClipRectBefore(const QRect& rect);
void setupAnimations();
void startGlitchAnimation();
void stopGlitchAnimation();
void updateClipKeyframes();
};
#endif // GLITCHTEXTWIDGET_H
================================================
FILE: Anime_Template_Project/Honeycomb_Grid/hexagonwidget.cpp
================================================
// Copyright (C) 2016 The Qt Company Ltd. // 版权所有 (C) 2016 Qt 公司。
// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR LGPL-3.0-only OR GPL-2.0-only OR GPL-3.0-only // SPDX-许可证标识符:LicenseRef-Qt-Commercial 或 LGPL-3.0-only 或 GPL-2.0-only 或 GPL-3.0-only
#include "hexagonwidget.h" // 包含 HexagonWidget 的头文件。
#include <QPainter> // 包含 QPainter 类,用于在部件上进行绘制。
#include <QtMath> // 包含 Qt 数学函数,例如 qSqrt, qDegreesToRadians。
#include <QMouseEvent> // 确保包含 QMouseEvent 头文件,用于处理鼠标事件。
// HexagonWidget 类的构造函数。
HexagonWidget::HexagonWidget(QWidget *parent)
: QWidget(parent) // 调用基类 QWidget 的构造函数。
, m_hexagonSize(50.0) // 初始化六边形边长。
, m_hexagonSpacing(5.0) // 初始化六边形间距。
, m_isHovering(false) // 初始状态为未悬停。
{
setMouseTracking(true); // 启用鼠标跟踪,即使没有按键也会触发 mouseMoveEvent。
calculateHexagonDimensions(); // 计算六边形的尺寸(宽度和高度)。
}
// 设置六边形边长的方法。
void HexagonWidget::setHexagonSize(double size)
{
if (size > 0 && m_hexagonSize != size) // 如果新尺寸有效且与当前尺寸不同。
{
m_hexagonSize = size; // 更新六边形边长。
calculateHexagonDimensions(); // 重新计算六边形尺寸。
update(); // 触发重绘以更新显示。
}
}
// 设置六边形间距的方法。
void HexagonWidget::setHexagonSpacing(double spacing)
{
if (spacing >= 0 && m_hexagonSpacing != spacing) // 如果新间距有效且与当前间距不同。
{
m_hexagonSpacing = spacing; // 更新六边形间距。
calculateHexagonDimensions(); // 重新计算六边形尺寸。
update(); // 触发重绘以更新显示。
}
}
void HexagonWidget::startAnimation()
{
QPropertyAnimation* m_animation1 = new QPropertyAnimation(this, "Center_Hexagon"); // 创建一个新的动画,目标属性为 Center_Hexagon。
m_animation1->setDuration(350); // 设置动画持续时间为 1000 毫秒(1 秒)。
m_animation1->setStartValue(1.0); // 设置动画起始值为 1.0。
m_animation1->setEndValue(1.2); // 设置动画结束值为 2.0。
m_animation1->setEasingCurve(QEasingCurve::InOutQuad); // 设置缓动曲线为 InOutQuad,使动画平滑过渡。
QPropertyAnimation * m_animation2 = new QPropertyAnimation(this, "Edge_Hexagon"); // 创建另一个动画,目标属性为 Edge_Hexagon。
m_animation2->setDuration(350); // 设置动画持续时间为 1000 毫秒(1 秒)。
m_animation2->setStartValue(1.0); // 设置动画起始值为 1.0。
m_animation2->setEndValue(0.6); // 设置动画结束值为 0.7。
m_animation2->setEasingCurve(QEasingCurve::InOutQuad); // 设置缓动曲线为 InOutQuad,使动画平滑过渡。
m_animation1->start(QAbstractAnimation::DeleteWhenStopped); // 启动动画。
m_animation2->start(QAbstractAnimation::DeleteWhenStopped); // 启动第二个动画。
}
// 计算六边形宽度和高度的方法。
void HexagonWidget::calculateHexagonDimensions()
{
m_hexagonWidth = m_hexagonSize * qSqrt(3.0); // 计算六边形宽度(对边距离)。
m_hexagonHeight = 2.0 * m_hexagonSize; // 计算六边形高度(顶点到对边顶点的距离)。
}
// 修改 createHexagon 以便接收当前绘制的六边形大小。
// 根据中心点和六边形大小创建六边形的 QPolygonF 对象。
QPolygonF HexagonWidget::createHexagon(QPointF center, double currentHexagonSize) const
{
QPolygonF hexagon; // 创建一个 QPolygonF 对象。
for (int i = 0; i < 6; ++i) // 循环 6 次,为六边形的每个顶点。
{
double angle_deg = 60 * i + 30; // 计算当前顶点的角度(度),加30度是为了使六边形平放。
double angle_rad = qDegreesToRadians(angle_deg); // 将角度从度转换为弧度。
hexagon << QPointF(center.x() + currentHexagonSize * qCos(angle_rad), // 计算顶点 X 坐标。
center.y() + currentHexagonSize * qSin(angle_rad)); // 计算顶点 Y 坐标。
}
return hexagon; // 返回构建好的六边形多边形。
}
// 新增:查找哪个六边形被悬停。
// 根据鼠标位置查找被悬停的六边形的中心点。
QPointF HexagonWidget::getHoveredHexagonCenter(const QPoint &pos)
{
// 计算实际的六边形宽度和高度,考虑间距。
double hexGridWidth = m_hexagonWidth + m_hexagonSpacing; // 计算网格中六边形的水平总宽度(包括间距)。
double hexGridHeight = m_hexagonHeight * 0.75 + m_hexagonSpacing; // 计算网格中六边形的垂直总高度(包括间距)。
// 初始偏移量。
double xOffset = m_hexagonWidth / 2.0; // 六边形第一列的 X 偏移。
double yOffset = m_hexagonSize; // 六边形第一行的 Y 偏移。
// 我们可以反向计算鼠标点可能落在哪一行哪一列。
// 这是一个简化的方法,更精确的需要考虑六边形形状。
// 粗略判断鼠标点在哪个“单元格”内。
// 考虑y轴偏移来找到最近的行。
int estimatedRow = qRound((pos.y() - yOffset) / hexGridHeight); // 估算鼠标所在行。
if (estimatedRow < 0) estimatedRow = 0; // 确保行号非负。
// 根据行数判断x轴偏移。
double currentXOffset = xOffset; // 默认 X 偏移。
if (estimatedRow % 2 != 0) { // 如果是奇数行。
currentXOffset += hexGridWidth / 2.0; // 奇数行会向右偏移半个网格宽度。
}
// 考虑x轴偏移来找到最近的列。
int estimatedCol = qRound((pos.x() - currentXOffset) / hexGridWidth); // 估算鼠标所在列。
if (estimatedCol < 0) estimatedCol = 0; // 确保列号非负。
// 遍历鼠标点附近的几个六边形,判断精确的悬停。
// 遍历周围的 3x3 区域,以确保找到正确的六边形。
for (int r_offset = -1; r_offset <= 1; ++r_offset) {
for (int c_offset = -1; c_offset <= 1; ++c_offset) {
int row = estimatedRow + r_offset; // 计算实际行。
int col = estimatedCol + c_offset; // 计算实际列。
if (row < 0 || col < 0) continue; // 避免负索引,跳过无效的行或列。
double x = col * hexGridWidth + xOffset; // 计算当前六边形的 X 坐标。
double y = row * hexGridHeight + yOffset; // 计算当前六边形的 Y 坐标。
if (row % 2 != 0) { // 奇数行交错。
x += hexGridWidth / 2.0; // 如果是奇数行,X 坐标需要额外偏移。
}
QPointF center(x, y); // 构成当前六边形的中心点。
// 检查鼠标点是否在当前计算出的六边形内部。
QPolygonF hexPolygon = createHexagon(center, m_hexagonSize); // 根据中心点和默认大小创建六边形多边形。
if (hexPolygon.containsPoint(pos, Qt::OddEvenFill)) { // 判断鼠标点是否在该多边形内。
return center; // 找到被悬停的六边形中心,并返回。
}
}
}
return QPointF(); // 没有六边形被悬停,返回空 QPointF。
}
// 新增:获取指定六边形的所有相邻六边形中心点。
// 根据给定的六边形中心点,计算并返回其所有相邻六边形的中心点列表。
QVector<QPointF> HexagonWidget::getNeighborHexagonCenters(QPointF center) const
{
QVector<QPointF> neighbors; // 用于存储相邻六边形中心的向量。
double hexGridWidth = m_hexagonWidth + m_hexagonSpacing; // 计算网格中六边形的水平总宽度。
double hexGridHeight = m_hexagonHeight * 0.75 + m_hexagonSpacing; // 计算网格中六边形的垂直总高度。
// 相邻偏移量 (相对一个六边形的中心)。
// 这是一个简化的表示,需要根据六边形中心推算其相邻六边形中心。
// 考虑六边形网格的两种相邻模式:水平方向和对角线方向。
// 直接水平相邻。
neighbors.append(QPointF(center.x() + hexGridWidth, center.y())); // 右侧相邻。
neighbors.append(QPointF(center.x() - hexGridWidth, center.y())); // 左侧相邻。
// 上下对角线相邻 (左上, 右上, 左下, 右下)。
// 这里的偏移量需要精确计算。
double x_offset_half = hexGridWidth / 2.0; // 水平偏移量的一半。
double y_offset_quarter_height = m_hexagonHeight * 0.75; // 六边形堆叠的垂直步长。
// 上方两相邻。
neighbors.append(QPointF(center.x() + x_offset_half, center.y() - y_offset_quarter_height - m_hexagonSpacing)); // 右上方相邻。
neighbors.append(QPointF(center.x() - x_offset_half, center.y() - y_offset_quarter_height - m_hexagonSpacing)); // 左上方相邻。
// 下方两相邻。
neighbors.append(QPointF(center.x() + x_offset_half, center.y() + y_offset_quarter_height + m_hexagonSpacing)); // 右下方相邻。
neighbors.append(QPointF(center.x() - x_offset_half, center.y() + y_offset_quarter_height + m_hexagonSpacing)); // 左下方相邻。
return neighbors; // 返回所有相邻六边形的中心点列表。
}
// 绘制事件处理函数,负责绘制六边形网格。
void HexagonWidget::paintEvent(QPaintEvent *event)
{
Q_UNUSED(event); // 标记 event 未使用,避免编译警告。
QPainter painter(this); // 创建 QPainter 对象,在当前部件上绘制。
painter.setRenderHint(QPainter::Antialiasing); // 启用抗锯齿,使图形更平滑。
painter.setPen(QPen(Qt::black, 1)); // 设置画笔为黑色,宽度为 1。
double hexGridWidth = m_hexagonWidth + m_hexagonSpacing; // 计算网格中六边形的水平总宽度。
double hexGridHeight = m_hexagonHeight * 0.75 + m_hexagonSpacing; // 计算网格中六边形的垂直总高度。
double xOffset = m_hexagonWidth / 2.0; // 六边形第一列的 X 偏移。
double yOffset = m_hexagonSize; // 六边形第一行的 Y 偏移。
// 获取相邻六边形的中心列表。
QVector<QPointF> neighborCenters; // 存储相邻六边形中心点的向量。
if (m_isHovering && !m_hoveredHexagonCenter.isNull())
{ // 如果鼠标悬停且悬停中心点有效。
neighborCenters = getNeighborHexagonCenters(m_hoveredHexagonCenter); // 获取悬停六边形的相邻中心点。
}
// 增加绘制范围,确保覆盖放大和缩小的六边形。
// 计算需要绘制的列数和行数,增加一些冗余以确保覆盖。
int numCols = qCeil((width() + m_hexagonSize * 2) / hexGridWidth) + 3;
int numRows = qCeil((height() + m_hexagonSize * 2) / hexGridHeight) + 3;
// 遍历所有可能的六边形位置。
for (int row = 0; row < numRows; ++row) {
for (int col = 0; col < numCols; ++col) {
double x = col * hexGridWidth + xOffset; // 计算当前六边形的 X 坐标。
double y = row * hexGridHeight + yOffset; // 计算当前六边形的 Y 坐标。
if (row % 2 != 0) { // 如果是奇数行。
x += hexGridWidth / 2.0; // 奇数行向右偏移。
}
QPointF currentHexagonCenter(x, y); // 当前六边形的中心点。
// 只有当六边形完全或部分在可见区域内时才绘制,并考虑放大后的尺寸。
// 检查六边形是否在可见区域内。
if (x - m_hexagonSize * 2 < width() && x + m_hexagonSize * 2 > 0 &&
y - m_hexagonSize * 2 < height() && y + m_hexagonSize * 2 > 0) {
double currentDrawSize = m_hexagonSize; // 默认绘制大小为 m_hexagonSize。
QBrush currentBrush = QBrush(Qt::cyan); // 默认填充颜色为青色。
if (m_isHovering) // 如果正在悬停。
{
if (currentHexagonCenter == m_hoveredHexagonCenter) { // 如果是悬停的六边形。
currentDrawSize = m_hexagonSize * m_Center_Hexagon; // 放大1.3倍。
currentBrush = QBrush(Qt::red); // 悬停六边形颜色为红色。
} else if (neighborCenters.contains(currentHexagonCenter)) { // 如果是悬停六边形的相邻六边形。
currentDrawSize = m_hexagonSize * m_Edge_Hexagon; // 缩小0.7倍。
currentBrush = QBrush(Qt::darkCyan); // 相邻六边形颜色为深青色。
}
}
painter.setBrush(currentBrush); // 设置画刷。
painter.drawPolygon(createHexagon(currentHexagonCenter, currentDrawSize)); // 绘制六边形。
}
}
}
}
// 新增:鼠标移动事件处理。
void HexagonWidget::mouseMoveEvent(QMouseEvent *event)
{
QPointF oldHoverCenter = m_hoveredHexagonCenter; // 记录旧的悬停中心。
m_hoveredHexagonCenter = getHoveredHexagonCenter(event->pos()); // 获取新的悬停中心。
if (m_hoveredHexagonCenter.isNull() && m_isHovering)
{
// 鼠标移出所有六边形,或从一个六边形移到空白区域。
m_isHovering = false; // 设置未悬停状态。
update(); // 触发重绘,恢复所有六边形到默认大小。
}
else if (!m_hoveredHexagonCenter.isNull() && m_hoveredHexagonCenter != oldHoverCenter)
{
// 鼠标移到新的六边形上。
m_isHovering = true; // 设置悬停状态。
startAnimation(); // 启动放大动画。
}
QWidget::mouseMoveEvent(event); // 调用基类的事件处理。
}
// 新增:鼠标离开控件事件处理。
void HexagonWidget::leaveEvent(QEvent *event)
{
if (m_isHovering)
{ // 如果之前处于悬停状态。
m_isHovering = true; // 设置未悬停状态。
m_hoveredHexagonCenter = QPointF(); // 清空悬停中心。
}
QWidget::leaveEvent(event); // 调用基类的事件处理。
}
qreal HexagonWidget::Center_Hexagon() const
{
return m_Center_Hexagon;
}
void HexagonWidget::setCenter_Hexagon(qreal newCenter_Hexagon)
{
if (qFuzzyCompare(m_Center_Hexagon, newCenter_Hexagon))
return;
m_Center_Hexagon = newCenter_Hexagon;
update(); // 更新绘制以反映新的中心六边形大小。
emit Center_HexagonChanged();
}
qreal HexagonWidget::Edge_Hexagon() const
{
return m_Edge_Hexagon;
}
void HexagonWidget::setEdge_Hexagon(qreal newEdge_Hexagon)
{
if (qFuzzyCompare(m_Edge_Hexagon, newEdge_Hexagon))
return;
m_Edge_Hexagon = newEdge_Hexagon;
emit Edge_HexagonChanged();
}
================================================
FILE: Anime_Template_Project/Honeycomb_Grid/hexagonwidget.h
================================================
// Copyright (C) 2016 The Qt Company Ltd. // 版权所有 (C) 2016 Qt 公司。
// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR LGPL-3.0-only OR GPL-2.0-only OR GPL-3.0-only // SPDX-许可证标识符:LicenseRef-Qt-Commercial 或 LGPL-3.0-only 或 GPL-2.0-only 或 GPL-3.0-only
#ifndef HEXAGONWIDGET_H // 如果未定义 HEXAGONWIDGET_H。
#define HEXAGONWIDGET_H // 定义 HEXAGONWIDGET_H。
#include <QWidget> // 包含 QWidget 类,它是所有用户界面对象的基类。
#include <QVector> // 包含 QVector 类,提供动态数组。
#include <QPointF> // 包含 QPointF 类,表示浮点精确度的点。
#include <QMap> // 用于存储六边形中心点和其对应的多边形。
//动画类
#include <QPropertyAnimation>
class HexagonWidget : public QWidget // HexagonWidget 类声明,继承自 QWidget。
{
Q_OBJECT // 宏,用于启用 Qt 的元对象系统,支持信号与槽。
//放大
Q_PROPERTY(qreal Center_Hexagon READ Center_Hexagon WRITE setCenter_Hexagon NOTIFY Center_HexagonChanged FINAL)
Q_PROPERTY(qreal Edge_Hexagon READ Edge_Hexagon WRITE setEdge_Hexagon NOTIFY Edge_HexagonChanged FINAL)
public:
explicit HexagonWidget(QWidget *parent = nullptr); // 显式构造函数,允许指定父部件。
void setHexagonSize(double size); // 设置六边形的基准边长。
void setHexagonSpacing(double spacing); // 设置六边形之间的间距。
//执行动画
void startAnimation(); // 启动六边形放大动画。
qreal Center_Hexagon() const;
void setCenter_Hexagon(qreal newCenter_Hexagon);
qreal Edge_Hexagon() const;
void setEdge_Hexagon(qreal newEdge_Hexagon);
signals:
void Center_HexagonChanged();
void Edge_HexagonChanged();
protected:
void paintEvent(QPaintEvent *event) override; // 覆盖 paintEvent,处理部件的绘制事件。
void mouseMoveEvent(QMouseEvent *event) override; // 新增:鼠标移动事件处理函数。
void leaveEvent(QEvent *event) override; // 新增:鼠标离开部件事件处理函数。
QPolygonF createHexagon(QPointF center, double currentHexagonSize) const; // 修改:增加一个参数来控制当前绘制的六边形大小。根据中心点和给定大小创建六边形多边形。
private:
double m_hexagonSize; // 六边形基准边长。
double m_hexagonSpacing; // 六边形间距。
double m_hexagonWidth; // 六边形宽度 (两相对边距离)。
double m_hexagonHeight; // 六边形高度 (两相对顶点距离)。
QPointF m_hoveredHexagonCenter; // 存储当前鼠标悬停的六边形中心点。
bool m_isHovering; // 标记是否正在悬停在某个六边形上。
void calculateHexagonDimensions(); // 计算六边形的内部尺寸(宽度和高度)。
// 根据鼠标位置查找哪个六边形被悬停。
QPointF getHoveredHexagonCenter(const QPoint &pos);
// 获取指定中心点的六边形的所有相邻六边形的中心点。
QVector<QPointF> getNeighborHexagonCenters(QPointF center) const;
qreal m_Center_Hexagon; // 当前中心六边形的大小。
qreal m_Edge_Hexagon; // 当前边缘六边形的大小。
};
#endif // HEXAGONWIDGET_H // 结束 HEXAGONWIDGET_H 头文件保护。
================================================
FILE: Anime_Template_Project/Honeycomb_Grid/mainwindow.cpp
================================================
#include "mainwindow.h"
#include <QVBoxLayout>
#include <QHBoxLayout>
#include <QWidget>
MainWindow::MainWindow(QWidget *parent)
: QMainWindow(parent)
{
// 创建中心Widget和布局
QWidget *centralWidget = new QWidget(this);
setCentralWidget(centralWidget);
QVBoxLayout *mainLayout = new QVBoxLayout(centralWidget);
// 添加 HexagonWidget
m_hexagonWidget = new HexagonWidget(this);
mainLayout->addWidget(m_hexagonWidget);
// 添加控制滑块
QHBoxLayout *controlsLayout = new QHBoxLayout();
// 边长控制
m_sizeLabel = new QLabel("边长: 50", this);
m_sizeSlider = new QSlider(Qt::Horizontal, this);
m_sizeSlider->setRange(10, 100);
m_sizeSlider->setValue(50);
connect(m_sizeSlider, &QSlider::valueChanged, this, &MainWindow::onSizeSliderChanged);
controlsLayout->addWidget(m_sizeLabel);
controlsLayout->addWidget(m_sizeSlider);
// 间距控制
m_spacingLabel = new QLabel("间距: 5", this);
m_spacingSlider = new QSlider(Qt::Horizontal, this);
m_spacingSlider->setRange(0, 30);
m_spacingSlider->setValue(5);
connect(m_spacingSlider, &QSlider::valueChanged, this, &MainWindow::onSpacingSliderChanged);
controlsLayout->addWidget(m_spacingLabel);
controlsLayout->addWidget(m_spacingSlider);
mainLayout->addLayout(controlsLayout);
setWindowTitle("蜂巢网格");
resize(800, 600);
}
MainWindow::~MainWindow()
{
}
void MainWindow::onSizeSliderChanged(int value)
{
m_hexagonWidget->setHexagonSize(static_cast<double>(value));
m_sizeLabel->setText(QString("边长: %1").arg(value));
}
void MainWindow::onSpacingSliderChanged(int value)
{
m_hexagonWidget->setHexagonSpacing(static_cast<double>(value));
m_spacingLabel->setText(QString("间距: %1").arg(value));
}
================================================
FILE: Anime_Template_Project/Honeycomb_Grid/mainwindow.h
================================================
#ifndef MAINWINDOW_H
#define MAINWINDOW_H
#include <QMainWindow>
#include "hexagonwidget.h"
#include <QSlider>
#include <QLabel>
class MainWindow : public QMainWindow
{
Q_OBJECT
public:
explicit MainWindow(QWidget *parent = nullptr);
~MainWindow();
private slots:
void onSizeSliderChanged(int value);
void onSpacingSliderChanged(int value);
private:
HexagonWidget *m_hexagonWidget;
QSlider *m_sizeSlider;
QSlider *m_spacingSlider;
QLabel *m_sizeLabel;
QLabel *m_spacingLabel;
};
#endif // MAINWINDOW_H
================================================
FILE: Anime_Template_Project/Letter_Glitch/CMakeLists.txt
================================================
cmake_minimum_required(VERSION 3.19)
project(untitled4 LANGUAGES CXX)
find_package(Qt6 6.5 REQUIRED COMPONENTS Core Widgets)
find_package(Qt6 REQUIRED COMPONENTS Widgets)
find_package(Qt6 REQUIRED COMPONENTS OpenGLWidgets)
qt_standard_project_setup()
qt_add_executable(untitled4
WIN32 MACOSX_BUNDLE
main.cpp
GlitchEffectWidget.cpp
GlitchEffectWidget.h
)
target_link_libraries(untitled4
PRIVATE
Qt::Core
Qt::Widgets
)
target_link_libraries(untitled4 PRIVATE Qt6::Widgets)
target_link_libraries(untitled4 PRIVATE Qt6::OpenGLWidgets)
include(GNUInstallDirs)
install(TARGETS untitled4
BUNDLE DESTINATION .
RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR}
LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR}
)
qt_generate_deploy_app_script(
TARGET untitled4
OUTPUT_SCRIPT deploy_script
NO_UNSUPPORTED_PLATFORM_ERROR
)
install(SCRIPT ${deploy_script})
================================================
FILE: Anime_Template_Project/Letter_Glitch/GlitchEffectWidget.cpp
================================================
#include "GlitchEffectWidget.h"
#include <QDebug>
#include <QFontMetricsF>
#include <cmath>
#include <QPainterPath>
#include <QElapsedTimer>
#include <QCoreApplication>
GlitchRenderThread::GlitchRenderThread(QObject *parent)
: QThread(parent),
m_columns(0), m_rows(0),
m_charWidth(0), m_charHeight(0), m_fontSize(0),
m_centerVignette(false), m_outerVignette(false),
m_widgetWidth(0), m_widgetHeight(0),
m_isDirtyFullRedraw(false)
{
setObjectName("GlitchRenderThread");
}
GlitchRenderThread::~GlitchRenderThread()
{
requestInterruption();
m_condition.wakeAll();
wait();
}
void GlitchRenderThread::setRenderData(const std::vector<GlitchLetter>& letters, int columns, int rows,
int charWidth, int charHeight, int fontSize,
bool centerVignette, bool outerVignette,
int widgetWidth, int widgetHeight)
{
QMutexLocker locker(&m_mutex);
m_letters = letters;
m_columns = columns;
m_rows = rows;
m_charWidth = charWidth;
m_charHeight = charHeight;
m_fontSize = fontSize;
m_centerVignette = centerVignette;
m_outerVignette = outerVignette;
m_widgetWidth = widgetWidth;
m_widgetHeight = widgetHeight;
m_isDirtyFullRedraw = true;
m_pendingChangedIndexes.clear();
}
void GlitchRenderThread::requestRender(const QList<int>& changedIndexes)
{
QMutexLocker locker(&m_mutex);
if (!changedIndexes.isEmpty()) {
m_pendingChangedIndexes.append(changedIndexes);
}
if (!m_isDirtyFullRedraw || !changedIndexes.isEmpty()) {
m_condition.wakeOne();
}
}
void GlitchRenderThread::run()
{
qDebug() << "GlitchRenderThread started";
while (!isInterruptionRequested()) {
m_mutex.lock();
if (!m_isDirtyFullRedraw && m_pendingChangedIndexes.empty()) {
m_condition.wait(&m_mutex);
}
bool doFullRedraw = m_isDirtyFullRedraw;
m_isDirtyFullRedraw = false;
QList<int> currentChangedIndexes = m_pendingChangedIndexes;
m_pendingChangedIndexes.clear();
m_mutex.unlock();
if (isInterruptionRequested()) {
break;
}
if (m_widgetWidth <= 0 || m_widgetHeight <= 0 || m_letters.empty() || m_columns <= 0 || m_rows <= 0) {
continue;
}
QSharedPointer<QImage> currentFrame;
QList<QRect> dirtyRects;
if (doFullRedraw || m_lastRenderedImage.isNull() ||
m_lastRenderedImage->width() != m_widgetWidth || m_lastRenderedImage->height() != m_widgetHeight)
{
currentFrame = QSharedPointer<QImage>::create(m_widgetWidth, m_widgetHeight, QImage::Format_ARGB32_Premultiplied);
currentFrame->fill(Qt::black);
dirtyRects.append(currentFrame->rect());
QPainter painter(currentFrame.data());
painter.setRenderHint(QPainter::Antialiasing, true);
QFont font("monospace", m_fontSize);
painter.setFont(font);
for (size_t i = 0; i < m_letters.size(); ++i) {
const GlitchLetter& letter = m_letters.at(i);
int x = (i % m_columns) * m_charWidth;
int y = (i / m_columns) * m_charHeight;
painter.setPen(letter.color);
painter.drawText(x, y + m_fontSize, QString(letter.character));
}
drawVignettes(painter, m_widgetWidth, m_widgetHeight);
} else {
currentFrame = m_lastRenderedImage;
QPainter painter(currentFrame.data());
painter.setRenderHint(QPainter::Antialiasing, true);
QFont font("monospace", m_fontSize);
painter.setFont(font);
for (int index : currentChangedIndexes) {
if (index < 0 || index >= static_cast<int>(m_letters.size())) continue;
const GlitchLetter& letter = m_letters.at(index);
int x = (index % m_columns) * m_charWidth;
int y = (index / m_columns) * m_charHeight;
QRect charRect(x, y, m_charWidth, m_charHeight);
painter.fillRect(charRect, Qt::black);
painter.setPen(letter.color);
painter.drawText(x, y + m_fontSize, QString(letter.character));
dirtyRects.append(charRect);
}
}
m_lastRenderedImage = currentFrame;
emit frameReady(currentFrame, dirtyRects);
}
qDebug() << "GlitchRenderThread stopped";
}
QList<QRect> GlitchRenderThread::mergeRects(const QList<QRect>& rects) {
if (rects.isEmpty()) return QList<QRect>();
QRect bounding = rects.first();
for (int i = 1; i < rects.size(); ++i) {
bounding = bounding.united(rects.at(i));
}
return QList<QRect>() << bounding;
}
void GlitchRenderThread::drawVignettes(QPainter& painter, int w, int h)
{
if (m_outerVignette) {
QRadialGradient outerGradient(w / 2.0, h / 2.0, qMin(w, h) / 2.0);
outerGradient.setColorAt(0.6, Qt::transparent);
outerGradient.setColorAt(1.0, Qt::black);
painter.setBrush(outerGradient);
painter.setPen(Qt::NoPen);
painter.drawRect(0, 0, w, h);
}
if (m_centerVignette) {
QRadialGradient centerGradient(w / 2.0, h / 2.0, qMin(w, h) / 2.0);
centerGradient.setColorAt(0.0, QColor(0, 0, 0, 204));
centerGradient.setColorAt(0.6, Qt::transparent);
painter.setBrush(centerGradient);
painter.setPen(Qt::NoPen);
painter.drawRect(0, 0, w, h);
}
}
GlitchEffectWidget::GlitchEffectWidget(QWidget *parent)
: QWidget(parent),
m_glitchColors({QColor(43, 69, 57, 255), QColor(97, 220, 163, 255), QColor(97, 179, 220, 255)}),
m_glitchSpeed(22),
m_smoothTransitions(true),
m_centerVignette(false),
m_outerVignette(true),
m_fontSize(16)
{
QPalette pal = palette();
pal.setColor(QPalette::Window, Qt::black);
setAutoFillBackground(true);
setPalette(pal);
m_lettersAndSymbols = "ABCDEFGHIJKLMNOPQRSTUVWXYZ!@#$&*()-_+=/[]{};:<>,0123456789";
QFont font("monospace", m_fontSize);
QFontMetricsF fm(font);
m_charWidth = static_cast<int>(fm.averageCharWidth());
m_charHeight = static_cast<int>(fm.height());
m_glitchTimer = new QTimer(this);
connect(m_glitchTimer, &QTimer::timeout, this, &GlitchEffectWidget::updateGlitch);
m_glitchTimer->start(m_glitchSpeed);
m_smoothTimer = new QTimer(this);
connect(m_smoothTimer, &QTimer::timeout, this, &GlitchEffectWidget::handleSmoothColorTransitions);
m_smoothTimer->start(16);
int numThreads = QThread::idealThreadCount();
if (numThreads <= 0) {
numThreads = 1;
}
qDebug() << "Creating" << numThreads << "render threads.";
for (int i = 0; i < numThreads; ++i) {
GlitchRenderThread *thread = new GlitchRenderThread(this);
thread->setObjectName(QString("GlitchRenderThread_%1").arg(i));
connect(thread, &GlitchRenderThread::frameReady, this, &GlitchEffectWidget::handleFrameReady);
m_renderThreads.append(thread);
thread->start();
}
m_displayTimer = new QTimer(this);
connect(m_displayTimer, &QTimer::timeout, this, &GlitchEffectWidget::displayNextFrame);
m_displayTimer->start(16);
}
GlitchEffectWidget::~GlitchEffectWidget()
{
m_displayTimer->stop();
for (GlitchRenderThread *thread : m_renderThreads) {
if (thread->isRunning()) {
thread->requestInterruption();
}
}
m_queueCondition.wakeAll();
for (GlitchRenderThread *thread : m_renderThreads) {
thread->wait();
delete thread;
}
m_renderThreads.clear();
}
void GlitchEffectWidget::setGlitchColors(const QList<QColor>& colors)
{
m_glitchColors = colors;
QList<int> changedIndexes;
QMutexLocker locker(&m_lettersMutex);
for (size_t i = 0; i < m_letters.size(); ++i) {
GlitchLetter& letter = m_letters[i];
letter.color = getRandomColor();
letter.targetColor = getRandomColor();
letter.colorProgress = 1.0;
changedIndexes.append(static_cast<int>(i));
}
for (GlitchRenderThread* thread : m_renderThreads) {
thread->setRenderData(m_letters, m_columns, m_rows, m_charWidth, m_charHeight,
m_fontSize, m_centerVignette, m_outerVignette,
static_cast<int>(width() * devicePixelRatioF()), static_cast<int>(height() * devicePixelRatioF()));
thread->requestRender(changedIndexes);
}
}
void GlitchEffectWidget::setGlitchSpeed(int speed)
{
m_glitchSpeed = speed;
m_glitchTimer->start(m_glitchSpeed);
}
void GlitchEffectWidget::setSmoothTransitions(bool smooth)
{
m_smoothTransitions = smooth;
if (m_smoothTransitions) {
m_smoothTimer->start(16);
} else {
m_smoothTimer->stop();
QList<int> changedIndexes;
QMutexLocker locker(&m_lettersMutex);
for (size_t i = 0; i < m_letters.size(); ++i) {
GlitchLetter& letter = m_letters[i];
if (letter.colorProgress < 1.0) {
letter.color = letter.targetColor;
letter.colorProgress = 1.0;
changedIndexes.append(static_cast<int>(i));
}
}
for (GlitchRenderThread* thread : m_renderThreads) {
thread->setRenderData(m_letters, m_columns, m_rows, m_charWidth, m_charHeight,
m_fontSize, m_centerVignette, m_outerVignette,
static_cast<int>(width() * devicePixelRatioF()), static_cast<int>(height() * devicePixelRatioF()));
thread->requestRender(changedIndexes);
}
}
}
void GlitchEffectWidget::setCenterVignette(bool enabled)
{
m_centerVignette = enabled;
for (GlitchRenderThread* thread : m_renderThreads) {
thread->setRenderData(m_letters, m_columns, m_rows, m_charWidth, m_charHeight,
m_fontSize, m_centerVignette, m_outerVignette,
static_cast<int>(width() * devicePixelRatioF()), static_cast<int>(height() * devicePixelRatioF()));
thread->requestRender();
}
}
void GlitchEffectWidget::setOuterVignette(bool enabled)
{
m_outerVignette = enabled;
for (GlitchRenderThread* thread : m_renderThreads) {
thread->setRenderData(m_letters, m_columns, m_rows, m_charWidth, m_charHeight,
m_fontSize, m_centerVignette, m_outerVignette,
static_cast<int>(width() * devicePixelRatioF()), static_cast<int>(height() * devicePixelRatioF()));
thread->requestRender();
}
}
QColor GlitchEffectWidget::hexToQColor(const QString& hex) {
QString actualHex = hex;
if (actualHex.startsWith("#")) {
actualHex = actualHex.mid(1);
}
if (actualHex.length() == 3) {
actualHex = QString(actualHex.at(0)) + actualHex.at(0) +
QString(actualHex.at(1)) + actualHex.at(1) +
QString(actualHex.at(2)) + actualHex.at(2);
}
return QColor("#" + actualHex);
}
QChar GlitchEffectWidget::getRandomChar()
{
return m_lettersAndSymbols.at(QRandomGenerator::global()->bounded(m_lettersAndSymbols.length()));
}
QColor GlitchEffectWidget::getRandomColor()
{
return m_glitchColors.at(QRandomGenerator::global()->bounded(m_glitchColors.length()));
}
void GlitchEffectWidget::calculateGrid(int width, int height)
{
QFont font("monospace", m_fontSize);
QFontMetricsF fm(font);
m_charWidth = static_cast<int>(fm.averageCharWidth());
m_charHeight = static_cast<int>(fm.height());
qreal dpr = devicePixelRatioF();
int actualWidth = static_cast<int>(width * dpr);
int actualHeight = static_cast<int>(height * dpr);
m_columns = qCeil(static_cast<qreal>(actualWidth) / m_charWidth);
m_rows = qCeil(static_cast<qreal>(actualHeight) / m_charHeight);
}
void GlitchEffectWidget::initializeLetters()
{
QMutexLocker locker(&m_lettersMutex);
m_letters.clear();
int totalLetters = m_columns * m_rows;
m_letters.reserve(totalLetters);
for (int i = 0; i < totalLetters; ++i) {
m_letters.push_back({getRandomChar(), getRandomColor(), getRandomColor(), 1.0});
}
for (GlitchRenderThread* thread : m_renderThreads) {
thread->setRenderData(m_letters, m_columns, m_rows, m_charWidth, m_charHeight,
m_fontSize, m_centerVignette, m_outerVignette,
static_cast<int>(width() * devicePixelRatioF()), static_cast<int>(height() * devicePixelRatioF()));
thread->requestRender();
}
}
void GlitchEffectWidget::paintEvent(QPaintEvent *event)
{
Q_UNUSED(event);
QPainter painter(this);
if (!m_currentDisplayedImage.isNull()) {
if (!m_currentDirtyRects.isEmpty()) {
qreal dpr = devicePixelRatioF();
for (const QRect& dirtyRect : m_currentDirtyRects) {
QRect actualDirtyRect(dirtyRect.x() * dpr, dirtyRect.y() * dpr,
dirtyRect.width() * dpr, dirtyRect.height() * dpr);
painter.drawImage(dirtyRect.topLeft(), *m_currentDisplayedImage, actualDirtyRect);
}
} else {
painter.drawImage(0, 0, *m_currentDisplayedImage);
}
}
}
void GlitchEffectWidget::resizeEvent(QResizeEvent *event)
{
QWidget::resizeEvent(event);
calculateGrid(event->size().width(), event->size().height());
initializeLetters();
}
void GlitchEffectWidget::updateGlitch()
{
QMutexLocker locker(&m_lettersMutex);
if (m_letters.empty()) {
return;
}
int updateCount = qMax(1, static_cast<int>(m_letters.size() * 0.05));
QList<int> changedIndexes;
for (int i = 0; i < updateCount; ++i) {
int index = QRandomGenerator::global()->bounded(static_cast<quint32>(m_letters.size()));
GlitchLetter& letter = m_letters[index];
letter.character = getRandomChar();
letter.targetColor = getRandomColor();
if (!m_smoothTransitions) {
letter.color = letter.targetColor;
letter.colorProgress = 1.0;
} else {
letter.colorProgress = 0.0;
}
changedIndexes.append(index);
}
for (GlitchRenderThread* thread : m_renderThreads) {
thread->setRenderData(m_letters, m_columns, m_rows, m_charWidth, m_charHeight,
m_fontSize, m_centerVignette, m_outerVignette,
static_cast<int>(width() * devicePixelRatioF()), static_cast<int>(height() * devicePixelRatioF()));
thread->requestRender(changedIndexes);
}
}
void GlitchEffectWidget::handleSmoothColorTransitions()
{
if (!m_smoothTransitions) {
return;
}
QList<int> changedIndexes;
QMutexLocker locker(&m_lettersMutex);
for (size_t i = 0; i < m_letters.size(); ++i) {
GlitchLetter& letter = m_letters[i];
if (letter.colorProgress < 1.0) {
letter.colorProgress += 0.05;
if (letter.colorProgress > 1.0) {
letter.colorProgress = 1.0;
}
int startR = letter.color.red();
int startG = letter.color.green();
int startB = letter.color.blue();
int endR = letter.targetColor.red();
int endG = letter.targetColor.green();
int endB = letter.targetColor.blue();
int r = qRound(startR + (endR - startR) * letter.colorProgress);
int g = qRound(startG + (endG - startG) * letter.colorProgress);
int b = qRound(startB + (endB - startB) * letter.colorProgress);
letter.color = QColor(qBound(0, r, 255), qBound(0, g, 255), qBound(0, b, 255));
changedIndexes.append(static_cast<int>(i));
}
}
if (!changedIndexes.isEmpty()) {
for (GlitchRenderThread* thread : m_renderThreads) {
thread->setRenderData(m_letters, m_columns, m_rows, m_charWidth, m_charHeight,
m_fontSize, m_centerVignette, m_outerVignette,
static_cast<int>(width() * devicePixelRatioF()), static_cast<int>(height() * devicePixelRatioF()));
thread->requestRender(changedIndexes);
}
}
}
void GlitchEffectWidget::handleFrameReady(QSharedPointer<QImage> image, const QList<QRect>& dirtyRects)
{
QMutexLocker locker(&m_queueMutex);
m_renderedFrameQueue.enqueue(qMakePair(image, dirtyRects));
m_queueCondition.wakeOne();
}
void GlitchEffectWidget::displayNextFrame()
{
QMutexLocker locker(&m_queueMutex);
if (!m_renderedFrameQueue.isEmpty()) {
QPair<QSharedPointer<QImage>, QList<QRect>> nextFrame = m_renderedFrameQueue.dequeue();
m_currentDisplayedImage = nextFrame.first;
m_currentDirtyRects = nextFrame.second;
if (!m_currentDirtyRects.isEmpty()) {
QRect unitedRect = m_currentDirtyRects.first();
for (int i = 1; i < m_currentDirtyRects.size(); ++i) {
unitedRect = unitedRect.united(m_currentDirtyRects.at(i));
}
update(unitedRect);
} else {
update();
}
}
}
================================================
FILE: Anime_Template_Project/Letter_Glitch/GlitchEffectWidget.h
================================================
#ifndef GLITCHEFFECTWIDGET_H
#define GLITCHEFFECTWIDGET_H
#include <QWidget>
#include <QTimer>
#include <QColor>
#include <QPainter>
#include <QResizeEvent>
#include <QRandomGenerator>
#include <vector>
#include <QImage>
#include <QThread>
#include <QMutex>
#include <QWaitCondition>
#include <QObject>
#include <QSharedPointer>
#include <QRect>
#include <QList>
#include <QQueue>
struct GlitchLetter {
QChar character;
QColor color;
QColor targetColor;
double colorProgress;
};
class GlitchRenderThread : public QThread
{
Q_OBJECT
public:
GlitchRenderThread(QObject *parent = nullptr);
~GlitchRenderThread();
void setRenderData(const std::vector<GlitchLetter>& letters, int columns, int rows,
int charWidth, int charHeight, int fontSize,
bool centerVignette, bool outerVignette,
int widgetWidth, int widgetHeight);
void requestRender(const QList<int>& changedIndexes = QList<int>());
signals:
void frameReady(QSharedPointer<QImage> image, const QList<QRect>& dirtyRects);
protected:
void run() override;
private:
std::vector<GlitchLetter> m_letters;
int m_columns;
int m_rows;
int m_charWidth;
int m_charHeight;
int m_fontSize;
bool m_centerVignette;
bool m_outerVignette;
int m_widgetWidth;
int m_widgetHeight;
bool m_isDirtyFullRedraw;
QList<int> m_pendingChangedIndexes;
QMutex m_mutex;
QWaitCondition m_condition;
QSharedPointer<QImage> m_lastRenderedImage;
void drawVignettes(QPainter& painter, int w, int h);
QList<QRect> mergeRects(const QList<QRect>& rects);
};
class GlitchEffectWidget : public QWidget
{
Q_OBJECT
public:
explicit GlitchEffectWidget(QWidget *parent = nullptr);
~GlitchEffectWidget();
void setGlitchColors(const QList<QColor>& colors);
void setGlitchSpeed(int speed);
void setSmoothTransitions(bool smooth);
void setCenterVignette(bool enabled);
void setOuterVignette(bool enabled);
protected:
void paintEvent(QPaintEvent *event) override;
void resizeEvent(QResizeEvent *event) override;
private slots:
void updateGlitch();
void handleSmoothColorTransitions();
void handleFrameReady(QSharedPointer<QImage> image, const QList<QRect>& dirtyRects);
void displayNextFrame();
private:
QList<QColor> m_glitchColors;
int m_glitchSpeed;
bool m_smoothTransitions;
bool m_centerVignette;
bool m_outerVignette;
QTimer *m_glitchTimer;
QTimer *m_smoothTimer;
QTimer *m_displayTimer;
std::vector<GlitchLetter> m_letters;
int m_columns;
int m_rows;
int m_fontSize;
int m_charWidth;
int m_charHeight;
QString m_lettersAndSymbols;
QColor hexToQColor(const QString& hex);
QChar getRandomChar();
QColor getRandomColor();
void calculateGrid(int width, int height);
void initializeLetters();
QList<GlitchRenderThread*> m_renderThreads;
QQueue<QPair<QSharedPointer<QImage>, QList<QRect>>> m_renderedFrameQueue;
QMutex m_queueMutex;
QWaitCondition m_queueCondition;
QSharedPointer<QImage> m_currentDisplayedImage;
QList<QRect> m_currentDirtyRects;
QMutex m_lettersMutex;
};
#endif
================================================
FILE: Anime_Template_Project/Letter_Glitch/main.cpp
================================================
#include <QApplication>
#include <QMainWindow>
#include "GlitchEffectWidget.h"
#include <QVBoxLayout>
#include <QPushButton>
int main(int argc, char *argv[])
{
QApplication a(argc, argv);
QMainWindow window;
window.resize(800, 600);
QWidget *centralWidget = new QWidget(&window);
QVBoxLayout *layout = new QVBoxLayout(centralWidget);
GlitchEffectWidget *glitchWidget = new GlitchEffectWidget(centralWidget);
layout->addWidget(glitchWidget);
QPushButton *smoothToggleBtn = new QPushButton("平滑过渡开关按钮", centralWidget);
QObject::connect(smoothToggleBtn, &QPushButton::clicked, [glitchWidget]() {
glitchWidget->setSmoothTransitions(!glitchWidget->property("smoothTransitions").toBool());
glitchWidget->setProperty("smoothTransitions", !glitchWidget->property("smoothTransitions").toBool());
});
glitchWidget->setProperty("smoothTransitions", true);
QPushButton *centerVignetteToggleBtn = new QPushButton("中心渐晕开关按钮", centralWidget);
QObject::connect(centerVignetteToggleBtn, &QPushButton::clicked, [glitchWidget]() {
glitchWidget->setCenterVignette(!glitchWidget->property("centerVignette").toBool());
glitchWidget->setProperty("centerVignette", !glitchWidget->property("centerVignette").toBool());
});
glitchWidget->setProperty("centerVignette", false);
QPushButton *outerVignetteToggleBtn = new QPushButton("外部渐晕开关按钮", centralWidget);
QObject::connect(outerVignetteToggleBtn, &QPushButton::clicked, [glitchWidget]() {
glitchWidget->setOuterVignette(!glitchWidget->property("outerVignette").toBool());
glitchWidget->setProperty("outerVignette", !glitchWidget->property("outerVignette").toBool());
});
glitchWidget->setProperty("outerVignette", true);
layout->addWidget(smoothToggleBtn);
layout->addWidget(centerVignetteToggleBtn);
layout->addWidget(outerVignetteToggleBtn);
window.setCentralWidget(centralWidget);
window.show();
return a.exec();
}
================================================
FILE: Anime_Template_Project/Liquid/image_processing.cpp
================================================
#include "image_processing.h"
Q_GLOBAL_STATIC(Image_Processing, fileRelatedInstance)
Image_Processing::Image_Processing(QObject* parent)
: QObject{ parent }
{ }
Image_Processing* Image_Processing::instance() {
return fileRelatedInstance;
}
template <class T>
void Image_Processing::qt_memrotate270_tiled_unpacked(const T* src, int w, int h, int sstride, T* dest, int dstride) {
const int numTilesX = (w + tileSize - 1) / tileSize;
const int numTilesY = (h + tileSize - 1) / tileSize;
for (int tx = 0; tx < numTilesX; ++tx) {
const int startx = tx * tileSize;
const int stopx = qMin(startx + tileSize, w);
for (int ty = 0; ty < numTilesY; ++ty) {
const int starty = h - 1 - ty * tileSize;
const int stopy = qMax(starty - tileSize, 0);
for (int x = startx; x < stopx; ++x) {
T* d = (T*)((char*)dest + x * dstride) + h - 1 - starty;
const char* s = (const char*)(src + x) + starty * sstride;
for (int y = starty; y >= stopy; --y) {
*d++ = *(const T*)s;
s -= sstride;
}
}
}
}
}
template <class T>
void Image_Processing::qt_memrotate270_template(const T* src, int srcWidth, int srcHeight, int srcStride, T* dest, int dstStride) {
qt_memrotate270_tiled_unpacked<T>(src, srcWidth, srcHeight, srcStride, dest, dstStride);
}
template <class T>
void Image_Processing::qt_memrotate90_tiled_unpacked(const T* src, int w, int h, int sstride, T* dest, int dstride) {
const int numTilesX = (w + tileSize - 1) / tileSize;
const int numTilesY = (h + tileSize - 1) / tileSize;
for (int tx = 0; tx < numTilesX; ++tx) {
const int startx = w - tx * tileSize - 1;
const int stopx = qMax(startx - tileSize, 0);
for (int ty = 0; ty < numTilesY; ++ty) {
const int starty = ty * tileSize;
const int stopy = qMin(starty + tileSize, h);
for (int x = startx; x >= stopx; --x) {
T* d = (T*)((char*)dest + (w - x - 1) * dstride) + starty;
const char* s = (const char*)(src + x) + starty * sstride;
for (int y = starty; y < stopy; ++y) {
*d++ = *(const T*)(s);
s += sstride;
}
}
}
}
}
template <class T>
voi
gitextract_vx1aefsx/ ├── Anime_Template_Project/ │ ├── Accordion/ │ │ ├── AccordionCard.cpp │ │ ├── AccordionCard.h │ │ ├── CMakeLists.txt │ │ ├── accordionwidget.cpp │ │ ├── accordionwidget.h │ │ ├── img.qrc │ │ └── main.cpp │ ├── Adaptive_Carousel/ │ │ ├── daen_no_kado.cpp │ │ ├── daen_no_kado.h │ │ ├── latticed_circle_button.cpp │ │ └── latticed_circle_button.h │ ├── Blur_Text/ │ │ ├── fuzzytextwidget.cpp │ │ └── fuzzytextwidget.h │ ├── Carousel_card/ │ │ ├── card_button.cpp │ │ ├── card_button.h │ │ ├── card_text.cpp │ │ ├── card_text.h │ │ ├── carousel_card.cpp │ │ ├── carousel_card.h │ │ ├── carrier_card.cpp │ │ └── carrier_card.h │ ├── Eye_of_Cthulhu/ │ │ ├── JellyfishWidget.cpp │ │ └── JellyfishWidget.h │ ├── Flowing_Gradient_Font/ │ │ ├── widget.cpp │ │ └── widget.h │ ├── FractalWidget/ │ │ ├── CMakeLists.txt │ │ ├── fractalwidget.cpp │ │ ├── fractalwidget.h │ │ ├── fractalworker.cpp │ │ ├── fractalworker.h │ │ ├── main.cpp │ │ ├── mainwindow.cpp │ │ └── mainwindow.h │ ├── Generative_Lines/ │ │ ├── widget.cpp │ │ └── widget.h │ ├── Glitch_Text/ │ │ ├── GlitchTextWidget.cpp │ │ └── GlitchTextWidget.h │ ├── Honeycomb_Grid/ │ │ ├── hexagonwidget.cpp │ │ ├── hexagonwidget.h │ │ ├── mainwindow.cpp │ │ └── mainwindow.h │ ├── Letter_Glitch/ │ │ ├── CMakeLists.txt │ │ ├── GlitchEffectWidget.cpp │ │ ├── GlitchEffectWidget.h │ │ └── main.cpp │ ├── Liquid/ │ │ ├── image_processing.cpp │ │ ├── image_processing.h │ │ ├── liquid_button.cpp │ │ ├── liquid_button.h │ │ ├── widget.cpp │ │ └── widget.h │ ├── LoadingAnime/ │ │ ├── Bouncing_Ball_Loading.h │ │ ├── CMakeLists.txt │ │ ├── Rectangle_Loading.h │ │ ├── Square_Pseudo_Bounce_Loading.cpp │ │ ├── Square_Pseudo_Bounce_Loading.h │ │ ├── black_white_ball_loading.cpp │ │ ├── black_white_ball_loading.h │ │ ├── bouncing_ball_loading.cpp │ │ ├── hexagonloaderwidget.cpp │ │ ├── hexagonloaderwidget.h │ │ ├── line_loading.cpp │ │ ├── line_loading.h │ │ ├── line_rotating_along_rectangular_border.cpp │ │ ├── line_rotating_along_rectangular_border.h │ │ ├── main.cpp │ │ ├── rectangle_loading.cpp │ │ ├── regular_loading.cpp │ │ ├── regular_loading.h │ │ ├── ring_loading.cpp │ │ ├── ring_loading.h │ │ ├── widget.cpp │ │ └── widget.h │ ├── Login_interface/ │ │ ├── hollow_button.cpp │ │ ├── hollow_button.h │ │ ├── input_box.cpp │ │ ├── input_box.h │ │ ├── login_button.cpp │ │ ├── login_button.h │ │ ├── login_form.cpp │ │ ├── login_form.h │ │ ├── other_login_buttons.cpp │ │ ├── other_login_buttons.h │ │ ├── registration_form.cpp │ │ ├── registration_form.h │ │ ├── responsive_form.cpp │ │ ├── responsive_form.h │ │ ├── scroll_bar.cpp │ │ ├── scroll_bar.h │ │ ├── transparent_transition_interface.cpp │ │ └── transparent_transition_interface.h │ ├── Magnet_Lines/ │ │ ├── CMakeLists.txt │ │ ├── RotatableLinesWidget.cpp │ │ ├── RotatableLinesWidget.h │ │ └── main.cpp │ ├── Mimic_Button/ │ │ ├── depressed_button.cpp │ │ ├── depressed_button.h │ │ ├── img.qrc │ │ ├── widget.cpp │ │ └── widget.h │ ├── Particle_Generation/ │ │ ├── CMakeLists.txt │ │ ├── ParticleWidget.h │ │ ├── main.cpp │ │ ├── mainwindow.cpp │ │ ├── mainwindow.h │ │ └── particlewidget.cpp │ ├── Physical_Text/ │ │ ├── DraggableElasticObject.cpp │ │ ├── draggableelasticobject.h │ │ └── main.cpp │ ├── PixelTransition/ │ │ ├── pixel_transition.cpp │ │ ├── pixel_transition.h │ │ ├── widget.cpp │ │ └── widget.h │ ├── Point_Wave/ │ │ ├── widget.cpp │ │ └── widget.h │ ├── Pressure_Block/ │ │ ├── squarepressurewidget.cpp │ │ └── squarepressurewidget.h │ ├── SplitText/ │ │ ├── Single_Text.cpp │ │ ├── Single_Text.h │ │ ├── SplitText.cpp │ │ └── SplitText.h │ ├── Star_Sky_Connection/ │ │ ├── MovingPointsWidget.cpp │ │ └── MovingPointsWidget.h │ ├── TreeScene/ │ │ ├── TreeScene.cpp │ │ └── TreeScene.h │ ├── Wave/ │ │ ├── waveswidget.cpp │ │ └── waveswidget.h │ ├── Zipper_Slider/ │ │ ├── pathwidget.cpp │ │ └── pathwidget.h │ ├── button_class/ │ │ ├── diffusion_button.cpp │ │ ├── diffusion_button.h │ │ ├── wave_button.cpp │ │ └── wave_button.h │ ├── dial_class/ │ │ ├── knob_page.cpp │ │ ├── knob_page.h │ │ ├── temperature_dial.cpp │ │ └── temperature_dial.h │ ├── json/ │ │ └── Anime_care_attributes.json │ ├── src.qrc │ └── utility_class/ │ ├── timer_animation.cpp │ ├── timer_animation.h │ ├── timer_animationgroup.cpp │ └── timer_animationgroup.h ├── LICENSE └── README.md
SYMBOL INDEX (156 symbols across 97 files)
FILE: Anime_Template_Project/Accordion/AccordionCard.cpp
function qreal (line 39) | qreal AccordionCard::currentStretch() const
FILE: Anime_Template_Project/Accordion/AccordionCard.h
function class (line 13) | class AccordionCard : public QWidget
FILE: Anime_Template_Project/Accordion/accordionwidget.h
function class (line 10) | class AccordionWidget : public QWidget
FILE: Anime_Template_Project/Accordion/main.cpp
function main (line 6) | int main(int argc, char *argv[])
FILE: Anime_Template_Project/Adaptive_Carousel/daen_no_kado.cpp
function qreal (line 434) | qreal Daen_no_Kado::Keisan_suru_shukusetsu_no_takasa(qreal& xLeft)
function qreal (line 452) | qreal Daen_no_Kado::calculateRectRotation(qreal& xLeft)
function qreal (line 500) | qreal Daen_no_Kado::Progress_Bar_X() const
function qreal (line 513) | qreal Daen_no_Kado::Progress_Bar_Width() const
function qreal (line 526) | qreal Daen_no_Kado::Expand_Collapse_Height() const
FILE: Anime_Template_Project/Adaptive_Carousel/daen_no_kado.h
function class (line 13) | class Daen_no_Kado : public QWidget
FILE: Anime_Template_Project/Adaptive_Carousel/latticed_circle_button.cpp
function QColor (line 122) | QColor Latticed_Circle_Button::Current_Color() const
FILE: Anime_Template_Project/Adaptive_Carousel/latticed_circle_button.h
function class (line 10) | class Latticed_Circle_Button : public QPushButton
FILE: Anime_Template_Project/Blur_Text/fuzzytextwidget.h
function class (line 9) | class FuzzyTextWidget : public QWidget
FILE: Anime_Template_Project/Carousel_card/card_button.cpp
function QColor (line 89) | QColor Card_button::getbutton_color() const
FILE: Anime_Template_Project/Carousel_card/card_button.h
function class (line 12) | class Card_button : public QPushButton
FILE: Anime_Template_Project/Carousel_card/card_text.h
function class (line 10) | class Card_text : public QWidget
FILE: Anime_Template_Project/Carousel_card/carousel_card.h
function class (line 15) | class Carousel_card : public QWidget
FILE: Anime_Template_Project/Carousel_card/carrier_card.cpp
function QColor (line 184) | QColor Carrier_card::getMostFrequentColor(const QPixmap& pixmap)
FILE: Anime_Template_Project/Carousel_card/carrier_card.h
function class (line 16) | class Carrier_card : public QWidget
FILE: Anime_Template_Project/Eye_of_Cthulhu/JellyfishWidget.cpp
function QPointF (line 49) | QPointF JellyfishWidget::calculateJellyfishPoint(double local_x, double ...
FILE: Anime_Template_Project/Eye_of_Cthulhu/JellyfishWidget.h
type GoreParticle (line 18) | struct GoreParticle {
type AcidDrip (line 27) | struct AcidDrip {
type TentacleShadow (line 37) | struct TentacleShadow {
function run (line 63) | void run() override {
function class (line 155) | class JellyfishWidget : public QWidget
FILE: Anime_Template_Project/Flowing_Gradient_Font/widget.cpp
function qreal (line 106) | qreal Widget::Circle_Ratio() const {
FILE: Anime_Template_Project/Flowing_Gradient_Font/widget.h
function class (line 12) | class Widget : public QWidget
FILE: Anime_Template_Project/FractalWidget/fractalwidget.h
function class (line 13) | class FractalWidget : public QWidget
FILE: Anime_Template_Project/FractalWidget/fractalworker.cpp
function QImage (line 90) | QImage FractalWorker::computeFractalChunk(const FractalChunkData &data)
function QRgb (line 207) | QRgb FractalWorker::getColor(int iterations, int maxIterationsUsed)
function QRgb (line 219) | QRgb FractalWorker::getNewtonColor(int iterations, int maxIterationsUsed...
FILE: Anime_Template_Project/FractalWidget/fractalworker.h
function class (line 9) | class FractalWorker : public QObject
FILE: Anime_Template_Project/FractalWidget/main.cpp
function main (line 4) | int main(int argc, char *argv[])
FILE: Anime_Template_Project/FractalWidget/mainwindow.h
function class (line 16) | class MainWindow : public QMainWindow
FILE: Anime_Template_Project/Generative_Lines/widget.cpp
function qreal (line 170) | qreal Widget::getOuterRadius() const
function qreal (line 181) | qreal Widget::getInnerRadius() const
function qreal (line 193) | qreal Widget::getAngleStep() const
FILE: Anime_Template_Project/Generative_Lines/widget.h
function class (line 17) | class Widget : public QWidget
FILE: Anime_Template_Project/Glitch_Text/GlitchTextWidget.cpp
function QSize (line 204) | QSize GlitchTextWidget::sizeHint() const {
function QRect (line 211) | QRect GlitchTextWidget::clipRectAfter() const { return m_clipRectAfter; }
function QRect (line 214) | QRect GlitchTextWidget::clipRectBefore() const { return m_clipRectBefore; }
FILE: Anime_Template_Project/Glitch_Text/GlitchTextWidget.h
function class (line 14) | class GlitchTextWidget : public QWidget
FILE: Anime_Template_Project/Honeycomb_Grid/hexagonwidget.cpp
function QPolygonF (line 76) | QPolygonF HexagonWidget::createHexagon(QPointF center, double currentHex...
function QPointF (line 91) | QPointF HexagonWidget::getHoveredHexagonCenter(const QPoint &pos)
function qreal (line 276) | qreal HexagonWidget::Center_Hexagon() const
function qreal (line 290) | qreal HexagonWidget::Edge_Hexagon() const
FILE: Anime_Template_Project/Honeycomb_Grid/hexagonwidget.h
function class (line 16) | class HexagonWidget : public QWidget // HexagonWidget 类声明,继承自 QWidget。
FILE: Anime_Template_Project/Honeycomb_Grid/mainwindow.h
function class (line 9) | class MainWindow : public QMainWindow
FILE: Anime_Template_Project/Letter_Glitch/GlitchEffectWidget.cpp
function QColor (line 306) | QColor GlitchEffectWidget::hexToQColor(const QString& hex) {
function QChar (line 319) | QChar GlitchEffectWidget::getRandomChar()
function QColor (line 324) | QColor GlitchEffectWidget::getRandomColor()
FILE: Anime_Template_Project/Letter_Glitch/GlitchEffectWidget.h
type GlitchLetter (line 21) | struct GlitchLetter {
function class (line 28) | class GlitchRenderThread : public QThread
function class (line 72) | class GlitchEffectWidget : public QWidget
FILE: Anime_Template_Project/Letter_Glitch/main.cpp
function main (line 7) | int main(int argc, char *argv[])
FILE: Anime_Template_Project/Liquid/image_processing.cpp
function Image_Processing (line 9) | Image_Processing* Image_Processing::instance() {
function qt_static_shift (line 74) | inline int qt_static_shift(int value) {
function QImage (line 232) | QImage Image_Processing::qt_halfScaled(const QImage& source) {
FILE: Anime_Template_Project/Liquid/image_processing.h
function class (line 11) | class Image_Processing : public QObject
FILE: Anime_Template_Project/Liquid/liquid_button.cpp
function QColor (line 53) | QColor Liquid_Button::color1() const
function QColor (line 64) | QColor Liquid_Button::textColor() const
FILE: Anime_Template_Project/Liquid/liquid_button.h
function class (line 10) | class Liquid_Button : public QWidget
FILE: Anime_Template_Project/Liquid/widget.h
type Circle (line 16) | struct Circle {
function class (line 23) | class Widget : public QWidget
FILE: Anime_Template_Project/LoadingAnime/Bouncing_Ball_Loading.h
function widthRadius (line 35) | int widthRadius() const;
function setBallColor (line 45) | void setBallColor(const QColor &color) { m_ballColor = color; }
function setAnimationFinished (line 48) | void setAnimationFinished(bool finished) { m_animationFinished = finishe...
function m_heightRadius (line 60) | int m_heightRadius{30};
function class (line 73) | class Bouncing_Ball_Loading : public QWidget
FILE: Anime_Template_Project/LoadingAnime/Rectangle_Loading.h
function class (line 9) | class Rectangle_Loading : public QWidget
FILE: Anime_Template_Project/LoadingAnime/Square_Pseudo_Bounce_Loading.h
function class (line 12) | class Square_Pseudo_Bounce_Loading : public QWidget
FILE: Anime_Template_Project/LoadingAnime/black_white_ball_loading.cpp
function QPointF (line 117) | QPointF Black_White_Ball_Loading::getPointOnLine(qreal progress, qreal d...
FILE: Anime_Template_Project/LoadingAnime/black_white_ball_loading.h
function class (line 9) | class Black_White_Ball_Loading : public QWidget
FILE: Anime_Template_Project/LoadingAnime/bouncing_ball_loading.cpp
function QPointF (line 165) | QPointF Sphere::position() const
function QPointF (line 204) | QPointF Sphere::fallEndPosition() const
FILE: Anime_Template_Project/LoadingAnime/hexagonloaderwidget.cpp
function qreal (line 52) | qreal HexagonLoaderWidget::centerGelScale() const { return m_centerGelCu...
function qreal (line 65) | qreal HexagonLoaderWidget::r1Scale() const { return m_r1CurrentScale; }
function qreal (line 78) | qreal HexagonLoaderWidget::r2Scale() const { return m_r2CurrentScale; }
function qreal (line 91) | qreal HexagonLoaderWidget::r3Scale() const { return m_r3CurrentScale; }
function QPointF (line 255) | QPointF HexagonLoaderWidget::calculateHexagonPoint(qreal size, qreal ang...
FILE: Anime_Template_Project/LoadingAnime/hexagonloaderwidget.h
function class (line 14) | class HexBrick : public QObject
function class (line 36) | class Gel
function class (line 59) | class HexagonLoaderWidget : public QWidget
FILE: Anime_Template_Project/LoadingAnime/line_loading.cpp
function qreal (line 25) | qreal M_Line::angle() const
FILE: Anime_Template_Project/LoadingAnime/line_loading.h
function Gradient_Position (line 48) | int Gradient_Position() const;
FILE: Anime_Template_Project/LoadingAnime/line_rotating_along_rectangular_border.cpp
function qreal (line 23) | qreal Line_Rotating_Along_Rectangular_Border::getRotationAngle() const
FILE: Anime_Template_Project/LoadingAnime/line_rotating_along_rectangular_border.h
function class (line 10) | class Line_Rotating_Along_Rectangular_Border : public QWidget
FILE: Anime_Template_Project/LoadingAnime/main.cpp
function main (line 5) | int main(int argc, char *argv[])
FILE: Anime_Template_Project/LoadingAnime/regular_loading.h
function class (line 11) | class Regular_Loading : public QWidget
FILE: Anime_Template_Project/LoadingAnime/ring_loading.h
function class (line 10) | class Ring_Loading : public QWidget
FILE: Anime_Template_Project/LoadingAnime/widget.h
function class (line 17) | class Widget : public QWidget
FILE: Anime_Template_Project/Login_interface/hollow_button.cpp
function QString (line 129) | QString Hollow_button::center_text() const
FILE: Anime_Template_Project/Login_interface/hollow_button.h
function class (line 10) | class Hollow_button : public QPushButton
FILE: Anime_Template_Project/Login_interface/input_box.h
function class (line 10) | class Input_box : public QLineEdit
FILE: Anime_Template_Project/Login_interface/login_button.cpp
function QString (line 104) | QString Login_button::center_text() const
FILE: Anime_Template_Project/Login_interface/login_button.h
function class (line 10) | class Login_button : public QPushButton
FILE: Anime_Template_Project/Login_interface/login_form.h
function class (line 13) | class Login_form : public QWidget
FILE: Anime_Template_Project/Login_interface/other_login_buttons.h
function class (line 9) | class Other_login_buttons : public QPushButton
FILE: Anime_Template_Project/Login_interface/registration_form.h
function class (line 13) | class Registration_form : public QWidget
FILE: Anime_Template_Project/Login_interface/responsive_form.h
function class (line 14) | class Responsive_form : public QWidget
FILE: Anime_Template_Project/Login_interface/scroll_bar.h
function class (line 9) | class Scroll_bar : public QWidget
FILE: Anime_Template_Project/Login_interface/transparent_transition_interface.h
function class (line 11) | class Transparent_transition_interface : public QWidget
FILE: Anime_Template_Project/Magnet_Lines/RotatableLinesWidget.h
function class (line 10) | class RotatableLinesWidget : public QWidget
FILE: Anime_Template_Project/Magnet_Lines/main.cpp
function main (line 12) | int main(int argc, char *argv[])
FILE: Anime_Template_Project/Mimic_Button/depressed_button.cpp
function qreal (line 83) | qreal Depressed_Button::JB() const
function QColor (line 97) | QColor Depressed_Button::clor() const
function qreal (line 111) | qreal Depressed_Button::SF() const
FILE: Anime_Template_Project/Mimic_Button/depressed_button.h
function class (line 11) | class Depressed_Button : public QPushButton
FILE: Anime_Template_Project/Mimic_Button/widget.h
function class (line 10) | class Widget : public QWidget
FILE: Anime_Template_Project/Particle_Generation/ParticleWidget.h
type MovingDot (line 16) | struct MovingDot {
function class (line 29) | class ParticleWidget : public QWidget {
FILE: Anime_Template_Project/Particle_Generation/main.cpp
function main (line 4) | int main(int argc, char *argv[])
FILE: Anime_Template_Project/Particle_Generation/mainwindow.h
function class (line 16) | class MainWindow : public QMainWindow
FILE: Anime_Template_Project/Particle_Generation/particlewidget.cpp
function QPoint (line 151) | QPoint ParticleWidget::mapProcessedToWidget(const cv::Point& p) const
function QImage (line 386) | QImage ParticleWidget::cvMatToQImage(const cv::Mat &mat)
FILE: Anime_Template_Project/Physical_Text/draggableelasticobject.h
type PhysicsBlockProperties (line 14) | struct PhysicsBlockProperties {
function class (line 31) | class DraggableElasticObject : public QWidget
FILE: Anime_Template_Project/Physical_Text/main.cpp
function main (line 8) | int main(int argc, char *argv[])
FILE: Anime_Template_Project/PixelTransition/pixel_transition.h
function class (line 14) | class Pixel_Transition : public QWidget
FILE: Anime_Template_Project/PixelTransition/widget.h
function class (line 15) | class Widget : public QWidget
FILE: Anime_Template_Project/Point_Wave/widget.h
type DotData (line 8) | struct DotData {
function class (line 12) | class Widget : public QWidget
FILE: Anime_Template_Project/Pressure_Block/squarepressurewidget.h
type SquareProperties (line 12) | struct SquareProperties
function class (line 22) | class SquarePressureWidget : public QWidget
FILE: Anime_Template_Project/SplitText/Single_Text.h
function class (line 6) | class Single_Text : public QWidget
FILE: Anime_Template_Project/SplitText/SplitText.h
function class (line 14) | class SplitText : public QMainWindow
FILE: Anime_Template_Project/Star_Sky_Connection/MovingPointsWidget.cpp
function QPointF (line 37) | QPointF MovingPoint::getPosition() const
function QColor (line 42) | QColor MovingPoint::getColor() const
function QPointF (line 47) | QPointF MovingPoint::getDirection() const
function QPointF (line 260) | QPointF MovingPointsWidget::generateRandomDirection() const
function QPointF (line 266) | QPointF MovingPointsWidget::calculateHexagonPoint(const QPointF& center,...
FILE: Anime_Template_Project/Star_Sky_Connection/MovingPointsWidget.h
function QPointF (line 25) | QPointF getPosition() const;
FILE: Anime_Template_Project/TreeScene/TreeScene.h
type SakuraPetal (line 37) | struct SakuraPetal {
type FallingSakura (line 44) | struct FallingSakura {
FILE: Anime_Template_Project/Wave/waveswidget.cpp
function QPointF (line 176) | QPointF WavesWidget::moved(const Point& point, bool withCursor)
FILE: Anime_Template_Project/Wave/waveswidget.h
type Grad (line 16) | struct Grad
function seed (line 56) | void seed(qreal seedVal)
function qreal (line 70) | static qreal fade(qreal t) { return t * t * t * (t * (t * 6 - 15) + 10); }
function qreal (line 72) | static qreal lerp(qreal a, qreal b, qreal t) { return (1 - t) * a + t * ...
function qreal (line 74) | qreal perlin2(qreal x, qreal y) const
type Point (line 100) | struct Point
type MouseState (line 107) | struct MouseState
type Config (line 118) | struct Config
function class (line 132) | class WavesWidget : public QWidget
FILE: Anime_Template_Project/Zipper_Slider/pathwidget.h
function class (line 11) | class PathWidget : public QWidget
FILE: Anime_Template_Project/button_class/diffusion_button.h
function class (line 11) | class Diffusion_button : public QPushButton
FILE: Anime_Template_Project/button_class/wave_button.h
function class (line 11) | class Wave_button : public QPushButton
FILE: Anime_Template_Project/dial_class/knob_page.h
function class (line 8) | class Knob_page : public QWidget
FILE: Anime_Template_Project/dial_class/temperature_dial.cpp
function QColor (line 175) | QColor Temperature_dial::getColorForAngle(int angle)
function QColor (line 188) | QColor Temperature_dial::interpolateColor(const QColor& start, const QCo...
FILE: Anime_Template_Project/dial_class/temperature_dial.h
function class (line 11) | class Temperature_dial : public QWidget {
FILE: Anime_Template_Project/utility_class/timer_animation.cpp
function QVariant (line 174) | QVariant Timer_animation::calculateIncrement(const QVariant &prev, const...
function QVariant (line 246) | QVariant Timer_animation::interpolate(qreal progress) const
FILE: Anime_Template_Project/utility_class/timer_animation.h
type State (line 17) | enum State {
function Direction (line 22) | Q_ENUM(State)
FILE: Anime_Template_Project/utility_class/timer_animationgroup.h
function class (line 9) | class Timer_AnimationGroup : public QObject
Condensed preview — 145 files, each showing path, character count, and a content snippet. Download the .json file or copy for the full structured content (590K chars).
[
{
"path": "Anime_Template_Project/Accordion/AccordionCard.cpp",
"chars": 3744,
"preview": "#include \"AccordionCard.h\"\r\n#include <QDebug>\r\n#include <QPalette>\r\n#include <QVariant>\r\n#include <QPainter>\r\n#include <"
},
{
"path": "Anime_Template_Project/Accordion/AccordionCard.h",
"chars": 1219,
"preview": "#ifndef ACCORDIONCARD_H\n#define ACCORDIONCARD_H\n\n#include <QWidget>\n#include <QLabel>\n#include <QVBoxLayout>\n#include <Q"
},
{
"path": "Anime_Template_Project/Accordion/CMakeLists.txt",
"chars": 2231,
"preview": "cmake_minimum_required(VERSION 3.16)\r\n\r\nproject(untitled4 VERSION 0.1 LANGUAGES CXX)\r\n\r\nset(CMAKE_AUTOUIC ON)\r\nset(CMAKE"
},
{
"path": "Anime_Template_Project/Accordion/accordionwidget.cpp",
"chars": 2054,
"preview": "#include \"AccordionWidget.h\" \r\n#include <QDebug> \r\n\r\nAccordionWidget::AccordionWidget(QWidget *parent)\r\n : QWidget(pa"
},
{
"path": "Anime_Template_Project/Accordion/accordionwidget.h",
"chars": 726,
"preview": "#ifndef ACCORDIONWIDGET_H \n#define ACCORDIONWIDGET_H \n\n#include <QWidget>\n#include <QHBoxLayout>\n#include <QList> \n#incl"
},
{
"path": "Anime_Template_Project/Accordion/img.qrc",
"chars": 521,
"preview": "<RCC>\r\n <qresource prefix=\"/\">\r\n <file>img/FvCpS5naYAA06ej.jpg</file>\r\n <file>img/GaznbVDaMAAp7pf.jpg</"
},
{
"path": "Anime_Template_Project/Accordion/main.cpp",
"chars": 847,
"preview": "#include <QApplication>\r\n#include <QMainWindow>\r\n#include \"AccordionWidget.h\"\r\n#include \"AccordionCard.h\"\r\n\r\nint main(in"
},
{
"path": "Anime_Template_Project/Adaptive_Carousel/daen_no_kado.cpp",
"chars": 16364,
"preview": "#include \"daen_no_kado.h\"\n\nDaen_no_Kado::Daen_no_Kado(QWidget *parent)\n : QWidget{parent}\n{\n this->resize(1200, 60"
},
{
"path": "Anime_Template_Project/Adaptive_Carousel/daen_no_kado.h",
"chars": 3364,
"preview": "#ifndef DAEN_NO_KADO_H\n#define DAEN_NO_KADO_H\n\n#include <QWidget>\n#include <QPainter>\n#include <QPainterPath>\n#include "
},
{
"path": "Anime_Template_Project/Adaptive_Carousel/latticed_circle_button.cpp",
"chars": 3371,
"preview": "#include \"latticed_circle_button.h\"\n\nLatticed_Circle_Button::Latticed_Circle_Button(QWidget* parent) : QPushButton{ par"
},
{
"path": "Anime_Template_Project/Adaptive_Carousel/latticed_circle_button.h",
"chars": 1264,
"preview": "#ifndef LATTICED_CIRCLE_BUTTON_H\n#define LATTICED_CIRCLE_BUTTON_H\n\n#include <QPushButton>\n#include <QPainter>\n#include "
},
{
"path": "Anime_Template_Project/Blur_Text/fuzzytextwidget.cpp",
"chars": 7166,
"preview": "#include \"FuzzyTextWidget.h\"\r\n#include <QPainter>\r\n#include <QPaintEvent>\r\n#include <QMouseEvent>\r\n#include <QDebug>\r\n#i"
},
{
"path": "Anime_Template_Project/Blur_Text/fuzzytextwidget.h",
"chars": 1478,
"preview": "#ifndef FUZZYTEXTWIDGET_H\r\n#define FUZZYTEXTWIDGET_H\r\n\r\n#include <QWidget>\r\n#include <QTimer>\r\n#include <QColor>\r\n#inclu"
},
{
"path": "Anime_Template_Project/Carousel_card/card_button.cpp",
"chars": 2919,
"preview": "#include \"card_button.h\"\n\nCard_button::Card_button(QString text, QColor button_color, QWidget* parent) : QPushButton{ p"
},
{
"path": "Anime_Template_Project/Carousel_card/card_button.h",
"chars": 1094,
"preview": "#ifndef CARD_BUTTON_H\n#define CARD_BUTTON_H\n\n#include <QPushButton>\n#include <QPainter>\n#include <QPainterPath>\n#includ"
},
{
"path": "Anime_Template_Project/Carousel_card/card_text.cpp",
"chars": 5862,
"preview": "#include \"card_text.h\"\n\nCard_text::Card_text(QString text, QString text1, QWidget *parent)\n : QWidget{parent}\n{\n "
},
{
"path": "Anime_Template_Project/Carousel_card/card_text.h",
"chars": 1414,
"preview": "#ifndef CARD_TEXT_H\n#define CARD_TEXT_H\n\n#include <QWidget>\n#include <QPainter>\n#include <QTextDocument>\n#include <QPro"
},
{
"path": "Anime_Template_Project/Carousel_card/carousel_card.cpp",
"chars": 5851,
"preview": "#include \"carousel_card.h\"\n\n\nCarousel_card::Carousel_card(QWidget *parent)\n : QWidget{parent}\n{\n this->setMaximum"
},
{
"path": "Anime_Template_Project/Carousel_card/carousel_card.h",
"chars": 1374,
"preview": "#ifndef CAROUSEL_CARD_H\n#define CAROUSEL_CARD_H\n\n#include <QWidget>\n#include \"carrier_card.h\"\n#include <QList>\n#include"
},
{
"path": "Anime_Template_Project/Carousel_card/carrier_card.cpp",
"chars": 9166,
"preview": "#include \"carrier_card.h\"\n\nCarrier_card::Carrier_card(QPixmap m_carrier_card, QString main_title, QString sub_title,QWi"
},
{
"path": "Anime_Template_Project/Carousel_card/carrier_card.h",
"chars": 2214,
"preview": "#ifndef CARRIER_CARD_H\n#define CARRIER_CARD_H\n\n#include <QWidget>\n#include <QPainter>\n#include <QPropertyAnimation>\n#in"
},
{
"path": "Anime_Template_Project/Eye_of_Cthulhu/JellyfishWidget.cpp",
"chars": 14890,
"preview": "#include \"jellyfishwidget.h\"\r\n#include <QtMath>\r\n#include <QDebug>\r\n#include <QRandomGenerator>\r\n#include <QMouseEvent>\r"
},
{
"path": "Anime_Template_Project/Eye_of_Cthulhu/JellyfishWidget.h",
"chars": 7474,
"preview": "#ifndef JELLYFISHWIDGET_H\n#define JELLYFISHWIDGET_H\n\n#include <QWidget>\n#include <QTimer>\n#include <QPainter>\n#include <"
},
{
"path": "Anime_Template_Project/Flowing_Gradient_Font/widget.cpp",
"chars": 3328,
"preview": "#include \"widget.h\"\n\nWidget::Widget(QWidget *parent)\n : QWidget(parent) {\n this->resize(1440, 880);\n\n animation"
},
{
"path": "Anime_Template_Project/Flowing_Gradient_Font/widget.h",
"chars": 1051,
"preview": "#ifndef WIDGET_H\n#define WIDGET_H\n\n\n#include <QWidget>\n#include <QPainter>\n#include <QPropertyAnimation>\n#include <QPush"
},
{
"path": "Anime_Template_Project/FractalWidget/CMakeLists.txt",
"chars": 2289,
"preview": "cmake_minimum_required(VERSION 3.16)\r\n\r\nproject(FractalWidget VERSION 0.1 LANGUAGES CXX)\r\n\r\nset(CMAKE_AUTOUIC ON)\r\nset(C"
},
{
"path": "Anime_Template_Project/FractalWidget/fractalwidget.cpp",
"chars": 14385,
"preview": "#include \"fractalwidget.h\"\r\n#include <QPainter>\r\n#include <QDebug>\r\n#include <cmath>\r\n#include <algorithm>\r\n#include <QR"
},
{
"path": "Anime_Template_Project/FractalWidget/fractalwidget.h",
"chars": 2179,
"preview": "#ifndef FRACTALWIDGET_H\r\n#define FRACTALWIDGET_H\r\n\r\n#include <QWidget>\r\n#include <QImage>\r\n#include <QTimer>\r\n#include <"
},
{
"path": "Anime_Template_Project/FractalWidget/fractalworker.cpp",
"chars": 9598,
"preview": "#include \"fractalworker.h\"\r\n#include <cmath>\r\n#include <complex>\r\n#include <QVector>\r\n#include <QThreadPool>\r\n#include <"
},
{
"path": "Anime_Template_Project/FractalWidget/fractalworker.h",
"chars": 1533,
"preview": "#ifndef FRACTALWORKER_H\n#define FRACTALWORKER_H\n\n#include <QObject>\n#include <QImage>\n#include <QtConcurrent/QtConcurren"
},
{
"path": "Anime_Template_Project/FractalWidget/main.cpp",
"chars": 185,
"preview": "#include \"mainwindow.h\"\r\n#include <QApplication>\r\n\r\nint main(int argc, char *argv[])\r\n{\r\n QApplication a(argc, argv);"
},
{
"path": "Anime_Template_Project/FractalWidget/mainwindow.cpp",
"chars": 3988,
"preview": "#include \"mainwindow.h\"\r\n#include <QVBoxLayout>\r\n#include <QHBoxLayout>\r\n#include <QWidget>\r\n#include <QDebug>\r\n\r\nMainWi"
},
{
"path": "Anime_Template_Project/FractalWidget/mainwindow.h",
"chars": 787,
"preview": "#ifndef MAINWINDOW_H\r\n#define MAINWINDOW_H\r\n\r\n#include <QMainWindow>\r\n#include \"fractalwidget.h\"\r\n#include <QComboBox>\r\n"
},
{
"path": "Anime_Template_Project/Generative_Lines/widget.cpp",
"chars": 4259,
"preview": "#include \"widget.h\"\r\n\r\nWidget::Widget(QWidget *parent)\r\n : QWidget(parent)\r\n{\r\n // 设置窗口大小\r\n resize(600, 600);\r\n"
},
{
"path": "Anime_Template_Project/Generative_Lines/widget.h",
"chars": 1359,
"preview": "#ifndef WIDGET_H\r\n#define WIDGET_H\r\n\r\n#include <QWidget>\r\n#include <QMetaType> // 引入 QMetaType\r\n#include <QPainter>\r\n#in"
},
{
"path": "Anime_Template_Project/Glitch_Text/GlitchTextWidget.cpp",
"chars": 6853,
"preview": "#include \"GlitchTextWidget.h\"\r\n#include <QDebug>\r\n#include <QMouseEvent>\r\n#include <QEnterEvent>\r\n#include <QAbstractAni"
},
{
"path": "Anime_Template_Project/Glitch_Text/GlitchTextWidget.h",
"chars": 1677,
"preview": "#ifndef GLITCHTEXTWIDGET_H\n#define GLITCHTEXTWIDGET_H\n\n#include <QWidget>\n#include <QPropertyAnimation>\n#include <QPaint"
},
{
"path": "Anime_Template_Project/Honeycomb_Grid/hexagonwidget.cpp",
"chars": 11206,
"preview": "// Copyright (C) 2016 The Qt Company Ltd. // 版权所有 (C) 2016 Qt 公司。\r\n// SPDX-License-Identifier: LicenseRef-Qt-Commercial "
},
{
"path": "Anime_Template_Project/Honeycomb_Grid/hexagonwidget.h",
"chars": 2539,
"preview": "// Copyright (C) 2016 The Qt Company Ltd. // 版权所有 (C) 2016 Qt 公司。\r\n// SPDX-License-Identifier: LicenseRef-Qt-Commercial "
},
{
"path": "Anime_Template_Project/Honeycomb_Grid/mainwindow.cpp",
"chars": 1798,
"preview": "#include \"mainwindow.h\"\r\n#include <QVBoxLayout>\r\n#include <QHBoxLayout>\r\n#include <QWidget>\r\n\r\nMainWindow::MainWindow(QW"
},
{
"path": "Anime_Template_Project/Honeycomb_Grid/mainwindow.h",
"chars": 577,
"preview": "#ifndef MAINWINDOW_H\r\n#define MAINWINDOW_H\r\n\r\n#include <QMainWindow>\r\n#include \"hexagonwidget.h\"\r\n#include <QSlider>\r\n#i"
},
{
"path": "Anime_Template_Project/Letter_Glitch/CMakeLists.txt",
"chars": 943,
"preview": "cmake_minimum_required(VERSION 3.19)\r\nproject(untitled4 LANGUAGES CXX)\r\n\r\nfind_package(Qt6 6.5 REQUIRED COMPONENTS Core "
},
{
"path": "Anime_Template_Project/Letter_Glitch/GlitchEffectWidget.cpp",
"chars": 17843,
"preview": "#include \"GlitchEffectWidget.h\"\r\n#include <QDebug>\r\n#include <QFontMetricsF>\r\n#include <cmath>\r\n#include <QPainterPath>\r"
},
{
"path": "Anime_Template_Project/Letter_Glitch/GlitchEffectWidget.h",
"chars": 3256,
"preview": "#ifndef GLITCHEFFECTWIDGET_H\n#define GLITCHEFFECTWIDGET_H\n\n#include <QWidget>\n#include <QTimer>\n#include <QColor>\n#inclu"
},
{
"path": "Anime_Template_Project/Letter_Glitch/main.cpp",
"chars": 2050,
"preview": "#include <QApplication>\r\n#include <QMainWindow>\r\n#include \"GlitchEffectWidget.h\"\r\n#include <QVBoxLayout>\r\n#include <QPus"
},
{
"path": "Anime_Template_Project/Liquid/image_processing.cpp",
"chars": 12342,
"preview": "#include \"image_processing.h\"\n\nQ_GLOBAL_STATIC(Image_Processing, fileRelatedInstance)\n\nImage_Processing::Image_Processin"
},
{
"path": "Anime_Template_Project/Liquid/image_processing.h",
"chars": 1727,
"preview": "#ifndef IMAGE_PROCESSING_H\n#define IMAGE_PROCESSING_H\n\n#include <QObject>\n#include <QImage>\n\n#define IMAGE_PROCESSING Im"
},
{
"path": "Anime_Template_Project/Liquid/liquid_button.cpp",
"chars": 1922,
"preview": "#include \"liquid_button.h\"\n\nLiquid_Button::Liquid_Button(QWidget *parent)\n : QWidget{parent}\n{\n this->setFixedSiz"
},
{
"path": "Anime_Template_Project/Liquid/liquid_button.h",
"chars": 889,
"preview": "#ifndef LIQUID_BUTTON_H\n#define LIQUID_BUTTON_H\n\n#include <QWidget>\n#include <QPainter>\n#include <QEvent>\n#include <QPa"
},
{
"path": "Anime_Template_Project/Liquid/widget.cpp",
"chars": 4848,
"preview": "#include \"widget.h\"\n\nWidget::Widget(QWidget *parent)\n : QWidget(parent)\n{\n this->resize(655, 655);\n button = n"
},
{
"path": "Anime_Template_Project/Liquid/widget.h",
"chars": 1102,
"preview": "#ifndef WIDGET_H\n#define WIDGET_H\n\n#include <QWidget>\n#include <QPropertyAnimation>\n#include <QPainter>\n#include \"image"
},
{
"path": "Anime_Template_Project/LoadingAnime/Bouncing_Ball_Loading.h",
"chars": 2593,
"preview": "#ifndef BOUNCING_BALL_LOADING_H\r\n#define BOUNCING_BALL_LOADING_H\r\n\r\n#include <QWidget>\r\n#include <QTimer>\r\n#include <QPr"
},
{
"path": "Anime_Template_Project/LoadingAnime/CMakeLists.txt",
"chars": 1531,
"preview": "cmake_minimum_required(VERSION 3.19)\r\nproject(LoadingAnime LANGUAGES CXX)\r\n\r\nfind_package(Qt6 6.5 REQUIRED COMPONENTS Co"
},
{
"path": "Anime_Template_Project/LoadingAnime/Rectangle_Loading.h",
"chars": 1127,
"preview": "#ifndef RECTANGLE_LOADING_H\r\n#define RECTANGLE_LOADING_H\r\n\r\n#include <QWidget>\r\n#include <QPropertyAnimation>\r\n#include "
},
{
"path": "Anime_Template_Project/LoadingAnime/Square_Pseudo_Bounce_Loading.cpp",
"chars": 4312,
"preview": "#include \"Square_Pseudo_Bounce_Loading.h\"\r\n#include <QDebug>\r\n\r\nSquare_Pseudo_Bounce_Loading::Square_Pseudo_Bounce_Loadi"
},
{
"path": "Anime_Template_Project/LoadingAnime/Square_Pseudo_Bounce_Loading.h",
"chars": 1372,
"preview": "#ifndef SQUARE_PSEUDO_BOUNCE_LOADING_H\n#define SQUARE_PSEUDO_BOUNCE_LOADING_H\n\n#include <QWidget>\n#include <QPropertyAni"
},
{
"path": "Anime_Template_Project/LoadingAnime/black_white_ball_loading.cpp",
"chars": 5629,
"preview": "#include \"black_white_ball_loading.h\"\r\n#include <QPainter>\r\n#include <QDebug>\r\n#include <QResizeEvent>\r\n#include <QtMath"
},
{
"path": "Anime_Template_Project/LoadingAnime/black_white_ball_loading.h",
"chars": 1296,
"preview": "#ifndef BLACK_WHITE_BALL_LOADING_H\r\n#define BLACK_WHITE_BALL_LOADING_H\r\n\r\n#include <QWidget>\r\n#include <QTimer>\r\n#includ"
},
{
"path": "Anime_Template_Project/LoadingAnime/bouncing_ball_loading.cpp",
"chars": 5849,
"preview": "#include \"Bouncing_Ball_Loading.h\"\r\n#include <QPainter>\r\n#include <QDebug>\r\n#include <cmath>\r\n\r\nBouncing_Ball_Loading::B"
},
{
"path": "Anime_Template_Project/LoadingAnime/hexagonloaderwidget.cpp",
"chars": 9279,
"preview": "#include \"HexagonLoaderWidget.h\"\r\n#include <QPainter>\r\n#include <QDebug>\r\n#include <QtMath>\r\n#include <QTimer>\r\n#include"
},
{
"path": "Anime_Template_Project/LoadingAnime/hexagonloaderwidget.h",
"chars": 3052,
"preview": "#ifndef HEXAGONWIDGET_H\r\n#define HEXAGONWIDGET_H\r\n\r\n#include <QWidget>\r\n#include <QColor>\r\n#include <QVector>\r\n#include "
},
{
"path": "Anime_Template_Project/LoadingAnime/line_loading.cpp",
"chars": 6296,
"preview": "// line_loading.cpp\r\n#include \"line_loading.h\"\r\n#include <QPainter>\r\n#include <QDebug>\r\n#include <QtMath>\r\n#include <QSc"
},
{
"path": "Anime_Template_Project/LoadingAnime/line_loading.h",
"chars": 1548,
"preview": "#ifndef LINE_LOADING_H\r\n#define LINE_LOADING_H\r\n\r\n#include <QWidget>\r\n#include <vector>\r\n#include <QPainter>\r\n#include <"
},
{
"path": "Anime_Template_Project/LoadingAnime/line_rotating_along_rectangular_border.cpp",
"chars": 2833,
"preview": "// Line_Rotating_Along_Rectangular_Border.cpp\r\n#include \"line_rotating_along_rectangular_border.h\"\r\n#include <QPropertyA"
},
{
"path": "Anime_Template_Project/LoadingAnime/line_rotating_along_rectangular_border.h",
"chars": 985,
"preview": "#ifndef LINE_ROTATING_ALONG_RECTANGULAR_BORDER_H\r\n#define LINE_ROTATING_ALONG_RECTANGULAR_BORDER_H\r\n\r\n#include <QWidget>"
},
{
"path": "Anime_Template_Project/LoadingAnime/main.cpp",
"chars": 175,
"preview": "#include \"widget.h\"\r\n\r\n#include <QApplication>\r\n\r\nint main(int argc, char *argv[])\r\n{\r\n QApplication a(argc, argv);\r\n"
},
{
"path": "Anime_Template_Project/LoadingAnime/rectangle_loading.cpp",
"chars": 4223,
"preview": "#include \"Rectangle_Loading.h\"\r\n#include <QDebug>\r\n#include <QFont>\r\n#include <QFontMetrics>\r\n\r\nRectangle_Loading::Recta"
},
{
"path": "Anime_Template_Project/LoadingAnime/regular_loading.cpp",
"chars": 1846,
"preview": "// regular_loading.cpp\r\n#include \"regular_loading.h\"\r\n#include <QDebug>\r\n\r\nRegular_Loading::Regular_Loading(QWidget *par"
},
{
"path": "Anime_Template_Project/LoadingAnime/regular_loading.h",
"chars": 773,
"preview": "// regular_loading.h\r\n#ifndef REGULAR_LOADING_H\r\n#define REGULAR_LOADING_H\r\n\r\n#include <QWidget>\r\n#include <QPainter>\r\n#"
},
{
"path": "Anime_Template_Project/LoadingAnime/ring_loading.cpp",
"chars": 8761,
"preview": "#include \"ring_loading.h\"\r\n#include <QPainter>\r\n#include <QPen>\r\n#include <QResizeEvent>\r\n#include <QtMath>\r\n\r\n\r\nRing_Lo"
},
{
"path": "Anime_Template_Project/LoadingAnime/ring_loading.h",
"chars": 3305,
"preview": "#ifndef RING_LOADING_H\r\n#define RING_LOADING_H\r\n\r\n#include <QWidget>\r\n#include <QPainter>\r\n#include <QColor>\r\n#include <"
},
{
"path": "Anime_Template_Project/LoadingAnime/widget.cpp",
"chars": 2185,
"preview": "#include \"widget.h\"\r\n\r\nWidget::Widget(QWidget *parent)\r\n : QWidget(parent)\r\n{\r\n this->resize(1200,860);\r\n\r\n m_r"
},
{
"path": "Anime_Template_Project/LoadingAnime/widget.h",
"chars": 1028,
"preview": "#ifndef WIDGET_H\r\n#define WIDGET_H\r\n\r\n#include <QWidget>\r\n#include <QResizeEvent>\r\n\r\n#include \"ring_loading.h\"\r\n#include"
},
{
"path": "Anime_Template_Project/Login_interface/hollow_button.cpp",
"chars": 4212,
"preview": "#include \"hollow_button.h\"\n\nHollow_button::Hollow_button(QWidget* parent) : QPushButton{ parent }\n{\n this->setCursor"
},
{
"path": "Anime_Template_Project/Login_interface/hollow_button.h",
"chars": 1435,
"preview": "#ifndef HOLLOW_BUTTON_H\n#define HOLLOW_BUTTON_H\n\n#include <QPushButton>\n#include <QPainter>\n#include <QPainterPath>\n#in"
},
{
"path": "Anime_Template_Project/Login_interface/input_box.cpp",
"chars": 1583,
"preview": "#include \"input_box.h\"\n\nInput_box::Input_box(QString icon, QWidget* parent) : QLineEdit{ parent }\n{\n this->icon = QP"
},
{
"path": "Anime_Template_Project/Login_interface/input_box.h",
"chars": 440,
"preview": "#ifndef INPUT_BOX_H\n#define INPUT_BOX_H\n\n#include <QLineEdit>\n#include <QWidget>\n#include <QPainter>\n#include <QPainter"
},
{
"path": "Anime_Template_Project/Login_interface/login_button.cpp",
"chars": 2919,
"preview": "#include \"login_button.h\"\n\nLogin_button::Login_button(QWidget* parent) : QPushButton{ parent }\n{\n this->resize(392, "
},
{
"path": "Anime_Template_Project/Login_interface/login_button.h",
"chars": 1124,
"preview": "#ifndef LOGIN_BUTTON_H\n#define LOGIN_BUTTON_H\n\n#include <QPushButton>\n#include <QPainter>\n#include <QPainterPath>\n#incl"
},
{
"path": "Anime_Template_Project/Login_interface/login_form.cpp",
"chars": 3493,
"preview": "#include \"login_form.h\"\n\nLogin_form::Login_form(QWidget *parent)\n : QWidget{parent}\n{\n this->resize(477, 620);\n\n "
},
{
"path": "Anime_Template_Project/Login_interface/login_form.h",
"chars": 936,
"preview": "#ifndef LOGIN_FORM_H\n#define LOGIN_FORM_H\n\n#include <QWidget>\n#include <QPainter>\n#include <QIntValidator>\n#include <QR"
},
{
"path": "Anime_Template_Project/Login_interface/other_login_buttons.cpp",
"chars": 974,
"preview": "#include \"other_login_buttons.h\"\n\nOther_login_buttons::Other_login_buttons(QString icon, QWidget* parent) : QPushButton"
},
{
"path": "Anime_Template_Project/Login_interface/other_login_buttons.h",
"chars": 411,
"preview": "#ifndef OTHER_LOGIN_BUTTONS_H\n#define OTHER_LOGIN_BUTTONS_H\n\n#include <QPushButton>\n#include <QPixmap>\n#include <QPaint"
},
{
"path": "Anime_Template_Project/Login_interface/registration_form.cpp",
"chars": 3860,
"preview": "#include \"registration_form.h\"\n\nRegistration_form::Registration_form(QWidget *parent)\n : QWidget{parent}\n{\n this-"
},
{
"path": "Anime_Template_Project/Login_interface/registration_form.h",
"chars": 994,
"preview": "#ifndef REGISTRATION_FORM_H\n#define REGISTRATION_FORM_H\n\n#include <QWidget>\n#include <QPainter>\n#include <QIntValidator"
},
{
"path": "Anime_Template_Project/Login_interface/responsive_form.cpp",
"chars": 7368,
"preview": "#include \"responsive_form.h\"\n\nResponsive_form::Responsive_form(QWidget *parent)\n : QWidget{parent}\n{\n this->setFi"
},
{
"path": "Anime_Template_Project/Login_interface/responsive_form.h",
"chars": 1771,
"preview": "#ifndef RESPONSIVE_FORM_H\n#define RESPONSIVE_FORM_H\n\n#include <QWidget>\n#include <QPainter>\n#include <QPainterPath>\n#in"
},
{
"path": "Anime_Template_Project/Login_interface/scroll_bar.cpp",
"chars": 884,
"preview": "#include \"scroll_bar.h\"\n\nScroll_bar::Scroll_bar(QWidget *parent)\n : QWidget{parent}\n{\n this->resize(1910, 620);\n "
},
{
"path": "Anime_Template_Project/Login_interface/scroll_bar.h",
"chars": 360,
"preview": "#ifndef SCROLL_BAR_H\n#define SCROLL_BAR_H\n\n#include <QWidget>\n#include <QPainter>\n#include <QPainterPath>\n#include <QPr"
},
{
"path": "Anime_Template_Project/Login_interface/transparent_transition_interface.cpp",
"chars": 2248,
"preview": "#include \"transparent_transition_interface.h\"\n\nTransparent_transition_interface::Transparent_transition_interface(QStri"
},
{
"path": "Anime_Template_Project/Login_interface/transparent_transition_interface.h",
"chars": 692,
"preview": "#ifndef TRANSPARENT_TRANSITION_INTERFACE_H\n#define TRANSPARENT_TRANSITION_INTERFACE_H\n\n#include <QWidget>\n#include <QPa"
},
{
"path": "Anime_Template_Project/Magnet_Lines/CMakeLists.txt",
"chars": 727,
"preview": "cmake_minimum_required(VERSION 3.19)\r\nproject(untitled3 LANGUAGES CXX)\r\n\r\nfind_package(Qt6 6.5 REQUIRED COMPONENTS Core "
},
{
"path": "Anime_Template_Project/Magnet_Lines/RotatableLinesWidget.cpp",
"chars": 3479,
"preview": "#include \"RotatableLinesWidget.h\"\r\n#include <QDebug>\r\n#include <QMouseEvent>\r\n#include <cmath>\r\n#include <QCursor>\r\n\r\nRo"
},
{
"path": "Anime_Template_Project/Magnet_Lines/RotatableLinesWidget.h",
"chars": 772,
"preview": "#ifndef ROTATABLELINESWIDGET_H\n#define ROTATABLELINESWIDGET_H\n\n#include <QWidget>\n#include <QPainter>\n#include <QPaintEv"
},
{
"path": "Anime_Template_Project/Magnet_Lines/main.cpp",
"chars": 1918,
"preview": "#include <QApplication>\r\n#include <QMainWindow>\r\n#include <QVBoxLayout>\r\n#include <QHBoxLayout>\r\n#include <QSpinBox>\r\n#i"
},
{
"path": "Anime_Template_Project/Mimic_Button/depressed_button.cpp",
"chars": 3372,
"preview": "#include \"depressed_button.h\"\n\nDepressed_Button::Depressed_Button(QString m_Function_Button_pixmap, QWidget* parent)\n "
},
{
"path": "Anime_Template_Project/Mimic_Button/depressed_button.h",
"chars": 1248,
"preview": "#ifndef DEPRESSED_BUTTON_H\n#define DEPRESSED_BUTTON_H\n\n#include <QPushButton>\n#include <QPropertyAnimation>\n#include <QE"
},
{
"path": "Anime_Template_Project/Mimic_Button/img.qrc",
"chars": 365,
"preview": "<RCC>\n <qresource prefix=\"/new/prefix1\">\n <file>img/twitter.png</file>\n <file>img/哔哩哔哩.png</file>\n "
},
{
"path": "Anime_Template_Project/Mimic_Button/widget.cpp",
"chars": 4677,
"preview": "#include \"widget.h\"\n\nWidget::Widget(QWidget *parent)\n : QWidget(parent)\n{\n this->resize(1111, 1111);\n\n xxxx1 = "
},
{
"path": "Anime_Template_Project/Mimic_Button/widget.h",
"chars": 1207,
"preview": "#ifndef WIDGET_H\n#define WIDGET_H\n\n#include <QWidget>\n#include <QPropertyAnimation>\n#include <QPainter>\n#include <QMouse"
},
{
"path": "Anime_Template_Project/Particle_Generation/CMakeLists.txt",
"chars": 1163,
"preview": "cmake_minimum_required(VERSION 3.19)\r\nproject(Particle_Generation LANGUAGES CXX)\r\n\r\nfind_package(Qt6 6.5 REQUIRED COMPON"
},
{
"path": "Anime_Template_Project/Particle_Generation/ParticleWidget.h",
"chars": 2115,
"preview": "#ifndef PARTICLEWIDGET_H\r\n#define PARTICLEWIDGET_H\r\n\r\n#include <QWidget>\r\n#include <QTimer>\r\n#include <opencv2/opencv.hp"
},
{
"path": "Anime_Template_Project/Particle_Generation/main.cpp",
"chars": 185,
"preview": "#include <QApplication>\r\n#include \"MainWindow.h\"\r\n\r\nint main(int argc, char *argv[])\r\n{\r\n QApplication a(argc, argv);"
},
{
"path": "Anime_Template_Project/Particle_Generation/mainwindow.cpp",
"chars": 6519,
"preview": "#include \"mainwindow.h\"\r\n#include <QColorDialog>\r\n\r\nMainWindow::MainWindow(QWidget *parent)\r\n : QMainWindow(parent)\r\n"
},
{
"path": "Anime_Template_Project/Particle_Generation/mainwindow.h",
"chars": 1203,
"preview": "#ifndef MAINWINDOW_H\r\n#define MAINWINDOW_H\r\n\r\n#include <QMainWindow>\r\n#include <QPushButton>\r\n#include <QSlider>\r\n#inclu"
},
{
"path": "Anime_Template_Project/Particle_Generation/particlewidget.cpp",
"chars": 12441,
"preview": "#include \"ParticleWidget.h\"\r\n#include <QPainter>\r\n#include <QRandomGenerator>\r\n#include <QDebug>\r\n#include <QtMath>\r\n#in"
},
{
"path": "Anime_Template_Project/Physical_Text/DraggableElasticObject.cpp",
"chars": 18718,
"preview": "#include \"draggableelasticobject.h\"\r\n#include <QPainter>\r\n#include <QtMath>\r\n#include <QRandomGenerator>\r\n#include <QDeb"
},
{
"path": "Anime_Template_Project/Physical_Text/draggableelasticobject.h",
"chars": 1975,
"preview": "#ifndef DRAGGABLEELASTICOBJECT_H\n#define DRAGGABLEELASTICOBJECT_H\n\n#include <QWidget>\n#include <QTimer>\n#include <QPoint"
},
{
"path": "Anime_Template_Project/Physical_Text/main.cpp",
"chars": 2224,
"preview": "#include <QApplication>\r\n#include \"draggableelasticobject.h\"\r\n#include <QMainWindow>\r\n#include <QRandomGenerator>\r\n#incl"
},
{
"path": "Anime_Template_Project/PixelTransition/pixel_transition.cpp",
"chars": 6904,
"preview": "#include \"pixel_transition.h\"\r\n\r\nPixel_Transition::Pixel_Transition(int count,QWidget *parent)\r\n : QWidget{parent}\r\n{"
},
{
"path": "Anime_Template_Project/PixelTransition/pixel_transition.h",
"chars": 1316,
"preview": "#ifndef PIXEL_TRANSITION_H\r\n#define PIXEL_TRANSITION_H\r\n\r\n#include <QWidget>\r\n#include <QList>\r\n#include <QRandomGenerat"
},
{
"path": "Anime_Template_Project/PixelTransition/widget.cpp",
"chars": 3111,
"preview": "#include \"widget.h\"\r\n\r\nWidget::Widget(QWidget *parent)\r\n : QWidget(parent)\r\n{\r\n this->resize(1200,500);\r\n\r\n pix"
},
{
"path": "Anime_Template_Project/PixelTransition/widget.h",
"chars": 722,
"preview": "#ifndef WIDGET_H\r\n#define WIDGET_H\r\n\r\n#include <QWidget>\r\n#include <QPainter.h>\r\n#include <QResizeEvent>\r\n#include <QSli"
},
{
"path": "Anime_Template_Project/Point_Wave/widget.cpp",
"chars": 2956,
"preview": "#include \"widget.h\"\r\n\r\nWidget::Widget(QWidget *parent)\r\n : QWidget(parent)\r\n{\r\n resize(w,h);\r\n timer = new QTim"
},
{
"path": "Anime_Template_Project/Point_Wave/widget.h",
"chars": 839,
"preview": "#ifndef WIDGET_H\r\n#define WIDGET_H\r\n\r\n#include <QWidget>\r\n#include <QPainter>\r\n#include <QResizeEvent>\r\n#include <QTimer"
},
{
"path": "Anime_Template_Project/Pressure_Block/squarepressurewidget.cpp",
"chars": 3870,
"preview": "// squarepressurewidget.cpp\r\n#include \"squarepressurewidget.h\"\r\n#include <algorithm>\r\n#include <cmath>\r\n\r\nSquarePressure"
},
{
"path": "Anime_Template_Project/Pressure_Block/squarepressurewidget.h",
"chars": 1057,
"preview": "#ifndef SQUAREPRESSUREWIDGET_H\r\n#define SQUAREPRESSUREWIDGET_H\r\n\r\n#include <QtWidgets/QWidget>\r\n#include <QtGui/QPainter"
},
{
"path": "Anime_Template_Project/SplitText/Single_Text.cpp",
"chars": 2975,
"preview": "#include \"Single_Text.h\"\r\n\r\nSingle_Text::Single_Text(QString text,QWidget *parent)\r\n : QWidget(parent)\r\n{\r\n this->"
},
{
"path": "Anime_Template_Project/SplitText/Single_Text.h",
"chars": 1116,
"preview": "#pragma once\r\n#include <QWidget>\r\n#include <QPropertyAnimation>\r\n#include <QPainter>\r\n\r\nclass Single_Text : public QWidg"
},
{
"path": "Anime_Template_Project/SplitText/SplitText.cpp",
"chars": 3169,
"preview": "#include \"SplitText.h\"\n\nSplitText::SplitText(QWidget* parent)\n : QMainWindow(parent)\n{\n this->resize(700, 700);\n "
},
{
"path": "Anime_Template_Project/SplitText/SplitText.h",
"chars": 649,
"preview": "#pragma once\n#include <QMainWindow>\n#include \"Single_Text.h\"\n//动态列表\n#include <vector>\n//按钮\n#include <QPushButton>\n//输入框\n"
},
{
"path": "Anime_Template_Project/Star_Sky_Connection/MovingPointsWidget.cpp",
"chars": 7715,
"preview": "#include \"MovingPointsWidget.h\"\r\n\r\n\r\n\r\nMovingPoint::MovingPoint(const QPointF& pos, const QPointF& direction, double spe"
},
{
"path": "Anime_Template_Project/Star_Sky_Connection/MovingPointsWidget.h",
"chars": 1633,
"preview": "#ifndef MOVINGPOINTSWIDGET_H\n#define MOVINGPOINTSWIDGET_H\n\n#include <QWidget>\n#include <QVector>\n#include <QTimer>\n#incl"
},
{
"path": "Anime_Template_Project/TreeScene/TreeScene.cpp",
"chars": 13382,
"preview": "#include \"TreeScene.h\"\r\n#include <QPainter>\r\n#include <QDebug>\r\n#include <cmath>\r\n#include <QPainterPath>\r\n\r\n#define PI "
},
{
"path": "Anime_Template_Project/TreeScene/TreeScene.h",
"chars": 2568,
"preview": "#pragma once\n\n#include <QWidget>\n#include <QTimer>\n#include <QElapsedTimer>\n#include <QVector>\n#include <QPointF>\n#inclu"
},
{
"path": "Anime_Template_Project/Wave/waveswidget.cpp",
"chars": 5432,
"preview": "#include \"waveswidget.h\"\r\n#include <QDebug>\r\n#include <random>\r\n#include <chrono>\r\n\r\nWavesWidget::WavesWidget(QWidget *p"
},
{
"path": "Anime_Template_Project/Wave/waveswidget.h",
"chars": 5639,
"preview": "#ifndef WAVESWIDGET_H\r\n#define WAVESWIDGET_H\r\n\r\n#include <QWidget>\r\n#include <QTimer>\r\n#include <QPainter>\r\n#include <QM"
},
{
"path": "Anime_Template_Project/Zipper_Slider/pathwidget.cpp",
"chars": 3411,
"preview": "#include \"PathWidget.h\"\n\nPathWidget::PathWidget(QWidget *parent)\n : QWidget(parent)\n{\n QPalette palette = this->pa"
},
{
"path": "Anime_Template_Project/Zipper_Slider/pathwidget.h",
"chars": 1106,
"preview": "#ifndef PATHWIDGET_H\n#define PATHWIDGET_H\n\n#include <QWidget>\n#include <QPainter>\n#include <QPainterPath>\n#include <QTim"
},
{
"path": "Anime_Template_Project/button_class/diffusion_button.cpp",
"chars": 2879,
"preview": "#include \"diffusion_button.h\"\n\nDiffusion_button::Diffusion_button(QWidget* parent) : QPushButton{ parent }\n{\n this->s"
},
{
"path": "Anime_Template_Project/button_class/diffusion_button.h",
"chars": 1087,
"preview": "#ifndef DIFFUSION_BUTTON_H\n#define DIFFUSION_BUTTON_H\n\n#include <QPushButton>\n#include <QPainter>\n#include <QMouseEvent"
},
{
"path": "Anime_Template_Project/button_class/wave_button.cpp",
"chars": 7457,
"preview": "#include \"wave_button.h\"\n\nWave_button::Wave_button(QWidget* parent) : QPushButton{ parent }\n{\n this->resize(147, 55);"
},
{
"path": "Anime_Template_Project/button_class/wave_button.h",
"chars": 1732,
"preview": "#ifndef WAVE_BUTTON_H\n#define WAVE_BUTTON_H\n\n#include <QPushButton>\n#include <QPainter>\n#include <QMouseEvent>\n#include"
},
{
"path": "Anime_Template_Project/dial_class/knob_page.cpp",
"chars": 1348,
"preview": "#include \"knob_page.h\"\n\nKnob_page::Knob_page(QWidget *parent)\n : QWidget{parent}\n{\n QPalette pal(this->palette())"
},
{
"path": "Anime_Template_Project/dial_class/knob_page.h",
"chars": 477,
"preview": "#ifndef KNOB_PAGE_H\n#define KNOB_PAGE_H\n\n#include <QWidget>\n#include \"temperature_dial.h\"\n#include \"../utility_class/ti"
},
{
"path": "Anime_Template_Project/dial_class/temperature_dial.cpp",
"chars": 9712,
"preview": "#include \"temperature_dial.h\"\n\nTemperature_dial::Temperature_dial(QWidget *parent) : QWidget(parent) \n{\n resize(260,"
},
{
"path": "Anime_Template_Project/dial_class/temperature_dial.h",
"chars": 1958,
"preview": "#ifndef TEMPERATURE_DIAL_H\n#define TEMPERATURE_DIAL_H\n\n#include <QWidget>\n#include <QPainter>\n#include <QMouseEvent>\n#i"
},
{
"path": "Anime_Template_Project/json/Anime_care_attributes.json",
"chars": 1433,
"preview": "{\n \"Anime_img_str_list\": [\n {\n \"img\": \"://img/card_image1.png\",\n \"str_1\": \"无职转生~到了异世界就拿出"
},
{
"path": "Anime_Template_Project/src.qrc",
"chars": 1001,
"preview": "<RCC>\n <qresource prefix=\"/\">\n <file>img/card_image1.png</file>\n <file>img/card_image2.png</file>\n "
},
{
"path": "Anime_Template_Project/utility_class/timer_animation.cpp",
"chars": 10646,
"preview": "#include \"timer_animation.h\"\n#include <QDebug>\n#include <QtMath>\n\nTimer_animation::Timer_animation(QObject* target, con"
},
{
"path": "Anime_Template_Project/utility_class/timer_animation.h",
"chars": 2129,
"preview": "#ifndef TIMER_ANIMATION_H\n#define TIMER_ANIMATION_H\n\n#include <QObject>\n#include <QTimer>\n#include <QVariant>\n#include "
},
{
"path": "Anime_Template_Project/utility_class/timer_animationgroup.cpp",
"chars": 3908,
"preview": "#include \"timer_animationgroup.h\"\n#include <algorithm>\n\nTimer_AnimationGroup::Timer_AnimationGroup(QObject *parent)\n "
},
{
"path": "Anime_Template_Project/utility_class/timer_animationgroup.h",
"chars": 1154,
"preview": "#ifndef ANIMATION_GROUP_H\n#define ANIMATION_GROUP_H\n\n#include <QObject>\n#include <QMap>\n#include <QList>\n#include \"timer"
},
{
"path": "LICENSE",
"chars": 35149,
"preview": " GNU GENERAL PUBLIC LICENSE\n Version 3, 29 June 2007\n\n Copyright (C) 2007 Free "
},
{
"path": "README.md",
"chars": 6529,
"preview": "<div align=\"center\">\n <img src=\"res/GQmst7takAMVmoS.jpg\" alt=\"\" width=\"120\" height=\"120\"/>\n <h1>Anime_Template</h1>\n"
}
]
About this extraction
This page contains the full source code of the daishuboluo/Anime_carousel GitHub repository, extracted and formatted as plain text for AI agents and large language models (LLMs). The extraction includes 145 files (528.6 KB), approximately 145.6k tokens, and a symbol index with 156 extracted functions, classes, methods, constants, and types. Use this with OpenClaw, Claude, ChatGPT, Cursor, Windsurf, or any other AI tool that accepts text input. You can copy the full output to your clipboard or download it as a .txt file.
Extracted by GitExtract — free GitHub repo to text converter for AI. Built by Nikandr Surkov.