mirror of
https://gitee.com/vnotex/vnote.git
synced 2025-07-05 22:09:52 +08:00
highlight: highlight MathJax formula in editor
This commit is contained in:
parent
05e4159530
commit
9566e6f5d2
@ -35,6 +35,7 @@ HGMarkdownHighlighter::HGMarkdownHighlighter(const QVector<HighlightingStyle> &s
|
|||||||
parsing(0),
|
parsing(0),
|
||||||
m_blockHLResultReady(false),
|
m_blockHLResultReady(false),
|
||||||
waitInterval(waitInterval),
|
waitInterval(waitInterval),
|
||||||
|
m_enableMathjax(false),
|
||||||
content(NULL),
|
content(NULL),
|
||||||
capacity(0),
|
capacity(0),
|
||||||
result(NULL)
|
result(NULL)
|
||||||
@ -42,6 +43,9 @@ HGMarkdownHighlighter::HGMarkdownHighlighter(const QVector<HighlightingStyle> &s
|
|||||||
codeBlockStartExp = QRegExp(VUtils::c_fencedCodeBlockStartRegExp);
|
codeBlockStartExp = QRegExp(VUtils::c_fencedCodeBlockStartRegExp);
|
||||||
codeBlockEndExp = QRegExp(VUtils::c_fencedCodeBlockEndRegExp);
|
codeBlockEndExp = QRegExp(VUtils::c_fencedCodeBlockEndRegExp);
|
||||||
|
|
||||||
|
m_mathjaxInlineExp = QRegExp(VUtils::c_mathjaxInlineRegExp);
|
||||||
|
m_mathjaxBlockExp = QRegExp(VUtils::c_mathjaxBlockRegExp);
|
||||||
|
|
||||||
m_codeBlockFormat.setForeground(QBrush(Qt::darkYellow));
|
m_codeBlockFormat.setForeground(QBrush(Qt::darkYellow));
|
||||||
for (int index = 0; index < styles.size(); ++index) {
|
for (int index = 0; index < styles.size(); ++index) {
|
||||||
const pmh_element_type &eleType = styles[index].type;
|
const pmh_element_type &eleType = styles[index].type;
|
||||||
@ -58,6 +62,8 @@ HGMarkdownHighlighter::HGMarkdownHighlighter(const QVector<HighlightingStyle> &s
|
|||||||
m_colorColumnFormat.setForeground(QColor(g_config->getEditorColorColumnFg()));
|
m_colorColumnFormat.setForeground(QColor(g_config->getEditorColorColumnFg()));
|
||||||
m_colorColumnFormat.setBackground(QColor(g_config->getEditorColorColumnBg()));
|
m_colorColumnFormat.setBackground(QColor(g_config->getEditorColorColumnBg()));
|
||||||
|
|
||||||
|
m_mathjaxFormat.setForeground(QColor(g_config->getEditorMathjaxFg()));
|
||||||
|
|
||||||
m_headerStyles.resize(6);
|
m_headerStyles.resize(6);
|
||||||
for (auto const & it : highlightingStyles) {
|
for (auto const & it : highlightingStyles) {
|
||||||
if (it.type >= pmh_H1 && it.type <= pmh_H6) {
|
if (it.type >= pmh_H1 && it.type <= pmh_H6) {
|
||||||
@ -108,6 +114,9 @@ void HGMarkdownHighlighter::updateBlockUserData(int p_blockNum, const QString &p
|
|||||||
if (!blockData) {
|
if (!blockData) {
|
||||||
blockData = new VTextBlockData();
|
blockData = new VTextBlockData();
|
||||||
setCurrentBlockUserData(blockData);
|
setCurrentBlockUserData(blockData);
|
||||||
|
} else {
|
||||||
|
blockData->setCodeBlockIndentation(-1);
|
||||||
|
blockData->clearMathjax();
|
||||||
}
|
}
|
||||||
|
|
||||||
if (blockData->getPreviews().isEmpty()) {
|
if (blockData->getPreviews().isEmpty()) {
|
||||||
@ -115,8 +124,6 @@ void HGMarkdownHighlighter::updateBlockUserData(int p_blockNum, const QString &p
|
|||||||
} else {
|
} else {
|
||||||
m_possiblePreviewBlocks.insert(p_blockNum);
|
m_possiblePreviewBlocks.insert(p_blockNum);
|
||||||
}
|
}
|
||||||
|
|
||||||
blockData->setCodeBlockIndentation(-1);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void HGMarkdownHighlighter::highlightBlock(const QString &text)
|
void HGMarkdownHighlighter::highlightBlock(const QString &text)
|
||||||
@ -171,10 +178,13 @@ void HGMarkdownHighlighter::highlightBlock(const QString &text)
|
|||||||
setCurrentBlockState(HighlightBlockState::Normal);
|
setCurrentBlockState(HighlightBlockState::Normal);
|
||||||
highlightCodeBlock(curBlock, text);
|
highlightCodeBlock(curBlock, text);
|
||||||
|
|
||||||
if (currentBlockState() == HighlightBlockState::Normal
|
if (currentBlockState() == HighlightBlockState::Normal) {
|
||||||
&& isVerbatimBlock(curBlock)) {
|
if (isVerbatimBlock(curBlock)) {
|
||||||
setCurrentBlockState(HighlightBlockState::Verbatim);
|
setCurrentBlockState(HighlightBlockState::Verbatim);
|
||||||
goto exit;
|
goto exit;
|
||||||
|
} else if (m_enableMathjax) {
|
||||||
|
highlightMathJax(curBlock, text);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// PEG Markdown Highlight does not handle links with spaces in the URL.
|
// PEG Markdown Highlight does not handle links with spaces in the URL.
|
||||||
@ -184,6 +194,10 @@ void HGMarkdownHighlighter::highlightBlock(const QString &text)
|
|||||||
|
|
||||||
highlightHeaderFast(blockNum, text);
|
highlightHeaderFast(blockNum, text);
|
||||||
|
|
||||||
|
if (currentBlockState() != HighlightBlockState::CodeBlock) {
|
||||||
|
goto exit;
|
||||||
|
}
|
||||||
|
|
||||||
// Highlight CodeBlock using VCodeBlockHighlightHelper.
|
// Highlight CodeBlock using VCodeBlockHighlightHelper.
|
||||||
if (m_codeBlockHighlights.size() > blockNum) {
|
if (m_codeBlockHighlights.size() > blockNum) {
|
||||||
const QVector<HLUnitStyle> &units = m_codeBlockHighlights[blockNum];
|
const QVector<HLUnitStyle> &units = m_codeBlockHighlights[blockNum];
|
||||||
@ -436,7 +450,7 @@ void HGMarkdownHighlighter::initBlockHighlihgtOne(unsigned long pos,
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void HGMarkdownHighlighter::highlightCodeBlock(const QTextBlock &p_block, const QString &text)
|
void HGMarkdownHighlighter::highlightCodeBlock(const QTextBlock &p_block, const QString &p_text)
|
||||||
{
|
{
|
||||||
VTextBlockData *blockData = currentBlockData();
|
VTextBlockData *blockData = currentBlockData();
|
||||||
Q_ASSERT(blockData);
|
Q_ASSERT(blockData);
|
||||||
@ -449,10 +463,10 @@ void HGMarkdownHighlighter::highlightCodeBlock(const QTextBlock &p_block, const
|
|||||||
if (preState != HighlightBlockState::CodeBlock
|
if (preState != HighlightBlockState::CodeBlock
|
||||||
&& preState != HighlightBlockState::CodeBlockStart) {
|
&& preState != HighlightBlockState::CodeBlockStart) {
|
||||||
// Need to find a new code block start.
|
// Need to find a new code block start.
|
||||||
index = codeBlockStartExp.indexIn(text);
|
index = codeBlockStartExp.indexIn(p_text);
|
||||||
if (index >= 0 && !isVerbatimBlock(p_block)) {
|
if (index >= 0 && !isVerbatimBlock(p_block)) {
|
||||||
// Start a new code block.
|
// Start a new code block.
|
||||||
length = text.length();
|
length = p_text.length();
|
||||||
state = HighlightBlockState::CodeBlockStart;
|
state = HighlightBlockState::CodeBlockStart;
|
||||||
|
|
||||||
// The leading spaces of code block start and end must be identical.
|
// The leading spaces of code block start and end must be identical.
|
||||||
@ -471,18 +485,18 @@ void HGMarkdownHighlighter::highlightCodeBlock(const QTextBlock &p_block, const
|
|||||||
startLeadingSpaces = preBlockData->getCodeBlockIndentation();
|
startLeadingSpaces = preBlockData->getCodeBlockIndentation();
|
||||||
}
|
}
|
||||||
|
|
||||||
index = codeBlockEndExp.indexIn(text);
|
index = codeBlockEndExp.indexIn(p_text);
|
||||||
|
|
||||||
// The closing ``` should have the same indentation as the open ```.
|
// The closing ``` should have the same indentation as the open ```.
|
||||||
if (index >= 0
|
if (index >= 0
|
||||||
&& startLeadingSpaces == codeBlockEndExp.capturedTexts()[1].size()) {
|
&& startLeadingSpaces == codeBlockEndExp.capturedTexts()[1].size()) {
|
||||||
// End of code block.
|
// End of code block.
|
||||||
length = text.length();
|
length = p_text.length();
|
||||||
state = HighlightBlockState::CodeBlockEnd;
|
state = HighlightBlockState::CodeBlockEnd;
|
||||||
} else {
|
} else {
|
||||||
// Within code block.
|
// Within code block.
|
||||||
index = 0;
|
index = 0;
|
||||||
length = text.length();
|
length = p_text.length();
|
||||||
state = HighlightBlockState::CodeBlock;
|
state = HighlightBlockState::CodeBlock;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -493,6 +507,101 @@ void HGMarkdownHighlighter::highlightCodeBlock(const QTextBlock &p_block, const
|
|||||||
setFormat(index, length, m_codeBlockFormat);
|
setFormat(index, length, m_codeBlockFormat);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static bool intersect(const QList<QPair<int, int>> &p_indices, int &p_start, int &p_end)
|
||||||
|
{
|
||||||
|
for (auto const & range : p_indices) {
|
||||||
|
if (p_end <= range.first) {
|
||||||
|
return false;
|
||||||
|
} else if (p_start < range.second) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
void HGMarkdownHighlighter::highlightMathJax(const QTextBlock &p_block, const QString &p_text)
|
||||||
|
{
|
||||||
|
const int blockMarkLength = 2;
|
||||||
|
const int inlineMarkLength = 1;
|
||||||
|
|
||||||
|
int startIdx = 0;
|
||||||
|
// Next position to search.
|
||||||
|
int pos = 0;
|
||||||
|
HighlightBlockState state = (HighlightBlockState)previousBlockState();
|
||||||
|
|
||||||
|
QList<QPair<int, int>> blockIdices;
|
||||||
|
|
||||||
|
// Mathjax block formula.
|
||||||
|
if (state != HighlightBlockState::MathjaxBlock) {
|
||||||
|
startIdx = m_mathjaxBlockExp.indexIn(p_text);
|
||||||
|
pos = startIdx + m_mathjaxBlockExp.matchedLength();
|
||||||
|
startIdx = pos - blockMarkLength;
|
||||||
|
}
|
||||||
|
|
||||||
|
while (startIdx >= 0) {
|
||||||
|
int endIdx = m_mathjaxBlockExp.indexIn(p_text, pos);
|
||||||
|
int mathLength = 0;
|
||||||
|
if (endIdx == -1) {
|
||||||
|
setCurrentBlockState(HighlightBlockState::MathjaxBlock);
|
||||||
|
mathLength = p_text.length() - startIdx;
|
||||||
|
} else {
|
||||||
|
mathLength = endIdx - startIdx + m_mathjaxBlockExp.matchedLength();
|
||||||
|
}
|
||||||
|
|
||||||
|
pos = startIdx + mathLength;
|
||||||
|
|
||||||
|
blockIdices.append(QPair<int, int>(startIdx, pos));
|
||||||
|
|
||||||
|
setFormat(startIdx, mathLength, m_mathjaxFormat);
|
||||||
|
startIdx = m_mathjaxBlockExp.indexIn(p_text, pos);
|
||||||
|
pos = startIdx + m_mathjaxBlockExp.matchedLength();
|
||||||
|
startIdx = pos - blockMarkLength;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Mathjax inline formula.
|
||||||
|
startIdx = 0;
|
||||||
|
pos = 0;
|
||||||
|
if (state != HighlightBlockState::MathjaxInline) {
|
||||||
|
startIdx = m_mathjaxInlineExp.indexIn(p_text);
|
||||||
|
pos = startIdx + m_mathjaxInlineExp.matchedLength();
|
||||||
|
startIdx = pos - inlineMarkLength;
|
||||||
|
}
|
||||||
|
|
||||||
|
while (startIdx >= 0) {
|
||||||
|
int endIdx = m_mathjaxInlineExp.indexIn(p_text, pos);
|
||||||
|
int mathLength = 0;
|
||||||
|
if (endIdx == -1) {
|
||||||
|
setCurrentBlockState(HighlightBlockState::MathjaxBlock);
|
||||||
|
mathLength = p_text.length() - startIdx;
|
||||||
|
} else {
|
||||||
|
mathLength = endIdx - startIdx + m_mathjaxInlineExp.matchedLength();
|
||||||
|
}
|
||||||
|
|
||||||
|
pos = startIdx + mathLength;
|
||||||
|
// Check if it intersect with blocks.
|
||||||
|
if (!intersect(blockIdices, startIdx, pos)) {
|
||||||
|
// A valid inline mathjax.
|
||||||
|
if (endIdx == -1) {
|
||||||
|
setCurrentBlockState(HighlightBlockState::MathjaxInline);
|
||||||
|
}
|
||||||
|
|
||||||
|
setFormat(startIdx, mathLength, m_mathjaxFormat);
|
||||||
|
|
||||||
|
startIdx = m_mathjaxInlineExp.indexIn(p_text, pos);
|
||||||
|
pos = startIdx + m_mathjaxInlineExp.matchedLength();
|
||||||
|
startIdx = pos - inlineMarkLength;
|
||||||
|
} else {
|
||||||
|
// Make the second mark as the first one and try again.
|
||||||
|
if (endIdx == -1) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
startIdx = pos - inlineMarkLength;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void HGMarkdownHighlighter::highlightCodeBlockColorColumn(const QString &p_text)
|
void HGMarkdownHighlighter::highlightCodeBlockColorColumn(const QString &p_text)
|
||||||
{
|
{
|
||||||
int cc = g_config->getColorColumn();
|
int cc = g_config->getColorColumn();
|
||||||
|
@ -155,6 +155,8 @@ public:
|
|||||||
|
|
||||||
QVector<HighlightingStyle> &getHighlightingStyles();
|
QVector<HighlightingStyle> &getHighlightingStyles();
|
||||||
|
|
||||||
|
void setMathjaxEnabled(bool p_enabled);
|
||||||
|
|
||||||
signals:
|
signals:
|
||||||
void highlightCompleted();
|
void highlightCompleted();
|
||||||
|
|
||||||
@ -197,10 +199,15 @@ private:
|
|||||||
|
|
||||||
QRegExp codeBlockStartExp;
|
QRegExp codeBlockStartExp;
|
||||||
QRegExp codeBlockEndExp;
|
QRegExp codeBlockEndExp;
|
||||||
|
|
||||||
|
QRegExp m_mathjaxInlineExp;
|
||||||
|
QRegExp m_mathjaxBlockExp;
|
||||||
|
|
||||||
QTextCharFormat m_codeBlockFormat;
|
QTextCharFormat m_codeBlockFormat;
|
||||||
QTextCharFormat m_linkFormat;
|
QTextCharFormat m_linkFormat;
|
||||||
QTextCharFormat m_imageFormat;
|
QTextCharFormat m_imageFormat;
|
||||||
QTextCharFormat m_colorColumnFormat;
|
QTextCharFormat m_colorColumnFormat;
|
||||||
|
QTextCharFormat m_mathjaxFormat;
|
||||||
|
|
||||||
QTextDocument *document;
|
QTextDocument *document;
|
||||||
|
|
||||||
@ -253,6 +260,8 @@ private:
|
|||||||
// Block number of those blocks which possible contains previewed image.
|
// Block number of those blocks which possible contains previewed image.
|
||||||
QSet<int> m_possiblePreviewBlocks;
|
QSet<int> m_possiblePreviewBlocks;
|
||||||
|
|
||||||
|
bool m_enableMathjax;
|
||||||
|
|
||||||
char *content;
|
char *content;
|
||||||
int capacity;
|
int capacity;
|
||||||
pmh_element **result;
|
pmh_element **result;
|
||||||
@ -260,7 +269,10 @@ private:
|
|||||||
static const int initCapacity;
|
static const int initCapacity;
|
||||||
|
|
||||||
void resizeBuffer(int newCap);
|
void resizeBuffer(int newCap);
|
||||||
void highlightCodeBlock(const QTextBlock &p_block, const QString &text);
|
|
||||||
|
void highlightCodeBlock(const QTextBlock &p_block, const QString &p_text);
|
||||||
|
|
||||||
|
void highlightMathJax(const QTextBlock &p_block, const QString &p_text);
|
||||||
|
|
||||||
// Highlight links using regular expression.
|
// Highlight links using regular expression.
|
||||||
// PEG Markdown Highlight treat URLs with spaces illegal. This function is
|
// PEG Markdown Highlight treat URLs with spaces illegal. This function is
|
||||||
@ -375,4 +387,9 @@ inline bool HGMarkdownHighlighter::isVerbatimBlock(const QTextBlock &p_block) co
|
|||||||
{
|
{
|
||||||
return m_verbatimBlocks.contains(p_block.blockNumber());
|
return m_verbatimBlocks.contains(p_block.blockNumber());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
inline void HGMarkdownHighlighter::setMathjaxEnabled(bool p_enabled)
|
||||||
|
{
|
||||||
|
m_enableMathjax = p_enabled;
|
||||||
|
}
|
||||||
#endif
|
#endif
|
||||||
|
@ -35,8 +35,10 @@ incremental-searched-word-background: ce93d8
|
|||||||
# [VNote] Style for color column in fenced code block
|
# [VNote] Style for color column in fenced code block
|
||||||
color-column-background: c9302c
|
color-column-background: c9302c
|
||||||
color-column-foreground: eeeeee
|
color-column-foreground: eeeeee
|
||||||
# [VNote} Style for preview image line
|
# [VNote] Style for preview image line
|
||||||
preview-image-line-foreground: 6f5799
|
preview-image-line-foreground: 6f5799
|
||||||
|
# [VNote] Style for MathJax
|
||||||
|
mathjax-foreground: ce93d8
|
||||||
|
|
||||||
editor-selection
|
editor-selection
|
||||||
foreground: dadada
|
foreground: dadada
|
||||||
|
@ -34,8 +34,10 @@ incremental-searched-word-background: ce93d8
|
|||||||
# [VNote] Style for color column in fenced code block
|
# [VNote] Style for color column in fenced code block
|
||||||
color-column-background: dd0000
|
color-column-background: dd0000
|
||||||
color-column-foreground: ffff00
|
color-column-foreground: ffff00
|
||||||
# [VNote} Style for preview image line
|
# [VNote] Style for preview image line
|
||||||
preview-image-line-foreground: 9575cd
|
preview-image-line-foreground: 9575cd
|
||||||
|
# [VNote] Style for MathJax
|
||||||
|
mathjax-foreground: 8e24aa
|
||||||
|
|
||||||
editor-selection
|
editor-selection
|
||||||
foreground: eeeeee
|
foreground: eeeeee
|
||||||
|
@ -35,8 +35,10 @@ incremental-searched-word-background: ce93d8
|
|||||||
# [VNote] Style for color column in fenced code block
|
# [VNote] Style for color column in fenced code block
|
||||||
color-column-background: dd0000
|
color-column-background: dd0000
|
||||||
color-column-foreground: ffff00
|
color-column-foreground: ffff00
|
||||||
# [VNote} Style for preview image line
|
# [VNote] Style for preview image line
|
||||||
preview-image-line-foreground: 9575cd
|
preview-image-line-foreground: 9575cd
|
||||||
|
# [VNote] Style for MathJax
|
||||||
|
mathjax-foreground: 8e24aa
|
||||||
|
|
||||||
editor-selection
|
editor-selection
|
||||||
foreground: eeeeee
|
foreground: eeeeee
|
||||||
|
@ -47,6 +47,10 @@ const QString VUtils::c_fencedCodeBlockStartRegExp = QString("^(\\s*)```([^`\\s]
|
|||||||
|
|
||||||
const QString VUtils::c_fencedCodeBlockEndRegExp = QString("^(\\s*)```$");
|
const QString VUtils::c_fencedCodeBlockEndRegExp = QString("^(\\s*)```$");
|
||||||
|
|
||||||
|
const QString VUtils::c_mathjaxInlineRegExp = QString("(?:^|[^\\$\\\\]|(?:^|[^\\\\])(?:\\\\\\\\)+)\\$(?!\\$)");
|
||||||
|
|
||||||
|
const QString VUtils::c_mathjaxBlockRegExp = QString("(?:^|[^\\$\\\\]|(?:^|[^\\\\])(?:\\\\\\\\)+)\\$\\$(?!\\$)");
|
||||||
|
|
||||||
const QString VUtils::c_previewImageBlockRegExp = QString("[\\n|^][ |\\t]*\\xfffc[ |\\t]*(?=\\n)");
|
const QString VUtils::c_previewImageBlockRegExp = QString("[\\n|^][ |\\t]*\\xfffc[ |\\t]*(?=\\n)");
|
||||||
|
|
||||||
const QString VUtils::c_headerRegExp = QString("^(#{1,6})\\s+(((\\d+\\.)+(?=\\s))?\\s*(\\S.*)?)$");
|
const QString VUtils::c_headerRegExp = QString("^(#{1,6})\\s+(((\\d+\\.)+(?=\\s))?\\s*(\\S.*)?)$");
|
||||||
|
@ -340,6 +340,14 @@ public:
|
|||||||
static const QString c_fencedCodeBlockStartRegExp;
|
static const QString c_fencedCodeBlockStartRegExp;
|
||||||
static const QString c_fencedCodeBlockEndRegExp;
|
static const QString c_fencedCodeBlockEndRegExp;
|
||||||
|
|
||||||
|
// Regular expression for inline mathjax formula.
|
||||||
|
// $..$
|
||||||
|
static const QString c_mathjaxInlineRegExp;
|
||||||
|
|
||||||
|
// Regular expression for block mathjax formula.
|
||||||
|
// $$..$$
|
||||||
|
static const QString c_mathjaxBlockRegExp;
|
||||||
|
|
||||||
// Regular expression for preview image block.
|
// Regular expression for preview image block.
|
||||||
static const QString c_previewImageBlockRegExp;
|
static const QString c_previewImageBlockRegExp;
|
||||||
|
|
||||||
|
@ -635,6 +635,7 @@ void VConfigManager::updateMarkdownEditStyle()
|
|||||||
m_editorColorColumnBg = defaultColor;
|
m_editorColorColumnBg = defaultColor;
|
||||||
m_editorColorColumnFg = defaultColor;
|
m_editorColorColumnFg = defaultColor;
|
||||||
m_editorPreviewImageLineFg = defaultColor;
|
m_editorPreviewImageLineFg = defaultColor;
|
||||||
|
m_editorMathjaxFg = defaultColor;
|
||||||
|
|
||||||
auto editorIt = styles.find("editor");
|
auto editorIt = styles.find("editor");
|
||||||
if (editorIt != styles.end()) {
|
if (editorIt != styles.end()) {
|
||||||
@ -707,6 +708,11 @@ void VConfigManager::updateMarkdownEditStyle()
|
|||||||
if (it != editorIt->end()) {
|
if (it != editorIt->end()) {
|
||||||
m_editorPreviewImageLineFg = "#" + *it;
|
m_editorPreviewImageLineFg = "#" + *it;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
it = editorIt->find("mathjax-foreground");
|
||||||
|
if (it != editorIt->end()) {
|
||||||
|
m_editorMathjaxFg = "#" + *it;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -316,6 +316,8 @@ public:
|
|||||||
|
|
||||||
const QString &getEditorPreviewImageLineFg() const;
|
const QString &getEditorPreviewImageLineFg() const;
|
||||||
|
|
||||||
|
const QString &getEditorMathjaxFg() const;
|
||||||
|
|
||||||
bool getEnableCodeBlockLineNumber() const;
|
bool getEnableCodeBlockLineNumber() const;
|
||||||
void setEnableCodeBlockLineNumber(bool p_enabled);
|
void setEnableCodeBlockLineNumber(bool p_enabled);
|
||||||
|
|
||||||
@ -779,6 +781,9 @@ private:
|
|||||||
// The foreground color of the preview image line.
|
// The foreground color of the preview image line.
|
||||||
QString m_editorPreviewImageLineFg;
|
QString m_editorPreviewImageLineFg;
|
||||||
|
|
||||||
|
// The foreground color of the MathJax.
|
||||||
|
QString m_editorMathjaxFg;
|
||||||
|
|
||||||
// Icon size of tool bar in pixels.
|
// Icon size of tool bar in pixels.
|
||||||
int m_toolBarIconSize;
|
int m_toolBarIconSize;
|
||||||
|
|
||||||
@ -1826,6 +1831,11 @@ inline const QString &VConfigManager::getEditorPreviewImageLineFg() const
|
|||||||
return m_editorPreviewImageLineFg;
|
return m_editorPreviewImageLineFg;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
inline const QString &VConfigManager::getEditorMathjaxFg() const
|
||||||
|
{
|
||||||
|
return m_editorMathjaxFg;
|
||||||
|
}
|
||||||
|
|
||||||
inline bool VConfigManager::getEnableCodeBlockLineNumber() const
|
inline bool VConfigManager::getEnableCodeBlockLineNumber() const
|
||||||
{
|
{
|
||||||
return m_enableCodeBlockLineNumber;
|
return m_enableCodeBlockLineNumber;
|
||||||
|
@ -121,7 +121,11 @@ enum HighlightBlockState
|
|||||||
Comment,
|
Comment,
|
||||||
|
|
||||||
// Verbatim code block.
|
// Verbatim code block.
|
||||||
Verbatim
|
Verbatim,
|
||||||
|
|
||||||
|
// Mathjax. It means the pending state of the block.
|
||||||
|
MathjaxBlock,
|
||||||
|
MathjaxInline
|
||||||
};
|
};
|
||||||
|
|
||||||
// Pages to open on start up.
|
// Pages to open on start up.
|
||||||
|
@ -63,6 +63,7 @@ VMdEditor::VMdEditor(VFile *p_file,
|
|||||||
g_config->getCodeBlockStyles(),
|
g_config->getCodeBlockStyles(),
|
||||||
g_config->getMarkdownHighlightInterval(),
|
g_config->getMarkdownHighlightInterval(),
|
||||||
document());
|
document());
|
||||||
|
m_mdHighlighter->setMathjaxEnabled(g_config->getEnableMathjax());
|
||||||
|
|
||||||
connect(m_mdHighlighter, &HGMarkdownHighlighter::headersUpdated,
|
connect(m_mdHighlighter, &HGMarkdownHighlighter::headersUpdated,
|
||||||
this, &VMdEditor::updateHeaders);
|
this, &VMdEditor::updateHeaders);
|
||||||
|
@ -129,6 +129,45 @@ struct VPreviewInfo
|
|||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
struct MathjaxInfo
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
MathjaxInfo()
|
||||||
|
: m_isBlock(false),
|
||||||
|
m_index(-1),
|
||||||
|
m_length(0)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
bool isValid() const
|
||||||
|
{
|
||||||
|
return m_index >= 0 && m_length > 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool isBlock() const
|
||||||
|
{
|
||||||
|
return m_isBlock;
|
||||||
|
}
|
||||||
|
|
||||||
|
void clear()
|
||||||
|
{
|
||||||
|
m_isBlock = false;
|
||||||
|
m_index = -1;
|
||||||
|
m_length = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Inline or block formula.
|
||||||
|
bool m_isBlock;
|
||||||
|
|
||||||
|
// Start index wihtin block, including the start mark.
|
||||||
|
int m_index;
|
||||||
|
|
||||||
|
// Length of this mathjax, including the end mark.
|
||||||
|
int m_length;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
// User data for each block.
|
// User data for each block.
|
||||||
class VTextBlockData : public QTextBlockUserData
|
class VTextBlockData : public QTextBlockUserData
|
||||||
{
|
{
|
||||||
@ -153,6 +192,16 @@ public:
|
|||||||
|
|
||||||
void setCodeBlockIndentation(int p_indent);
|
void setCodeBlockIndentation(int p_indent);
|
||||||
|
|
||||||
|
void clearMathjax();
|
||||||
|
|
||||||
|
const MathjaxInfo &getPendingMathjax() const;
|
||||||
|
|
||||||
|
void setPendingMathjax(const MathjaxInfo &p_info);
|
||||||
|
|
||||||
|
const QVector<MathjaxInfo> getMathjax() const;
|
||||||
|
|
||||||
|
void addMathjax(const MathjaxInfo &p_info);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
// Check the order of elements.
|
// Check the order of elements.
|
||||||
bool checkOrder() const;
|
bool checkOrder() const;
|
||||||
@ -162,6 +211,12 @@ private:
|
|||||||
|
|
||||||
// Indentation of the this code block if this block is a fenced code block.
|
// Indentation of the this code block if this block is a fenced code block.
|
||||||
int m_codeBlockIndentation;
|
int m_codeBlockIndentation;
|
||||||
|
|
||||||
|
// Pending Mathjax info, such as this block is the start of a Mathjax formula.
|
||||||
|
MathjaxInfo m_pendingMathjax;
|
||||||
|
|
||||||
|
// Mathjax info ends in this block.
|
||||||
|
QVector<MathjaxInfo> m_mathjax;
|
||||||
};
|
};
|
||||||
|
|
||||||
inline const QVector<VPreviewInfo *> &VTextBlockData::getPreviews() const
|
inline const QVector<VPreviewInfo *> &VTextBlockData::getPreviews() const
|
||||||
@ -178,4 +233,31 @@ inline void VTextBlockData::setCodeBlockIndentation(int p_indent)
|
|||||||
{
|
{
|
||||||
m_codeBlockIndentation = p_indent;
|
m_codeBlockIndentation = p_indent;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
inline void VTextBlockData::clearMathjax()
|
||||||
|
{
|
||||||
|
m_pendingMathjax.clear();
|
||||||
|
m_mathjax.clear();
|
||||||
|
}
|
||||||
|
|
||||||
|
inline const MathjaxInfo &VTextBlockData::getPendingMathjax() const
|
||||||
|
{
|
||||||
|
return m_pendingMathjax;
|
||||||
|
}
|
||||||
|
|
||||||
|
inline void VTextBlockData::setPendingMathjax(const MathjaxInfo &p_info)
|
||||||
|
{
|
||||||
|
m_pendingMathjax = p_info;
|
||||||
|
}
|
||||||
|
|
||||||
|
inline const QVector<MathjaxInfo> VTextBlockData::getMathjax() const
|
||||||
|
{
|
||||||
|
return m_mathjax;
|
||||||
|
}
|
||||||
|
|
||||||
|
inline void VTextBlockData::addMathjax(const MathjaxInfo &p_info)
|
||||||
|
{
|
||||||
|
m_mathjax.append(p_info);
|
||||||
|
}
|
||||||
|
|
||||||
#endif // VTEXTBLOCKDATA_H
|
#endif // VTEXTBLOCKDATA_H
|
||||||
|
Loading…
x
Reference in New Issue
Block a user