-
-
Save lierdakil/6a95278d02256a74a0fc to your computer and use it in GitHub Desktop.
{-# LANGUAGE OverloadedStrings #-} | |
import Text.Pandoc.JSON | |
import System.Directory | |
import System.FilePath ((</>)) | |
import qualified Data.Hash.MD5 as MD5 | |
import qualified Data.Text as T | |
import System.IO.Temp | |
import System.Process | |
import Control.Monad (unless) | |
main :: IO () | |
main = toJSONFilter mathToSvg | |
mathToSvg :: Inline -> IO Inline | |
mathToSvg m@(Math mathType x) = do | |
let wrap = T.unpack . removeNewline . case mathType of | |
InlineMath -> \x' -> "\\(" <> x' <> "\\)" | |
DisplayMath -> \x' -> "\\[" <> x' <> "\\]" | |
preamble =[ | |
"\\documentclass[border=1pt,varwidth]{standalone}", | |
"\\usepackage{standalone}" <> | |
"\\usepackage{amsmath}" <> | |
"\\usepackage{amssymb}" <> | |
"\\usepackage{cancel}" <> | |
"\\begin{document}" | |
] | |
postamble = [ "\\end{document}" ] | |
removeNewline = T.filter (`notElem` ("\r\n" :: [Char])) | |
tempDir <- getTemporaryDirectory | |
let cacheDir = tempDir </> "pandoc.texsvg.cache" | |
createDirectoryIfMissing True cacheDir | |
let mathHash = MD5.md5s $ MD5.Str $ show m | |
outfilename = cacheDir </> mathHash <> ".svg" | |
fileExists <- doesFileExist outfilename | |
unless fileExists $ | |
withSystemTempDirectory "pandoc.dir" $ \tmpDir -> | |
do | |
origDir <- getCurrentDirectory | |
setCurrentDirectory tmpDir | |
_ <- readProcess "latex" (preamble <> [wrap x] <> postamble) [] | |
_ <- readProcess "dvisvgm" | |
["-b2pt", "-Z1.2", "-n", "-o", outfilename, "standalone.dvi"] [] | |
setCurrentDirectory origDir | |
svg <- T.pack <$> readFile outfilename | |
return $ RawInline (Format "html") $ case mathType of | |
InlineMath -> svg | |
DisplayMath -> "<p>" <> svg <> "</p>" | |
mathToSvg x = return x |
Yeah... this filter is pretty outdated. Let me see if I can easily update it.
Okay, updated, but tbh, it'd be probably easier to write a lua filter that would essentially do the same thing. All this filter does is basically run latex
and then convert its output to SVG using dvisvgm
for each math element in document. Should be pretty easy to implement in pandoc Lua I think. The only caveat is it does some hashing for caching, because otherwise it's very slow, and hashing isn't that easy with Lua. Doable though.
Hi @lierdakil i try to make a lua filter, but i am a newer in either lua or haskell, and i failed to install pandoc via cabal...thus i try to make a lua version:
local default_template = [[
\documentclass[12pt,preview]{standalone}
{{ preamble }}
\begin{document}
\begin{preview}
{{ code }}
\end{preview}
\end{document}
]]
local default_preamble = [[
\usepackage[utf8x]{inputenc}
\usepackage{amsmath}
\usepackage{amsfonts}
\usepackage{amssymb}
\usepackage{amstext}
\usepackage{newtxtext}
\usepackage{mhchem}
\usepackage{chemfig}
\usepackage[libertine]{newtxmath}
\DeclareOldFontCommand{\rm}{\normalfont\rmfamily}{\mathrm}
\DeclareOldFontCommand{\sf}{\normalfont\sffamily}{\mathsf}
\DeclareOldFontCommand{\tt}{\normalfont\ttfamily}{\mathtt}
\DeclareOldFontCommand{\bf}{\normalfont\bfseries}{\mathbf}
\DeclareOldFontCommand{\it}{\normalfont\itshape}{\mathit}
\DeclareOldFontCommand{\sl}{\normalfont\slshape}{\@nomath\sl}
\DeclareOldFontCommand{\sc}{\normalfont\scshape}{\@nomath\sc}
\newcommand{\N}{\mathbb{N}}
\newcommand{\R}{\mathbb{R}}
\newcommand{\Z}{\mathbb{Z}}
]]
function exec_math (elem)
-- Convert Math El -> DVI via latex --
mathEq = default_template:gsub("{{ preamble }}", default_preamble):gsub("{{ code }}", elem.text)
local tex = io.open("input.tex", "w")
tex:write(mathEq)
io.close(tex)
os.execute("latex input.tex")
os.execute("dvisvgm --no-fonts input.dvi output.svg")
local svg = io.open("output.svg", "rb")
if not svg then
return nil
end
local content = svg:read "*a"
local output
if elem.mathtype == 'InlineMath' then
output = content
else
output = "<p>" .. content .. "<p>"
end
elem = pandoc.RawInline('html', output)
return elem
end
return {
{ Math = exec_math }
}
but after generating svg with markdown math $\chemfig{C([2]-H)([6]=H)}$
and return a RawInline elem, it still renders a <span class="math inline">$\chemfig{C([2]-H)([6]=H)}$</span>
, and log a warning in the console:
[WARNING] Could not convert TeX math \chemfig{C([2]-H)([6]=H)}, rendering as TeX:
\chemfig{C([2]-H)([6]=H)}
^
unexpected control sequence \chemfig
expecting "%", "\\label", "\\tag", "\\nonumber" or whitespace
Do you have any idea how to fix it?.....
a google group link pubed by myself.. https://groups.google.com/g/pandoc-discuss/c/4CirnNd-ETs
To begin with, your call to dvisvgm
is not quite right... Try using dvisvgm --no-fonts input.dvi -o output.svg
. Besides, I'm pretty sure that call to table.insert
will fail, since neither argument is a table. I don't think you need it to begin with.
sorry but i find that you're right... as i have read a wrong document... thx:)
Here's my gist https://gist.github.com/PassionPenguin/43fc09b942cedc428ae246bff8b6e193 :)
Sorry, I seem to have lacked a library. I've now installed "missingH" via debians package manager but get more serious looking errors (see below).