texmath-0.6.7: extra/texmath.hs
{-# LANGUAGE CPP #-}
module Main where
import Text.TeXMath
import Text.XML.Light
import Text.TeXMath.Types
import System.IO
import System.Environment
import Control.Applicative
import System.Console.GetOpt
inHtml :: Element -> Element
inHtml e =
add_attr (Attr (unqual "xmlns") "http://www.w3.org/1999/xhtml") $
unode "html"
[ unode "head" $
add_attr (Attr (unqual "content") "application/xhtml+xml; charset=UTF-8") $
add_attr (Attr (unqual "http-equiv") "Content-Type") $
unode "meta" ()
, unode "body" e ]
getUTF8Contents :: IO String
getUTF8Contents =
hGetContents stdin
type Reader = String -> Either String [Exp]
data Writer = XMLWriter (DisplayType -> [Exp] -> Element)
| StringWriter (DisplayType -> [Exp] -> String)
readers :: [(String, Reader)]
readers = [
("tex", readLaTeX)
, ("mml", readMathML)]
writers :: [(String, Writer)]
writers = [
("native", StringWriter (\_ es -> show es) )
, ("tex", StringWriter toLaTeX)
, ("omml", XMLWriter toOMML)
, ("xhtml", XMLWriter (\dt e -> inHtml (toMathML dt e)))
, ("mml", XMLWriter toMathML)]
data Options = Options {
optDisplay :: DisplayType
, optIn :: String
, optOut :: String }
def :: Options
def = Options DisplayBlock "latex" "mml"
options :: [OptDescr (Options -> Options)]
options =
[ Option [] ["inline"]
(NoArg (\opts -> opts {optDisplay = DisplayInline}))
"Choose display type"
, Option "f" []
(ReqArg (\s opts -> opts {optIn = s}) "FORMAT")
"Input format"
, Option "t" []
(ReqArg (\s opts -> opts {optOut = s}) "FORMAT")
"Output format"
]
output :: DisplayType -> Writer -> [Exp] -> String
output dt (XMLWriter w) es = output dt (StringWriter (\dt' -> ppTopElement . w dt' )) es
output dt (StringWriter w) es = w dt es
main :: IO ()
main = do
(actions, _, _) <- getOpt RequireOrder options <$> getArgs
let opts = (foldl (.) id actions) def
let reader = case lookup (optIn opts) readers of
Just r -> r
Nothing -> error "Unrecognised reader"
let writer = case lookup (optOut opts) writers of
Just w -> w
Nothing -> error "Unrecognised writer"
inp <- getUTF8Contents
let formula = reader inp
case (formula) of
Left err -> hPutStrLn stderr err
Right v -> putStr (output (optDisplay opts) writer v)