git.iko.soy/typeable/pandoc
on master help sign in
Groff writers escaping changes.

- Improve escaping of accented characters with `--ascii`. Combining accents are now handled properly. - Don't escape spaces and tabs in code blocks. This doesn't seem to be necessary.

commit261cbad0ef2f42735c3914c6c448f5f21331de14 authorJohn MacFarlane <jgm@berkeley.edu> dateMon 22 Oct 2018, 23:47 (8 years ago) parent8b204dd
3 files changed+56−54
src/Text/Pandoc/Writers/Groff.hs+24−22 test/writer.man+16−16 test/writer.ms+16−16
src/Text/Pandoc/Writers/Groff.hs+24−22
@@ -43,12 +43,13 @@ import Data.Char (ord, isAscii)
4343import Control.Monad.State.Strict
4444import Data.List (intercalate)
4545import qualified Data.Map as Map
46−import Data.Maybe (fromMaybe)
46+import Data.Maybe (fromMaybe, isJust, catMaybes)
4747import Text.Pandoc.Class (PandocMonad)
4848import Text.Pandoc.Definition
4949import Text.Pandoc.Pretty
5050import Text.Printf (printf)
51−import Text.Pandoc.GroffChar (essentialEscapes, characterCodes)
51+import Text.Pandoc.GroffChar (essentialEscapes, characterCodes,
52+ combiningAccents)
5253
5354data WriterState = WriterState { stHasInlineMath :: Bool
5455 , stFirstPara :: Bool
@@ -79,32 +80,33 @@ type Note = [Block]
7980
8081type MS = StateT WriterState
8182
82−escapeChar :: Bool -> Char -> String
83−escapeChar useAscii c =
84− case Map.lookup c essentialEscapes of
85− Just s -> s
86− Nothing
87− | useAscii
88− , not (isAscii c) ->
89− case Map.lookup c characterCodeMap of
90− Just t -> "\\[" <> t <> "]"
91− Nothing -> printf "\\[u%04X]" (ord c)
92− | otherwise -> [c]
83+combiningAccentsMap :: Map.Map Char String
84+combiningAccentsMap = Map.fromList combiningAccents
9385
9486-- | Escape special characters for groff.
9587escapeString :: Bool -> String -> String
96−escapeString useAscii = concatMap (escapeChar useAscii)
88+escapeString _ [] = []
89+escapeString useAscii (x:xs) =
90+ case Map.lookup x essentialEscapes of
91+ Just s -> s ++ escapeString useAscii xs
92+ Nothing
93+ | isAscii x || not useAscii -> x : escapeString useAscii xs
94+ | otherwise ->
95+ let accents = catMaybes $ takeWhile isJust
96+ (map (\c -> Map.lookup c combiningAccentsMap) xs)
97+ rest = drop (length accents) xs
98+ s = case Map.lookup x characterCodeMap of
99+ Just t -> "\\[" <> unwords (t:accents) <> "]"
100+ Nothing -> "\\[" <> unwords
101+ (printf "u%04X" (ord x) : accents) <> "]"
102+ in s ++ escapeString useAscii rest
97103
98104-- | Escape a literal (code) section for groff.
99105escapeCode :: Bool -> String -> String
100−escapeCode useAScii = intercalate "\n" . map escapeLine . lines
101− where escapeCodeChar ' ' = "\\ "
102− escapeCodeChar '\t' = "\\\t"
103− escapeCodeChar c = escapeChar useAScii c
104− escapeLine codeline =
105− case concatMap escapeCodeChar codeline of
106− a@('.':_) -> "\\&" ++ a
107− b -> b
106+escapeCode useAscii = intercalate "\n" . map escapeLine . lines
107+ where escapeLine xs = case xs of
108+ ('.':_) -> "\\%" ++ escapeString useAscii xs
109+ _ -> escapeString useAscii xs
108110
109111characterCodeMap :: Map.Map Char String
110112characterCodeMap = Map.fromList characterCodes
test/writer.man+16−16
@@ -54,8 +54,8 @@ Code in a block quote:
5454.IP
5555.nf
5656\f[C]
57−sub\ status\ {
58−\ \ \ \ print\ \[dq]working\[dq];
57+sub status {
58+ print \[dq]working\[dq];
5959}
6060\f[R]
6161.fi
@@ -88,13 +88,13 @@ Code:
8888.IP
8989.nf
9090\f[C]
91−\-\-\-\-\ (should\ be\ four\ hyphens)
91+\-\-\-\- (should be four hyphens)
9292
93−sub\ status\ {
94−\ \ \ \ print\ \[dq]working\[dq];
93+sub status {
94+ print \[dq]working\[dq];
9595}
9696
97−this\ code\ block\ is\ indented\ by\ one\ tab
97+this code block is indented by one tab
9898\f[R]
9999.fi
100100.PP
@@ -102,9 +102,9 @@ And:
102102.IP
103103.nf
104104\f[C]
105−\ \ \ \ this\ code\ block\ is\ indented\ by\ two\ tabs
105+ this code block is indented by two tabs
106106
107−These\ should\ not\ be\ escaped:\ \ \[rs]$\ \[rs]\[rs]\ \[rs]>\ \[rs][\ \[rs]{
107+These should not be escaped: \[rs]$ \[rs]\[rs] \[rs]> \[rs][ \[rs]{
108108\f[R]
109109.fi
110110.PP
@@ -364,7 +364,7 @@ orange fruit
364364.IP
365365.nf
366366\f[C]
367−{\ orange\ code\ block\ }
367+{ orange code block }
368368\f[R]
369369.fi
370370.RS
@@ -430,7 +430,7 @@ This should be a code block, though:
430430.nf
431431\f[C]
432432<div>
433−\ \ \ \ foo
433+ foo
434434</div>
435435\f[R]
436436.fi
@@ -454,7 +454,7 @@ Code block:
454454.IP
455455.nf
456456\f[C]
457−<!\-\-\ Comment\ \-\->
457+<!\-\- Comment \-\->
458458\f[R]
459459.fi
460460.PP
@@ -464,7 +464,7 @@ Code:
464464.IP
465465.nf
466466\f[C]
467−<hr\ />
467+<hr />
468468\f[R]
469469.fi
470470.PP
@@ -545,7 +545,7 @@ Here\[cq]s one that has a line break in it:
545545.PP
546546These shouldn\[cq]t be math:
547547.IP \[bu] 2
548−To get the famous equation, write \f[C]$e\ =\ mc\[ha]2$\f[R].
548+To get the famous equation, write \f[C]$e = mc\[ha]2$\f[R].
549549.IP \[bu] 2
550550$22,000 is a \f[I]lot\f[R] of money.
551551So is $34,000.
@@ -653,7 +653,7 @@ This should [not][] be a link.
653653.IP
654654.nf
655655\f[C]
656−[not]:\ /url
656+[not]: /url
657657\f[R]
658658.fi
659659.PP
@@ -690,7 +690,7 @@ Auto\-links should not occur here: \f[C]<http://example.com/>\f[R]
690690.IP
691691.nf
692692\f[C]
693−or\ here:\ <http://example.com/>
693+or here: <http://example.com/>
694694\f[R]
695695.fi
696696.PP
@@ -733,7 +733,7 @@ with list items).
733733.IP
734734.nf
735735\f[C]
736−\ \ {\ <code>\ }
736+ { <code> }
737737\f[R]
738738.fi
739739.PP
test/writer.ms+16−16
@@ -158,8 +158,8 @@ Code in a block quote:
158158.IP
159159.nf
160160\f[C]
161−sub\ status\ {
162−\ \ \ \ print\ \[dq]working\[dq];
161+sub status {
162+ print \[dq]working\[dq];
163163}
164164\f[]
165165.fi
@@ -194,13 +194,13 @@ Code:
194194.IP
195195.nf
196196\f[C]
197−\-\-\-\-\ (should\ be\ four\ hyphens)
197+\-\-\-\- (should be four hyphens)
198198
199−sub\ status\ {
200−\ \ \ \ print\ \[dq]working\[dq];
199+sub status {
200+ print \[dq]working\[dq];
201201}
202202
203−this\ code\ block\ is\ indented\ by\ one\ tab
203+this code block is indented by one tab
204204\f[]
205205.fi
206206.LP
@@ -208,9 +208,9 @@ And:
208208.IP
209209.nf
210210\f[C]
211−\ \ \ \ this\ code\ block\ is\ indented\ by\ two\ tabs
211+ this code block is indented by two tabs
212212
213−These\ should\ not\ be\ escaped:\ \ \[rs]$\ \[rs]\[rs]\ \[rs]>\ \[rs][\ \[rs]{
213+These should not be escaped: \[rs]$ \[rs]\[rs] \[rs]> \[rs][ \[rs]{
214214\f[]
215215.fi
216216.HLINE
@@ -496,7 +496,7 @@ orange fruit
496496.IP
497497.nf
498498\f[C]
499−{\ orange\ code\ block\ }
499+{ orange code block }
500500\f[]
501501.fi
502502.RS
@@ -579,7 +579,7 @@ This should be a code block, though:
579579.nf
580580\f[C]
581581<div>
582−\ \ \ \ foo
582+ foo
583583</div>
584584\f[]
585585.fi
@@ -603,7 +603,7 @@ Code block:
603603.IP
604604.nf
605605\f[C]
606−<!\-\-\ Comment\ \-\->
606+<!\-\- Comment \-\->
607607\f[]
608608.fi
609609.LP
@@ -613,7 +613,7 @@ Code:
613613.IP
614614.nf
615615\f[C]
616−<hr\ />
616+<hr />
617617\f[]
618618.fi
619619.LP
@@ -704,7 +704,7 @@ Here’s one that has a line break in it: @alpha + omega times x sup 2@.
704704.LP
705705These shouldn’t be math:
706706.IP \[bu] 3
707−To get the famous equation, write \f[C]$e\ =\ mc\[ha]2$\f[R].
707+To get the famous equation, write \f[C]$e = mc\[ha]2$\f[R].
708708.IP \[bu] 3
709709$22,000 is a \f[I]lot\f[R] of money.
710710So is $34,000.
@@ -867,7 +867,7 @@ This should [not][] be a link.
867867.IP
868868.nf
869869\f[C]
870−[not]:\ /url
870+[not]: /url
871871\f[]
872872.fi
873873.LP
@@ -939,7 +939,7 @@ Auto\-links should not occur here: \f[C]<http://example.com/>\f[R]
939939.IP
940940.nf
941941\f[C]
942−or\ here:\ <http://example.com/>
942+or here: <http://example.com/>
943943\f[]
944944.fi
945945.HLINE
@@ -975,7 +975,7 @@ with list items).
975975.IP
976976.nf
977977\f[C]
978−\ \ {\ <code>\ }
978+ { <code> }
979979\f[]
980980.fi
981981.LP