feat: v0.3.0 —— 默认编辑模式就地渲染,侧栏自动刷新
编辑模式 / 源代码模式语义修正 - 默认「编辑模式」不再显示 #、**、反引号等标记:标题按级别放大加粗、 粗体真加粗、行内代码带底色、链接只保留文字 - 光标所在行会露出原始标记,方便直接修改;切换行时只重排这两行 - 源代码模式仍是原样显示 + 着色,左下角 <src> 切换 高亮器 - QSyntaxHighlighter::setFormat 是整段替换而非合并,改为每段先与 当前行基础格式(标题 / 引用 / 代码块)compose 后再设置 - 强调正则收紧,避免 **粗体** 被 *斜体* 抢先匹配 侧栏 - 去掉刷新按钮,改为每 5 秒自动扫描;文件集合没变就不重建列表 - 状态栏左下角新增「侧栏」开关按钮,与 Ctrl+B 同步 其它 - 使用 logo.png 作为窗口图标(resources.qrc) - 版本号 0.3.0,README 同步更新
This commit is contained in:
+67
-26
@@ -193,6 +193,10 @@ void MainWindow::createActions()
|
||||
connect(m_sidebarAction, &QAction::toggled, this, [this](bool visible) {
|
||||
if (m_sidebar)
|
||||
m_sidebar->setVisible(visible);
|
||||
if (m_sidebarButton) {
|
||||
const QSignalBlocker blocker(m_sidebarButton);
|
||||
m_sidebarButton->setChecked(visible);
|
||||
}
|
||||
QSettings().setValue(QStringLiteral("window/sidebarVisible"), visible);
|
||||
});
|
||||
|
||||
@@ -230,16 +234,9 @@ void MainWindow::createSidebar()
|
||||
layout->setContentsMargins(8, 8, 8, 8);
|
||||
layout->setSpacing(6);
|
||||
|
||||
QHBoxLayout *header = new QHBoxLayout();
|
||||
header->setSpacing(4);
|
||||
m_folderLabel = new QLabel(tr("未打开文件夹"), content);
|
||||
m_folderLabel->setSizePolicy(QSizePolicy::Ignored, QSizePolicy::Preferred);
|
||||
QToolButton *refreshButton = new QToolButton(content);
|
||||
refreshButton->setText(tr("刷新"));
|
||||
refreshButton->setToolTip(tr("重新扫描文件夹里的 Markdown 文件"));
|
||||
header->addWidget(m_folderLabel, 1);
|
||||
header->addWidget(refreshButton);
|
||||
layout->addLayout(header);
|
||||
layout->addWidget(m_folderLabel);
|
||||
|
||||
m_fileList = new QListWidget(content);
|
||||
m_fileList->setFrameShape(QFrame::NoFrame);
|
||||
@@ -252,8 +249,13 @@ void MainWindow::createSidebar()
|
||||
addDockWidget(Qt::LeftDockWidgetArea, m_sidebar);
|
||||
resizeDocks({m_sidebar}, {250}, Qt::Horizontal);
|
||||
|
||||
connect(refreshButton, &QToolButton::clicked, this, &MainWindow::refreshFolder);
|
||||
connect(m_fileList, &QListWidget::itemClicked, this, &MainWindow::openSidebarItem);
|
||||
|
||||
// 列表自己刷新:没有“刷新”按钮,每 5 秒比对一次文件集合,变了才重建。
|
||||
m_folderRefreshTimer = new QTimer(this);
|
||||
m_folderRefreshTimer->setInterval(5000);
|
||||
connect(m_folderRefreshTimer, &QTimer::timeout, this, &MainWindow::refreshFolder);
|
||||
m_folderRefreshTimer->start();
|
||||
}
|
||||
|
||||
void MainWindow::createMenus()
|
||||
@@ -330,7 +332,16 @@ void MainWindow::createMenus()
|
||||
|
||||
void MainWindow::createStatusBar()
|
||||
{
|
||||
// 左下角的 <src> 开关:切到源代码模式。
|
||||
// 左下角:侧栏开关 + 源代码模式开关。
|
||||
m_sidebarButton = new QToolButton(this);
|
||||
m_sidebarButton->setText(tr("侧栏"));
|
||||
m_sidebarButton->setCheckable(true);
|
||||
m_sidebarButton->setChecked(true);
|
||||
m_sidebarButton->setCursor(Qt::PointingHandCursor);
|
||||
m_sidebarButton->setToolTip(tr("显示 / 隐藏文件夹侧栏(Ctrl+B)"));
|
||||
statusBar()->addWidget(m_sidebarButton);
|
||||
connect(m_sidebarButton, &QToolButton::toggled, m_sidebarAction, &QAction::setChecked);
|
||||
|
||||
m_sourceButton = new QToolButton(this);
|
||||
m_sourceButton->setText(QStringLiteral("<src>"));
|
||||
m_sourceButton->setCheckable(true);
|
||||
@@ -719,24 +730,13 @@ void MainWindow::openFolder(const QString &path)
|
||||
m_sidebarAction->setChecked(true);
|
||||
}
|
||||
|
||||
void MainWindow::refreshFolder()
|
||||
QStringList MainWindow::scanFolder() const
|
||||
{
|
||||
if (!m_fileList)
|
||||
return;
|
||||
|
||||
m_fileList->clear();
|
||||
|
||||
if (m_folderPath.isEmpty() || !QFileInfo(m_folderPath).isDir()) {
|
||||
m_folderLabel->setText(tr("未打开文件夹"));
|
||||
m_folderLabel->setToolTip(tr("文件 → 打开文件夹…"));
|
||||
return;
|
||||
}
|
||||
QStringList files;
|
||||
if (m_folderPath.isEmpty() || !QFileInfo(m_folderPath).isDir())
|
||||
return files;
|
||||
|
||||
const QDir root(m_folderPath);
|
||||
m_folderLabel->setText(root.dirName().isEmpty() ? m_folderPath : root.dirName());
|
||||
m_folderLabel->setToolTip(QDir::toNativeSeparators(m_folderPath));
|
||||
|
||||
QStringList files;
|
||||
QDirIterator iterator(m_folderPath,
|
||||
{QStringLiteral("*.md"), QStringLiteral("*.markdown"),
|
||||
QStringLiteral("*.mdown"), QStringLiteral("*.mkd")},
|
||||
@@ -753,6 +753,47 @@ void MainWindow::refreshFolder()
|
||||
return root.relativeFilePath(left).compare(root.relativeFilePath(right),
|
||||
Qt::CaseInsensitive) < 0;
|
||||
});
|
||||
return files;
|
||||
}
|
||||
|
||||
void MainWindow::refreshFolder()
|
||||
{
|
||||
if (!m_fileList)
|
||||
return;
|
||||
|
||||
if (m_folderPath.isEmpty() || !QFileInfo(m_folderPath).isDir()) {
|
||||
if (m_fileList->count() > 0 || m_displayedFolder != m_folderPath) {
|
||||
m_fileList->clear();
|
||||
m_displayedFolder = m_folderPath;
|
||||
m_folderLabel->setText(tr("未打开文件夹"));
|
||||
m_folderLabel->setToolTip(tr("文件 → 打开文件夹…"));
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
const QDir root(m_folderPath);
|
||||
if (m_displayedFolder != m_folderPath) {
|
||||
m_displayedFolder = m_folderPath;
|
||||
m_fileList->clear();
|
||||
m_folderLabel->setText(root.dirName().isEmpty() ? m_folderPath : root.dirName());
|
||||
m_folderLabel->setToolTip(QDir::toNativeSeparators(m_folderPath));
|
||||
}
|
||||
|
||||
const QStringList files = scanFolder();
|
||||
|
||||
// 和当前显示的内容一致就什么都不做,避免每 5 秒闪一下、丢失选中项。
|
||||
QStringList shown;
|
||||
shown.reserve(m_fileList->count());
|
||||
for (int index = 0; index < m_fileList->count(); ++index) {
|
||||
const QString path = m_fileList->item(index)->data(Qt::UserRole).toString();
|
||||
if (!path.isEmpty())
|
||||
shown.append(path);
|
||||
}
|
||||
if (files == shown)
|
||||
return;
|
||||
|
||||
const QString selectedPath = m_currentPath;
|
||||
m_fileList->clear();
|
||||
|
||||
for (const QString &filePath : files) {
|
||||
QListWidgetItem *item = new QListWidgetItem(root.relativeFilePath(filePath), m_fileList);
|
||||
@@ -765,7 +806,7 @@ void MainWindow::refreshFolder()
|
||||
empty->setFlags(Qt::NoItemFlags);
|
||||
}
|
||||
|
||||
selectInSidebar(m_currentPath);
|
||||
selectInSidebar(selectedPath);
|
||||
}
|
||||
|
||||
void MainWindow::openSidebarItem(QListWidgetItem *item)
|
||||
|
||||
Reference in New Issue
Block a user