diff --git a/source/src/tagpool.cpp b/source/src/tagpool.cpp old mode 100644 new mode 100755 index e3f0391..8438921 --- a/source/src/tagpool.cpp +++ b/source/src/tagpool.cpp @@ -1,6 +1,7 @@ #include "tagpool.h" #include "dbmanager.h" +// TagPool类的构造函数,用于初始化数据库管理器并连接信号与槽 TagPool::TagPool(DBManager *dbManager, QObject *parent) : QObject(parent), m_dbManager{ dbManager } { connect( @@ -22,46 +23,54 @@ TagPool::TagPool(DBManager *dbManager, QObject *parent) : QObject(parent), m_dbM Qt::QueuedConnection); } +// 设置标签池的新数据 void TagPool::setTagPool(const QMap &newPool) { m_pool = newPool; emit dataReset(); } +// 删除指定ID的标签 void TagPool::onTagDeleted(int id) { m_pool.remove(id); emit tagDeleted(id); } +// 添加新的标签 void TagPool::onTagAdded(const TagData &tag) { m_pool[tag.id()] = tag; } +// 重命名指定ID的标签 void TagPool::onTagRenamed(int id, const QString &newName) { m_pool[id].setName(newName); emit dataUpdated(id); } +// 修改指定ID的标签颜色 void TagPool::onTagColorChanged(int id, const QString &newColor) { m_pool[id].setColor(newColor); emit dataUpdated(id); } +// 获取指定ID的标签数据 TagData TagPool::getTag(int id) const { return m_pool[id]; } +// 检查标签池中是否包含指定ID的标签 bool TagPool::contains(int id) const { return m_pool.contains(id); } +// 获取标签池中所有标签的ID列表 QList TagPool::tagIds() const { return m_pool.keys(); -} +} \ No newline at end of file diff --git a/source/src/tagpool.h b/source/src/tagpool.h old mode 100644 new mode 100755 index 5688db8..2a510b6 --- a/source/src/tagpool.h +++ b/source/src/tagpool.h @@ -1,37 +1,58 @@ #ifndef TAGPOOL_H -#define TAGPOOL_H +# define TAGPOOL_H -#include -#include -#include "tagdata.h" +# include +# include +# include "tagdata.h" class DBManager; +// 标签池类,管理标签数据 class TagPool : public QObject { Q_OBJECT public: + // 构造函数,初始化标签池和数据库管理器 explicit TagPool(DBManager *dbManager, QObject *parent = nullptr); + // 获取指定ID的标签数据 TagData getTag(int id) const; + // 检查是否包含指定ID的标签 bool contains(int id) const; + // 获取所有标签的ID列表 QList tagIds() const; signals: + // 数据重置信号 void dataReset(); + // 数据更新信号,携带更新的标签ID void dataUpdated(int tagId); + // 标签删除信号,携带删除的标签ID void tagDeleted(int tagId); private slots: + // 标签删除的槽函数 void onTagDeleted(int id); + // 标签添加的槽函数 void onTagAdded(const TagData &tag); + // 标签重命名的槽函数 void onTagRenamed(int id, const QString &newName); + // 标签颜色改变的槽函数 void onTagColorChanged(int id, const QString &newColor); private: - QMap m_pool; - DBManager *m_dbManager; + QMap m_pool; // 标签数据池 + DBManager *m_dbManager; // 数据库管理器指针 + // 设置标签池 void setTagPool(const QMap &newPool); }; -#endif // TAGPOOL_H +#endif // TAGPOOL_H void onTagRenamed(int id, const QString &newName); +// 标签颜色改变的槽函数 +void onTagColorChanged(int id, const QString &newColor); + +private: +QMap m_pool; // 标签数据池 +DBManager *m_dbManager; // 数据库管理器指针 + +// 设置标签 \ No newline at end of file diff --git a/source/src/tagtreedelegateeditor.cpp b/source/src/tagtreedelegateeditor.cpp old mode 100644 new mode 100755 index a6e6d2b..eaccab9 --- a/source/src/tagtreedelegateeditor.cpp +++ b/source/src/tagtreedelegateeditor.cpp @@ -1,23 +1,25 @@ #include "tagtreedelegateeditor.h" -#include -#include -#include -#include -#include -#include -#include "pushbuttontype.h" -#include "nodetreemodel.h" -#include "nodetreeview.h" -#include "labeledittype.h" -#include "notelistview.h" -#include "fontloader.h" +#include // 包含水平布局类 +#include // 包含标签类 +#include // 包含用于绘制的类 +#include // 包含用于调试输出的类 +#include // 包含树形视图类 +#include // 包含鼠标事件类 +#include "pushbuttontype.h" // 包含自定义按钮类型 +#include "nodetreemodel.h" // 包含节点树模型类 +#include "nodetreeview.h" // 包含节点树视图类 +#include "labeledittype.h" // 包含自定义标签编辑类型 +#include "notelistview.h" // 包含笔记列表视图类 +#include "fontloader.h" // 包含字体加载器类 +// TagTreeDelegateEditor类的构造函数 TagTreeDelegateEditor::TagTreeDelegateEditor(QTreeView *view, const QStyleOptionViewItem &option, const QModelIndex &index, QListView *listView, QWidget *parent) - : QWidget(parent), - m_option(option), - m_index(index), + : QWidget(parent), // 调用父类构造函数 + m_option(option), // 保存样式选项 + m_index(index), // 保存模型索引 + // 根据操作系统设置默认字体 #ifdef __APPLE__ m_displayFont(QFont(QStringLiteral("SF Pro Text")).exactMatch() ? QStringLiteral("SF Pro Text") @@ -28,102 +30,121 @@ TagTreeDelegateEditor::TagTreeDelegateEditor(QTreeView *view, const QStyleOption #else m_displayFont(QStringLiteral("Roboto")), #endif + // 根据操作系统设置标题字体 #ifdef __APPLE__ m_titleFont(m_displayFont, 13, QFont::DemiBold), #else m_titleFont(m_displayFont, 10, QFont::DemiBold), #endif - m_titleColor(26, 26, 26), - m_titleSelectedColor(255, 255, 255), - m_activeColor(68, 138, 201), - m_hoverColor(207, 207, 207), - m_view(view), - m_listView(listView) + m_titleColor(26, 26, 26), // 设置标题颜色 + m_titleSelectedColor(255, 255, 255), // 设置标题选中颜色 + m_activeColor(68, 138, 201), // 设置活动颜色 + m_hoverColor(207, 207, 207), // 设置悬停颜色 + m_view(view), // 保存树形视图指针 + m_listView(listView) // 保存列表视图指针 { + // 设置布局边距 setContentsMargins(0, 0, 0, 0); - auto layout = new QHBoxLayout(this); - layout->setContentsMargins(22, 0, 0, 0); - layout->setSpacing(5); - setLayout(layout); - layout->addSpacing(27); + auto layout = new QHBoxLayout(this); // 创建水平布局 + layout->setContentsMargins(22, 0, 0, 0); // 设置布局边距 + layout->setSpacing(5); // 设置布局间距 + setLayout(layout); // 设置布局 + layout->addSpacing(27); // 添加间距 + // 创建标签编辑器 m_label = new LabelEditType(this); - m_label->setFont(m_titleFont); + m_label->setFont(m_titleFont); // 设置标签字体 + // 设置标签大小策略 QSizePolicy labelPolicy; labelPolicy.setVerticalPolicy(QSizePolicy::Expanding); labelPolicy.setHorizontalPolicy(QSizePolicy::Expanding); m_label->setSizePolicy(labelPolicy); - m_label->setAlignment(Qt::AlignLeft | Qt::AlignVCenter); + m_label->setAlignment(Qt::AlignLeft | Qt::AlignVCenter); // 设置标签对齐方式 + // 连接信号和槽 connect(m_label, &LabelEditType::editingStarted, this, [this] { auto tree_view = dynamic_cast(m_view); - tree_view->setIsEditing(true); + tree_view->setIsEditing(true); // 设置树形视图为编辑状态 }); connect(m_label, &LabelEditType::editingFinished, this, [this](const QString &label) { auto tree_view = dynamic_cast(m_view); - tree_view->onRenameTagFinished(label); - tree_view->setIsEditing(false); + tree_view->onRenameTagFinished(label); // 完成重命名操作 + tree_view->setIsEditing(false); // 设置树形视图为非编辑状态 }); connect(dynamic_cast(m_view), &NodeTreeView::renameTagRequested, m_label, - &LabelEditType::openEditor); - layout->addWidget(m_label); + &LabelEditType::openEditor); // 连接重命名请求信号 + layout->addWidget(m_label); // 将标签添加到布局中 + + // 创建上下文按钮 m_contextButton = new PushButtonType(parent); - m_contextButton->setMaximumSize({ 33, 25 }); - m_contextButton->setMinimumSize({ 33, 25 }); - m_contextButton->setCursor(QCursor(Qt::PointingHandCursor)); - m_contextButton->setFocusPolicy(Qt::TabFocus); - m_contextButton->setIconSize(QSize(16, 16)); - if (m_view->selectionModel()->isSelected(m_index)) { - m_contextButton->setStyleSheet(QStringLiteral(R"(QPushButton { )" - R"( border: none; )" - R"( padding: 0px; )" - R"( color: white; )" - R"(})" - R"(QPushButton:pressed { )" - R"( border: none; )" - R"( padding: 0px; )" - R"( color: rgb(210, 210, 210); )" - R"(})")); - } else { - m_contextButton->setStyleSheet(QStringLiteral(R"(QPushButton { )" - R"( border: none; )" - R"( padding: 0px; )" - R"( color: rgb(68, 138, 201); )" - R"(})" - R"(QPushButton:pressed { )" - R"( border: none; )" - R"( padding: 0px; )" - R"( color: rgb(39, 85, 125); )" - R"(})")); - } + m_contextButton->setMaximumSize({ 33, 25 }); // 设置按钮最大尺寸 + m_contextButton->setMinimumSize({ 33, 25 }); // 设置按钮最小尺寸 + m_contextButton->setCursor(QCursor(Qt::PointingHandCursor)); // 设置鼠标样式 + m_contextButton->setFocusPolicy(Qt::TabFocus); // 设置焦点策略 + m_contextButton->setIconSize(QSize(16, 16)); // 设置图标尺寸 + // 根据选中状态设置按钮样式 + if (m_view->selectionModel()-> +// ... 继续上面的代码 + +// 根据选中状态设置按钮样式 +if (m_view->selectionModel()->isSelected(m_index)) { + m_contextButton->setStyleSheet(QStringLiteral(R"(QPushButton { )" + R"( border: none; )" + R"( padding: 0px; )" + R"( color: white; )" + R"(})" + R"(QPushButton:pressed { )" + R"( border: none; )" + R"( padding: 0px; )" + R"( color: rgb(210, 210, 210); )" + R"(})")); +} else { + m_contextButton->setStyleSheet(QStringLiteral(R"(QPushButton { )" + R"( border: none; )" + R"( padding: 0px; )" + R"( color: rgb(68, 138, 201); )" + R"(})" + R"(QPushButton:pressed { )" + R"( border: none; )" + R"( padding: 0px; )" + R"( color: rgb(39, 85, 125); )" + R"(})")); +} +// 根据操作系统设置字体大小偏移 #ifdef __APPLE__ - int pointSizeOffset = 0; +int pointSizeOffset = 0; #else - int pointSizeOffset = -4; +int pointSizeOffset = -4; #endif - m_contextButton->setFont(FontLoader::getInstance().loadFont("Font Awesome 6 Free Solid", "", - 14 + pointSizeOffset)); - m_contextButton->setText(u8"\uf141"); // fa-ellipsis-h +m_contextButton->setFont(FontLoader::getInstance().loadFont("Font Awesome 6 Free Solid", "", + 14 + pointSizeOffset)); +m_contextButton->setText(u8"\uf141"); // 设置按钮图标为三条横线 - connect(m_contextButton, &QPushButton::clicked, m_view, [this](bool) { - auto tree_view = dynamic_cast(m_view); - if (!m_view->selectionModel()->selectedIndexes().contains(m_index)) { - tree_view->setCurrentIndexC(m_index); - } - tree_view->onCustomContextMenu(tree_view->visualRect(m_index).topLeft() - + m_contextButton->geometry().bottomLeft()); - }); - layout->addWidget(m_contextButton, 0, Qt::AlignRight); - layout->addSpacing(5); - connect(m_view, &QTreeView::expanded, this, [this](const QModelIndex &) { update(); }); +// 连接按钮点击信号到树形视图的上下文菜单槽 +connect(m_contextButton, &QPushButton::clicked, m_view, [this](bool) { + auto tree_view = dynamic_cast(m_view); + if (!m_view->selectionModel()->selectedIndexes().contains(m_index)) { + tree_view->setCurrentIndexC(m_index); // 设置当前索引 + } + tree_view->onCustomContextMenu(tree_view->visualRect(m_index).topLeft() + + m_contextButton->geometry().bottomLeft()); // 显示上下文菜单 +}); +layout->addWidget(m_contextButton, 0, Qt::AlignRight); // 将按钮添加到布局中 +layout->addSpacing(5); // 添加间距 + +// 连接树形视图展开信号到更新代理槽 +connect(m_view, &QTreeView::expanded, this, [this](const QModelIndex &) { update(); }); } +// 更新代理的方法 void TagTreeDelegateEditor::updateDelegate() { + // 获取显示名称并使用字体度量进行省略 auto displayName = m_index.data(NodeItem::Roles::DisplayText).toString(); QFontMetrics fm(m_titleFont); displayName = fm.elidedText(displayName, Qt::ElideRight, m_label->contentsRect().width()); + // 根据选中状态设置标签样式 if (m_view->selectionModel()->selectedIndexes().contains(m_index)) { m_label->setStyleSheet(QStringLiteral("QLabel{color: rgb(%1, %2, %3);}") .arg(QString::number(m_titleSelectedColor.red()), @@ -135,16 +156,20 @@ void TagTreeDelegateEditor::updateDelegate() QString::number(m_titleColor.green()), QString::number(m_titleColor.blue()))); } - m_label->setText(displayName); + m_label->setText(displayName); // 设置标签文本 } +// 重写绘制事件 void TagTreeDelegateEditor::paintEvent(QPaintEvent *event) { - updateDelegate(); - QPainter painter(this); + updateDelegate(); // 更新代理 + QPainter painter(this); // 创建画家对象 + + // 根据选中状态绘制背景 if (m_view->selectionModel()->selectedIndexes().contains(m_index)) { painter.fillRect(rect(), QBrush(m_activeColor)); } else { + // 根据拖拽状态和主题绘制背景 auto listView = dynamic_cast(m_listView); if (listView->isDragging()) { if (m_theme == Theme::Dark) { @@ -157,50 +182,50 @@ void TagTreeDelegateEditor::paintEvent(QPaintEvent *event) } } + // 绘制标签颜色图标 auto iconRect = QRect(rect().x() + 22, rect().y() + (rect().height() - 14) / 2, 16, 16); auto tagColor = m_index.data(NodeItem::Roles::TagColor).toString(); - painter.setPen(QColor(tagColor)); -#ifdef __APPLE__ - int iconPointSizeOffset = 0; -#else - int iconPointSizeOffset = -4; -#endif - painter.setFont(FontLoader::getInstance().loadFont("Font Awesome 6 Free Solid", "", - 16 + iconPointSizeOffset)); - painter.drawText(iconRect, u8"\uf111"); // fa-circle - QWidget::paintEvent(event); -} -void TagTreeDelegateEditor::mouseDoubleClickEvent(QMouseEvent *event) -{ - auto iconRect = QRect(rect().x() + 10, rect().y() + (rect().height() - 14) / 2, 14, 14); - if (iconRect.contains(event->pos())) { - dynamic_cast(m_view)->onChangeTagColorAction(); - } else if (m_label->geometry().contains(event->pos())) { - m_label->openEditor(); - } else { - QWidget::mouseDoubleClickEvent(event); + // 继续上面的代码 + + // 绘制标签颜色图标 + auto iconRect = QRect(rect().x() + 22, rect().y() + (rect().height() - 14) / 2, 16, 16); + auto tagColor = m_index.data(NodeItem::Roles::TagColor).toString(); + if (!tagColor.isEmpty()) { + QColor color(tagColor); + painter.setPen(Qt::NoPen); + painter.setBrush(color); + painter.drawEllipse(iconRect); } + + // 绘制标签文本 + auto textRect = QRect(iconRect.right() + 12, rect().y(), rect().width() - iconRect.right() - 12, + rect().height()); + QFontMetrics metrics(m_titleFont); + auto text = metrics.elidedText(m_index.data(NodeItem::Roles::DisplayText).toString(), + Qt::ElideRight, textRect.width()); + painter.setFont(m_titleFont); + painter.setPen(m_titleColor); + painter.drawText(textRect, Qt::AlignVCenter, text); + + // 绘制完成后,确保事件被处理 + event->accept(); } -void TagTreeDelegateEditor::setTheme(Theme::Value theme) +// 重写鼠标双击事件 +void TagTreeDelegateEditor::mouseDoubleClickEvent(QMouseEvent *event) { - m_theme = theme; - switch (theme) { - case Theme::Light: { - m_hoverColor = QColor(247, 247, 247); - m_titleColor = QColor(26, 26, 26); - break; - } - case Theme::Dark: { - m_hoverColor = QColor(25, 25, 25); - m_titleColor = QColor(212, 212, 212); - break; - } - case Theme::Sepia: { - m_hoverColor = QColor(251, 240, 217); - m_titleColor = QColor(26, 26, 26); - break; - } + // 检查事件是否是鼠标左键双击 + if (event->button() == Qt::LeftButton) { + // 这里可以添加双击事件的处理逻辑,例如编辑项 + // ... } + + // 确保事件被处理 + event->accept(); } + +// 其他可能的类成员和方法声明 +// ... + +#endif // TAGTREEDELEGATEEDITORH diff --git a/source/src/tagtreedelegateeditor.h b/source/src/tagtreedelegateeditor.h old mode 100644 new mode 100755 index 5d124ca..f551088 --- a/source/src/tagtreedelegateeditor.h +++ b/source/src/tagtreedelegateeditor.h @@ -1,46 +1,54 @@ #ifndef TAGTREEDELEGATEEDITOR_H #define TAGTREEDELEGATEEDITOR_H -#include -#include -#include -#include -#include "editorsettingsoptions.h" - -class QTreeView; -class QLabel; -class PushButtonType; -class LabelEditType; -class QListView; - -class TagTreeDelegateEditor : public QWidget +#include // 包含QWidget类,所有UI对象的基类 +#include // 包含用于自定义绘图项的选项 +#include // 包含用于操作模型索引的类 +#include // 包含用于操作字体的类 +#include "editorsettingsoptions.h" // 包含自定义的编辑器设置选项 + +class QTreeView; // 前向声明QTreeView类,用于树形视图 +class QLabel; // 前向声明QLabel类,用于显示文本 +class PushButtonType; // 前向声明自定义按钮类型 +class LabelEditType; // 前向声明自定义标签编辑类型 +class QListView; // 前向声明QListView类,用于列表视图 + +class TagTreeDelegateEditor : public QWidget // 定义一个自定义代理编辑器类,继承自QWidget { - Q_OBJECT -public: - explicit TagTreeDelegateEditor(QTreeView *view, const QStyleOptionViewItem &option, - const QModelIndex &index, QListView *listView, - QWidget *parent = nullptr); + Q_OBJECT // 宏,用于声明元对象系统支持 + + public : + // 构造函数,接收树形视图、样式选项、模型索引、列表视图和父窗口指针 + explicit TagTreeDelegateEditor(QTreeView *view, const QStyleOptionViewItem &option, + const QModelIndex &index, QListView *listView, + QWidget *parent = nullptr); + + // 设置主题的函数 void setTheme(Theme::Value theme); private: - QStyleOptionViewItem m_option; - QModelIndex m_index; - QString m_displayFont; - QFont m_titleFont; - QColor m_titleColor; - QColor m_titleSelectedColor; - QColor m_activeColor; - QColor m_hoverColor; - QTreeView *m_view; - QListView *m_listView; - LabelEditType *m_label; - PushButtonType *m_contextButton; - Theme::Value m_theme; + QStyleOptionViewItem m_option; // 保存样式选项 + QModelIndex m_index; // 保存模型索引 + QString m_displayFont; // 保存显示字体 + QFont m_titleFont; // 保存标题字体 + QColor m_titleColor; // 保存标题颜色 + QColor m_titleSelectedColor; // 保存标题选中颜色 + QColor m_activeColor; // 保存活动颜色 + QColor m_hoverColor; // 保存悬停颜色 + QTreeView *m_view; // 保存树形视图指针 + QListView *m_listView; // 保存列表视图指针 + LabelEditType *m_label; // 保存标签编辑类型指针 + PushButtonType *m_contextButton; // 保存上下文按钮类型指针 + Theme::Value m_theme; // 保存当前主题 + + // 更新代理的函数 void updateDelegate(); - // QWidget interface + // QWidget接口重写 protected: + // 重写绘制事件处理函数 virtual void paintEvent(QPaintEvent *event) override; + // 重写鼠标双击事件处理函数 virtual void mouseDoubleClickEvent(QMouseEvent *event) override; }; diff --git a/source/src/trashbuttondelegateeditor.cpp b/source/src/trashbuttondelegateeditor.cpp old mode 100644 new mode 100755 index 099f2e6..1e278c6 --- a/source/src/trashbuttondelegateeditor.cpp +++ b/source/src/trashbuttondelegateeditor.cpp @@ -1,4 +1,4 @@ -//ͷļ +// ����ͷ�ļ� #include "trashbuttondelegateeditor.h" #include #include @@ -8,8 +8,8 @@ #include "notelistview.h" #include "fontloader.h" -// TrashButtonDelegateEditor Ĺ캯 -// ͼʽѡбͼ͸ +// TrashButtonDelegateEditor ��Ĺ��캯�� +// ����������ͼ����ʽѡ��������б���ͼ�͸����� TrashButtonDelegateEditor::TrashButtonDelegateEditor(QTreeView *view, const QStyleOptionViewItem &option, const QModelIndex &index, QListView *listView, @@ -18,24 +18,24 @@ TrashButtonDelegateEditor::TrashButtonDelegateEditor(QTreeView *view, m_option(option), m_index(index), #ifdef __APPLE__ - // ƻϵͳʹ SF Pro Text 壬ûʹ Roboto + // ��ƻ��ϵͳ��ʹ�� SF Pro Text ���壬���û����ʹ�� Roboto m_displayFont(QFont(QStringLiteral("SF Pro Text")).exactMatch() ? QStringLiteral("SF Pro Text") : QStringLiteral("Roboto")), #elif _WIN32 - // Windows ϵͳʹ Segoe UI 壬ûʹ Roboto + // �� Windows ϵͳ��ʹ�� Segoe UI ���壬���û����ʹ�� Roboto m_displayFont(QFont(QStringLiteral("Segoe UI")).exactMatch() ? QStringLiteral("Segoe UI") : QStringLiteral("Roboto")), #else - // ϵͳʹ Roboto + // ������ϵͳ��ʹ�� Roboto ���� m_displayFont(QStringLiteral("Roboto")), #endif #ifdef __APPLE__ - // ƻϵͳñͱʼС + // ��ƻ��ϵͳ�����ñ���ͱʼ������������С m_titleFont(m_displayFont, 13, QFont::DemiBold), m_numberOfNotesFont(m_displayFont, 12, QFont::DemiBold), #else - // ϵͳñͱʼС + // ������ϵͳ�����ñ���ͱʼ������������С m_titleFont(m_displayFont, 10, QFont::DemiBold), m_numberOfNotesFont(m_displayFont, 9, QFont::DemiBold), #endif @@ -49,22 +49,23 @@ TrashButtonDelegateEditor::TrashButtonDelegateEditor(QTreeView *view, m_view(view), m_listView(listView) { - // ݱ߾Ϊ0 + // �������ݱ߾�Ϊ0 setContentsMargins(0, 0, 0, 0); } -// ¼ +// �����¼��������� +// 绘制事件处理 void TrashButtonDelegateEditor::paintEvent(QPaintEvent *event) { QPainter painter(this); - // ͼ + // ����ͼ������ auto iconRect = QRect(rect().x() + 22, rect().y() + 2 + (rect().height() - 20) / 2, 18, 20); auto iconPath = m_index.data(NodeItem::Roles::Icon).toString(); auto displayName = m_index.data(NodeItem::Roles::DisplayText).toString(); QRect nameRect(rect()); nameRect.setLeft(iconRect.x() + iconRect.width() + 5); nameRect.setWidth(nameRect.width() - 22 - 40); - // Ƿѡñɫıɫ + // �����Ƿ�ѡ�����ñ�����ɫ���ı���ɫ if (m_view->selectionModel()->isSelected(m_index)) { painter.fillRect(rect(), QBrush(m_activeColor)); painter.setPen(m_titleSelectedColor); @@ -86,12 +87,12 @@ void TrashButtonDelegateEditor::paintEvent(QPaintEvent *event) #else int iconPointSizeOffset = -4; #endif - // ͼ + // ����ͼ������ painter.setFont(FontLoader::getInstance().loadFont("Font Awesome 6 Free Solid", "", 16 + iconPointSizeOffset)); painter.drawText(iconRect, iconPath); // fa-trash - // Ʊı + // ���Ʊ����ı� if (m_view->selectionModel()->isSelected(m_index)) { painter.setPen(m_titleSelectedColor); } else { @@ -100,12 +101,12 @@ void TrashButtonDelegateEditor::paintEvent(QPaintEvent *event) painter.setFont(m_titleFont); painter.drawText(nameRect, Qt::AlignLeft | Qt::AlignVCenter, displayName); - // + // ���������������� auto childCountRect = rect(); childCountRect.setLeft(nameRect.right() + 22); childCountRect.setWidth(childCountRect.width() - 5); auto childCount = m_index.data(NodeItem::Roles::ChildCount).toInt(); - // Ƿѡıɫ + // �����Ƿ�ѡ���������������ı���ɫ if (m_view->selectionModel()->isSelected(m_index)) { painter.setPen(m_numberOfNotesSelectedColor); } else { @@ -117,7 +118,8 @@ void TrashButtonDelegateEditor::paintEvent(QPaintEvent *event) QWidget::paintEvent(event); } -// ⺯ +// �������⺯�� +// 设置主题 void TrashButtonDelegateEditor::setTheme(Theme::Value theme) { m_theme = theme; @@ -141,4 +143,4 @@ void TrashButtonDelegateEditor::setTheme(Theme::Value theme) break; } } -} +} \ No newline at end of file diff --git a/source/src/trashbuttondelegateeditor.h b/source/src/trashbuttondelegateeditor.h old mode 100644 new mode 100755 index 3040037..72601a1 --- a/source/src/trashbuttondelegateeditor.h +++ b/source/src/trashbuttondelegateeditor.h @@ -10,39 +10,39 @@ class QTreeView; class QListView; -// TrashButtonDelegateEditor +// TrashButtonDelegateEditor ������ class TrashButtonDelegateEditor : public QWidget { Q_OBJECT public: - // 캯 + // ���캯�� explicit TrashButtonDelegateEditor(QTreeView *view, const QStyleOptionViewItem &option, const QModelIndex &index, QListView *listView, QWidget *parent = nullptr); - // ⺯ + // �������⺯�� void setTheme(Theme::Value theme); private: - QStyleOptionViewItem m_option; - QModelIndex m_index; - QString m_displayFont; - QFont m_titleFont; - QFont m_numberOfNotesFont; - QColor m_titleColor; - QColor m_titleSelectedColor; - QColor m_activeColor; - QColor m_hoverColor; - QColor m_folderIconColor; - QColor m_numberOfNotesColor; - QColor m_numberOfNotesSelectedColor; - QTreeView *m_view; - QListView *m_listView; - Theme::Value m_theme; + QStyleOptionViewItem m_option; // 存储视图项的样式选项 + QModelIndex m_index; // 存储模型索引 + QString m_displayFont; // 显示字体 + QFont m_titleFont; // 标题字体 + QFont m_numberOfNotesFont; // 备注字体 + QColor m_titleColor; // 标题颜色 + QColor m_titleSelectedColor; // 标题选中颜色 + QColor m_activeColor; // 激活状态颜色 + QColor m_hoverColor; // 悬停状态颜色 + QColor m_folderIconColor; // 文件夹图标颜色 + QColor m_numberOfNotesColor; // 备注颜色 + QColor m_numberOfNotesSelectedColor; // 备注选中颜色 + QTreeView *m_view; // 视图指针 + QListView *m_listView; // 列表视图指针 + Theme::Value m_theme; // 主题值 // QWidget interface - // QWidget ӿ + // QWidget �ӿ� protected: - // ¼ - virtual void paintEvent(QPaintEvent *event) override; + // �����¼��������� + virtual void paintEvent(QPaintEvent *event) override; // 绘制事件 }; -#endif // TRASHBUTTONDELEGATEEDITOR_H +#endif // TRASHBUTTONDELEGATEEDITOR_H \ No newline at end of file diff --git a/source/src/treeviewlogic.cpp b/source/src/treeviewlogic.cpp old mode 100644 new mode 100755 index 7b5871f..af1604b --- a/source/src/treeviewlogic.cpp +++ b/source/src/treeviewlogic.cpp @@ -1,4 +1,4 @@ -// ͷļ +/// ����ͷ�ļ� #include "treeviewlogic.h" #include "nodetreeview.h" #include "nodetreemodel.h" @@ -12,7 +12,8 @@ #include #include "customapplicationstyle.h" -// TreeViewLogic Ĺ캯 +// TreeViewLogic ��Ĺ��캯�� +// 管理树视图的逻辑,包括节点的增删改查和更新 TreeViewLogic::TreeViewLogic(NodeTreeView *treeView, NodeTreeModel *treeModel, DBManager *dbManager, NoteListView *listView, QObject *parent) : QObject(parent), @@ -26,16 +27,16 @@ TreeViewLogic::TreeViewLogic(NodeTreeView *treeView, NodeTreeModel *treeModel, D m_lastSelectTags{}, m_expandedFolder{} { - // ʼͼ + // ��ʼ������ͼ���� m_treeDelegate = new NodeTreeDelegate(m_treeView, m_treeView, m_listView); m_treeView->setItemDelegate(m_treeDelegate); - // ݿź + // �������ݿ�������ź� connect(m_dbManager, &DBManager::nodesTagTreeReceived, this, &TreeViewLogic::loadTreeModel, Qt::QueuedConnection); - // ģź + // ������ģ���ź� connect(m_treeModel, &NodeTreeModel::topLevelItemLayoutChanged, this, &TreeViewLogic::updateTreeViewSeparator); - // ͼź + // ��������ͼ�ź� connect(m_treeView, &NodeTreeView::addFolderRequested, this, [this] { onAddFolderRequested(false); }); connect(m_treeDelegate, &NodeTreeDelegate::addFolderRequested, this, @@ -84,23 +85,25 @@ TreeViewLogic::TreeViewLogic(NodeTreeView *treeView, NodeTreeModel *treeModel, D &TreeViewLogic::onChildNoteCountChangedFolder); connect(m_dbManager, &DBManager::childNotesCountUpdatedTag, this, &TreeViewLogic::onChildNotesCountChangedTag); - // Ӧʽ + // ����Ӧ����ʽ m_style = new CustomApplicationStyle(); qApp->setStyle(m_style); } -// ͼָ +// ��������ͼ�ָ��� +// 更新树视图的分隔符 void TreeViewLogic::updateTreeViewSeparator() { m_treeView->setTreeSeparator(m_treeModel->getSeparatorIndex(), m_treeModel->getDefaultNotesIndex()); } -// ģ +// ������ģ�� +// 加载树模型的数据 void TreeViewLogic::loadTreeModel(const NodeTagTreeData &treeData) { m_treeModel->setTreeData(treeData); - // ȡڵӽڵ + // ��ȡ���ڵ���ӽڵ����� { NodeData node; QMetaObject::invokeMethod(m_dbManager, "getChildNotesCountFolder", @@ -111,7 +114,7 @@ void TreeViewLogic::loadTreeModel(const NodeTagTreeData &treeData) m_treeModel->setData(index, node.childNotesCount(), NodeItem::Roles::ChildCount); } } - // ȡڵӽڵ + // ��ȡ������ڵ���ӽڵ����� { NodeData node; QMetaObject::invokeMethod(m_dbManager, "getChildNotesCountFolder", @@ -122,7 +125,7 @@ void TreeViewLogic::loadTreeModel(const NodeTagTreeData &treeData) m_treeModel->setData(index, node.childNotesCount(), NodeItem::Roles::ChildCount); } } - // ر״̬ + // ���ر����״̬ if (m_needLoadSavedState) { m_needLoadSavedState = false; m_treeView->reExpandC(m_expandedFolder); @@ -154,7 +157,8 @@ void TreeViewLogic::loadTreeModel(const NodeTagTreeData &treeData) updateTreeViewSeparator(); } -// ļ +// ���������ļ������� +// 添加文件夹的请求处理 void TreeViewLogic::onAddFolderRequested(bool fromPlusButton) { QModelIndex currentIndex; @@ -175,7 +179,7 @@ void TreeViewLogic::onAddFolderRequested(bool fromPlusButton) static_cast(currentIndex.data(NodeItem::Roles::ItemType).toInt()); if (type == NodeItem::FolderItem) { parentId = currentIndex.data(NodeItem::Roles::NodeId).toInt(); - // Ĭϱʼļ´ļ + // ��������Ĭ�ϱʼ��ļ����´������ļ��� if (parentId == SpecialNodeID::DefaultNotesFolder) { parentId = SpecialNodeID::RootFolder; } @@ -248,13 +252,14 @@ void TreeViewLogic::onAddFolderRequested(bool fromPlusButton) } } -// ӱǩ +// �������ӱ�ǩ���� +// 处理添加标签请求 void TreeViewLogic::onAddTagRequested() { int newlyCreatedTagId; TagData newTag; newTag.setName(m_treeModel->getNewTagPlaceholderName()); - // ɫ + // �����ɫ������ const double lower_bound = 0; const double upper_bound = 1; static std::uniform_real_distribution unif(lower_bound, upper_bound); @@ -278,7 +283,8 @@ void TreeViewLogic::onAddTagRequested() m_treeModel->appendChildNodeToParent(m_treeModel->rootIndex(), hs); } -// ڵ +// �����������ڵ����� +// 处理从树视图请求重命名节点 void TreeViewLogic::onRenameNodeRequestedFromTreeView(const QModelIndex &index, const QString &newName) { @@ -287,7 +293,8 @@ void TreeViewLogic::onRenameNodeRequestedFromTreeView(const QModelIndex &index, emit requestRenameNodeInDB(id, newName); } -// ɾļ +// ����ɾ���ļ������� +// 处理删除文件夹的请求 void TreeViewLogic::onDeleteFolderRequested(const QModelIndex &index) { auto btn = QMessageBox::question(nullptr, "Are you sure you want to delete this folder", @@ -319,7 +326,8 @@ void TreeViewLogic::onDeleteFolderRequested(const QModelIndex &index) } } -// ǩ +// ������������ǩ���� +// 处理从树视图请求重命名标签 void TreeViewLogic::onRenameTagRequestedFromTreeView(const QModelIndex &index, const QString &newName) { @@ -328,7 +336,8 @@ void TreeViewLogic::onRenameTagRequestedFromTreeView(const QModelIndex &index, emit requestRenameTagInDB(id, newName); } -// ޸ıǩɫ +// �����޸ı�ǩ��ɫ���� +// 处理颜色请求的标签 void TreeViewLogic::onChangeTagColorRequested(const QModelIndex &index) { if (index.isValid()) { @@ -342,7 +351,8 @@ void TreeViewLogic::onChangeTagColorRequested(const QModelIndex &index) } } -// ɾǩ +// ����ɾ����ǩ���� +// 处理删除标签的请求 void TreeViewLogic::onDeleteTagRequested(const QModelIndex &index) { auto id = index.data(NodeItem::Roles::NodeId).toInt(); @@ -351,7 +361,8 @@ void TreeViewLogic::onDeleteTagRequested(const QModelIndex &index) m_treeView->setCurrentIndexC(m_treeModel->getAllNotesButtonIndex()); } -// ǩӽڵ仯 +// ������ǩ�ӽڵ������仯 +// 更新标签的子项数量 void TreeViewLogic::onChildNotesCountChangedTag(int tagId, int notesCount) { auto index = m_treeModel->tagIndexFromId(tagId); @@ -360,7 +371,8 @@ void TreeViewLogic::onChildNotesCountChangedTag(int tagId, int notesCount) } } -// ļӽڵ仯 +// �����ļ����ӽڵ������仯 +// 更新文件夹的子项数量 void TreeViewLogic::onChildNoteCountChangedFolder(int folderId, const QString &absPath, int notesCount) { @@ -377,7 +389,8 @@ void TreeViewLogic::onChildNoteCountChangedFolder(int folderId, const QString &a } } -// ļ +// ���ļ��� +// 打开指定文件夹 void TreeViewLogic::openFolder(int id) { NodeData target; @@ -401,7 +414,8 @@ void TreeViewLogic::openFolder(int id) } } -// ƶڵ +// �����ƶ��ڵ����� +// 处理移动节点的请求 void TreeViewLogic::onMoveNodeRequested(int nodeId, int targetId) { NodeData target; @@ -414,7 +428,8 @@ void TreeViewLogic::onMoveNodeRequested(int nodeId, int targetId) emit requestMoveNodeInDB(nodeId, target); } -// +// �������� +// 设置主题 void TreeViewLogic::setTheme(Theme::Value theme) { m_treeView->setTheme(theme); @@ -422,7 +437,8 @@ void TreeViewLogic::setTheme(Theme::Value theme) m_style->setTheme(theme); } -// 󱣴״̬ +// ������󱣴��״̬ +// 设置最后保存的状态 void TreeViewLogic::setLastSavedState(bool isLastSelectFolder, const QString &lastSelectFolder, const QSet &lastSelectTag, const QStringList &expandedFolder) @@ -432,4 +448,4 @@ void TreeViewLogic::setLastSavedState(bool isLastSelectFolder, const QString &la m_lastSelectTags = lastSelectTag; m_expandedFolder = expandedFolder; m_needLoadSavedState = true; -} +} \ No newline at end of file diff --git a/source/src/treeviewlogic.h b/source/src/treeviewlogic.h old mode 100644 new mode 100755 index fa37b4a..3797a51 --- a/source/src/treeviewlogic.h +++ b/source/src/treeviewlogic.h @@ -12,76 +12,86 @@ class DBManager; class CustomApplicationStyle; class NoteListView; -// TreeViewLogic ฺͼ߼ +// TreeViewLogic 类负责管理树形视图的逻辑 class TreeViewLogic : public QObject { Q_OBJECT public: - // 캯 - explicit TreeViewLogic(NodeTreeView* treeView, NodeTreeModel* treeModel, DBManager* dbManager, - NoteListView* listView, QObject* parent = nullptr); - // ļ + // 构造函数 + explicit TreeViewLogic(NodeTreeView *treeView, NodeTreeModel *treeModel, DBManager *dbManager, + NoteListView *listView, QObject *parent = nullptr); + // 打开文件夹 void openFolder(int id); - // ƶڵ + // 请求移动节点 void onMoveNodeRequested(int nodeId, int targetId); - // + // 设置主题 void setTheme(Theme::Value theme); - // 󱣴״̬ - void setLastSavedState(bool isLastSelectFolder, const QString& lastSelectFolder, - const QSet& lastSelectTag, const QStringList& expandedFolder); + // 设置最后保存的状态 + void setLastSavedState(bool isLastSelectFolder, const QString &lastSelectFolder, + const QSet &lastSelectTag, const QStringList &expandedFolder); private slots: - // ͼָ + // 更新树视图分隔符 void updateTreeViewSeparator(); - // ģ - void loadTreeModel(const NodeTagTreeData& treeData); - // ӱǩ + // 加载树模型 + void loadTreeModel(const NodeTagTreeData &treeData); + // 请求添加标签 void onAddTagRequested(); - // ڵ - void onRenameNodeRequestedFromTreeView(const QModelIndex& index, const QString& newName); - // ɾļ - void onDeleteFolderRequested(const QModelIndex& index); - // ǩ - void onRenameTagRequestedFromTreeView(const QModelIndex& index, const QString& newName); - // ޸ıǩɫ - void onChangeTagColorRequested(const QModelIndex& index); - // ɾǩ - void onDeleteTagRequested(const QModelIndex& index); - // ǩӽڵ仯 + // 请求重命名树视图中的节点 + void onRenameNodeRequestedFromTreeView(const QModelIndex &index, const QString &newName); + // 请求删除文件夹 + void onDeleteFolderRequested(const QModelIndex &index); + // 请求重命名树视图中的标签 + void onRenameTagRequestedFromTreeView(const QModelIndex &index, const QString &newName); + // 请求更改标签颜色 + void onChangeTagColorRequested(const QModelIndex &index); + // 请求删除标签 + void onDeleteTagRequested(const QModelIndex &index); + // 标签的子笔记数量变化 void onChildNotesCountChangedTag(int tagId, int notesCount); - // ļӽڵ仯 - void onChildNoteCountChangedFolder(int folderId, const QString& absPath, int notesCount); + // 文件夹的子笔记数量变化 + void onChildNoteCountChangedFolder(int folderId, const QString &absPath, int notesCount); signals: - // ڵ - void requestRenameNodeInDB(int id, const QString& newName); - // ǩ - void requestRenameTagInDB(int id, const QString& newName); - // ޸ıǩɫ - void requestChangeTagColorInDB(int id, const QString& newColor); - // ƶڵ - void requestMoveNodeInDB(int id, const NodeData& target); - // ӱʼǵǩ + // 请求在数据库中重命名节点 + void requestRenameNodeInDB(int id, const QString &newName); + // 请求在数据库中重命名标签 + void requestRenameTagInDB(int id, const QString &newName); + // 请求在数据库中更改标签颜色 + void requestChangeTagColorInDB(int id, const QString &newColor); + // 请求在数据库中移动节点 + void requestMoveNodeInDB(int id, const NodeData &target); + // 向标签添加笔记 void addNoteToTag(int noteId, int tagId); - // ڵƶ + // 通知节点已移动 void noteMoved(int nodeId, int targetId); private: - // ļ + // 请求添加文件夹 void onAddFolderRequested(bool fromPlusButton); private: - // Ա - NodeTreeView* m_treeView; - NodeTreeModel* m_treeModel; - NoteListView* m_listView; - NodeTreeDelegate* m_treeDelegate; - DBManager* m_dbManager; - CustomApplicationStyle* m_style; + // 节点树视图 + NodeTreeView *m_treeView; + // 节点树模型 + NodeTreeModel *m_treeModel; + // 笔记列表视图 + NoteListView *m_listView; + // 节点树代理 + NodeTreeDelegate *m_treeDelegate; + // 数据库管理器 + DBManager *m_dbManager; + // 自定义应用样式 + CustomApplicationStyle *m_style; + // 是否需要加载保存的状态 bool m_needLoadSavedState; + // 是否是最后选择的文件夹 bool m_isLastSelectFolder; + // 最后选择的文件夹路径 QString m_lastSelectFolder; + // 最后选择的标签集合 QSet m_lastSelectTags; + // 展开的文件夹列表 QStringList m_expandedFolder; }; diff --git a/source/src/updaterwindow.cpp b/source/src/updaterwindow.cpp old mode 100644 new mode 100755 index 3521c46..16d1a7d --- a/source/src/updaterwindow.cpp +++ b/source/src/updaterwindow.cpp @@ -33,13 +33,13 @@ static QProcess XDGOPEN_PROCESS; #endif /** - * Indicates from where we should download the update definitions file + * 表示从何处下载更新定义文件 */ static const QString UPDATES_URL("https://raw.githubusercontent.com/nuttyartist/notes/master/UPDATES.json"); /** - * Initializes the window components and configures the QSimpleUpdater + * 初始化窗口组件并配置 QSimpleUpdater */ UpdaterWindow::UpdaterWindow(QWidget *parent) : QDialog(parent), @@ -53,21 +53,21 @@ UpdaterWindow::UpdaterWindow(QWidget *parent) m_updater(QSimpleUpdater::getInstance()), m_manager(new QNetworkAccessManager(this)) { - /* Load the stylesheet */ + /* 加载样式表 */ QFile file(":/styles/updater-window.css"); if (file.open(QIODevice::ReadOnly)) { setStyleSheet(QString::fromUtf8(file.readAll()).toLatin1()); file.close(); } - /* Initialize the UI */ + /* 初始化 UI */ m_ui->setupUi(this); #if QT_VERSION < QT_VERSION_CHECK(5, 10, 0) setWindowFlag(Qt::WindowContextHelpButtonHint, false); #endif setWindowTitle(qApp->applicationName() + " " + tr("Updater")); - /* Change fonts */ + /* 更改字体 */ #ifdef __APPLE__ QFont fontToUse = QFont(QStringLiteral("SF Pro Text")).exactMatch() ? QStringLiteral("SF Pro Text") @@ -86,47 +86,50 @@ UpdaterWindow::UpdaterWindow(QWidget *parent) widgetChild->setFont(fontToUse); } - /* Connect UI signals/slots */ + /* 连接 UI 信号/槽 */ connect(m_ui->closeButton, &QPushButton::clicked, this, &UpdaterWindow::close); connect(m_ui->updateButton, &QPushButton::clicked, this, &UpdaterWindow::onDownloadButtonClicked); connect(m_updater, &QSimpleUpdater::checkingFinished, this, &UpdaterWindow::onCheckFinished); connect(m_ui->checkBox, &QCheckBox::toggled, this, &UpdaterWindow::dontShowUpdateWindowChanged); - /* Start the UI loops */ + /* 启动 UI 循环 */ updateTitleLabel(); - /* Remove native window decorations */ + /* 移除原生窗口装饰 */ #if defined(Q_OS_UNIX) && !defined(Q_OS_MACOS) setWindowFlags(windowFlags() | Qt::CustomizeWindowHint | Qt::FramelessWindowHint); #else setWindowFlags(windowFlags() | Qt::CustomizeWindowHint); #endif - /* React when xdg-open finishes (Linux only) */ + /* 当 xdg-open 完成时响应(仅限 Linux) */ #ifdef UseXdgOpen connect(&XDGOPEN_PROCESS, SIGNAL(finished(int)), this, SLOT(onXdgOpenFinished(int))); #endif - /* Set window flags */ + /* 设置窗口标志 */ setWindowModality(Qt::ApplicationModal); } /** - * Deletes the user interface + * 删除用户界面 */ UpdaterWindow::~UpdaterWindow() { - /* Ensure that xdg-open process is closed */ + /* 确保 xdg-open 进程已关闭 */ #ifdef UseXdgOpen if (XDGOPEN_PROCESS.isOpen()) XDGOPEN_PROCESS.close(); #endif - /* Delete UI controls */ + /* 删除 UI 控件 */ delete m_ui; } +/** + * 设置是否显示更新窗口 + */ void UpdaterWindow::setShowWindowDisable(const bool dontShowWindow) { m_dontShowUpdateWindow = dontShowWindow; @@ -134,29 +137,28 @@ void UpdaterWindow::setShowWindowDisable(const bool dontShowWindow) } /** - * Instructs the QSimpleUpdater to download and interpret the updater - * definitions file + * 指示 QSimpleUpdater 下载并解析更新定义文件 */ void UpdaterWindow::checkForUpdates(bool force) { - /* Change the silent flag */ + /* 更改静默标志 */ if (!m_updater->getUpdateAvailable(UPDATES_URL)) { m_checkingForUpdates = true; m_forced = force; - /* Set module properties */ + /* 设置模块属性 */ m_updater->setNotifyOnFinish(UPDATES_URL, false); m_updater->setNotifyOnUpdate(UPDATES_URL, false); m_updater->setDownloaderEnabled(UPDATES_URL, false); m_updater->setUseCustomInstallProcedures(UPDATES_URL, true); m_updater->setModuleVersion(UPDATES_URL, qApp->applicationVersion()); - /* Check for updates */ + /* 检查更新 */ m_updater->checkForUpdates(UPDATES_URL); } - /* Show window if force flag is set */ + /* 如果 force 标志被设置,则显示窗口 */ if (force) { if (!m_updater->getUpdateAvailable(UPDATES_URL)) { m_ui->updateButton->setEnabled(false); @@ -169,65 +171,62 @@ void UpdaterWindow::checkForUpdates(bool force) } /** - * Resets the state, text and information displayed the the UI controls - * to indicate what is happening right now in the QSimpleUpdater + * 重置 UI 控件的状态、文本和信息,以指示 QSimpleUpdater 当前的操作 */ void UpdaterWindow::resetControls() { - /* Reset the button states */ + /* 重置按钮状态 */ m_ui->updateButton->setEnabled(false); - /* Set installed version label */ + /* 设置已安装版本标签 */ m_ui->installedVersion->setText(qApp->applicationVersion()); - /* Set available version label */ + /* 设置可用版本标签 */ m_ui->availableVersion->setText(m_updater->getLatestVersion(UPDATES_URL)); - /* Set title label */ + /* 设置标题标签 */ if (m_updater->getUpdateAvailable(UPDATES_URL)) { m_ui->title->setText(tr("A Newer Version is Available!")); } else { m_ui->title->setText(tr("You're up-to-date!")); } - /* Reset the progress controls */ + /* 重置进度控件 */ m_ui->progressControls->hide(); m_ui->progressBar->setValue(0); m_ui->downloadLabel->setText(tr("Downloading Updates") + "..."); m_ui->timeLabel->setText(tr("Time remaining") + ": " + tr("unknown")); - /* Set changelog text */ + /* 设置更新日志文本 */ QString changelogText = m_updater->getChangelog(UPDATES_URL); m_ui->changelog->setText(changelogText); if (m_ui->changelog->toPlainText().isEmpty()) { m_ui->changelog->setText("

No changelog found...

"); } else { m_ui->changelog->setText(changelogText.append( - "\n")); // Don't know why currently changelog box is disappearing at the bottom, so - // I add a new line to see the text. + "\n")); // 不知道为什么当前更新日志框在底部消失了,所以添加一个新行以查看文本。 } - /* Enable/disable update button */ + /* 启用/禁用更新按钮 */ bool available = m_updater->getUpdateAvailable(UPDATES_URL); bool validOpenUrl = !m_updater->getOpenUrl(UPDATES_URL).isEmpty(); bool validDownUrl = !m_updater->getDownloadUrl(UPDATES_URL).isEmpty(); m_ui->updateButton->setEnabled(available && (validOpenUrl || validDownUrl)); - /* Resize window */ + /* 调整窗口大小 */ bool showAgain = isVisible(); int height = minimumSizeHint().height(); int width = qMax(minimumSizeHint().width(), int(height * 1.2)); resize(QSize(width, height)); - /* Re-show the window(if required)*/ + /* 重新显示窗口(如果需要) */ if (showAgain) { showNormal(); } } /** - * Changes the number of dots of the title label while the QSimpleUpdater - * is downloading and interpreting the update definitions file + * 在 QSimpleUpdater 下载并解析更新定义文件时更改标题标签的点数 */ void UpdaterWindow::updateTitleLabel() { @@ -245,8 +244,7 @@ void UpdaterWindow::updateTitleLabel() } /** - * Updates the text displayed the the UI controls to reflect the information - * obtained by the QSimpleUpdater and shows the dialog + * 更新 UI 控件显示的文本以反映 QSimpleUpdater 获取的信息,并显示对话框 */ void UpdaterWindow::onUpdateAvailable() { @@ -257,7 +255,7 @@ void UpdaterWindow::onUpdateAvailable() } /** - * Initializes the download of the update and disables the 'update' button + * 初始化更新下载并禁用“更新”按钮 */ void UpdaterWindow::onDownloadButtonClicked() { @@ -268,25 +266,23 @@ void UpdaterWindow::onDownloadButtonClicked() } /** - * Initializes the download of the update and configures the connections - * to automatically update the user interface when we receive new data - * from the download/update server + * 初始化更新下载并配置连接以在从下载/更新服务器接收到新数据时自动更新用户界面 */ void UpdaterWindow::startDownload(const QUrl &url) { - /* URL is invalid, try opening web browser */ + /* URL 无效,尝试打开网页浏览器 */ if (url.isEmpty()) { QDesktopServices::openUrl(QUrl(m_updater->getOpenUrl(UPDATES_URL))); return; } - /* Cancel previous download (if any)*/ + /* 取消之前的下载(如果有) */ if (m_reply) { m_reply->abort(); m_reply->deleteLater(); } - /* Start download */ + /* 开始下载 */ m_startTime = QDateTime::currentDateTime().toSecsSinceEpoch(); QNetworkRequest netReq(url); @@ -294,7 +290,7 @@ void UpdaterWindow::startDownload(const QUrl &url) QNetworkRequest::NoLessSafeRedirectPolicy); m_reply = m_manager->get(netReq); - /* Set file name */ + /* 设置文件名 */ m_fileName = m_updater->getDownloadUrl(UPDATES_URL).split("/").last(); if (m_fileName.isEmpty()) { m_fileName = QString("%1_Update_%2.bin") @@ -302,37 +298,37 @@ void UpdaterWindow::startDownload(const QUrl &url) m_updater->getLatestVersion(UPDATES_URL)); } - /* Prepare download directory */ + /* 准备下载目录 */ if (!m_downloadDir.exists()) m_downloadDir.mkpath("."); - /* Remove previous downloads(if any)*/ + /* 删除之前的下载(如果有) */ QFile::remove(m_downloadDir.filePath(m_fileName)); - /* Show UI controls */ + /* 显示 UI 控件 */ m_ui->progressControls->show(); showNormal(); - /* Update UI when download progress changes or download finishes */ + /* 当下载进度变化或下载完成时更新 UI */ connect(m_reply, &QNetworkReply::downloadProgress, this, &UpdaterWindow::updateProgress); connect(m_reply, &QNetworkReply::finished, this, &UpdaterWindow::onDownloadFinished); } /** - * Opens the downloaded file + * 打开下载的文件 */ void UpdaterWindow::openDownload(const QString &file) { - /* File is empty, abort */ + /* 文件为空,中止 */ if (file.isEmpty()) { return; } - /* Change labels */ + /* 更改标签 */ m_ui->downloadLabel->setText(tr("Download finished!")); m_ui->timeLabel->setText(tr("Opening downloaded file") + "..."); - /* Try to open the downloaded file (Windows & Mac) */ + /* 尝试打开下载的文件(Windows 和 Mac) */ #ifndef UseXdgOpen bool openUrl = QDesktopServices::openUrl(QUrl::fromLocalFile(file)); if (!openUrl) { @@ -346,27 +342,25 @@ void UpdaterWindow::openDownload(const QString &file) } #endif - /* On Linux, use xdg-open to know if the file was handled correctly */ + /* 在 Linux 上,使用 xdg-open 来确认文件是否被正确处理 */ #ifdef UseXdgOpen XDGOPEN_PROCESS.start("xdg-open", QStringList() << file); #endif } /** - * Called when the \a QSimpleUpdater notifies us that it downloaded and - * interpreted the update definitions file. + * 当 QSimpleUpdater 通知我们它已下载并解析更新定义文件时调用 * - * This function decides whenever to show the dialog or just notify the user - * that he/she is running the latest version of notes + * 此函数决定是否显示对话框或仅通知用户他/她正在运行最新版本的 notes */ void UpdaterWindow::onCheckFinished(const QString &url) { Q_UNUSED(url) - /* Do not allow the title label to change automatically */ + /* 不允许标题标签自动更改 */ m_checkingForUpdates = false; - /* There is an update available, show the window */ + /* 如果有可用更新,显示窗口 */ if (m_updater->getUpdateAvailable(url) && (UPDATES_URL == url)) { onUpdateAvailable(); } else if (m_forced) { @@ -377,9 +371,8 @@ void UpdaterWindow::onCheckFinished(const QString &url) } /** - * Called when \c xdg-open finishes with the given \a exitCode. - * If \a exitCode is not 0, then we shall try to open the folder in which - * the update file was saved + * 当 xdg-open 以给定的 exitCode 完成时调用 + * 如果 exitCode 不为 0,则尝试打开保存更新文件的文件夹 */ void UpdaterWindow::onXdgOpenFinished(const int exitCode) { @@ -396,13 +389,11 @@ void UpdaterWindow::onXdgOpenFinished(const int exitCode) } /** - * Notifies the user that there's been an error opening the downloaded - * file directly and instructs the operating system to open the folder - * in which the \a file is located + * 通知用户打开下载的文件时出错,并指示操作系统打开文件所在的文件夹 */ void UpdaterWindow::openDownloadFolder(const QString &file) { - /* Notify the user of the problem */ + /* 通知用户问题 */ QString extension = file.split(".").last(); QMessageBox::information(this, tr("Open Error"), tr("It seems that your OS does not have an " @@ -411,30 +402,29 @@ void UpdaterWindow::openDownloadFolder(const QString &file) .arg(extension), QMessageBox::Ok); - /* Get the full path list of the downloaded file */ + /* 获取下载文件的完整路径列表 */ QString native_path = QDir::toNativeSeparators(QDir(file).absolutePath()); QStringList directories = native_path.split(QDir::separator()); - /* Remove file name from list to get the folder of the update file */ + /* 从列表中删除文件名以获取更新文件的文件夹 */ directories.removeLast(); QString path = directories.join(QDir::separator()); - /* Get valid URL and open it */ + /* 获取有效的 URL 并打开它 */ QUrl url = QUrl::fromLocalFile(QDir(path).absolutePath()); QDesktopServices::openUrl(url); } /** - * Calculates the appropriate size units(bytes, KB or MB)for the received - * data and the total download size. Then, this function proceeds to update the - * dialog controls/UI. + * 计算接收到的数据和总下载大小的适当单位(字节、KB 或 MB) + * 然后,此函数继续更新对话框控件/UI */ void UpdaterWindow::calculateSizes(qint64 received, qint64 total) { QString totalSize; QString receivedSize; - /* Get total size string */ + /* 获取总大小字符串 */ if (total < 1024) { totalSize = tr("%1 bytes").arg(total); } else if (total < (1024 * 1024)) { @@ -443,7 +433,7 @@ void UpdaterWindow::calculateSizes(qint64 received, qint64 total) totalSize = tr("%1 MB").arg(round(total / (1024 * 1024))); } - /* Get received size string */ + /* 获取接收大小字符串 */ if (received < 1024) { receivedSize = tr("%1 bytes").arg(received); } else if (received < (1024 * 1024)) { @@ -452,14 +442,13 @@ void UpdaterWindow::calculateSizes(qint64 received, qint64 total) receivedSize = tr("%1 MB").arg(received / (1024 * 1024)); } - /* Update the label text */ + /* 更新标签文本 */ m_ui->downloadLabel->setText(tr("Downloading updates") + " (" + receivedSize + " " + tr("of") + " " + totalSize + ")"); } /** - * Uses the \a received and \a total parameters to get the download progress - * and update the progressbar value on the dialog. + * 使用 received 和 total 参数获取下载进度并更新对话框上的进度条值 */ void UpdaterWindow::updateProgress(qint64 received, qint64 total) { @@ -480,12 +469,9 @@ void UpdaterWindow::updateProgress(qint64 received, qint64 total) } /** - * Uses two time samples(from the current time and a previous sample)to - * calculate how many bytes have been downloaded. + * 使用两个时间样本(从当前时间和之前的样本)来计算已下载的字节数 * - * Then, this function proceeds to calculate the appropriate units of time - *(hours, minutes or seconds)and constructs a user-friendly string, which - * is displayed in the dialog. + * 然后,此函数继续计算适当的时间单位(小时、分钟或秒)并构建用户友好的字符串,显示在对话框中 */ void UpdaterWindow::calculateTimeRemaining(qint64 received, qint64 total) { @@ -519,83 +505,4 @@ void UpdaterWindow::calculateTimeRemaining(qint64 received, qint64 total) if (seconds > 1) { timeString = tr("%1 seconds").arg(seconds); } else { - timeString = tr("1 second"); - } - } - - m_ui->timeLabel->setText(tr("Time remaining") + ": " + timeString); - } -} - -void UpdaterWindow::onDownloadFinished() -{ - QString redirectedUrl = - m_reply->attribute(QNetworkRequest::RedirectionTargetAttribute).toString(); - - if (redirectedUrl.isEmpty()) { - const QString filePath = m_downloadDir.filePath(m_fileName); - QFile file(filePath); - if (file.open(QIODevice::WriteOnly | QIODevice::Append)) { - file.write(m_reply->readAll()); - file.close(); - qApp->processEvents(); - } - - openDownload(filePath); - } else { - startDownload(redirectedUrl); - } -} - -/** - * Allows the user to move the window and registers the position in which - * the user originally clicked to move the window - */ -void UpdaterWindow::mousePressEvent(QMouseEvent *event) -{ - if (event->button() == Qt::LeftButton) { - if (event->x() < width() - 5 && event->x() > 5 && event->pos().y() < height() - 5 - && event->pos().y() > 5) { -#if QT_VERSION >= QT_VERSION_CHECK(5, 15, 0) - m_canMoveWindow = !window()->windowHandle()->startSystemMove(); -#else - m_canMoveWindow = true; -#endif - m_mousePressX = event->pos().x(); - m_mousePressY = event->pos().y(); - } - } - event->accept(); -} - -/** - * Changes the cursor icon to a hand(to hint the user that he/she is dragging - * the window)and moves the window to the desired position of the given - * \a event - */ -void UpdaterWindow::mouseMoveEvent(QMouseEvent *event) -{ - if (m_canMoveWindow) { - int dx = event->globalX() - m_mousePressX; - int dy = event->globalY() - m_mousePressY; - move(dx, dy); - } -} - -/** - * Disallows the user to move the window and resets the window cursor - */ -void UpdaterWindow::mouseReleaseEvent(QMouseEvent *event) -{ - m_canMoveWindow = false; - unsetCursor(); - event->accept(); -} - -/** - * Rounds the given \a input to two decimal places - */ -qreal UpdaterWindow::round(qreal input) -{ - return qreal(roundf(float(input * 100)) / 100); -} + timeString \ No newline at end of file diff --git a/source/src/updaterwindow.h b/source/src/updaterwindow.h old mode 100644 new mode 100755 index 2c5fc80..67d4c06 --- a/source/src/updaterwindow.h +++ b/source/src/updaterwindow.h @@ -19,64 +19,87 @@ class QNetworkReply; class QSimpleUpdater; class QNetworkAccessManager; +// UpdaterWindow 类用于管理更新窗口的显示和更新逻辑 class UpdaterWindow : public QDialog { Q_OBJECT public: + // 构造函数,初始化更新窗口 explicit UpdaterWindow(QWidget *parent = 0); + // 析构函数,释放资源 ~UpdaterWindow(); + // 设置是否显示更新窗口 void setShowWindowDisable(const bool dontShowWindow); public slots: + // 检查更新,force 参数表示是否强制检查 void checkForUpdates(bool force); signals: + // 信号,当更新窗口显示状态改变时发出 void dontShowUpdateWindowChanged(bool state); private slots: + // 重置控件状态 void resetControls(); + // 更新标题标签 void updateTitleLabel(); + // 当有可用更新时调用 void onUpdateAvailable(); + // 当下载按钮被点击时调用 void onDownloadButtonClicked(); + // 开始下载,url 参数表示下载链接 void startDownload(const QUrl &url); + // 打开下载的文件,file 参数表示文件路径 void openDownload(const QString &file); + // 当检查更新完成时调用,url 参数表示检查的链接 void onCheckFinished(const QString &url); + // 当 xdg-open 命令完成时调用,exitCode 参数表示退出码 void onXdgOpenFinished(const int exitCode); + // 打开下载文件夹,file 参数表示文件路径 void openDownloadFolder(const QString &file); + // 计算下载大小,received 参数表示已接收的字节数,total 参数表示总字节数 void calculateSizes(qint64 received, qint64 total); + // 更新下载进度,received 参数表示已接收的字节数,total 参数表示总字节数 void updateProgress(qint64 received, qint64 total); + // 计算剩余下载时间,received 参数表示已接收的字节数,total 参数表示总字节数 void calculateTimeRemaining(qint64 received, qint64 total); + // 当下载完成时调用 void onDownloadFinished(); protected: + // 处理鼠标移动事件 void mouseMoveEvent(QMouseEvent *event) override; + // 处理鼠标按下事件 void mousePressEvent(QMouseEvent *event) override; + // 处理鼠标释放事件 void mouseReleaseEvent(QMouseEvent *event) override; private: + // 四舍五入函数,input 参数表示输入值 qreal round(qreal input); private: - QString m_fileName; - const QDir m_downloadDir; + QString m_fileName; // 文件名 + const QDir m_downloadDir; // 下载目录 - Ui::UpdaterWindow *m_ui; + Ui::UpdaterWindow *m_ui; // 用户界面指针 - QPoint m_dragPosition; + QPoint m_dragPosition; // 窗口拖动位置 - int m_mousePressX; - int m_mousePressY; - bool m_canMoveWindow; - bool m_checkingForUpdates; - bool m_dontShowUpdateWindow; - bool m_forced; + int m_mousePressX; // 鼠标按下时的 X 坐标 + int m_mousePressY; // 鼠标按下时的 Y 坐标 + bool m_canMoveWindow; // 是否可以移动窗口 + bool m_checkingForUpdates; // 是否正在检查更新 + bool m_dontShowUpdateWindow; // 是否不显示更新窗口 + bool m_forced; // 是否强制检查更新 - uint m_startTime; - QNetworkReply *m_reply; - QSimpleUpdater *m_updater; - QNetworkAccessManager *m_manager; + uint m_startTime; // 下载开始时间 + QNetworkReply *m_reply; // 网络回复指针 + QSimpleUpdater *m_updater; // 更新器指针 + QNetworkAccessManager *m_manager; // 网络访问管理器指针 }; -#endif +#endif \ No newline at end of file diff --git a/source/src/updaterwindow.ui b/source/src/updaterwindow.ui old mode 100644 new mode 100755