summaryrefslogtreecommitdiff
path: root/src/Math.hs
diff options
context:
space:
mode:
Diffstat (limited to 'src/Math.hs')
-rw-r--r--src/Math.hs63
1 files changed, 45 insertions, 18 deletions
diff --git a/src/Math.hs b/src/Math.hs
index e927fdd..db01f75 100644
--- a/src/Math.hs
+++ b/src/Math.hs
@@ -2,40 +2,61 @@ module Math
2 ( compileMath 2 ( compileMath
3 ) where 3 ) where
4 4
5import System.IO (stdout, stderr, hPutStrLn, writeFile, readFile)
5import System.IO.Temp (withSystemTempDirectory) 6import System.IO.Temp (withSystemTempDirectory)
6import System.Process (callProcess) 7import System.Process (callProcess, readProcessWithExitCode)
7import System.Directory (copyFile, getCurrentDirectory, setCurrentDirectory) 8import System.Directory (copyFile, getCurrentDirectory, setCurrentDirectory)
8import System.FilePath (takeFileName, FilePath(..), (</>)) 9import System.FilePath (takeFileName, FilePath(..), (</>))
10import System.Exit (ExitCode(..))
9 11
10import Control.Monad 12import Control.Monad (when)
11import Control.Exception (bracket) 13import Control.Exception (bracket, throwIO)
14import Data.Maybe (fromMaybe, listToMaybe)
15
16import Control.Monad.Writer.Strict (WriterT(..), execWriterT, tell)
17import Control.Monad.Trans (liftIO)
12 18
13import Control.DeepSeq (($!!)) 19import Control.DeepSeq (($!!))
14 20
15compileMath :: String -> IO String 21import Text.Regex.TDFA ((=~))
22
23instance Monoid ExitCode where
24 mempty = ExitSuccess
25 (ExitFailure a) `mappend` _ = ExitFailure a
26 ExitSuccess `mappend` x@(ExitFailure _) = x
27 ExitSuccess `mappend` ExitSuccess = ExitSuccess
28
29
30compileMath :: String -> IO (String, String)
16compileMath = withSystemTempDirectory "math" . compileMath' 31compileMath = withSystemTempDirectory "math" . compileMath'
17 32
18compileMath' :: String -> FilePath -> IO String 33compileMath' :: String -> FilePath -> IO (String, String)
19compileMath' input tmpDir = do 34compileMath' input tmpDir = do
20 mapM_ (copyToTmp . ("tex" </>)) [ "preamble.tex" 35 mapM_ (copyToTmp . ("tex" </>)) [ "preamble.tex"
21 , "preview.dtx" 36 , "preview.dtx"
22 , "preview.ins" 37 , "preview.ins"
23 ] 38 ]
24 withCurrentDirectory tmpDir $ do 39 (exitCode, out, err) <- withCurrentDirectory tmpDir $ execWriterT $ do
25 callProcess "latex" [ "-interaction=batchmode" 40 run "latex" [ "-interaction=batchmode"
26 , "preview.ins" 41 , "preview.ins"
27 ] 42 ] ""
28 writeFile (tmpDir </> "image.tex") input 43 liftIO $ writeFile (tmpDir </> "image.tex") input
29 callProcess "latex" [ "-interaction=batchmode" 44 run "latex" [ "-interaction=batchmode"
30 , "image.tex" 45 , "image.tex"
31 ] 46 ] ""
32 callProcess "dvisvgm" [ "--exact" 47 run "dvisvgm" [ "--exact"
33 , "--no-fonts" 48 , "--no-fonts"
34 , tmpDir </> "image.dvi" 49 , tmpDir </> "image.dvi"
35 ] 50 ] ""
36 (\x -> return $!! x) =<< (readFile $ tmpDir </> "image.svg") 51 when (exitCode /= ExitSuccess) $ do
52 hPutStrLn stdout out
53 hPutStrLn stderr err
54 throwIO exitCode
55 (\x -> return $!! (x, extractAlignment err)) =<< (readFile $ tmpDir </> "image.svg")
37 where 56 where
38 copyToTmp fp = copyFile fp (tmpDir </> takeFileName fp) 57 copyToTmp fp = copyFile fp (tmpDir </> takeFileName fp)
58 run :: String -> [String] -> String -> WriterT (ExitCode, String, String) IO ()
59 run bin args stdin = tell =<< liftIO (readProcessWithExitCode bin args stdin)
39 60
40withCurrentDirectory :: FilePath -- ^ Directory to execute in 61withCurrentDirectory :: FilePath -- ^ Directory to execute in
41 -> IO a -- ^ Action to be executed 62 -> IO a -- ^ Action to be executed
@@ -44,3 +65,9 @@ withCurrentDirectory dir action =
44 bracket getCurrentDirectory setCurrentDirectory $ \ _ -> do 65 bracket getCurrentDirectory setCurrentDirectory $ \ _ -> do
45 setCurrentDirectory dir 66 setCurrentDirectory dir
46 action 67 action
68
69extractAlignment :: String -> String
70extractAlignment = fromMaybe "0pt" . extract . (=~ "depth=([^\\s]+)")
71 where
72 extract :: (String, String, String, [String]) -> Maybe String
73 extract (_, _, _, xs) = listToMaybe xs