stackedit转为TeX表达式的正则替换规则
stackedit是一个比较好的在线数学编辑器, 可以随时写出漂亮的数学公式. 支持mathjax语法. 使用UserCustom extension中如下代码:
userCustom.onPagedownConfigure = function (editor) {
var thmCounter = { num: 0 };
var excsCounter = { num: 0 };
var environmentMap = {
thm: { title: "Theorem" ,counter: thmCounter },
lem: { title: "Lemma" ,counter: thmCounter },
cor: { title: "Corollary" ,counter: thmCounter },
prop: { title: "Property" ,counter: thmCounter },
defn: { title: "Definition" ,counter: thmCounter },
rem: { title: "Remark" ,counter: thmCounter },
prob: { title: "Problem" ,counter: excsCounter },
excs: { title: "Exercise" ,counter: excsCounter },
examp: { title: "Example" ,counter: excsCounter },
proof: { title: "Proof" },
claim: { title: "Claim" }
};
var converter = editor.getConverter();
// Save the preConversion callbacks stack
var preConversion = converter.hooks.preConversion;
converter.hooks.preConversion = function (text) {
// Change \begin...\end to /begin.../end to avoid MathJax processing
text = text.replace(/\\begin{(\w+)}([\s\S]*?)\\end{\1}/g, function (wholeMatch, m1, m2) {
if(!environmentMap[m1]) return wholeMatch;
// At this stage we need to keep the same number of characters for accurate section parsing
return '/begin{' + m1 + '}' + m2 + '/end{' + m1 + '}';
});
// Transform \title and \section into markdown title to take benefit of partial rendering
text = text.replace(/\\(\w+){([^\r\n}]+)}/g, function (wholeMatch, m1, m2) {
// At this stage we need to keep the same number of characters for accurate section parsing
if (m1 == 'section') {
// \section{} has to be replaced by 10 chars
return '\n### ' + m2 + '\n';
}
if (m1 == 'subsection') {
// \subsection{} has to be replaced by 13 chars
return '\n#### ' + m2 + '\n';
}
if (m1 == 'subsubsection') {
// \subsubsection{} has to be replaced by 16 chars
return '\n##### ' + m2 + '\n';
}
if (m1 == 'title') {
// \title{} has to be replaced by 8 chars
return '\n## ' + m2 + '\n';
}
return wholeMatch;
});
// We are replacing the preConversion stack, call the other preConversion callbacks from the old stack
return preConversion(text);
};
converter.hooks.chain("preBlockGamut", function (text, blockGamutHookCallback) {
text = text.replace(/\\ref{(\w+):(\d+)}/g, function (wholeMatch, m1, m2) {
if(!environmentMap[m1]) return wholeMatch;
return '<a class="latex_ref" href="#' + m1 + ':' + m2 + '">' + environmentMap[m1].title + ' ' + m2 + '</a>';
});
text = text.replace(/\\(author|date){([\s\S]*?)}/g, '<div class="latex_$1">$2</div>');
return text.replace(/\/begin{(\w+)}([\s\S]*?)\/end{\1}/g, function (wholeMatch, m1, m2) {
if(!environmentMap[m1]) return wholeMatch;
var result = '<div class="latex_' + m1 + '"><span class="latex_title"></span>' + blockGamutHookCallback(m2);
if (m1 == "proof") {
result += '<span class="latex_proofend" style="float:right">$■$</span>';
}
return result + '</div>';
});
});
var previewContentsElt = document.getElementById('preview-contents');
editor.hooks.chain('onPreviewRefresh', function() {
thmCounter.num = 0;
excsCounter.num = 0;
_.each(previewContentsElt.querySelectorAll('[class^="latex_"]'), function(elt) {
var key = elt.className.match(/^latex_(\S+)/)[1];
var environment = environmentMap[key];
if(!environment) return;
var title = environment.title;
if(environment.counter) {
environment.counter.num++;
title += ' ' + environment.counter.num;
elt.id = key + ':' + environment.counter.num;
}
elt.querySelector('.latex_title').innerHTML = title + '.';
});
});
};
userCustom.onReady = function () {
var style = [
'.latex_thm, .latex_lem, .latex_cor, .latex_defn, .latex_prop, .latex_rem, .latex_claim {',
' font-style:italic;',
' display: block;',
' margin:15px 0;',
'}',
'.latex_prob, .latex_examp, .latex_excs, .latex_proof {',
' font-style:normal;',
' margin: 10px 0;',
' display: block;',
'}',
'.latex_title {',
' float:left;',
' font-weight:bold;',
' padding-right: 10px;',
'}',
'.latex_proofend {',
' float:right;',
'}',
].join('\n');
$("head").append($('<style type="text/css">').html(style));
};
可以非常容易的写出定理等环境: 例如/begin{thm}.../end{thm}, 可以看到与TeX的写法略有不同.
下面我利用WinEdt的正则表达式, 将上述/begin{thm}.../end{thm}转换为标准的\begin{thm}...\end{thm}.
设置如图所示, 然后点击Replace All即可.

需要注意的是WinEdt默认的就是非贪婪(non-greedy)模式, 这与传统的RegEx是不同的.
本作品采用创作共用版权协议, 要求署名、非商业用途和保持一致. 转载本站内容必须也遵循署名-非商业用途-保持一致的创作共用协议.

发表回复