git.iko.soy/typeable/pandoc
on master help sign in
Add support for writing nested tables to asciidoc (#6972)
668596ctimo-a
src/Text/Pandoc/Writers/AsciiDoc.hs+32−7
@@ -37,6 +37,7 @@ import Text.Pandoc.Shared
37import Text.Pandoc.Templates (renderTemplate)
37import Text.Pandoc.Templates (renderTemplate)
38import Text.Pandoc.Writers.Shared
38import Text.Pandoc.Writers.Shared
39
39
40+
40data WriterState = WriterState { defListMarker :: Text
41data WriterState = WriterState { defListMarker :: Text
41 , orderedListLevel :: Int
42 , orderedListLevel :: Int
42 , bulletListLevel :: Int
43 , bulletListLevel :: Int
@@ -45,6 +46,10 @@ data WriterState = WriterState { defListMarker :: Text
45 , asciidoctorVariant :: Bool
46 , asciidoctorVariant :: Bool
46 , inList :: Bool
47 , inList :: Bool
47 , hasMath :: Bool
48 , hasMath :: Bool
49+ -- |0 is no table
50+ -- 1 is top level table
51+ -- 2 is a table in a table
52+ , tableNestingLevel :: Int
48 }
53 }
49
54
50defaultWriterState :: WriterState
55defaultWriterState :: WriterState
@@ -56,6 +61,7 @@ defaultWriterState = WriterState { defListMarker = "::"
56 , asciidoctorVariant = False
61 , asciidoctorVariant = False
57 , inList = False
62 , inList = False
58 , hasMath = False
63 , hasMath = False
64+ , tableNestingLevel = 0
59 }
65 }
60
66
61-- | Convert Pandoc to AsciiDoc.
67-- | Convert Pandoc to AsciiDoc.
@@ -194,7 +200,7 @@ blockToAsciiDoc opts (BlockQuote blocks) = do
194 else contents
200 else contents
195 let bar = text "____"
201 let bar = text "____"
196 return $ bar $$ chomp contents' $$ bar <> blankline
202 return $ bar $$ chomp contents' $$ bar <> blankline
197−blockToAsciiDoc opts (Table _ blkCapt specs thead tbody tfoot) = do
203+blockToAsciiDoc opts block@(Table _ blkCapt specs thead tbody tfoot) = do
198 let (caption, aligns, widths, headers, rows) =
204 let (caption, aligns, widths, headers, rows) =
199 toLegacyTable blkCapt specs thead tbody tfoot
205 toLegacyTable blkCapt specs thead tbody tfoot
200 caption' <- inlineListToAsciiDoc opts caption
206 caption' <- inlineListToAsciiDoc opts caption
@@ -236,23 +242,42 @@ blockToAsciiDoc opts (Table _ blkCapt specs thead tbody tfoot) = do
236 $ zipWith colspec aligns widths')
242 $ zipWith colspec aligns widths')
237 <> text ","
243 <> text ","
238 <> headerspec <> text "]"
244 <> headerspec <> text "]"
245+
246+ -- construct cells and recurse in case of nested tables
247+ parentTableLevel <- gets tableNestingLevel
248+ let currentNestingLevel = parentTableLevel + 1
249+
250+ modify $ \st -> st{ tableNestingLevel = currentNestingLevel }
251+
252+ let separator = text (if parentTableLevel == 0
253+ then "|" -- top level separator
254+ else "!") -- nested separator
255+
239 let makeCell [Plain x] = do d <- blockListToAsciiDoc opts [Plain x]
256 let makeCell [Plain x] = do d <- blockListToAsciiDoc opts [Plain x]
240− return $ text "|" <> chomp d
257+ return $ separator <> chomp d
241 makeCell [Para x] = makeCell [Plain x]
258 makeCell [Para x] = makeCell [Plain x]
242− makeCell [] = return $ text "|"
259+ makeCell [] = return separator
260+ makeCell bs = if currentNestingLevel == 2
261+ then do
262+ --asciidoc only supports nesting once
263+ report $ BlockNotRendered block
264+ return separator
265+ else do
243− makeCell bs = do d <- blockListToAsciiDoc opts bs
266+ d <- blockListToAsciiDoc opts bs
244− return $ text "a|" $$ d
267+ return $ (text "a" <> separator) $$ d
268+
245 let makeRow cells = hsep `fmap` mapM makeCell cells
269 let makeRow cells = hsep `fmap` mapM makeCell cells
246 rows' <- mapM makeRow rows
270 rows' <- mapM makeRow rows
247 head' <- makeRow headers
271 head' <- makeRow headers
272+ modify $ \st -> st{ tableNestingLevel = parentTableLevel }
248 let head'' = if all null headers then empty else head'
273 let head'' = if all null headers then empty else head'
249 let colwidth = if writerWrapText opts == WrapAuto
274 let colwidth = if writerWrapText opts == WrapAuto
250 then writerColumns opts
275 then writerColumns opts
251 else 100000
276 else 100000
252 let maxwidth = maximum $ map offset (head':rows')
277 let maxwidth = maximum $ map offset (head':rows')
253 let body = if maxwidth > colwidth then vsep rows' else vcat rows'
278 let body = if maxwidth > colwidth then vsep rows' else vcat rows'
254− let border = text "|==="
279+ let border = separator <> text "==="
255− return $
280+ return $
256 caption'' $$ tablespec $$ border $$ head'' $$ body $$ border $$ blankline
281 caption'' $$ tablespec $$ border $$ head'' $$ body $$ border $$ blankline
257blockToAsciiDoc opts (BulletList items) = do
282blockToAsciiDoc opts (BulletList items) = do
258 inlist <- gets inList
283 inlist <- gets inList
test/command/nested-table-to-asciidoc-6942.mdnew file+82
@@ -0,0 +1,82 @@
1+A table within a table should be convertet into a table within table
2+
3+```
4+% pandoc -f html -t asciidoc
5+<!doctype html>
6+<html>
7+<head>
8+<meta charset="utf-8">
9+<title> NestedTables </title>
10+</head>
11+<body>
12+<table>
13+ <tr>
14+ <td >
15+ <table> <tr> <td> a1 </td> <td> a2 </td> </tr> </table>
16+ </td>
17+ <td>b</td>
18+ </tr>
19+ <tr>
20+ <td>c</td> <td>d </td>
21+ </tr>
22+</table>
23+</body>
24+</html>
25+^D
26+[width="100%",cols="50%,50%",]
27+|===
28+a|
29+[cols=",",]
30+!===
31+!a1 !a2
32+!===
33+
34+|b
35+|c |d
36+|===
37+```
38+
39+A table within a table within a table cannot be converted because asciidoc only
40+supports two levels of tables.
41+The table on level 3 is thus converted to level 2 and a warning is produced
42+```
43+% pandoc -f html -t asciidoc --verbose
44+<!doctype html>
45+<html>
46+<head>
47+<meta charset="utf-8">
48+<title> NestedTables </title>
49+</head>
50+<body>
51+<table>
52+ <tr>
53+ <td>
54+ <table> <tr>
55+ <td> a1 </td>
56+ <td>
57+ <table> <tr> <td> 1 </td> <td> 2 </td> </tr> </table>
58+ </td>
59+ </tr> </table>
60+ </td>
61+ <td>b</td>
62+ </tr>
63+ <tr>
64+ <td>c</td> <td>d </td>
65+ </tr>
66+</table>
67+</body>
68+</html>
69+^D
70+[INFO] Not rendering Table ("",[],[]) (Caption Nothing []) [(AlignDefault,ColWidth 0.5),(AlignDefault,ColWidth 0.5)] (TableHead ("",[],[]) []) [TableBody ("",[],[]) (RowHeadColumns 0) [] [Row ("",[],[]) [Cell ("",[],[]) AlignDefault (RowSpan 1) (ColSpan 1) [Plain [Str "a1"]],Cell ("",[],[]) AlignDefault (RowSpan 1) (ColSpan 1) [Table ("",[],[]) (Caption Nothing []) [(AlignDefault,ColWidthDefault),(AlignDefault,ColWidthDefault)] (TableHead ("",[],[]) []) [TableBody ("",[],[]) (RowHeadColumns 0) [] [Row ("",[],[]) [Cell ("",[],[]) AlignDefault (RowSpan 1) (ColSpan 1) [Plain [Str "1"]],Cell ("",[],[]) AlignDefault (RowSpan 1) (ColSpan 1) [Plain [Str "2"]]]]] (TableFoot ("",[],[]) [])]]]] (TableFoot ("",[],[]) [])
71+[width="100%",cols="50%,50%",]
72+|===
73+a|
74+[width="100%",cols="50%,50%",]
75+!===
76+!a1 !
77+!===
78+
79+|b
80+|c |d
81+|===
82+```