@@ -19,7 +19,7 @@ Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
20 Module : Text.Pandoc.Parsing
20 Module : Text.Pandoc.Parsing
21 Copyright : Copyright (C) 2006-2010 John MacFarlane
21 Copyright : Copyright (C) 2006-2010 John MacFarlane
22− License : GNU GPL, version 2 or above
22+ License : GNU GPL, version 2 or above
24 Maintainer : John MacFarlane <jgm@berkeley.edu>
24 Maintainer : John MacFarlane <jgm@berkeley.edu>
25 Stability : alpha
25 Stability : alpha
@@ -27,7 +27,9 @@ Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
28A utility library with parsers used in pandoc readers.
28A utility library with parsers used in pandoc readers.
30−module Text.Pandoc.Parsing ( (>>~),
30+module Text.Pandoc.Parsing ( GeneralParser,
32 many1Till,
34 many1Till,
33 notFollowedBy',
35 notFollowedBy',
@@ -86,64 +88,68 @@ import Text.Pandoc.Shared
86import qualified Data.Map as M
88import qualified Data.Map as M
87import Text.TeXMath.Macros (applyMacros, Macro, parseMacroDefinitions)
89import Text.TeXMath.Macros (applyMacros, Macro, parseMacroDefinitions)
91+type GeneralParser st a = GenParser Char st a
93+type PandocParser a = GeneralParser ParserState a
89-- | Like >>, but returns the operation on the left.
95-- | Like >>, but returns the operation on the left.
90-- (Suggested by Tillmann Rendel on Haskell-cafe list.)
96-- (Suggested by Tillmann Rendel on Haskell-cafe list.)
91(>>~) :: (Monad m) => m a -> m b -> m a
97(>>~) :: (Monad m) => m a -> m b -> m a
92a >>~ b = a >>= \x -> b >> return x
98a >>~ b = a >>= \x -> b >> return x
94-- | Parse any line of text
100-- | Parse any line of text
95−anyLine :: GenParser Char st [Char]
101+anyLine :: GeneralParser st String
96anyLine = manyTill anyChar newline
102anyLine = manyTill anyChar newline
98-- | Like @manyTill@, but reads at least one item.
104-- | Like @manyTill@, but reads at least one item.
99−many1Till :: GenParser tok st a
105+many1Till :: GeneralParser st a
100− -> GenParser tok st end
106+ -> GeneralParser st end
101− -> GenParser tok st [a]
107+ -> GeneralParser st [a]
102many1Till p end = do
108many1Till p end = do
103 first <- p
109 first <- p
104 rest <- manyTill p end
110 rest <- manyTill p end
105 return (first:rest)
111 return (first:rest)
107−-- | A more general form of @notFollowedBy@. This one allows any
113+-- | A more general form of @notFollowedBy@. This one allows any
108-- type of parser to be specified, and succeeds only if that parser fails.
114-- type of parser to be specified, and succeeds only if that parser fails.
109-- It does not consume any input.
115-- It does not consume any input.
110−notFollowedBy' :: Show b => GenParser a st b -> GenParser a st ()
116+notFollowedBy' :: Show b => GeneralParser st b -> GeneralParser st ()
111notFollowedBy' p = try $ join $ do a <- try p
117notFollowedBy' p = try $ join $ do a <- try p
112 return (unexpected (show a))
118 return (unexpected (show a))
114 return (return ())
120 return (return ())
115-- (This version due to Andrew Pimlott on the Haskell mailing list.)
121-- (This version due to Andrew Pimlott on the Haskell mailing list.)
117−-- | Parses one of a list of strings (tried in order).
123+-- | Parses one of a list of strings (tried in order).
118−oneOfStrings :: [String] -> GenParser Char st String
124+oneOfStrings :: [String] -> GeneralParser st String
119oneOfStrings listOfStrings = choice $ map (try . string) listOfStrings
125oneOfStrings listOfStrings = choice $ map (try . string) listOfStrings
121-- | Parses a space or tab.
127-- | Parses a space or tab.
122−spaceChar :: CharParser st Char
128+spaceChar :: GeneralParser st Char
123spaceChar = satisfy $ \c -> c == ' ' || c == '\t'
129spaceChar = satisfy $ \c -> c == ' ' || c == '\t'
125-- | Skips zero or more spaces or tabs.
131-- | Skips zero or more spaces or tabs.
126−skipSpaces :: GenParser Char st ()
132+skipSpaces :: GeneralParser st ()
127skipSpaces = skipMany spaceChar
133skipSpaces = skipMany spaceChar
129-- | Skips zero or more spaces or tabs, then reads a newline.
135-- | Skips zero or more spaces or tabs, then reads a newline.
130−blankline :: GenParser Char st Char
136+blankline :: GeneralParser st Char
131blankline = try $ skipSpaces >> newline
137blankline = try $ skipSpaces >> newline
133-- | Parses one or more blank lines and returns a string of newlines.
139-- | Parses one or more blank lines and returns a string of newlines.
134−blanklines :: GenParser Char st [Char]
140+blanklines :: GeneralParser st [Char]
135blanklines = many1 blankline
141blanklines = many1 blankline
137-- | Parses material enclosed between start and end parsers.
143-- | Parses material enclosed between start and end parsers.
138−enclosed :: GenParser Char st t -- ^ start parser
144+enclosed :: GeneralParser st t -- ^ start parser
139− -> GenParser Char st end -- ^ end parser
145+ -> GeneralParser st end -- ^ end parser
140− -> GenParser Char st a -- ^ content parser (to be used repeatedly)
146+ -> GeneralParser st a -- ^ content parser (to be used repeatedly)
141− -> GenParser Char st [a]
147+ -> GeneralParser st [a]
142−enclosed start end parser = try $
148+enclosed start end parser = try $
143 start >> notFollowedBy space >> many1Till parser end
149 start >> notFollowedBy space >> many1Till parser end
145-- | Parse string, case insensitive.
151-- | Parse string, case insensitive.
146−stringAnyCase :: [Char] -> CharParser st String
152+stringAnyCase :: [Char] -> GeneralParser st String
147stringAnyCase [] = string ""
153stringAnyCase [] = string ""
148stringAnyCase (x:xs) = do
154stringAnyCase (x:xs) = do
149 firstChar <- char (toUpper x) <|> char (toLower x)
155 firstChar <- char (toUpper x) <|> char (toLower x)
@@ -151,7 +157,7 @@ stringAnyCase (x:xs) = do
151 return (firstChar:rest)
157 return (firstChar:rest)
153-- | Parse contents of 'str' using 'parser' and return result.
159-- | Parse contents of 'str' using 'parser' and return result.
154−parseFromString :: GenParser tok st a -> [tok] -> GenParser tok st a
160+parseFromString :: GeneralParser st a -> String -> GeneralParser st a
155parseFromString parser str = do
161parseFromString parser str = do
156 oldPos <- getPosition
162 oldPos <- getPosition
157 oldInput <- getInput
163 oldInput <- getInput
@@ -162,8 +168,8 @@ parseFromString parser str = do
162 return result
168 return result
164-- | Parse raw line block up to and including blank lines.
170-- | Parse raw line block up to and including blank lines.
165−lineClump :: GenParser Char st String
171+lineClump :: GeneralParser st String
166−lineClump = blanklines
172+lineClump = blanklines
167 <|> (many1 (notFollowedBy blankline >> anyLine) >>= return . unlines)
173 <|> (many1 (notFollowedBy blankline >> anyLine) >>= return . unlines)
169-- | Parse a string of characters between an open character
175-- | Parse a string of characters between an open character
@@ -172,7 +178,7 @@ lineClump = blanklines
172-- @charsInBalanced '(' ')'@ will parse "(hello (there))"
178-- @charsInBalanced '(' ')'@ will parse "(hello (there))"
173-- and return "hello (there)". Stop if a blank line is
179-- and return "hello (there)". Stop if a blank line is
174-- encountered.
180-- encountered.
175−charsInBalanced :: Char -> Char -> GenParser Char st String
181+charsInBalanced :: Char -> Char -> GeneralParser st String
176charsInBalanced open close = try $ do
182charsInBalanced open close = try $ do
177 char open
183 char open
178 raw <- many $ (many1 (satisfy $ \c ->
184 raw <- many $ (many1 (satisfy $ \c ->
@@ -184,7 +190,7 @@ charsInBalanced open close = try $ do
184 return $ concat raw
190 return $ concat raw
186-- | Like @charsInBalanced@, but allow blank lines in the content.
192-- | Like @charsInBalanced@, but allow blank lines in the content.
187−charsInBalanced' :: Char -> Char -> GenParser Char st String
193+charsInBalanced' :: Char -> Char -> GeneralParser st String
188charsInBalanced' open close = try $ do
194charsInBalanced' open close = try $ do
189 char open
195 char open
190 raw <- many $ (many1 (satisfy $ \c -> c /= open && c /= close))
196 raw <- many $ (many1 (satisfy $ \c -> c /= open && c /= close))
@@ -203,13 +209,13 @@ uppercaseRomanDigits = map toUpper lowercaseRomanDigits
204-- | Parses a roman numeral (uppercase or lowercase), returns number.
210-- | Parses a roman numeral (uppercase or lowercase), returns number.
205romanNumeral :: Bool -- ^ Uppercase if true
211romanNumeral :: Bool -- ^ Uppercase if true
206− -> GenParser Char st Int
212+ -> GeneralParser st Int
207romanNumeral upperCase = do
213romanNumeral upperCase = do
208− let romanDigits = if upperCase
214+ let romanDigits = if upperCase
209− then uppercaseRomanDigits
215+ then uppercaseRomanDigits
210 else lowercaseRomanDigits
216 else lowercaseRomanDigits
211 lookAhead $ oneOf romanDigits
217 lookAhead $ oneOf romanDigits
212− let [one, five, ten, fifty, hundred, fivehundred, thousand] =
218+ let [one, five, ten, fifty, hundred, fivehundred, thousand] =
213 map char romanDigits
219 map char romanDigits
214 thousands <- many thousand >>= (return . (1000 *) . length)
220 thousands <- many thousand >>= (return . (1000 *) . length)
215 ninehundreds <- option 0 $ try $ hundred >> thousand >> return 900
221 ninehundreds <- option 0 $ try $ hundred >> thousand >> return 900
@@ -233,14 +239,14 @@ romanNumeral upperCase = do
234-- Parsers for email addresses and URIs
240-- Parsers for email addresses and URIs
236−emailChar :: GenParser Char st Char
242+emailChar :: GeneralParser st Char
237emailChar = alphaNum <|>
243emailChar = alphaNum <|>
238 satisfy (\c -> c == '-' || c == '+' || c == '_' || c == '.')
244 satisfy (\c -> c == '-' || c == '+' || c == '_' || c == '.')
240−domainChar :: GenParser Char st Char
246+domainChar :: GeneralParser st Char
241domainChar = alphaNum <|> char '-'
247domainChar = alphaNum <|> char '-'
243−domain :: GenParser Char st [Char]
249+domain :: GeneralParser st [Char]
244domain = do
250domain = do
245 first <- many1 domainChar
251 first <- many1 domainChar
246 dom <- many1 $ try (char '.' >> many1 domainChar )
252 dom <- many1 $ try (char '.' >> many1 domainChar )
@@ -248,7 +254,7 @@ domain = do
249-- | Parses an email address; returns original and corresponding
255-- | Parses an email address; returns original and corresponding
250-- escaped mailto: URI.
256-- escaped mailto: URI.
251−emailAddress :: GenParser Char st (String, String)
257+emailAddress :: GeneralParser st (String, String)
252emailAddress = try $ do
258emailAddress = try $ do
253 firstLetter <- alphaNum
259 firstLetter <- alphaNum
254 restAddr <- many emailChar
260 restAddr <- many emailChar
@@ -259,7 +265,7 @@ emailAddress = try $ do
259 return (full, escapeURI $ "mailto:" ++ full)
265 return (full, escapeURI $ "mailto:" ++ full)
261-- | Parses a URI. Returns pair of original and URI-escaped version.
267-- | Parses a URI. Returns pair of original and URI-escaped version.
262−uri :: GenParser Char st (String, String)
268+uri :: GeneralParser st (String, String)
263uri = try $ do
269uri = try $ do
264 let protocols = [ "http:", "https:", "ftp:", "file:", "mailto:",
270 let protocols = [ "http:", "https:", "ftp:", "file:", "mailto:",
265 "news:", "telnet:" ]
271 "news:", "telnet:" ]
@@ -293,8 +299,8 @@ uri = try $ do
293-- displacement (the difference between the source column at the end
299-- displacement (the difference between the source column at the end
294-- and the source column at the beginning). Vertical displacement
300-- and the source column at the beginning). Vertical displacement
295-- (source row) is ignored.
301-- (source row) is ignored.
296−withHorizDisplacement :: GenParser Char st a -- ^ Parser to apply
302+withHorizDisplacement :: GeneralParser st a -- ^ Parser to apply
297− -> GenParser Char st (a, Int) -- ^ (result, displacement)
303+ -> GeneralParser st (a, Int) -- ^ (result, displacement)
298withHorizDisplacement parser = do
304withHorizDisplacement parser = do
299 pos1 <- getPosition
305 pos1 <- getPosition
300 result <- parser
306 result <- parser
@@ -303,43 +309,43 @@ withHorizDisplacement parser = do
304-- | Parses a character and returns 'Null' (so that the parser can move on
310-- | Parses a character and returns 'Null' (so that the parser can move on
305-- if it gets stuck).
311-- if it gets stuck).
306−nullBlock :: GenParser Char st Block
312+nullBlock :: GeneralParser st Block
307nullBlock = anyChar >> return Null
313nullBlock = anyChar >> return Null
309-- | Fail if reader is in strict markdown syntax mode.
315-- | Fail if reader is in strict markdown syntax mode.
310−failIfStrict :: GenParser a ParserState ()
316+failIfStrict :: PandocParser ()
311failIfStrict = do
317failIfStrict = do
312 state <- getState
318 state <- getState
313 if stateStrict state then fail "strict mode" else return ()
319 if stateStrict state then fail "strict mode" else return ()
315-- | Fail unless we're in literate haskell mode.
321-- | Fail unless we're in literate haskell mode.
316−failUnlessLHS :: GenParser tok ParserState ()
322+failUnlessLHS :: PandocParser ()
317failUnlessLHS = do
323failUnlessLHS = do
318 state <- getState
324 state <- getState
319 if stateLiterateHaskell state then return () else fail "Literate haskell feature"
325 if stateLiterateHaskell state then return () else fail "Literate haskell feature"
321-- | Parses backslash, then applies character parser.
327-- | Parses backslash, then applies character parser.
322−escaped :: GenParser Char st Char -- ^ Parser for character to escape
328+escaped :: GeneralParser st Char -- ^ Parser for character to escape
323− -> GenParser Char st Inline
329+ -> GeneralParser st Inline
324escaped parser = try $ do
330escaped parser = try $ do
325 char '\\'
331 char '\\'
326 result <- parser
332 result <- parser
327 return (Str [result])
333 return (Str [result])
329-- | Parses an uppercase roman numeral and returns (UpperRoman, number).
335-- | Parses an uppercase roman numeral and returns (UpperRoman, number).
330−upperRoman :: GenParser Char st (ListNumberStyle, Int)
336+upperRoman :: GeneralParser st (ListNumberStyle, Int)
331upperRoman = do
337upperRoman = do
332 num <- romanNumeral True
338 num <- romanNumeral True
333 return (UpperRoman, num)
339 return (UpperRoman, num)
335-- | Parses a lowercase roman numeral and returns (LowerRoman, number).
341-- | Parses a lowercase roman numeral and returns (LowerRoman, number).
336−lowerRoman :: GenParser Char st (ListNumberStyle, Int)
342+lowerRoman :: GeneralParser st (ListNumberStyle, Int)
337lowerRoman = do
343lowerRoman = do
338 num <- romanNumeral False
344 num <- romanNumeral False
339 return (LowerRoman, num)
345 return (LowerRoman, num)
341-- | Parses a decimal numeral and returns (Decimal, number).
347-- | Parses a decimal numeral and returns (Decimal, number).
342−decimal :: GenParser Char st (ListNumberStyle, Int)
348+decimal :: GeneralParser st (ListNumberStyle, Int)
343decimal = do
349decimal = do
344 num <- many1 digit
350 num <- many1 digit
345 return (Decimal, read num)
351 return (Decimal, read num)
@@ -348,7 +354,7 @@ decimal = do
348-- returns (DefaultStyle, [next example number]). The next
354-- returns (DefaultStyle, [next example number]). The next
349-- example number is incremented in parser state, and the label
355-- example number is incremented in parser state, and the label
350-- (if present) is added to the label table.
356-- (if present) is added to the label table.
351−exampleNum :: GenParser Char ParserState (ListNumberStyle, Int)
357+exampleNum :: PandocParser (ListNumberStyle, Int)
352exampleNum = do
358exampleNum = do
354 lab <- many (alphaNum <|> satisfy (\c -> c == '_' || c == '-'))
360 lab <- many (alphaNum <|> satisfy (\c -> c == '_' || c == '-'))
@@ -362,38 +368,38 @@ exampleNum = do
362 return (Example, num)
368 return (Example, num)
364-- | Parses a '#' returns (DefaultStyle, 1).
370-- | Parses a '#' returns (DefaultStyle, 1).
365−defaultNum :: GenParser Char st (ListNumberStyle, Int)
371+defaultNum :: GeneralParser st (ListNumberStyle, Int)
366defaultNum = do
372defaultNum = do
368 return (DefaultStyle, 1)
374 return (DefaultStyle, 1)
370-- | Parses a lowercase letter and returns (LowerAlpha, number).
376-- | Parses a lowercase letter and returns (LowerAlpha, number).
371−lowerAlpha :: GenParser Char st (ListNumberStyle, Int)
377+lowerAlpha :: GeneralParser st (ListNumberStyle, Int)
372lowerAlpha = do
378lowerAlpha = do
373 ch <- oneOf ['a'..'z']
379 ch <- oneOf ['a'..'z']
374 return (LowerAlpha, ord ch - ord 'a' + 1)
380 return (LowerAlpha, ord ch - ord 'a' + 1)
376-- | Parses an uppercase letter and returns (UpperAlpha, number).
382-- | Parses an uppercase letter and returns (UpperAlpha, number).
377−upperAlpha :: GenParser Char st (ListNumberStyle, Int)
383+upperAlpha :: GeneralParser st (ListNumberStyle, Int)
378upperAlpha = do
384upperAlpha = do
379 ch <- oneOf ['A'..'Z']
385 ch <- oneOf ['A'..'Z']
380 return (UpperAlpha, ord ch - ord 'A' + 1)
386 return (UpperAlpha, ord ch - ord 'A' + 1)
382-- | Parses a roman numeral i or I
388-- | Parses a roman numeral i or I
383−romanOne :: GenParser Char st (ListNumberStyle, Int)
389+romanOne :: GeneralParser st (ListNumberStyle, Int)
384romanOne = (char 'i' >> return (LowerRoman, 1)) <|>
390romanOne = (char 'i' >> return (LowerRoman, 1)) <|>
385 (char 'I' >> return (UpperRoman, 1))
391 (char 'I' >> return (UpperRoman, 1))
387-- | Parses an ordered list marker and returns list attributes.
393-- | Parses an ordered list marker and returns list attributes.
388−anyOrderedListMarker :: GenParser Char ParserState ListAttributes
394+anyOrderedListMarker :: PandocParser ListAttributes
389−anyOrderedListMarker = choice $
395+anyOrderedListMarker = choice $
390 [delimParser numParser | delimParser <- [inPeriod, inOneParen, inTwoParens],
396 [delimParser numParser | delimParser <- [inPeriod, inOneParen, inTwoParens],
391 numParser <- [decimal, exampleNum, defaultNum, romanOne,
397 numParser <- [decimal, exampleNum, defaultNum, romanOne,
392 lowerAlpha, lowerRoman, upperAlpha, upperRoman]]
398 lowerAlpha, lowerRoman, upperAlpha, upperRoman]]
394-- | Parses a list number (num) followed by a period, returns list attributes.
400-- | Parses a list number (num) followed by a period, returns list attributes.
395−inPeriod :: GenParser Char st (ListNumberStyle, Int)
401+inPeriod :: GeneralParser st (ListNumberStyle, Int)
396− -> GenParser Char st ListAttributes
402+ -> GeneralParser st ListAttributes
397inPeriod num = try $ do
403inPeriod num = try $ do
398 (style, start) <- num
404 (style, start) <- num
@@ -401,18 +407,18 @@ inPeriod num = try $ do
401 then DefaultDelim
407 then DefaultDelim
402 else Period
408 else Period
403 return (start, style, delim)
409 return (start, style, delim)
405-- | Parses a list number (num) followed by a paren, returns list attributes.
411-- | Parses a list number (num) followed by a paren, returns list attributes.
406−inOneParen :: GenParser Char st (ListNumberStyle, Int)
412+inOneParen :: GeneralParser st (ListNumberStyle, Int)
407− -> GenParser Char st ListAttributes
413+ -> GeneralParser st ListAttributes
408inOneParen num = try $ do
414inOneParen num = try $ do
409 (style, start) <- num
415 (style, start) <- num
411 return (start, style, OneParen)
417 return (start, style, OneParen)
413-- | Parses a list number (num) enclosed in parens, returns list attributes.
419-- | Parses a list number (num) enclosed in parens, returns list attributes.
414−inTwoParens :: GenParser Char st (ListNumberStyle, Int)
420+inTwoParens :: GeneralParser st (ListNumberStyle, Int)
415− -> GenParser Char st ListAttributes
421+ -> GeneralParser st ListAttributes
416inTwoParens num = try $ do
422inTwoParens num = try $ do
418 (style, start) <- num
424 (style, start) <- num
@@ -421,9 +427,9 @@ inTwoParens num = try $ do
422-- | Parses an ordered list marker with a given style and delimiter,
428-- | Parses an ordered list marker with a given style and delimiter,
423-- returns number.
429-- returns number.
424−orderedListMarker :: ListNumberStyle
430+orderedListMarker :: ListNumberStyle
425− -> ListNumberDelim
431+ -> ListNumberDelim
426− -> GenParser Char ParserState Int
432+ -> PandocParser Int
427orderedListMarker style delim = do
433orderedListMarker style delim = do
428 let num = defaultNum <|> -- # can continue any kind of list
434 let num = defaultNum <|> -- # can continue any kind of list
429 case style of
435 case style of
@@ -443,19 +449,19 @@ orderedListMarker style delim = do
443 return start
449 return start
445-- | Parses a character reference and returns a Str element.
451-- | Parses a character reference and returns a Str element.
446−charRef :: GenParser Char st Inline
452+charRef :: GeneralParser st Inline
447charRef = do
453charRef = do
448 c <- characterReference
454 c <- characterReference
449 return $ Str [c]
455 return $ Str [c]
451-- | Parse a table using 'headerParser', 'rowParser',
457-- | Parse a table using 'headerParser', 'rowParser',
452-- 'lineParser', and 'footerParser'.
458-- 'lineParser', and 'footerParser'.
453−tableWith :: GenParser Char ParserState ([[Block]], [Alignment], [Int])
459+tableWith :: PandocParser ([[Block]], [Alignment], [Int])
454− -> ([Int] -> GenParser Char ParserState [[Block]])
460+ -> ([Int] -> PandocParser [[Block]])
455− -> GenParser Char ParserState sep
461+ -> PandocParser sep
456− -> GenParser Char ParserState end
462+ -> PandocParser end
457− -> GenParser Char ParserState [Inline]
463+ -> PandocParser [Inline]
458− -> GenParser Char ParserState Block
464+ -> PandocParser Block
459tableWith headerParser rowParser lineParser footerParser captionParser = try $ do
465tableWith headerParser rowParser lineParser footerParser captionParser = try $ do
460 caption' <- option [] captionParser
466 caption' <- option [] captionParser
461 (heads, aligns, indices) <- headerParser
467 (heads, aligns, indices) <- headerParser
@@ -473,8 +479,8 @@ tableWith headerParser rowParser lineParser footerParser captionParser = try $ d
473widthsFromIndices :: Int -- Number of columns on terminal
479widthsFromIndices :: Int -- Number of columns on terminal
474 -> [Int] -- Indices
480 -> [Int] -- Indices
475 -> [Double] -- Fractional relative sizes of columns
481 -> [Double] -- Fractional relative sizes of columns
476−widthsFromIndices _ [] = []
482+widthsFromIndices _ [] = []
477−widthsFromIndices numColumns' indices =
483+widthsFromIndices numColumns' indices =
478 let numColumns = max numColumns' (if null indices then 0 else last indices)
484 let numColumns = max numColumns' (if null indices then 0 else last indices)
479 lengths' = zipWith (-) indices (0:indices)
485 lengths' = zipWith (-) indices (0:indices)
480 lengths = reverse $
486 lengths = reverse $
@@ -498,10 +504,10 @@ widthsFromIndices numColumns' indices =
498-- (which may be grid), then the rows,
504-- (which may be grid), then the rows,
499-- which may be grid, separated by blank lines, and
505-- which may be grid, separated by blank lines, and
500-- ending with a footer (dashed line followed by blank line).
506-- ending with a footer (dashed line followed by blank line).
501−gridTableWith :: GenParser Char ParserState Block -- ^ Block parser
507+gridTableWith :: PandocParser Block -- ^ Block parser
502− -> GenParser Char ParserState [Inline] -- ^ Caption parser
508+ -> PandocParser [Inline] -- ^ Caption parser
503 -> Bool -- ^ Headerless table
509 -> Bool -- ^ Headerless table
504− -> GenParser Char ParserState Block
510+ -> PandocParser Block
505gridTableWith block tableCaption headless =
511gridTableWith block tableCaption headless =
506 tableWith (gridTableHeader headless block) (gridTableRow block) (gridTableSep '-') gridTableFooter tableCaption
512 tableWith (gridTableHeader headless block) (gridTableRow block) (gridTableSep '-') gridTableFooter tableCaption
@@ -509,13 +515,13 @@ gridTableSplitLine :: [Int] -> String -> [String]
509gridTableSplitLine indices line = map removeFinalBar $ tail $
515gridTableSplitLine indices line = map removeFinalBar $ tail $
510 splitByIndices (init indices) $ removeTrailingSpace line
516 splitByIndices (init indices) $ removeTrailingSpace line
512−gridPart :: Char -> GenParser Char st (Int, Int)
518+gridPart :: Char -> GeneralParser st (Int, Int)
513gridPart ch = do
519gridPart ch = do
514 dashes <- many1 (char ch)
520 dashes <- many1 (char ch)
516 return (length dashes, length dashes + 1)
522 return (length dashes, length dashes + 1)
518−gridDashedLines :: Char -> GenParser Char st [(Int,Int)]
524+gridDashedLines :: Char -> GeneralParser st [(Int,Int)]
519gridDashedLines ch = try $ char '+' >> many1 (gridPart ch) >>~ blankline
525gridDashedLines ch = try $ char '+' >> many1 (gridPart ch) >>~ blankline
521removeFinalBar :: String -> String
527removeFinalBar :: String -> String
@@ -523,18 +529,18 @@ removeFinalBar =
523 reverse . dropWhile (`elem` " \t") . dropWhile (=='|') . reverse
529 reverse . dropWhile (`elem` " \t") . dropWhile (=='|') . reverse
525-- | Separator between rows of grid table.
531-- | Separator between rows of grid table.
526−gridTableSep :: Char -> GenParser Char ParserState Char
532+gridTableSep :: Char -> PandocParser Char
527gridTableSep ch = try $ gridDashedLines ch >> return '\n'
533gridTableSep ch = try $ gridDashedLines ch >> return '\n'
529-- | Parse header for a grid table.
535-- | Parse header for a grid table.
530gridTableHeader :: Bool -- ^ Headerless table
536gridTableHeader :: Bool -- ^ Headerless table
531− -> GenParser Char ParserState Block
537+ -> PandocParser Block
532− -> GenParser Char ParserState ([[Block]], [Alignment], [Int])
538+ -> PandocParser ([[Block]], [Alignment], [Int])
533gridTableHeader headless block = try $ do
539gridTableHeader headless block = try $ do
534 optional blanklines
540 optional blanklines
535 dashes <- gridDashedLines '-'
541 dashes <- gridDashedLines '-'
536 rawContent <- if headless
542 rawContent <- if headless
537− then return $ repeat ""
543+ then return $ repeat ""
538 else many1
544 else many1
539 (notFollowedBy (gridTableSep '=') >> char '|' >>
545 (notFollowedBy (gridTableSep '=') >> char '|' >>
540 many1Till anyChar newline)
546 many1Till anyChar newline)
@@ -553,16 +559,16 @@ gridTableHeader headless block = try $ do
553 map removeLeadingTrailingSpace rawHeads
559 map removeLeadingTrailingSpace rawHeads
554 return (heads, aligns, indices)
560 return (heads, aligns, indices)
556−gridTableRawLine :: [Int] -> GenParser Char ParserState [String]
562+gridTableRawLine :: [Int] -> PandocParser [String]
557gridTableRawLine indices = do
563gridTableRawLine indices = do
559 line <- many1Till anyChar newline
565 line <- many1Till anyChar newline
560 return (gridTableSplitLine indices line)
566 return (gridTableSplitLine indices line)
562-- | Parse row of grid table.
568-- | Parse row of grid table.
563−gridTableRow :: GenParser Char ParserState Block
569+gridTableRow :: PandocParser Block
565− -> GenParser Char ParserState [[Block]]
571+ -> PandocParser [[Block]]
566gridTableRow block indices = do
572gridTableRow block indices = do
567 colLines <- many1 (gridTableRawLine indices)
573 colLines <- many1 (gridTableRawLine indices)
568 let cols = map ((++ "\n") . unlines . removeOneLeadingSpace) $
574 let cols = map ((++ "\n") . unlines . removeOneLeadingSpace) $
@@ -581,23 +587,23 @@ compactifyCell :: [Block] -> [Block]
581compactifyCell bs = head $ compactify [bs]
587compactifyCell bs = head $ compactify [bs]
583-- | Parse footer for a grid table.
589-- | Parse footer for a grid table.
584−gridTableFooter :: GenParser Char ParserState [Char]
590+gridTableFooter :: PandocParser [Char]
585gridTableFooter = blanklines
591gridTableFooter = blanklines
589-- | Parse a string with a given parser and state.
595-- | Parse a string with a given parser and state.
590−readWith :: GenParser t ParserState a -- ^ parser
596+readWith :: PandocParser a -- ^ parser
591 -> ParserState -- ^ initial state
597 -> ParserState -- ^ initial state
592− -> [t] -- ^ input
598+ -> String -- ^ input
594−readWith parser state input =
600+readWith parser state input =
595 case runParser parser state "source" input of
601 case runParser parser state "source" input of
596 Left err -> error $ "\nError:\n" ++ show err
602 Left err -> error $ "\nError:\n" ++ show err
597 Right result -> result
603 Right result -> result
599-- | Parse a string with @parser@ (for testing).
605-- | Parse a string with @parser@ (for testing).
600−testStringWith :: (Show a) => GenParser Char ParserState a
606+testStringWith :: (Show a) => PandocParser a
601 -> String
607 -> String
603testStringWith parser str = UTF8.putStrLn $ show $
609testStringWith parser str = UTF8.putStrLn $ show $
@@ -623,7 +629,7 @@ data ParserState = ParserState
623 stateHeaderTable :: [HeaderType], -- ^ Ordered list of header types used
629 stateHeaderTable :: [HeaderType], -- ^ Ordered list of header types used
624 stateIndentedCodeClasses :: [String], -- ^ Classes to use for indented code blocks
630 stateIndentedCodeClasses :: [String], -- ^ Classes to use for indented code blocks
625 stateNextExample :: Int, -- ^ Number of next example
631 stateNextExample :: Int, -- ^ Number of next example
626− stateExamples :: M.Map String Int, -- ^ Map from example labels to numbers
632+ stateExamples :: M.Map String Int, -- ^ Map from example labels to numbers
627 stateHasChapters :: Bool, -- ^ True if \chapter encountered
633 stateHasChapters :: Bool, -- ^ True if \chapter encountered
628 stateApplyMacros :: Bool, -- ^ Apply LaTeX macros?
634 stateApplyMacros :: Bool, -- ^ Apply LaTeX macros?
629 stateMacros :: [Macro] -- ^ List of macros defined so far
635 stateMacros :: [Macro] -- ^ List of macros defined so far
@@ -631,7 +637,7 @@ data ParserState = ParserState
631 deriving Show
637 deriving Show
633defaultParserState :: ParserState
639defaultParserState :: ParserState
634−defaultParserState =
640+defaultParserState =
635 ParserState { stateParseRaw = False,
641 ParserState { stateParseRaw = False,
636 stateParserContext = NullState,
642 stateParserContext = NullState,
637 stateQuoteContext = NoQuote,
643 stateQuoteContext = NoQuote,
@@ -655,12 +661,12 @@ defaultParserState =
655 stateApplyMacros = True,
661 stateApplyMacros = True,
656 stateMacros = []}
662 stateMacros = []}
658−data HeaderType
664+data HeaderType
659 = SingleHeader Char -- ^ Single line of characters underneath
665 = SingleHeader Char -- ^ Single line of characters underneath
660 | DoubleHeader Char -- ^ Lines of characters above and below
666 | DoubleHeader Char -- ^ Lines of characters above and below
661 deriving (Eq, Show)
667 deriving (Eq, Show)
663−data ParserContext
669+data ParserContext
664 = ListItemState -- ^ Used when running parser on list item contents
670 = ListItemState -- ^ Used when running parser on list item contents
665 | NullState -- ^ Default state
671 | NullState -- ^ Default state
666 deriving (Eq, Show)
672 deriving (Eq, Show)
@@ -699,25 +705,25 @@ lookupKeySrc table key = case M.lookup key table of
699 Just src -> Just src
705 Just src -> Just src
701-- | Fail unless we're in "smart typography" mode.
707-- | Fail unless we're in "smart typography" mode.
702−failUnlessSmart :: GenParser tok ParserState ()
708+failUnlessSmart :: PandocParser ()
703failUnlessSmart = getState >>= guard . stateSmart
709failUnlessSmart = getState >>= guard . stateSmart
705−smartPunctuation :: GenParser Char ParserState Inline
711+smartPunctuation :: PandocParser Inline
706− -> GenParser Char ParserState Inline
712+ -> PandocParser Inline
707smartPunctuation inlineParser = do
713smartPunctuation inlineParser = do
708 failUnlessSmart
714 failUnlessSmart
709 choice [ quoted inlineParser, apostrophe, dash, ellipses ]
715 choice [ quoted inlineParser, apostrophe, dash, ellipses ]
711−apostrophe :: GenParser Char ParserState Inline
717+apostrophe :: PandocParser Inline
712apostrophe = (char '\'' <|> char '\8217') >> return Apostrophe
718apostrophe = (char '\'' <|> char '\8217') >> return Apostrophe
714−quoted :: GenParser Char ParserState Inline
720+quoted :: PandocParser Inline
715− -> GenParser Char ParserState Inline
721+ -> PandocParser Inline
716quoted inlineParser = doubleQuoted inlineParser <|> singleQuoted inlineParser
722quoted inlineParser = doubleQuoted inlineParser <|> singleQuoted inlineParser
718withQuoteContext :: QuoteContext
724withQuoteContext :: QuoteContext
719− -> (GenParser Char ParserState Inline)
725+ -> (PandocParser Inline)
720− -> GenParser Char ParserState Inline
726+ -> PandocParser Inline
721withQuoteContext context parser = do
727withQuoteContext context parser = do
722 oldState <- getState
728 oldState <- getState
723 let oldQuoteContext = stateQuoteContext oldState
729 let oldQuoteContext = stateQuoteContext oldState
@@ -727,75 +733,75 @@ withQuoteContext context parser = do
727 setState newState { stateQuoteContext = oldQuoteContext }
733 setState newState { stateQuoteContext = oldQuoteContext }
728 return result
734 return result
730−singleQuoted :: GenParser Char ParserState Inline
736+singleQuoted :: PandocParser Inline
731− -> GenParser Char ParserState Inline
737+ -> PandocParser Inline
732singleQuoted inlineParser = try $ do
738singleQuoted inlineParser = try $ do
733 singleQuoteStart
739 singleQuoteStart
734 withQuoteContext InSingleQuote $ many1Till inlineParser singleQuoteEnd >>=
740 withQuoteContext InSingleQuote $ many1Till inlineParser singleQuoteEnd >>=
735 return . Quoted SingleQuote . normalizeSpaces
741 return . Quoted SingleQuote . normalizeSpaces
737−doubleQuoted :: GenParser Char ParserState Inline
743+doubleQuoted :: PandocParser Inline
738− -> GenParser Char ParserState Inline
744+ -> PandocParser Inline
739doubleQuoted inlineParser = try $ do
745doubleQuoted inlineParser = try $ do
740 doubleQuoteStart
746 doubleQuoteStart
741 withQuoteContext InDoubleQuote $ do
747 withQuoteContext InDoubleQuote $ do
742 contents <- manyTill inlineParser doubleQuoteEnd
748 contents <- manyTill inlineParser doubleQuoteEnd
743 return . Quoted DoubleQuote . normalizeSpaces $ contents
749 return . Quoted DoubleQuote . normalizeSpaces $ contents
745−failIfInQuoteContext :: QuoteContext -> GenParser tok ParserState ()
751+failIfInQuoteContext :: QuoteContext -> PandocParser ()
746failIfInQuoteContext context = do
752failIfInQuoteContext context = do
747 st <- getState
753 st <- getState
748 if stateQuoteContext st == context
754 if stateQuoteContext st == context
749 then fail "already inside quotes"
755 then fail "already inside quotes"
750 else return ()
756 else return ()
752−charOrRef :: [Char] -> GenParser Char st Char
758+charOrRef :: [Char] -> GeneralParser st Char
753charOrRef cs =
759charOrRef cs =
754 oneOf cs <|> try (do c <- characterReference
760 oneOf cs <|> try (do c <- characterReference
755 guard (c `elem` cs)
761 guard (c `elem` cs)
756 return c)
762 return c)
758−singleQuoteStart :: GenParser Char ParserState ()
764+singleQuoteStart :: PandocParser ()
759−singleQuoteStart = do
765+singleQuoteStart = do
760 failIfInQuoteContext InSingleQuote
766 failIfInQuoteContext InSingleQuote
761 try $ do charOrRef "'\8216"
767 try $ do charOrRef "'\8216"
762 notFollowedBy (oneOf ")!],.;:-? \t\n")
768 notFollowedBy (oneOf ")!],.;:-? \t\n")
763 notFollowedBy (try (oneOfStrings ["s","t","m","ve","ll","re"] >>
769 notFollowedBy (try (oneOfStrings ["s","t","m","ve","ll","re"] >>
764− satisfy (not . isAlphaNum)))
770+ satisfy (not . isAlphaNum)))
765 -- possess/contraction
771 -- possess/contraction
766 return ()
772 return ()
768−singleQuoteEnd :: GenParser Char st ()
774+singleQuoteEnd :: GeneralParser st ()
769singleQuoteEnd = try $ do
775singleQuoteEnd = try $ do
770 charOrRef "'\8217"
776 charOrRef "'\8217"
771 notFollowedBy alphaNum
777 notFollowedBy alphaNum
773−doubleQuoteStart :: GenParser Char ParserState ()
779+doubleQuoteStart :: PandocParser ()
774doubleQuoteStart = do
780doubleQuoteStart = do
775 failIfInQuoteContext InDoubleQuote
781 failIfInQuoteContext InDoubleQuote
776 try $ do charOrRef "\"\8220"
782 try $ do charOrRef "\"\8220"
777 notFollowedBy (satisfy (\c -> c == ' ' || c == '\t' || c == '\n'))
783 notFollowedBy (satisfy (\c -> c == ' ' || c == '\t' || c == '\n'))
779−doubleQuoteEnd :: GenParser Char st ()
785+doubleQuoteEnd :: GeneralParser st ()
780doubleQuoteEnd = do
786doubleQuoteEnd = do
781 charOrRef "\"\8221"
787 charOrRef "\"\8221"
782 return ()
788 return ()
784−ellipses :: GenParser Char st Inline
790+ellipses :: GeneralParser st Inline
785ellipses = do
791ellipses = do
786 try (charOrRef "…") <|> try (string "..." >> return '…')
792 try (charOrRef "…") <|> try (string "..." >> return '…')
787 return Ellipses
793 return Ellipses
789−dash :: GenParser Char st Inline
795+dash :: GeneralParser st Inline
790dash = enDash <|> emDash
796dash = enDash <|> emDash
792−enDash :: GenParser Char st Inline
798+enDash :: GeneralParser st Inline
793enDash = do
799enDash = do
794 try (charOrRef "–") <|>
800 try (charOrRef "–") <|>
795 try (char '-' >> lookAhead (satisfy isDigit) >> return '–')
801 try (char '-' >> lookAhead (satisfy isDigit) >> return '–')
796 return EnDash
802 return EnDash
798−emDash :: GenParser Char st Inline
804+emDash :: GeneralParser st Inline
799emDash = do
805emDash = do
800 try (charOrRef "—") <|> (try $ string "--" >> optional (char '-') >> return '—')
806 try (charOrRef "—") <|> (try $ string "--" >> optional (char '-') >> return '—')
801 return EmDash
807 return EmDash
@@ -805,7 +811,7 @@ emDash = do
807-- | Parse a \newcommand or \renewcommand macro definition.
813-- | Parse a \newcommand or \renewcommand macro definition.
808−macro :: GenParser Char ParserState Block
814+macro :: PandocParser Block
809macro = do
815macro = do
810 getState >>= guard . stateApplyMacros
816 getState >>= guard . stateApplyMacros
811 inp <- getInput
817 inp <- getInput
@@ -817,11 +823,10 @@ macro = do
817 return Null
823 return Null
819-- | Apply current macros to string.
825-- | Apply current macros to string.
820−applyMacros' :: String -> GenParser Char ParserState String
826+applyMacros' :: String -> PandocParser String
821applyMacros' target = do
827applyMacros' target = do
822 apply <- liftM stateApplyMacros getState
828 apply <- liftM stateApplyMacros getState
824 then do macros <- liftM stateMacros getState
830 then do macros <- liftM stateMacros getState
825 return $ applyMacros macros target
831 return $ applyMacros macros target
826 else return target
832 else return target