From 9cf27c92c136cce4785744542eaf962c05f1052c Mon Sep 17 00:00:00 2001
From: John MacFarlane <jgm@berkeley.edu>
Date: Tue, 26 Oct 2010 21:06:51 -0700
Subject: [PATCH] Added support for MathJax for displaying math in HTML.

Added --mathjax option.
Added MathJax to HTMLMathMethod.
Supported MathJax in HTML writer.

Resolves Issue #259.
---
 README                          | 27 ++++++++++++++-------------
 man/man1/pandoc.1.md            |  4 ++++
 src/Text/Pandoc/Shared.hs       |  1 +
 src/Text/Pandoc/Writers/HTML.hs | 17 +++++++++++++++--
 src/pandoc.hs                   |  6 ++++++
 5 files changed, 40 insertions(+), 15 deletions(-)

diff --git a/README b/README
index af229b9f4..5020ea0fe 100644
--- a/README
+++ b/README
@@ -331,9 +331,7 @@ For further documentation, see the `pandoc(1)` man page.
     no *url* is provided, the contents of the script will be inserted
     directly; this provides portability at the price of efficiency. If
     you plan to use math on several pages, it is much better to link to
-    a copy of `LaTeXMathML.js`, which can be cached. (See `--jsmath`,
-    `--gladtex`, `--webtex`, and `--mimetex` for alternative ways of
-    dealing with math in HTML.)
+    a copy of `LaTeXMathML.js`, which can be cached.
 
 `--mathml`
 :   causes `pandoc` to convert all TeX math to MathML.
@@ -345,29 +343,31 @@ For further documentation, see the `pandoc(1)` man page.
     TeX math in HTML, Slidy, or S5. The *url* should point to the jsMath
     load script (e.g. `jsMath/easy/load.js`). If it is provided, a link
     to it will be included in the header of standalone HTML documents.
-    (See `--latexmathml`, `--mimetex`, `--webtex`, and `--gladtex` for
-    alternative ways of dealing with math in HTML.)
+
+\--mathjax=*URL*
+:   causes `pandoc` to use [MathJax] to display embedded TeX math in HTML
+    output. The *URL* should point to the `MathJax.js` load script.
+    Pandoc will use MathML with MathJax, so your `config/MathJax.js`
+    file should contain the following settings:
+
+        extensions: ["mml2jax.js"],
+        jax: ["input/MathML", "output/HTML-CSS"],
 
 `--gladtex`*[=url]*
 :   causes TeX formulas to be enclosed in `<eq>` tags in HTML, Slidy, or
     S5 output. This output can then be processed by [gladTeX] to produce
-    links to images with the typeset formulas. (See `--latexmathml`,
-    `--jsmath`, `--webtex`, and `--mimetex` for alternative ways of
-    dealing with math in HTML.)
+    links to images with the typeset formulas.
 
 `--mimetex`*[=url]*
 :   causes TeX formulas to be replaced by `<img>` tags linking to the
     [mimeTeX] CGI script, which will produce images with the typeset
-    formulas. (See `--latexmathml`, `--jsmath`, `--webtex`, and
-    `--gladtex` for alternative ways of dealing with math in HTML.)
+    formulas.
 
 `--webtex`*[=url]*
 :   causes TeX formulas to be replaced by `<img>` tags linking to an
     external service that converts TeX formulas to images. The formula
     will be concatenated with the URL provided. If no URL
-    is specified, the Google Chart API is used. (See `--latexmathml`,
-    `--jsmath`, `--mimetex`, and `--gladtex` for alternative ways of
-    dealing with math in HTML.)
+    is specified, the Google Chart API is used.
 
 `-i` or `--incremental`
 :   causes all lists in Slidy or S5 output to be displayed incrementally by
@@ -470,6 +470,7 @@ For further documentation, see the `pandoc(1)` man page.
 [Smartypants]: http://daringfireball.net/projects/smartypants/
 [LaTeXMathML]: http://math.etsu.edu/LaTeXMathML/
 [jsMath]:  http://www.math.union.edu/~dpvc/jsmath/
+[MathJax]: http://www.mathjax.org/
 [gladTeX]:  http://www.math.uio.no/~martingu/gladtex/index.html
 [mimeTeX]: http://www.forkosh.com/mimetex.html 
 [Dublin Core elements]: http://dublincore.org/documents/dces/
diff --git a/man/man1/pandoc.1.md b/man/man1/pandoc.1.md
index 502b0b98d..28a085b68 100644
--- a/man/man1/pandoc.1.md
+++ b/man/man1/pandoc.1.md
@@ -127,6 +127,10 @@ should pipe input and output through `iconv`:
     The *URL* should point to the jsMath load script; if provided,
     it will be linked to in the header of standalone HTML documents.
 
+\--mathjax=*URL*
+:   Use MathJax to display embedded TeX math in HTML output.
+    The *URL* should point to the `MathJax.js` load script.
+
 \--gladtex
 :   Enclose TeX math in `<eq>` tags in HTML output.  These can then
     be processed by gladTeX to produce links to images of the typeset
diff --git a/src/Text/Pandoc/Shared.hs b/src/Text/Pandoc/Shared.hs
index 633708046..0fdaf42f3 100644
--- a/src/Text/Pandoc/Shared.hs
+++ b/src/Text/Pandoc/Shared.hs
@@ -459,6 +459,7 @@ data HTMLMathMethod = PlainMath
                     | GladTeX
                     | WebTeX String               -- url of TeX->image script.
                     | MathML (Maybe String)       -- url of MathMLinHTML.js
+                    | MathJax String              -- url of MathJax.js
                     deriving (Show, Read, Eq)
 
 -- | Methods for obfuscating email addresses in HTML.
diff --git a/src/Text/Pandoc/Writers/HTML.hs b/src/Text/Pandoc/Writers/HTML.hs
index eaaf18426..7374cb343 100644
--- a/src/Text/Pandoc/Writers/HTML.hs
+++ b/src/Text/Pandoc/Writers/HTML.hs
@@ -134,6 +134,8 @@ pandocToHtml opts (Pandoc (Meta title' authors' date') blocks) = do
                            MathML (Just url) ->
                               script ! 
                               [src url, thetype "text/javascript"] $ noHtml
+                           MathJax url ->
+                              script ! [src url, thetype "text/javascript"] $ noHtml
                            JsMath (Just url) ->
                               script !
                               [src url, thetype "text/javascript"] $ noHtml
@@ -464,8 +466,7 @@ inlineToHtml opts inline =
                                               stringToHtml "”")
                         in  do contents <- inlineListToHtml opts lst
                                return $ leftQuote +++ contents +++ rightQuote
-    (Math t str) -> 
-                        modify (\st -> st {stMath = True}) >> 
+    (Math t str) ->     modify (\st -> st {stMath = True}) >> 
                         (case writerHTMLMathMethod opts of
                                LaTeXMathML _ -> 
                                   -- putting LaTeXMathML in container with class "LaTeX" prevents
@@ -502,6 +503,18 @@ inlineToHtml opts inline =
                                         Left  _ -> inlineListToHtml opts
                                                    (readTeXMath str) >>= return .
                                                      (thespan !  [theclass "math"])
+                               MathJax _ -> do
+                                  let dt = if t == InlineMath
+                                              then DisplayInline
+                                              else DisplayBlock
+                                  let conf = useShortEmptyTags (const False)
+                                               defaultConfigPP
+                                  case texMathToMathML dt str of
+                                        Right r -> return $ primHtml $
+                                                    ppcElement conf r
+                                        Left  _ -> inlineListToHtml opts
+                                                   (readTeXMath str) >>= return .
+                                                     (thespan !  [theclass "math"])
                                PlainMath -> do
                                   x <- inlineListToHtml opts (readTeXMath str)
                                   let m = thespan ! [theclass "math"] $ x
diff --git a/src/pandoc.hs b/src/pandoc.hs
index 3adb9746d..082e337f5 100644
--- a/src/pandoc.hs
+++ b/src/pandoc.hs
@@ -309,6 +309,12 @@ options =
                   "URL")
                  "" -- "Use jsMath for HTML math"
 
+    , Option "" ["mathjax"]
+                 (ReqArg
+                  (\arg opt -> return opt { optHTMLMathMethod = MathJax arg})
+                  "URL")
+                 "" -- "Use MathJax for HTML math"
+
     , Option "" ["gladtex"]
                  (NoArg
                   (\opt -> return opt { optHTMLMathMethod = GladTeX }))