texmath 0.6.0.2 → 0.6.0.3
raw patch · 2 files changed
+118/−106 lines, 2 filesdep ~parsecPVP ok
version bump matches the API change (PVP)
Dependency ranges changed: parsec
API changes (from Hackage documentation)
Files
- Text/TeXMath/Parser.hs +117/−105
- texmath.cabal +1/−1
Text/TeXMath/Parser.hs view
@@ -29,9 +29,12 @@ import qualified Text.ParserCombinators.Parsec.Token as P import Text.ParserCombinators.Parsec.Language import Text.TeXMath.Types+import Control.Applicative ((<*), (*>), (<$>)) +type TP = GenParser Char ()+ texMathDef :: LanguageDef st-texMathDef = LanguageDef +texMathDef = LanguageDef { commentStart = "" , commentEnd = "" , commentLine = "%"@@ -47,18 +50,18 @@ -- The parser -expr1 :: GenParser Char st Exp+expr1 :: TP Exp expr1 = choice [ inbraces , variable , number , texSymbol , text- , root + , root , unary , binary , enclosure- , array+ , environment , diacritical , escaped , unicode@@ -70,29 +73,29 @@ parseFormula inp = either (Left . show) (Right . id) $ parse formula "formula" inp -formula :: GenParser Char st [Exp]+formula :: TP [Exp] formula = do whiteSpace f <- many expr eof return f -expr :: GenParser Char st Exp+expr :: TP Exp expr = do a <- expr1 limits <- limitsIndicator subSup limits a <|> superOrSubscripted limits a <|> return a -limitsIndicator :: GenParser Char st (Maybe Bool)+limitsIndicator :: TP (Maybe Bool) limitsIndicator = try (symbol "\\limits" >> return (Just True)) <|> try (symbol "\\nolimits" >> return (Just False)) <|> return Nothing -inbraces :: GenParser Char st Exp+inbraces :: TP Exp inbraces = liftM EGrouped (braces $ many $ notFollowedBy (char '}') >> expr) -texToken :: GenParser Char st Exp+texToken :: TP Exp texToken = inbraces <|> inbrackets <|> do c <- anyChar spaces@@ -100,19 +103,19 @@ then (ENumber [c]) else (EIdentifier [c]) -inbrackets :: GenParser Char st Exp+inbrackets :: TP Exp inbrackets = liftM EGrouped (brackets $ many $ notFollowedBy (char ']') >> expr) -number :: GenParser Char st Exp+number :: TP Exp number = lexeme $ liftM ENumber $ many1 digit -enclosure :: GenParser Char st Exp+enclosure :: TP Exp enclosure = basicEnclosure <|> left <|> right <|> scaledEnclosure -basicEnclosure :: GenParser Char st Exp+basicEnclosure :: TP Exp basicEnclosure = choice $ map (\(s, v) -> try (symbol s) >> return v) enclosures -left :: GenParser Char st Exp+left :: TP Exp left = try $ do symbol "\\left" enc <- basicEnclosure <|> (try (symbol ".") >> return (ESymbol Open "\xFEFF"))@@ -120,7 +123,7 @@ (ESymbol Open _) -> tilRight enc <|> return (EStretchy enc) _ -> pzero -right :: GenParser Char st Exp+right :: TP Exp right = try $ do symbol "\\right" enc <- basicEnclosure <|> (try (symbol ".") >> return (ESymbol Close "\xFEFF"))@@ -131,7 +134,7 @@ -- We want stuff between \left( and \right) to be in an mrow, -- so that the scaling is based just on this unit, and not the -- whole containing formula.-tilRight :: Exp -> GenParser Char st Exp+tilRight :: Exp -> TP Exp tilRight start = try $ do contents <- manyTill expr (try $ symbol "\\right" >> lookAhead basicEnclosure)@@ -144,88 +147,98 @@ _ -> "" return $ EDelimited startChar endChar contents -scaledEnclosure :: GenParser Char st Exp+scaledEnclosure :: TP Exp scaledEnclosure = try $ do cmd <- command case M.lookup cmd scalers of Just r -> liftM (EScaled r . EStretchy) basicEnclosure- Nothing -> pzero + Nothing -> pzero -endLine :: GenParser Char st Char+endLine :: TP Char endLine = try $ do symbol "\\\\" optional inbrackets -- can contain e.g. [1.0in] for a line height, not yet supported return '\n' -arrayLine :: GenParser Char st ArrayLine+arrayLine :: TP ArrayLine arrayLine = notFollowedBy (try $ char '\\' >> symbol "end" >> return '\n') >> sepBy1 (many (notFollowedBy endLine >> expr)) (symbol "&") -array :: GenParser Char st Exp-array = stdarray <|> eqnarray <|> align <|> cases <|> matrix <|> split+arrayAlignments :: TP [Alignment]+arrayAlignments = try $ do+ as <- braces (many letter)+ let letterToAlignment 'l' = AlignLeft+ letterToAlignment 'c' = AlignCenter+ letterToAlignment 'r' = AlignRight+ letterToAlignment _ = AlignDefault+ return $ map letterToAlignment as -matrix :: GenParser Char st Exp-matrix = matrixWith "pmatrix" "(" ")"- <|> matrixWith "bmatrix" "[" "]"- <|> matrixWith "Bmatrix" "{" "}"- <|> matrixWith "vmatrix" "\x2223" "\x2223"- <|> matrixWith "Vmatrix" "\x2225" "\x2225"+environment :: TP Exp+environment = try $ do+ char '\\'+ symbol "begin"+ name <- char '{' *> manyTill anyChar (char '}')+ spaces+ let name' = filter (/='*') name+ case M.lookup name' environments of+ Just env -> env <* spaces <* char '\\' <* symbol "end"+ <* braces (string name) <* spaces+ Nothing -> mzero -matrixWith :: String -> String -> String -> GenParser Char st Exp-matrixWith keywd opendelim closedelim =- inEnvironment keywd $ do- aligns <- option [] arrayAlignments- lines' <- sepEndBy1 arrayLine endLine- return $ EDelimited opendelim closedelim [EArray aligns lines']+environments :: M.Map String (TP Exp)+environments = M.fromList+ [ ("array", stdarray)+ , ("eqnarray", eqnarray)+ , ("align", align)+ , ("aligned", align)+ , ("alignat", inbraces *> spaces *> align)+ , ("alignedat", inbraces *> spaces *> align)+ , ("flalign", flalign)+ , ("flaligned", flalign)+ , ("cases", cases)+ , ("pmatrix", matrixWith "(" ")")+ , ("bmatrix", matrixWith "[" "]")+ , ("Bmatrix", matrixWith "{" "}")+ , ("vmatrix", matrixWith "\x2223" "\x2223")+ , ("Vmatrix", matrixWith "\x2225" "\x2225")+ , ("split", align)+ , ("multiline", gather)+ , ("gather", gather)+ , ("gathered", gather)+ ] -stdarray :: GenParser Char st Exp-stdarray = inEnvironment "array" $ do+matrixWith :: String -> String -> TP Exp+matrixWith opendelim closedelim = do aligns <- option [] arrayAlignments- liftM (EArray aligns) $ sepEndBy1 arrayLine endLine+ lines' <- sepEndBy1 arrayLine endLine+ return $ EDelimited opendelim closedelim [EArray aligns lines'] -eqnarray :: GenParser Char st Exp-eqnarray = inEnvironment "eqnarray" $- liftM (EArray [AlignRight, AlignCenter, AlignLeft]) $- sepEndBy1 arrayLine endLine+stdarray :: TP Exp+stdarray = do+ aligns <- option [] arrayAlignments+ (EArray aligns) <$> sepEndBy1 arrayLine endLine -align :: GenParser Char st Exp-align = inEnvironment "align" $- liftM (EArray [AlignRight, AlignLeft]) $- sepEndBy1 arrayLine endLine+gather :: TP Exp+gather = (EArray []) <$> sepEndBy arrayLine endLine -cases :: GenParser Char st Exp-cases = inEnvironment "cases" $ do- rs <- sepEndBy1 arrayLine endLine- return $ EDelimited "{" "" [EArray [] rs]+eqnarray :: TP Exp+eqnarray = (EArray [AlignRight, AlignCenter, AlignLeft]) <$>+ sepEndBy1 arrayLine endLine -split :: GenParser Char st Exp-split = inEnvironment "split" $ do- rs <- sepEndBy1 arrayLine endLine- return $ EArray [AlignRight, AlignLeft] rs+align :: TP Exp+align = (EArray [AlignRight, AlignLeft]) <$>+ sepEndBy1 arrayLine endLine -arrayAlignments :: GenParser Char st [Alignment]-arrayAlignments = try $ do- as <- braces (many letter)- let letterToAlignment 'l' = AlignLeft- letterToAlignment 'c' = AlignCenter- letterToAlignment 'r' = AlignRight- letterToAlignment _ = AlignDefault- return $ map letterToAlignment as+flalign :: TP Exp+flalign = (EArray [AlignLeft, AlignRight]) <$>+ sepEndBy1 arrayLine endLine -inEnvironment :: String- -> GenParser Char st Exp- -> GenParser Char st Exp-inEnvironment envType p = do- try $ do char '\\'- symbol "begin"- braces $ symbol envType >> optional (symbol "*")- result <- p- char '\\'- symbol "end"- braces $ symbol envType >> optional (symbol "*")- return result +cases :: TP Exp+cases = do+ rs <- sepEndBy1 arrayLine endLine+ return $ EDelimited "{" "" [EArray [] rs] -variable :: GenParser Char st Exp+variable :: TP Exp variable = do v <- letter spaces@@ -245,7 +258,7 @@ "\x2210","\x2A01","\x2A02","\x2A00","\x2A04"] isConvertible _ = False -subSup :: Maybe Bool -> Exp -> GenParser Char st Exp+subSup :: Maybe Bool -> Exp -> TP Exp subSup limits a = try $ do symbol "_" b <- expr1@@ -256,7 +269,7 @@ Nothing | isConvertible a -> EDownup a b c _ -> ESubsup a b c -superOrSubscripted :: Maybe Bool -> Exp -> GenParser Char st Exp+superOrSubscripted :: Maybe Bool -> Exp -> TP Exp superOrSubscripted limits a = try $ do c <- oneOf "^_" spaces@@ -272,19 +285,18 @@ _ -> ESub a b _ -> pzero -escaped :: GenParser Char st Exp-escaped = lexeme $ try $ +escaped :: TP Exp+escaped = lexeme $ try $ char '\\' >> liftM (ESymbol Ord . (:[])) (satisfy $ not . isAlphaNum) -unicode :: GenParser Char st Exp+unicode :: TP Exp unicode = lexeme $ liftM (ESymbol Ord . (:[])) $ satisfy (not . isAscii) -ensuremath :: GenParser Char st Exp-ensuremath = lexeme $ try $- string "\\ensuremath" >> inbraces+ensuremath :: TP Exp+ensuremath = try $ lexeme (string "\\ensuremath") >> inbraces -command :: GenParser Char st String+command :: TP String command = try $ char '\\' >> liftM ('\\':) (identifier <|> lexeme (count 1 anyChar)) unaryOps :: [String]@@ -319,12 +331,12 @@ parseText (x:xs) = x : parseText xs parseText [] = [] -diacritical :: GenParser Char st Exp+diacritical :: TP Exp diacritical = try $ do c <- command case M.lookup c diacriticals of Just r -> liftM r texToken- Nothing -> pzero + Nothing -> pzero diacriticals :: M.Map String (Exp -> Exp) diacriticals = M.fromList@@ -351,51 +363,51 @@ , ("\\underline", \e -> EUnder e (ESymbol Accent "\x00AF")) ] -unary :: GenParser Char st Exp+unary :: TP Exp unary = try $ do c <- command- unless (c `elem` unaryOps) pzero + unless (c `elem` unaryOps) pzero a <- texToken return $ EUnary c a -text :: GenParser Char st Exp+text :: TP Exp text = try $ do c <- command case M.lookup c textOps of Just f -> liftM f $ braces (many (noneOf "}" <|> (char '\\' >> char '}')))- Nothing -> pzero + Nothing -> pzero -- note: sqrt can be unary, \sqrt{2}, or binary, \sqrt[3]{2}-root :: GenParser Char st Exp+root :: TP Exp root = try $ do try (symbol "\\sqrt") <|> symbol "\\surd" a <- inbrackets b <- texToken return $ EBinary "\\sqrt" b a -binary :: GenParser Char st Exp+binary :: TP Exp binary = try $ do c <- command- unless (c `elem` binaryOps) pzero + unless (c `elem` binaryOps) pzero a <- texToken b <- texToken return $ EBinary c a b -texSymbol :: GenParser Char st Exp+texSymbol :: TP Exp texSymbol = try $ do sym <- operator <|> command case M.lookup sym symbols of Just s -> return s- Nothing -> pzero + Nothing -> pzero -- The lexer lexer :: P.TokenParser st lexer = P.makeTokenParser texMathDef- + lexeme :: CharParser st a -> CharParser st a lexeme = P.lexeme lexer -whiteSpace :: CharParser st () +whiteSpace :: CharParser st () whiteSpace = P.whiteSpace lexer identifier :: CharParser st String@@ -408,7 +420,7 @@ symbol :: String -> CharParser st String symbol = lexeme . P.symbol lexer -braces :: CharParser st a -> CharParser st a +braces :: CharParser st a -> CharParser st a braces = lexeme . P.braces lexer brackets :: CharParser st a -> CharParser st a@@ -500,32 +512,32 @@ , ("\\varepsilon", EIdentifier "\x025B") , ("\\eta", EIdentifier "\x03B7") , ("\\gamma", EIdentifier "\x03B3")- , ("\\Gamma", ESymbol Op "\x0393") + , ("\\Gamma", ESymbol Op "\x0393") , ("\\iota", EIdentifier "\x03B9") , ("\\kappa", EIdentifier "\x03BA") , ("\\lambda", EIdentifier "\x03BB")- , ("\\Lambda", ESymbol Op "\x039B") + , ("\\Lambda", ESymbol Op "\x039B") , ("\\mu", EIdentifier "\x03BC") , ("\\nu", EIdentifier "\x03BD") , ("\\omega", EIdentifier "\x03C9") , ("\\Omega", ESymbol Op "\x03A9") , ("\\phi", EIdentifier "\x03C6") , ("\\varphi", EIdentifier "\x03D5")- , ("\\Phi", ESymbol Op "\x03A6") + , ("\\Phi", ESymbol Op "\x03A6") , ("\\pi", EIdentifier "\x03C0")- , ("\\Pi", ESymbol Op "\x03A0") + , ("\\Pi", ESymbol Op "\x03A0") , ("\\psi", EIdentifier "\x03C8") , ("\\Psi", ESymbol Ord "\x03A8") , ("\\rho", EIdentifier "\x03C1") , ("\\sigma", EIdentifier "\x03C3")- , ("\\Sigma", ESymbol Op "\x03A3") + , ("\\Sigma", ESymbol Op "\x03A3") , ("\\tau", EIdentifier "\x03C4") , ("\\theta", EIdentifier "\x03B8") , ("\\vartheta", EIdentifier "\x03D1")- , ("\\Theta", ESymbol Op "\x0398") + , ("\\Theta", ESymbol Op "\x0398") , ("\\upsilon", EIdentifier "\x03C5") , ("\\xi", EIdentifier "\x03BE")- , ("\\Xi", ESymbol Op "\x039E") + , ("\\Xi", ESymbol Op "\x039E") , ("\\zeta", EIdentifier "\x03B6") , ("\\frac12", ESymbol Ord "\x00BD") , ("\\frac14", ESymbol Ord "\x00BC")@@ -734,7 +746,7 @@ , ("\\sup", EMathOperator "sup") , ("\\tan", EMathOperator "tan") , ("\\tanh", EMathOperator "tanh")- ] + ] -- MathML has a mathvariant attribute which is unimplemented in Firefox -- (see https://bugzilla.mozilla.org/show_bug.cgi?id=114365)
texmath.cabal view
@@ -1,5 +1,5 @@ Name: texmath-Version: 0.6.0.2+Version: 0.6.0.3 Cabal-Version: >= 1.6 Build-type: Custom Synopsis: Conversion of LaTeX math formulas to MathML or OMML.