Skip to content

Commit 2e98318

Browse files
authored
math2svg: SVG caching (#155)
1 parent cbd600a commit 2e98318

File tree

2 files changed

+57
-11
lines changed

2 files changed

+57
-11
lines changed

math2svg/README.md

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,12 @@ No Internet connection is required when generating or viewing SVG formulas,
1818
resulting in both absolute privacy and offline, standalone robustness.
1919

2020

21+
## Version history
22+
23+
- 2021-01-19: SVG caching
24+
- 2021-01-16: Initial release
25+
26+
2127
## Requirements
2228

2329
First, use the package manager of your operating system to install `pandoc`,
@@ -54,7 +60,7 @@ pandoc --mathml --filter='math2svg.lua'
5460

5561
The math2svg filter is entirely configurable over
5662
[`--metadata` key value pairs](pandoc.metadata).
57-
Nine configuration keys are available with sensible default values.
63+
Ten configuration keys are available with sensible default values.
5864
Hence, depending on your system and intentions, not all keys are necessarily
5965
required.
6066

@@ -69,6 +75,7 @@ required.
6975
|`math2svg_ex`|`6`|
7076
|`math2svg_width`|`100`|
7177
|`math2svg_extensions`|`''`|
78+
|`math2svg_cache`|`true`|
7279

7380

7481
### Key value `math2svg_tex2svg`
@@ -138,6 +145,11 @@ This MathJaX extension can be loaded by specifying the string `'TeX/AMSmath'`
138145
as the value of the `math2svg_extensions` key.
139146

140147

148+
### Key value `math2svg_cache`
149+
Caching avoids repetition of the SVG rendering of identical math formulas,
150+
both for display and inline math. Caching is on by default.
151+
152+
141153
### Adding `header-includes`
142154
It might turn out useful to systematically include LaTeX macros, for example as
143155
shown below, a series of `\newcommand`.

math2svg/math2svg.lua

Lines changed: 44 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,6 @@
1+
-- VERSION 2021-01-19
2+
3+
14
-- DESCRIPTION
25
--
36
-- This Lua filter for Pandoc converts LaTeX math to MathJax generated
@@ -75,6 +78,17 @@ local extensions = ''
7578
-- /usr/local/lib/node_modules/mathjax-node-cli/node_modules/mathjax/unpacked/\
7679
-- extensions/
7780

81+
-- Speed up conversion by caching SVG.
82+
local cache = true
83+
84+
local _cache = {}
85+
_cache.DisplayMath = {}
86+
_cache.InlineMath = {}
87+
88+
local tags = {}
89+
tags.DisplayMath = {'<span class="math display">', '</span>'}
90+
tags.InlineMath = {'<span class="math inline">', '</span>'}
91+
7892

7993
function Meta(meta)
8094

@@ -87,14 +101,15 @@ function Meta(meta)
87101
ex = tostring(meta.math2svg_ex or ex)
88102
width = tostring(meta.math2svg_width or width)
89103
extensions = tostring(meta.math2svg_extensions or extensions)
104+
cache = tostring(meta.math2svg_cache or cache)
90105

91106
end
92107

93108

94109
function Math(elem)
95110

96111
local svg = nil
97-
local tags = nil
112+
98113
local argumentlist = {
99114
'--speech', speech,
100115
'--linebreaks', linebreaks,
@@ -117,26 +132,45 @@ function Math(elem)
117132
--extensions extra MathJax extensions [default: ""]
118133
-- e.g. 'Safe,TeX/noUndefined'
119134

120-
if elem.mathtype == 'DisplayMath' and display2svg then
121-
svg = pandoc.pipe(tex2svg, argumentlist, '')
122-
tags = {'<span class="math display">', '</span>'}
135+
if (elem.mathtype == 'DisplayMath' and display2svg)
136+
or (elem.mathtype == 'InlineMath' and inline2svg ) then
137+
138+
if cache then
139+
-- Attempt to retrieve cache.
140+
svg = _cache[elem.mathtype][elem.text]
141+
end
142+
143+
if not svg then
144+
145+
if elem.mathtype == 'InlineMath' then
146+
-- Add the --inline argument to the argument list.
147+
table.insert(argumentlist, 1, '--inline')
148+
end
149+
150+
-- Generate SVG.
151+
svg = pandoc.pipe(tex2svg, argumentlist, '')
152+
153+
if cache then
154+
-- Add to cache.
155+
_cache[elem.mathtype][elem.text] = svg
156+
end
123157

124-
elseif elem.mathtype == 'InlineMath' and inline2svg then
125-
table.insert(argumentlist, 1, '--inline')
126-
svg = pandoc.pipe(tex2svg, argumentlist, '')
127-
tags = {'<span class="math inline">', '</span>'}
158+
end
128159

129160
end
130161

162+
-- Return
131163
if svg then
132164

133165
if FORMAT:match '^html.?' then
134-
svg = tags[1] .. svg .. tags[2]
166+
svg = tags[elem.mathtype][1] .. svg .. tags[elem.mathtype][2]
135167
return pandoc.RawInline(FORMAT, svg)
168+
136169
else
137170
local filename = pandoc.sha1(svg) .. '.svg'
138171
pandoc.mediabag.insert(filename, 'image/svg+xml', svg)
139172
return pandoc.Image('', filename)
173+
140174
end
141175

142176
else
@@ -145,7 +179,7 @@ function Math(elem)
145179

146180
end
147181

148-
end
182+
end -- function
149183

150184

151185
-- Redefining the execution order.

0 commit comments

Comments
 (0)