|
|
|
@ -15,8 +15,9 @@
|
|
|
|
|
#include <QFontMetrics>
|
|
|
|
|
#include "fontloader.h"
|
|
|
|
|
|
|
|
|
|
NodeTreeDelegate::NodeTreeDelegate(QTreeView *view, QObject *parent, QListView *listView)
|
|
|
|
|
NodeTreeDelegate::NodeTreeDelegate(QTreeView *view, QObject *parent, QListView *listView)// 构造函数,初始化NodeTreeDelegate
|
|
|
|
|
: QStyledItemDelegate{ parent },
|
|
|
|
|
// 根据平台选择合适的字体
|
|
|
|
|
#ifdef __APPLE__
|
|
|
|
|
m_displayFont(QFont(QStringLiteral("SF Pro Text")).exactMatch()
|
|
|
|
|
? QStringLiteral("SF Pro Text")
|
|
|
|
@ -27,6 +28,7 @@ NodeTreeDelegate::NodeTreeDelegate(QTreeView *view, QObject *parent, QListView *
|
|
|
|
|
#else
|
|
|
|
|
m_displayFont(QStringLiteral("Roboto")),
|
|
|
|
|
#endif
|
|
|
|
|
// 根据平台设置字体大小和样式
|
|
|
|
|
#ifdef __APPLE__
|
|
|
|
|
m_titleFont(m_displayFont, 13, QFont::DemiBold),
|
|
|
|
|
m_titleSelectedFont(m_displayFont, 13),
|
|
|
|
@ -39,7 +41,7 @@ NodeTreeDelegate::NodeTreeDelegate(QTreeView *view, QObject *parent, QListView *
|
|
|
|
|
m_dateFont(m_displayFont, 10),
|
|
|
|
|
m_separatorFont(m_displayFont, 9, QFont::Normal),
|
|
|
|
|
m_numberOfNotesFont(m_displayFont, 9, QFont::DemiBold),
|
|
|
|
|
#endif
|
|
|
|
|
#endif// 初始化颜色设置
|
|
|
|
|
m_titleColor(26, 26, 26),
|
|
|
|
|
m_titleSelectedColor(255, 255, 255),
|
|
|
|
|
m_dateColor(132, 132, 132),
|
|
|
|
@ -57,15 +59,15 @@ NodeTreeDelegate::NodeTreeDelegate(QTreeView *view, QObject *parent, QListView *
|
|
|
|
|
m_view(view),
|
|
|
|
|
m_listView(listView),
|
|
|
|
|
m_theme(Theme::Light)
|
|
|
|
|
{
|
|
|
|
|
{// 构造函数体为空
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// 设置主题
|
|
|
|
|
void NodeTreeDelegate::setTheme(Theme::Value theme)
|
|
|
|
|
{
|
|
|
|
|
emit themeChanged(theme);
|
|
|
|
|
m_theme = theme;
|
|
|
|
|
emit themeChanged(theme); // 发出主题变化信号
|
|
|
|
|
m_theme = theme; // 更新当前主题
|
|
|
|
|
switch (theme) {
|
|
|
|
|
case Theme::Light: {
|
|
|
|
|
case Theme::Light: {// 设置浅色主题的颜色
|
|
|
|
|
m_titleColor = QColor(26, 26, 26);
|
|
|
|
|
m_dateColor = QColor(26, 26, 26);
|
|
|
|
|
m_defaultColor = QColor(247, 247, 247);
|
|
|
|
@ -76,7 +78,7 @@ void NodeTreeDelegate::setTheme(Theme::Value theme)
|
|
|
|
|
m_numberOfNotesColor = QColor(26, 26, 26, 127);
|
|
|
|
|
break;
|
|
|
|
|
}
|
|
|
|
|
case Theme::Dark: {
|
|
|
|
|
case Theme::Dark: {// 设置深色主题的颜色
|
|
|
|
|
m_titleColor = QColor(212, 212, 212);
|
|
|
|
|
m_dateColor = QColor(212, 212, 212);
|
|
|
|
|
m_defaultColor = QColor(25, 25, 25);
|
|
|
|
@ -87,7 +89,7 @@ void NodeTreeDelegate::setTheme(Theme::Value theme)
|
|
|
|
|
m_numberOfNotesColor = QColor(212, 212, 212, 127);
|
|
|
|
|
break;
|
|
|
|
|
}
|
|
|
|
|
case Theme::Sepia: {
|
|
|
|
|
case Theme::Sepia: {// 设置棕褐色主题的颜色
|
|
|
|
|
m_titleColor = QColor(26, 26, 26);
|
|
|
|
|
m_dateColor = QColor(26, 26, 26);
|
|
|
|
|
m_defaultColor = QColor(251, 240, 217);
|
|
|
|
@ -100,27 +102,28 @@ void NodeTreeDelegate::setTheme(Theme::Value theme)
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// 绘制函数
|
|
|
|
|
void NodeTreeDelegate::paint(QPainter *painter, const QStyleOptionViewItem &option,
|
|
|
|
|
const QModelIndex &index) const
|
|
|
|
|
{
|
|
|
|
|
painter->setRenderHint(QPainter::Antialiasing);
|
|
|
|
|
painter->setRenderHint(QPainter::Antialiasing);// 开启抗锯齿
|
|
|
|
|
auto itemType = static_cast<NodeItem::Type>(index.data(NodeItem::Roles::ItemType).toInt());
|
|
|
|
|
|
|
|
|
|
// 根据平台设置图标字体大小偏移
|
|
|
|
|
#ifdef __APPLE__
|
|
|
|
|
int iconPointSizeOffset = 0;
|
|
|
|
|
#else
|
|
|
|
|
int iconPointSizeOffset = -4;
|
|
|
|
|
#endif
|
|
|
|
|
|
|
|
|
|
painter->fillRect(option.rect, m_currentBackgroundColor);
|
|
|
|
|
painter->fillRect(option.rect, m_currentBackgroundColor);// 填充背景色
|
|
|
|
|
switch (itemType) {
|
|
|
|
|
// 绘制逻辑根据不同的项类型进行分支处理
|
|
|
|
|
case NodeItem::Type::RootItem: {
|
|
|
|
|
break;
|
|
|
|
|
}
|
|
|
|
|
case NodeItem::Type::AllNoteButton:
|
|
|
|
|
case NodeItem::Type::TrashButton: {
|
|
|
|
|
paintBackgroundSelectable(painter, option, index);
|
|
|
|
|
paintBackgroundSelectable(painter, option, index);// 绘制可选择背景
|
|
|
|
|
auto iconRect = QRect(option.rect.x() + 22,
|
|
|
|
|
option.rect.y() + (option.rect.height() - 20) / 2, 18, 20);
|
|
|
|
|
QFont previousPainterFont = painter->font();
|
|
|
|
@ -276,7 +279,7 @@ void NodeTreeDelegate::paint(QPainter *painter, const QStyleOptionViewItem &opti
|
|
|
|
|
break;
|
|
|
|
|
}
|
|
|
|
|
case NodeItem::Type::TagItem: {
|
|
|
|
|
paintBackgroundSelectable(painter, option, index);
|
|
|
|
|
paintBackgroundSelectable(painter, option, index);// 绘制可选择的背景
|
|
|
|
|
auto iconRect = QRect(option.rect.x() + 22,
|
|
|
|
|
option.rect.y() + (option.rect.height() - 14) / 2, 16, 16);
|
|
|
|
|
auto tagColor = index.data(NodeItem::Roles::TagColor).toString();
|
|
|
|
@ -315,45 +318,45 @@ void NodeTreeDelegate::paint(QPainter *painter, const QStyleOptionViewItem &opti
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// 绘制可选择的背景
|
|
|
|
|
void NodeTreeDelegate::paintBackgroundSelectable(QPainter *painter,
|
|
|
|
|
const QStyleOptionViewItem &option,
|
|
|
|
|
const QModelIndex &index) const
|
|
|
|
|
{
|
|
|
|
|
if ((option.state & QStyle::State_Selected) == QStyle::State_Selected) {
|
|
|
|
|
painter->fillRect(option.rect, QBrush(m_ActiveColor));
|
|
|
|
|
painter->fillRect(option.rect, QBrush(m_ActiveColor));// 如果选中,填充活动颜色
|
|
|
|
|
} else if ((option.state & QStyle::State_MouseOver) == QStyle::State_MouseOver) {
|
|
|
|
|
auto treeView = dynamic_cast<NodeTreeView *>(m_view);
|
|
|
|
|
auto itemType = static_cast<NodeItem::Type>(index.data(NodeItem::Roles::ItemType).toInt());
|
|
|
|
|
if (itemType == NodeItem::Type::TrashButton) {
|
|
|
|
|
return;
|
|
|
|
|
return;// 垃圾桶按钮不绘制悬停背景
|
|
|
|
|
}
|
|
|
|
|
if (!treeView->isDragging()) {
|
|
|
|
|
painter->fillRect(option.rect, QBrush(m_hoverColor));
|
|
|
|
|
painter->fillRect(option.rect, QBrush(m_hoverColor));// 如果悬停,填充悬停颜色
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// 计算项的大小提示
|
|
|
|
|
QSize NodeTreeDelegate::sizeHint(const QStyleOptionViewItem &option, const QModelIndex &index) const
|
|
|
|
|
{
|
|
|
|
|
QSize result = QStyledItemDelegate::sizeHint(option, index);
|
|
|
|
|
auto itemType = static_cast<NodeItem::Type>(index.data(NodeItem::Roles::ItemType).toInt());
|
|
|
|
|
if (itemType == NodeItem::Type::FolderSeparator) {
|
|
|
|
|
result.setHeight(NoteTreeConstant::folderLabelHeight);
|
|
|
|
|
result.setHeight(NoteTreeConstant::folderLabelHeight);// 文件夹分隔符的高度
|
|
|
|
|
} else if (itemType == NodeItem::Type::TagSeparator) {
|
|
|
|
|
result.setHeight(NoteTreeConstant::tagLabelHeight);
|
|
|
|
|
result.setHeight(NoteTreeConstant::tagLabelHeight);// 标签分隔符的高度
|
|
|
|
|
} else if (itemType == NodeItem::Type::FolderItem || itemType == NodeItem::Type::TrashButton
|
|
|
|
|
|| itemType == NodeItem::Type::AllNoteButton) {
|
|
|
|
|
result.setHeight(NoteTreeConstant::folderItemHeight);
|
|
|
|
|
result.setHeight(NoteTreeConstant::folderItemHeight);// 文件夹项、垃圾桶按钮、所有笔记按钮的高度
|
|
|
|
|
} else if (itemType == NodeItem::Type::TagItem) {
|
|
|
|
|
result.setHeight(NoteTreeConstant::tagItemHeight);
|
|
|
|
|
result.setHeight(NoteTreeConstant::tagItemHeight);// 标签项的高度
|
|
|
|
|
} else {
|
|
|
|
|
result.setHeight(30);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
return result;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// 创建编辑器
|
|
|
|
|
QWidget *NodeTreeDelegate::createEditor(QWidget *parent, const QStyleOptionViewItem &option,
|
|
|
|
|
const QModelIndex &index) const
|
|
|
|
|
{
|
|
|
|
@ -445,7 +448,7 @@ QWidget *NodeTreeDelegate::createEditor(QWidget *parent, const QStyleOptionViewI
|
|
|
|
|
}
|
|
|
|
|
return nullptr;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// 更新编辑器的几何形状
|
|
|
|
|
void NodeTreeDelegate::updateEditorGeometry(QWidget *editor, const QStyleOptionViewItem &option,
|
|
|
|
|
const QModelIndex &index) const
|
|
|
|
|
{
|
|
|
|
|