mirror of
https://gitee.com/vnotex/vnote.git
synced 2025-07-05 13:59:52 +08:00
export: support MHTML format
This commit is contained in:
parent
28765bf4bb
commit
bccc0b28db
@ -215,9 +215,20 @@ QWidget *VExportDialog::setupHTMLAdvancedSettings()
|
||||
"the original page"));
|
||||
m_completeHTMLCB->setChecked(true);
|
||||
|
||||
// Mime HTML.
|
||||
m_mimeHTMLCB = new QCheckBox(tr("MIME HTML"), this);
|
||||
m_mimeHTMLCB->setToolTip(tr("Export as a complete web page in MIME HTML format"));
|
||||
connect(m_mimeHTMLCB, &QCheckBox::stateChanged,
|
||||
this, [this](int p_state) {
|
||||
bool checked = p_state == Qt::Checked;
|
||||
m_embedStyleCB->setEnabled(!checked);
|
||||
m_completeHTMLCB->setEnabled(!checked);
|
||||
});
|
||||
|
||||
QFormLayout *advLayout = new QFormLayout();
|
||||
advLayout->addRow(m_embedStyleCB);
|
||||
advLayout->addRow(m_completeHTMLCB);
|
||||
advLayout->addRow(m_mimeHTMLCB);
|
||||
|
||||
advLayout->setContentsMargins(0, 0, 0, 0);
|
||||
|
||||
@ -311,8 +322,9 @@ void VExportDialog::startExport()
|
||||
m_renderStyleCB->currentData().toString(),
|
||||
m_renderCodeBlockStyleCB->currentData().toString(),
|
||||
&m_pageLayout,
|
||||
m_embedStyleCB->isChecked(),
|
||||
m_completeHTMLCB->isChecked());
|
||||
ExportHTMLOption(m_embedStyleCB->isChecked(),
|
||||
m_completeHTMLCB->isChecked(),
|
||||
m_mimeHTMLCB->isChecked()));
|
||||
|
||||
s_lastExportFormat = opt.m_format;
|
||||
|
||||
@ -683,7 +695,7 @@ int VExportDialog::doExportHTML(VFile *p_file,
|
||||
}
|
||||
|
||||
// Get output file.
|
||||
QString suffix = ".html";
|
||||
QString suffix = p_opt.m_htmlOpt.m_mimeHTML ? ".mht" : ".html";
|
||||
QString name = VUtils::getFileNameWithSequence(p_outputFolder,
|
||||
QFileInfo(p_file->getName()).completeBaseName() + suffix);
|
||||
QString outputPath = QDir(p_outputFolder).filePath(name);
|
||||
|
@ -38,6 +38,23 @@ enum class ExportFormat
|
||||
};
|
||||
|
||||
|
||||
struct ExportHTMLOption
|
||||
{
|
||||
ExportHTMLOption(bool p_embedCssStyle,
|
||||
bool p_completeHTML,
|
||||
bool p_mimeHTML)
|
||||
: m_embedCssStyle(p_embedCssStyle),
|
||||
m_completeHTML(p_completeHTML),
|
||||
m_mimeHTML(p_mimeHTML)
|
||||
{
|
||||
}
|
||||
|
||||
bool m_embedCssStyle;
|
||||
bool m_completeHTML;
|
||||
bool m_mimeHTML;
|
||||
};
|
||||
|
||||
|
||||
struct ExportOption
|
||||
{
|
||||
ExportOption(ExportSource p_source,
|
||||
@ -47,8 +64,7 @@ struct ExportOption
|
||||
const QString &p_renderStyle,
|
||||
const QString &p_renderCodeBlockStyle,
|
||||
QPageLayout *p_layout,
|
||||
bool p_embedCssStyle,
|
||||
bool p_completeHTML)
|
||||
const ExportHTMLOption &p_htmlOpt)
|
||||
: m_source(p_source),
|
||||
m_format(p_format),
|
||||
m_renderer(p_renderer),
|
||||
@ -56,8 +72,7 @@ struct ExportOption
|
||||
m_renderStyle(p_renderStyle),
|
||||
m_renderCodeBlockStyle(p_renderCodeBlockStyle),
|
||||
m_layout(p_layout),
|
||||
m_embedCssStyle(p_embedCssStyle),
|
||||
m_completeHTML(p_completeHTML)
|
||||
m_htmlOpt(p_htmlOpt)
|
||||
{
|
||||
}
|
||||
|
||||
@ -72,8 +87,7 @@ struct ExportOption
|
||||
QString m_renderCodeBlockStyle;
|
||||
QPageLayout *m_layout;
|
||||
|
||||
bool m_embedCssStyle;
|
||||
bool m_completeHTML;
|
||||
ExportHTMLOption m_htmlOpt;
|
||||
};
|
||||
|
||||
|
||||
@ -191,6 +205,8 @@ private:
|
||||
|
||||
QCheckBox *m_completeHTMLCB;;
|
||||
|
||||
QCheckBox *m_mimeHTMLCB;
|
||||
|
||||
VNotebook *m_notebook;
|
||||
|
||||
VDirectory *m_directory;
|
||||
|
@ -7,7 +7,7 @@ mdhl_file=v_moonlight.mdhl
|
||||
css_file=v_moonlight.css
|
||||
codeblock_css_file=v_moonlight_codeblock.css
|
||||
mermaid_css_file=v_moonlight_mermaid.css
|
||||
version=4
|
||||
version=5
|
||||
|
||||
; This mapping will be used to translate colors when the content of HTML is copied
|
||||
; without background. You could just specify the foreground colors mapping here.
|
||||
@ -329,6 +329,7 @@ editwindow_corner_icon_fg=@master_bg
|
||||
editwindow_corner_icon_inactive_fg=@icon_fg
|
||||
|
||||
; CheckBox.
|
||||
checkbox_disabled_fg=@disabled_fg
|
||||
checkbox_indicator_hover_bg=@hover_bg
|
||||
checkbox_indicator_pressed_bg=@pressed_bg
|
||||
|
||||
|
@ -1114,6 +1114,10 @@ QCheckBox {
|
||||
spacing: 5px;
|
||||
}
|
||||
|
||||
QCheckBox:disabled {
|
||||
color: @checkbox_disabled_fg;
|
||||
}
|
||||
|
||||
QCheckBox::indicator {
|
||||
width: 20px;
|
||||
height: 20px;
|
||||
|
@ -7,7 +7,7 @@ mdhl_file=v_pure.mdhl
|
||||
css_file=v_pure.css
|
||||
codeblock_css_file=v_pure_codeblock.css
|
||||
mermaid_css_file=v_pure_mermaid.css
|
||||
version=4
|
||||
version=5
|
||||
|
||||
[phony]
|
||||
; Abstract color attributes.
|
||||
@ -322,6 +322,7 @@ editwindow_corner_icon_fg=@master_bg
|
||||
editwindow_corner_icon_inactive_fg=#D3D3D3
|
||||
|
||||
; CheckBox.
|
||||
checkbox_disabled_fg=@disabled_fg
|
||||
checkbox_indicator_hover_bg=@hover_bg
|
||||
checkbox_indicator_pressed_bg=@pressed_bg
|
||||
|
||||
|
@ -1117,6 +1117,10 @@ QCheckBox {
|
||||
spacing: 5px;
|
||||
}
|
||||
|
||||
QCheckBox:disabled {
|
||||
color: @checkbox_disabled_fg;
|
||||
}
|
||||
|
||||
QCheckBox::indicator {
|
||||
width: 20px;
|
||||
height: 20px;
|
||||
|
@ -7,7 +7,7 @@ mdhl_file=v_white.mdhl
|
||||
css_file=v_white.css
|
||||
codeblock_css_file=v_white_codeblock.css
|
||||
mermaid_css_file=v_white_mermaid.css
|
||||
version=4
|
||||
version=5
|
||||
|
||||
[phony]
|
||||
; Abstract color attributes.
|
||||
@ -287,6 +287,7 @@ editwindow_corner_icon_fg=@icon_fg
|
||||
editwindow_corner_icon_inactive_fg=#808080
|
||||
|
||||
; CheckBox.
|
||||
checkbox_disabled_fg=@disabled_fg
|
||||
checkbox_indicator_hover_bg=@hover_bg
|
||||
checkbox_indicator_pressed_bg=@pressed_bg
|
||||
|
||||
|
@ -1003,6 +1003,10 @@ QCheckBox {
|
||||
spacing: 5px;
|
||||
}
|
||||
|
||||
QCheckBox:disabled {
|
||||
color: @checkbox_disabled_fg;
|
||||
}
|
||||
|
||||
QCheckBox::indicator {
|
||||
width: 20px;
|
||||
height: 20px;
|
||||
|
@ -3,6 +3,7 @@
|
||||
#include <QDebug>
|
||||
#include <QWidget>
|
||||
#include <QWebChannel>
|
||||
#include <QWebEngineProfile>
|
||||
#include <QRegExp>
|
||||
|
||||
#include "vconfigmanager.h"
|
||||
@ -64,9 +65,10 @@ void VExporter::initWebViewer(VFile *p_file, const ExportOption &p_opt)
|
||||
|
||||
VPreviewPage *page = new VPreviewPage(m_webViewer);
|
||||
m_webViewer->setPage(page);
|
||||
|
||||
connect(page, &VPreviewPage::loadFinished,
|
||||
this, &VExporter::handleLoadFinished);
|
||||
connect(page->profile(), &QWebEngineProfile::downloadRequested,
|
||||
this, &VExporter::handleDownloadRequested);
|
||||
|
||||
m_webDocument = new VDocument(p_file, m_webViewer);
|
||||
connect(m_webDocument, &VDocument::logicsFinished,
|
||||
@ -199,11 +201,16 @@ bool VExporter::exportViaWebView(VFile *p_file,
|
||||
break;
|
||||
|
||||
case ExportFormat::HTML:
|
||||
exportRet = exportToHTML(m_webViewer,
|
||||
m_webDocument,
|
||||
p_opt.m_embedCssStyle,
|
||||
p_opt.m_completeHTML,
|
||||
if (p_opt.m_htmlOpt.m_mimeHTML) {
|
||||
exportRet = exportToMHTML(m_webViewer,
|
||||
p_opt.m_htmlOpt,
|
||||
p_outputFile);
|
||||
} else {
|
||||
exportRet = exportToHTML(m_webDocument,
|
||||
p_opt.m_htmlOpt,
|
||||
p_outputFile);
|
||||
}
|
||||
|
||||
break;
|
||||
|
||||
default:
|
||||
@ -236,13 +243,10 @@ exit:
|
||||
return ret;
|
||||
}
|
||||
|
||||
bool VExporter::exportToHTML(VWebView *p_webViewer,
|
||||
VDocument *p_webDocument,
|
||||
bool p_embedCssStyle,
|
||||
bool p_completeHTML,
|
||||
bool VExporter::exportToHTML(VDocument *p_webDocument,
|
||||
const ExportHTMLOption &p_opt,
|
||||
const QString &p_filePath)
|
||||
{
|
||||
Q_UNUSED(p_webViewer);
|
||||
int htmlExported = 0;
|
||||
|
||||
connect(p_webDocument, &VDocument::htmlContentFinished,
|
||||
@ -269,7 +273,7 @@ bool VExporter::exportToHTML(VWebView *p_webViewer,
|
||||
qDebug() << "HTML files folder" << resFolderPath;
|
||||
|
||||
QString html(m_exportHtmlTemplate);
|
||||
if (!p_styleContent.isEmpty() && p_embedCssStyle) {
|
||||
if (!p_styleContent.isEmpty() && p_opt.m_embedCssStyle) {
|
||||
QString content(p_styleContent);
|
||||
fixStyleResources(resFolderPath, content);
|
||||
html.replace(HtmlHolder::c_styleHolder, content);
|
||||
@ -279,7 +283,7 @@ bool VExporter::exportToHTML(VWebView *p_webViewer,
|
||||
html.replace(HtmlHolder::c_headHolder, p_headContent);
|
||||
}
|
||||
|
||||
if (p_completeHTML) {
|
||||
if (p_opt.m_completeHTML) {
|
||||
QString content(p_bodyContent);
|
||||
fixBodyResources(m_baseUrl, resFolderPath, content);
|
||||
html.replace(HtmlHolder::c_bodyHolder, content);
|
||||
@ -389,3 +393,29 @@ QString VExporter::getResourceRelativePath(const QString &p_file)
|
||||
Q_ASSERT(idx > 0 && idx2 < idx);
|
||||
return "." + p_file.mid(idx2);
|
||||
}
|
||||
|
||||
bool VExporter::exportToMHTML(VWebView *p_webViewer,
|
||||
const ExportHTMLOption &p_opt,
|
||||
const QString &p_filePath)
|
||||
{
|
||||
m_downloadState = QWebEngineDownloadItem::DownloadRequested;
|
||||
|
||||
p_webViewer->page()->save(p_filePath, QWebEngineDownloadItem::MimeHtmlSaveFormat);
|
||||
|
||||
while (m_downloadState == QWebEngineDownloadItem::DownloadRequested
|
||||
|| m_downloadState == QWebEngineDownloadItem::DownloadInProgress) {
|
||||
VUtils::sleepWait(100);
|
||||
}
|
||||
|
||||
return m_downloadState == QWebEngineDownloadItem::DownloadCompleted;
|
||||
}
|
||||
|
||||
void VExporter::handleDownloadRequested(QWebEngineDownloadItem *p_item)
|
||||
{
|
||||
if (p_item->savePageFormat() == QWebEngineDownloadItem::MimeHtmlSaveFormat) {
|
||||
connect(p_item, &QWebEngineDownloadItem::stateChanged,
|
||||
this, [this](QWebEngineDownloadItem::DownloadState p_state) {
|
||||
m_downloadState = p_state;
|
||||
});
|
||||
}
|
||||
}
|
||||
|
@ -4,6 +4,7 @@
|
||||
#include <QObject>
|
||||
#include <QPageLayout>
|
||||
#include <QUrl>
|
||||
#include <QWebEngineDownloadItem>
|
||||
|
||||
#include "dialog/vexportdialog.h"
|
||||
|
||||
@ -33,6 +34,8 @@ private slots:
|
||||
|
||||
void handleLoadFinished(bool p_ok);
|
||||
|
||||
void handleDownloadRequested(QWebEngineDownloadItem *p_item);
|
||||
|
||||
private:
|
||||
enum class ExportState
|
||||
{
|
||||
@ -73,12 +76,15 @@ private:
|
||||
const QString &p_filePath,
|
||||
const QPageLayout &p_layout);
|
||||
|
||||
bool exportToHTML(VWebView *p_webViewer,
|
||||
VDocument *p_webDocument,
|
||||
bool p_embedCssStyle,
|
||||
bool p_completeHTML,
|
||||
bool exportToHTML(VDocument *p_webDocument,
|
||||
const ExportHTMLOption &p_opt,
|
||||
const QString &p_filePath);
|
||||
|
||||
bool exportToMHTML(VWebView *p_webViewer,
|
||||
const ExportHTMLOption &p_opt,
|
||||
const QString &p_filePath);
|
||||
|
||||
|
||||
// Fix @p_html's resources like url("...") with "file" or "qrc" schema.
|
||||
// Copy the resource to @p_folder and fix the url string.
|
||||
static bool fixStyleResources(const QString &p_folder,
|
||||
@ -110,6 +116,9 @@ private:
|
||||
NoteState m_noteState;
|
||||
|
||||
ExportState m_state;
|
||||
|
||||
// Download state used for MIME HTML.
|
||||
QWebEngineDownloadItem::DownloadState m_downloadState;
|
||||
};
|
||||
|
||||
inline void VExporter::clearNoteState()
|
||||
|
Loading…
x
Reference in New Issue
Block a user