maruku 0.6.1 → 0.7.0.beta1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (263) hide show
  1. checksums.yaml +7 -0
  2. checksums.yaml.gz.sig +0 -0
  3. data.tar.gz.sig +0 -0
  4. data/MIT-LICENSE.txt +20 -0
  5. data/bin/maruku +153 -152
  6. data/bin/marutex +2 -29
  7. data/data/entities.xml +261 -0
  8. data/docs/math.md +14 -18
  9. data/lib/maruku.rb +65 -77
  10. data/lib/maruku/attributes.rb +109 -214
  11. data/lib/maruku/defaults.rb +45 -67
  12. data/lib/maruku/document.rb +43 -0
  13. data/lib/maruku/element.rb +112 -0
  14. data/lib/maruku/errors.rb +71 -0
  15. data/lib/maruku/ext/div.rb +105 -113
  16. data/lib/maruku/ext/fenced_code.rb +97 -0
  17. data/lib/maruku/ext/math.rb +22 -26
  18. data/lib/maruku/ext/math/elements.rb +20 -26
  19. data/lib/maruku/ext/math/mathml_engines/blahtex.rb +92 -104
  20. data/lib/maruku/ext/math/mathml_engines/itex2mml.rb +33 -26
  21. data/lib/maruku/ext/math/mathml_engines/none.rb +11 -19
  22. data/lib/maruku/ext/math/mathml_engines/ritex.rb +2 -4
  23. data/lib/maruku/ext/math/parsing.rb +107 -113
  24. data/lib/maruku/ext/math/to_html.rb +184 -187
  25. data/lib/maruku/ext/math/to_latex.rb +30 -21
  26. data/lib/maruku/helpers.rb +158 -257
  27. data/lib/maruku/html.rb +254 -0
  28. data/lib/maruku/input/charsource.rb +272 -319
  29. data/lib/maruku/input/extensions.rb +62 -63
  30. data/lib/maruku/input/html_helper.rb +220 -189
  31. data/lib/maruku/input/linesource.rb +90 -110
  32. data/lib/maruku/input/mdline.rb +129 -0
  33. data/lib/maruku/input/parse_block.rb +618 -612
  34. data/lib/maruku/input/parse_doc.rb +145 -215
  35. data/lib/maruku/input/parse_span.rb +658 -0
  36. data/lib/maruku/input/rubypants.rb +200 -128
  37. data/lib/maruku/inspect_element.rb +60 -0
  38. data/lib/maruku/maruku.rb +10 -31
  39. data/lib/maruku/output/entity_table.rb +33 -0
  40. data/lib/maruku/output/s5/fancy.rb +462 -462
  41. data/lib/maruku/output/s5/to_s5.rb +115 -135
  42. data/lib/maruku/output/to_html.rb +898 -983
  43. data/lib/maruku/output/to_latex.rb +561 -560
  44. data/lib/maruku/output/to_markdown.rb +207 -162
  45. data/lib/maruku/output/to_s.rb +11 -52
  46. data/lib/maruku/string_utils.rb +129 -179
  47. data/lib/maruku/toc.rb +185 -196
  48. data/lib/maruku/version.rb +33 -38
  49. data/spec/block_docs/abbrev.md +776 -0
  50. data/{tests/unittest → spec/block_docs}/abbreviations.md +11 -20
  51. data/{tests/unittest → spec/block_docs}/alt.md +2 -14
  52. data/{tests/unittest/pending → spec/block_docs}/amps.md +1 -13
  53. data/{tests/unittest → spec/block_docs}/attributes/att2.md +0 -12
  54. data/{tests/unittest → spec/block_docs}/attributes/att3.md +2 -14
  55. data/{tests/unittest → spec/block_docs}/attributes/attributes.md +12 -16
  56. data/{tests/unittest → spec/block_docs}/attributes/circular.md +0 -12
  57. data/{tests/unittest → spec/block_docs}/attributes/default.md +1 -13
  58. data/{tests/unittest → spec/block_docs}/blank.md +0 -12
  59. data/{tests/unittest → spec/block_docs}/blanks_in_code.md +16 -15
  60. data/{tests/unittest/loss.md → spec/block_docs/bug_def.md} +6 -18
  61. data/{tests/unittest → spec/block_docs}/bug_table.md +3 -15
  62. data/{tests/unittest → spec/block_docs}/code.md +7 -14
  63. data/{tests/unittest → spec/block_docs}/code2.md +4 -14
  64. data/{tests/unittest → spec/block_docs}/code3.md +12 -16
  65. data/{tests/unittest → spec/block_docs}/data_loss.md +2 -14
  66. data/{tests/unittest → spec/block_docs}/divs/div1.md +0 -12
  67. data/{tests/unittest → spec/block_docs}/divs/div2.md +0 -12
  68. data/{tests/unittest → spec/block_docs}/divs/div3_nest.md +3 -15
  69. data/{tests/unittest → spec/block_docs}/easy.md +1 -13
  70. data/spec/block_docs/email.md +29 -0
  71. data/{tests/unittest/pending → spec/block_docs}/empty_cells.md +3 -15
  72. data/{tests/unittest → spec/block_docs}/encoding/iso-8859-1.md +1 -14
  73. data/{tests/unittest → spec/block_docs}/encoding/utf-8.md +0 -12
  74. data/{tests/unittest → spec/block_docs}/entities.md +27 -29
  75. data/{tests/unittest/notyet → spec/block_docs}/escape.md +2 -14
  76. data/{tests/unittest → spec/block_docs}/escaping.md +11 -22
  77. data/{tests/unittest → spec/block_docs}/extra_dl.md +2 -13
  78. data/{tests/unittest → spec/block_docs}/extra_header_id.md +14 -20
  79. data/{tests/unittest → spec/block_docs}/extra_table1.md +3 -15
  80. data/spec/block_docs/fenced_code_blocks.md +66 -0
  81. data/spec/block_docs/fenced_code_blocks_highlighted.md +18 -0
  82. data/{tests/unittest → spec/block_docs}/footnotes.md +12 -24
  83. data/spec/block_docs/footnotes2.md +78 -0
  84. data/spec/block_docs/hard.md +25 -0
  85. data/spec/block_docs/header_after_par.md +62 -0
  86. data/{tests/unittest → spec/block_docs}/headers.md +10 -18
  87. data/{tests/unittest → spec/block_docs}/hex_entities.md +7 -18
  88. data/{tests/unittest → spec/block_docs}/hrule.md +5 -12
  89. data/{tests/unittest → spec/block_docs}/html3.md +1 -13
  90. data/{tests/unittest → spec/block_docs}/html4.md +2 -14
  91. data/{tests/unittest → spec/block_docs}/html5.md +2 -14
  92. data/spec/block_docs/html_block_in_para.md +22 -0
  93. data/spec/block_docs/html_inline.md +25 -0
  94. data/spec/block_docs/html_trailing.md +31 -0
  95. data/spec/block_docs/ie.md +62 -0
  96. data/spec/block_docs/iframe.md +29 -0
  97. data/{tests/unittest → spec/block_docs}/images.md +22 -28
  98. data/{tests/unittest → spec/block_docs}/images2.md +7 -17
  99. data/{tests/unittest → spec/block_docs}/inline_html.md +37 -67
  100. data/{tests/unittest → spec/block_docs}/inline_html2.md +1 -13
  101. data/spec/block_docs/inline_html_beginning.md +10 -0
  102. data/spec/block_docs/issue20.md +9 -0
  103. data/spec/block_docs/issue26.md +22 -0
  104. data/spec/block_docs/issue29.md +9 -0
  105. data/spec/block_docs/issue30.md +30 -0
  106. data/spec/block_docs/issue31.md +25 -0
  107. data/spec/block_docs/issue40.md +40 -0
  108. data/spec/block_docs/issue64.md +55 -0
  109. data/spec/block_docs/issue67.md +19 -0
  110. data/spec/block_docs/issue70.md +11 -0
  111. data/spec/block_docs/issue72.md +17 -0
  112. data/spec/block_docs/issue74.md +38 -0
  113. data/spec/block_docs/issue79.md +15 -0
  114. data/spec/block_docs/issue83.md +13 -0
  115. data/spec/block_docs/issue85.md +25 -0
  116. data/spec/block_docs/issue88.md +19 -0
  117. data/spec/block_docs/issue89.md +12 -0
  118. data/spec/block_docs/issue90.md +38 -0
  119. data/{tests/unittest/pending → spec/block_docs}/link.md +21 -18
  120. data/{tests/unittest → spec/block_docs}/links.md +33 -32
  121. data/spec/block_docs/links2.md +21 -0
  122. data/{tests/unittest → spec/block_docs}/list1.md +0 -12
  123. data/{tests/unittest → spec/block_docs}/list12.md +2 -14
  124. data/{tests/unittest → spec/block_docs}/list2.md +2 -14
  125. data/spec/block_docs/list_multipara.md +42 -0
  126. data/{tests/unittest → spec/block_docs}/lists.md +28 -29
  127. data/{tests/unittest → spec/block_docs}/lists10.md +2 -14
  128. data/spec/block_docs/lists11.md +23 -0
  129. data/spec/block_docs/lists12.md +43 -0
  130. data/spec/block_docs/lists13.md +55 -0
  131. data/spec/block_docs/lists14.md +61 -0
  132. data/spec/block_docs/lists15.md +36 -0
  133. data/spec/block_docs/lists6.md +88 -0
  134. data/spec/block_docs/lists7b.md +58 -0
  135. data/spec/block_docs/lists9.md +53 -0
  136. data/{tests/unittest → spec/block_docs}/lists_after_paragraph.md +19 -25
  137. data/spec/block_docs/lists_blank.md +35 -0
  138. data/{tests/unittest/list3.md → spec/block_docs/lists_blockquote_code.md} +2 -14
  139. data/{tests/unittest/list4.md → spec/block_docs/lists_need_blank_line.md} +50 -21
  140. data/spec/block_docs/lists_nested.md +44 -0
  141. data/spec/block_docs/lists_nested_blankline.md +28 -0
  142. data/spec/block_docs/lists_nested_deep.md +43 -0
  143. data/{tests/unittest → spec/block_docs}/lists_ol.md +37 -54
  144. data/spec/block_docs/lists_paraindent.md +47 -0
  145. data/spec/block_docs/lists_tab.md +54 -0
  146. data/spec/block_docs/loss.md +17 -0
  147. data/spec/block_docs/math-blahtex/equations.md +30 -0
  148. data/spec/block_docs/math-blahtex/inline.md +48 -0
  149. data/spec/block_docs/math-blahtex/math2.md +45 -0
  150. data/spec/block_docs/math-blahtex/table.md +25 -0
  151. data/spec/block_docs/math/embedded_invalid_svg.md +79 -0
  152. data/spec/block_docs/math/embedded_svg.md +97 -0
  153. data/spec/block_docs/math/equations.md +44 -0
  154. data/{tests/unittest → spec/block_docs}/math/inline.md +7 -19
  155. data/spec/block_docs/math/math2.md +45 -0
  156. data/{tests/unittest → spec/block_docs}/math/notmath.md +0 -12
  157. data/spec/block_docs/math/raw_mathml.md +87 -0
  158. data/spec/block_docs/math/table.md +25 -0
  159. data/{tests/unittest → spec/block_docs}/math/table2.md +5 -17
  160. data/{tests/unittest → spec/block_docs}/misc_sw.md +181 -118
  161. data/{tests/unittest → spec/block_docs}/olist.md +6 -18
  162. data/{tests/unittest → spec/block_docs}/one.md +0 -12
  163. data/{tests/unittest → spec/block_docs}/paragraph.md +0 -12
  164. data/{tests/unittest → spec/block_docs}/paragraph_rules/dont_merge_ref.md +4 -12
  165. data/{tests/unittest → spec/block_docs}/paragraph_rules/tab_is_blank.md +0 -12
  166. data/{tests/unittest → spec/block_docs}/paragraphs.md +1 -13
  167. data/{tests/unittest → spec/block_docs}/recover/recover_links.md +4 -16
  168. data/{tests/unittest/pending/ref.md → spec/block_docs/ref_with_period.md} +7 -16
  169. data/spec/block_docs/ref_with_title.md +22 -0
  170. data/{tests/unittest → spec/block_docs}/references/long_example.md +16 -23
  171. data/{tests/unittest → spec/block_docs}/references/spaces_and_numbers.md +0 -12
  172. data/{tests/unittest → spec/block_docs}/smartypants.md +24 -31
  173. data/{tests/unittest → spec/block_docs}/syntax_hl.md +13 -17
  174. data/{tests/unittest → spec/block_docs}/table_attributes.md +2 -14
  175. data/spec/block_docs/tables.md +58 -0
  176. data/{tests/unittest → spec/block_docs}/test.md +1 -13
  177. data/{tests/unittest/notyet → spec/block_docs}/ticks.md +1 -13
  178. data/spec/block_docs/toc.md +87 -0
  179. data/{tests/unittest/notyet → spec/block_docs}/triggering.md +14 -25
  180. data/{tests/unittest → spec/block_docs}/underscore_in_words.md +0 -12
  181. data/{tests/unittest → spec/block_docs}/wrapping.md +4 -16
  182. data/spec/block_docs/xml.md +33 -0
  183. data/{tests/unittest → spec/block_docs}/xml2.md +0 -12
  184. data/spec/block_docs/xml3.md +24 -0
  185. data/{tests/unittest → spec/block_docs}/xml_instruction.md +9 -20
  186. data/spec/block_spec.rb +110 -0
  187. data/spec/cli_spec.rb +8 -0
  188. data/spec/span_spec.rb +256 -0
  189. data/spec/spec_helper.rb +2 -0
  190. data/spec/to_html_utf8_spec.rb +13 -0
  191. metadata +205 -243
  192. metadata.gz.sig +3 -0
  193. data/Rakefile +0 -48
  194. data/bin/marudown +0 -29
  195. data/bin/marutest +0 -345
  196. data/docs/changelog.md +0 -334
  197. data/lib/maruku/errors_management.rb +0 -92
  198. data/lib/maruku/ext/math/latex_fix.rb +0 -12
  199. data/lib/maruku/input/parse_span_better.rb +0 -746
  200. data/lib/maruku/input/type_detection.rb +0 -147
  201. data/lib/maruku/output/to_latex_entities.rb +0 -367
  202. data/lib/maruku/output/to_latex_strings.rb +0 -64
  203. data/lib/maruku/structures.rb +0 -167
  204. data/lib/maruku/structures_inspect.rb +0 -87
  205. data/lib/maruku/structures_iterators.rb +0 -61
  206. data/lib/maruku/tests/benchmark.rb +0 -82
  207. data/lib/maruku/tests/new_parser.rb +0 -373
  208. data/lib/maruku/tests/tests.rb +0 -136
  209. data/lib/maruku/usage/example1.rb +0 -33
  210. data/tests/bugs/code_in_links.md +0 -101
  211. data/tests/bugs/complex_escaping.md +0 -38
  212. data/tests/math/syntax.md +0 -46
  213. data/tests/math_usage/document.md +0 -13
  214. data/tests/others/abbreviations.md +0 -11
  215. data/tests/others/blank.md +0 -4
  216. data/tests/others/code.md +0 -5
  217. data/tests/others/code2.md +0 -8
  218. data/tests/others/code3.md +0 -16
  219. data/tests/others/email.md +0 -4
  220. data/tests/others/entities.md +0 -19
  221. data/tests/others/escaping.md +0 -16
  222. data/tests/others/extra_dl.md +0 -101
  223. data/tests/others/extra_header_id.md +0 -13
  224. data/tests/others/extra_table1.md +0 -40
  225. data/tests/others/footnotes.md +0 -17
  226. data/tests/others/headers.md +0 -10
  227. data/tests/others/hrule.md +0 -10
  228. data/tests/others/images.md +0 -20
  229. data/tests/others/inline_html.md +0 -42
  230. data/tests/others/links.md +0 -38
  231. data/tests/others/list1.md +0 -4
  232. data/tests/others/list2.md +0 -5
  233. data/tests/others/list3.md +0 -8
  234. data/tests/others/lists.md +0 -32
  235. data/tests/others/lists_after_paragraph.md +0 -44
  236. data/tests/others/lists_ol.md +0 -39
  237. data/tests/others/misc_sw.md +0 -105
  238. data/tests/others/one.md +0 -1
  239. data/tests/others/paragraphs.md +0 -13
  240. data/tests/others/sss06.md +0 -352
  241. data/tests/others/test.md +0 -4
  242. data/tests/s5/s5profiling.md +0 -48
  243. data/tests/unittest/bug_def.md +0 -28
  244. data/tests/unittest/email.md +0 -32
  245. data/tests/unittest/html2.md +0 -34
  246. data/tests/unittest/ie.md +0 -61
  247. data/tests/unittest/links2.md +0 -34
  248. data/tests/unittest/lists11.md +0 -28
  249. data/tests/unittest/lists6.md +0 -53
  250. data/tests/unittest/lists9.md +0 -76
  251. data/tests/unittest/math/equations.md +0 -86
  252. data/tests/unittest/math/math2.md +0 -57
  253. data/tests/unittest/math/table.md +0 -37
  254. data/tests/unittest/notyet/header_after_par.md +0 -70
  255. data/tests/unittest/red_tests/abbrev.md +0 -1388
  256. data/tests/unittest/red_tests/lists7.md +0 -68
  257. data/tests/unittest/red_tests/lists7b.md +0 -128
  258. data/tests/unittest/red_tests/lists8.md +0 -76
  259. data/tests/unittest/red_tests/xml.md +0 -70
  260. data/tests/unittest/xml3.md +0 -38
  261. data/tests/utf8-files/simple.md +0 -1
  262. data/unit_test_block.sh +0 -5
  263. data/unit_test_span.sh +0 -3
@@ -1,164 +1,209 @@
1
- #--
2
- # Copyright (C) 2006 Andrea Censi <andrea (at) rubyforge.org>
3
- #
4
- # This file is part of Maruku.
5
- #
6
- # Maruku is free software; you can redistribute it and/or modify
7
- # it under the terms of the GNU General Public License as published by
8
- # the Free Software Foundation; either version 2 of the License, or
9
- # (at your option) any later version.
10
- #
11
- # Maruku is distributed in the hope that it will be useful,
12
- # but WITHOUT ANY WARRANTY; without even the implied warranty of
13
- # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14
- # GNU General Public License for more details.
15
- #
16
- # You should have received a copy of the GNU General Public License
17
- # along with Maruku; if not, write to the Free Software
18
- # Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
19
- #++
20
-
21
-
22
- class String
23
- # XXX: markdown escaping
24
- def to_md(c=nil)
25
- to_s
26
- end
27
-
28
- # " andrea censi " => [" andrea ", "censi "]
29
- def mysplit
30
- split.map{|x| x+" "}
31
- end
32
- end
1
+ module MaRuKu::Out::Markdown
2
+
3
+ DefaultLineLength = 40
4
+
5
+ def to_md(context={})
6
+ children_to_md(context)
7
+ end
8
+
9
+ # " andrea censi " => [" andrea ", "censi "]
10
+ def mysplit(c)
11
+ res = c.split.map {|x| x + " " }
12
+ if c[0] == ' ' && res[0]
13
+ res[0] = " " + res[0]
14
+ end
15
+ res
16
+ end
17
+
18
+ def to_md_header(context)
19
+ pounds = "#" * @level
20
+ "#{pounds} #{children_to_md(context)} #{pounds}\n\n"
21
+ end
22
+
23
+ def to_md_inline_code(context)
24
+ "`#{@raw_code}`"
25
+ end
26
+
27
+ def to_md_code(context)
28
+ @raw_code.split("\n").collect { |line| " " + line}.join("\n") + "\n\n"
29
+ end
30
+
31
+ def to_md_quote(context)
32
+ line_length = (context[:line_length] || DefaultLineLength) - 2
33
+ wrap(@children, line_length, context).split(/\n/).collect { |line| "> " + line}.join("\n") + "\n"
34
+ end
35
+
36
+ def to_md_hrule(context)
37
+ "* * *\n"
38
+ end
39
+
40
+ def to_md_emphasis(context)
41
+ "*#{children_to_md(context)}*"
42
+ end
43
+
44
+ def to_md_strong(context)
45
+ "**#{children_to_md(context)}**"
46
+ end
47
+
48
+ def to_md_immediate_link(context)
49
+ "<#{@url}>"
50
+ end
51
+
52
+ def to_md_email_address(context)
53
+ "<#{@email}>"
54
+ end
55
+
56
+ def to_md_entity(context)
57
+ "&#{@entity_name};"
58
+ end
59
+
60
+ def to_md_linebreak(context)
61
+ "\n"
62
+ end
63
+
64
+ def to_md_paragraph(context)
65
+ line_length = context[:line_length] || DefaultLineLength
66
+ wrap(@children, line_length, context)+"\n"
67
+ end
68
+
69
+ def to_md_im_link(context)
70
+ "[#{children_to_md(context)}](#{@url}#{" \"#{@title}\"" if @title})"
71
+ end
72
+
73
+ def to_md_link(context)
74
+ "[#{children_to_md(context)}][#{@ref_id}]"
75
+ end
76
+
77
+ def to_md_im_image(context)
78
+ "![#{children_to_md(context)}](#{@url}#{" \"#{@title}\"" if @title})"
79
+ end
33
80
 
81
+ def to_md_image(context)
82
+ "![#{children_to_md(context)}][#{@ref_id}]"
83
+ end
34
84
 
35
- module MaRuKu; module Out; module Markdown
36
-
37
- DefaultLineLength = 40
38
-
39
- def to_md(context={})
40
- children_to_md(context)
41
- end
42
-
43
- def to_md_paragraph(context)
44
- line_length = context[:line_length] || DefaultLineLength
45
- wrap(@children, line_length, context)+"\n"
46
- end
47
-
48
- def to_md_li_span(context)
49
- len = (context[:line_length] || DefaultLineLength) - 2
50
- s = add_tabs(wrap(@children, len-2, context), 1, ' ')
51
- s[0] = ?*
52
- s + "\n"
53
- end
54
-
55
- def to_md_abbr_def(context)
56
- "*[#{self.abbr}]: #{self.text}\n"
57
- end
58
-
59
- def to_md_ol(context)
60
- len = (context[:line_length] || DefaultLineLength) - 2
61
- md = ""
62
- self.children.each_with_index do |li, i|
63
- s = add_tabs(w=wrap(li.children, len-2, context), 1, ' ')+"\n"
64
- s[0,4] = "#{i+1}. "[0,4]
65
- # puts w.inspect
66
- md += s
67
- end
68
- md + "\n"
69
- end
70
-
71
- def to_md_ul(context)
72
- len = (context[:line_length] || DefaultLineLength) - 2
73
- md = ""
74
- self.children.each_with_index do |li, i|
75
- w = wrap(li.children, len-2, context)
76
- # puts "W: "+ w.inspect
77
- s = add_indent(w)
78
- # puts "S: " +s.inspect
79
- s[0,1] = "-"
80
- md += s
81
- end
82
- md + "\n"
83
- end
84
-
85
- def add_indent(s,char=" ")
86
- t = s.split("\n").map{|x| char+x }.join("\n")
87
- s << ?\n if t[-1] == ?\n
88
- s
89
- end
90
-
91
- # Convert each child to html
92
- def children_to_md(context)
93
- array_to_md(@children, context)
94
- end
95
-
96
- def wrap(array, line_length, context)
97
- out = ""
98
- line = ""
99
- array.each do |c|
100
- if c.kind_of?(MDElement) && c.node_type == :linebreak
101
- out << line.strip << " \n"; line="";
102
- next
103
- end
104
-
105
- pieces =
106
- if c.kind_of? String
107
- c.to_md.mysplit
108
- else
109
- [c.to_md(context)].flatten
110
- end
111
-
112
- # puts "Pieces: #{pieces.inspect}"
113
- pieces.each do |p|
114
- if p.size + line.size > line_length
115
- out << line.strip << "\n";
116
- line = ""
117
- end
118
- line << p
119
- end
120
- end
121
- out << line.strip << "\n" if line.size > 0
122
- out << ?\n if not out[-1] == ?\n
123
- out
124
- end
125
-
126
-
127
- def array_to_md(array, context, join_char='')
128
- e = []
129
- array.each do |c|
130
- method = c.kind_of?(MDElement) ?
131
- "to_md_#{c.node_type}" : "to_md"
132
-
133
- if not c.respond_to?(method)
134
- #raise "Object does not answer to #{method}: #{c.class} #{c.inspect[0,100]}"
135
- # tell_user "Using default for #{c.node_type}"
136
- method = 'to_md'
137
- end
138
-
139
- # puts "#{c.inspect} created with method #{method}"
140
- h = c.send(method, context)
141
-
142
- if h.nil?
143
- raise "Nil md for #{c.inspect} created with method #{method}"
144
- end
145
-
146
- if h.kind_of?Array
147
- e = e + h
148
- else
149
- e << h
150
- end
151
- end
152
- e.join(join_char)
153
- end
154
-
155
- end end end
156
-
157
- module MaRuKu; class MDDocument
158
- alias old_md to_md
159
- def to_md(context={})
160
- s = old_md(context)
161
- # puts s
162
- s
163
- end
164
- end end
85
+ def to_md_ref_definition(context)
86
+ "[#{@ref_id}] #{@url}#{" \"#{@title}\"" if @title}"
87
+ end
88
+
89
+ def to_md_abbr_def(context)
90
+ "*[#{self.abbr}]: #{self.text}\n"
91
+ end
92
+
93
+ def to_md_ol(context)
94
+ len = (context[:line_length] || DefaultLineLength) - 2
95
+ md = ""
96
+ self.children.each_with_index do |li, i|
97
+ # s = (w=wrap(li.children, len-2, context)).rstrip.gsub(/^/, ' ')+"\n"
98
+ # s[0,4] = "#{i+1}. "[0,4]
99
+ # puts w.inspect
100
+ s = "#{i+1}. " + wrap(li.children, len-2, context).rstrip + "\n"
101
+ md += s
102
+ end
103
+ md + "\n"
104
+ end
105
+
106
+ def to_md_ul(context)
107
+ len = (context[:line_length] || DefaultLineLength) - 2
108
+ md = ""
109
+ self.children.each_with_index do |li, i|
110
+ w = wrap(li.children, len-2, context)
111
+ s = "- " + w
112
+ # puts "W: "+ w.inspect
113
+ # s = add_indent(w)
114
+ # puts "S: " +s.inspect
115
+ # s[0,1] = "-"
116
+ md += s
117
+ end
118
+ md + "\n"
119
+ end
120
+
121
+ def add_indent(s,char=" ")
122
+ t = s.split("\n").map{|x| char+x }.join("\n")
123
+ s << ?\n if t[-1] == ?\n
124
+ s
125
+ end
126
+
127
+ # Convert each child to html
128
+ def children_to_md(context)
129
+ array_to_md(@children, context)
130
+ end
131
+
132
+ def wrap(array, line_length, context)
133
+ out = ""
134
+ line = ""
135
+ array.each do |c|
136
+ if c.kind_of?(MaRuKu::MDElement) && c.node_type == :linebreak
137
+ out << line.strip << " \n"; line="";
138
+ next
139
+ end
140
+
141
+ pieces =
142
+ if c.kind_of? String
143
+ mysplit(c)
144
+ elsif c.kind_of?(MaRuKu::MDElement)
145
+ method = "to_md_#{c.node_type}"
146
+ method = "to_md" unless c.respond_to?(method)
147
+ [c.send(method, context)].flatten
148
+ else
149
+ [c.to_md(context)].flatten
150
+ end
151
+
152
+ # puts "Pieces: #{pieces.inspect}"
153
+ pieces.each do |p|
154
+ if p.size + line.size > line_length
155
+ out << line.strip << "\n";
156
+ line = ""
157
+ end
158
+ line << p
159
+ end
160
+ end
161
+ out << line.strip << "\n" if line.size > 0
162
+ out << ?\n if not out[-1] == ?\n
163
+ out
164
+ end
165
+
166
+
167
+ def array_to_md(array, context, join_char='')
168
+ e = []
169
+ array.each do |c|
170
+ if c.is_a?(String)
171
+ e << c
172
+ else
173
+ method = c.kind_of?(MaRuKu::MDElement) ?
174
+ "to_md_#{c.node_type}" : "to_md"
175
+
176
+ if not c.respond_to?(method)
177
+ #raise "Object does not answer to #{method}: #{c.class} #{c.inspect[0,100]}"
178
+ # tell_user "Using default for #{c.node_type}"
179
+ method = 'to_md'
180
+ end
181
+
182
+ # puts "#{c.inspect} created with method #{method}"
183
+ h = c.send(method, context)
184
+
185
+ if h.nil?
186
+ raise "Nil md for #{c.inspect} created with method #{method}"
187
+ end
188
+
189
+ if h.kind_of?Array
190
+ e = e + h
191
+ else
192
+ e << h
193
+ end
194
+ end
195
+ end
196
+ e.join(join_char)
197
+ end
198
+
199
+ end
200
+
201
+ module MaRuKu
202
+ class MDDocument
203
+ alias old_md to_md
204
+ def to_md(context={})
205
+ warn "Maruku#to_md is deprecated and will be removed in a near-future version of Maruku."
206
+ old_md(context)
207
+ end
208
+ end
209
+ end
@@ -1,56 +1,15 @@
1
- #--
2
- # Copyright (C) 2006 Andrea Censi <andrea (at) rubyforge.org>
3
- #
4
- # This file is part of Maruku.
5
- #
6
- # Maruku is free software; you can redistribute it and/or modify
7
- # it under the terms of the GNU General Public License as published by
8
- # the Free Software Foundation; either version 2 of the License, or
9
- # (at your option) any later version.
10
- #
11
- # Maruku is distributed in the hope that it will be useful,
12
- # but WITHOUT ANY WARRANTY; without even the implied warranty of
13
- # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14
- # GNU General Public License for more details.
15
- #
16
- # You should have received a copy of the GNU General Public License
17
- # along with Maruku; if not, write to the Free Software
18
- # Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
19
- #++
20
-
21
-
22
1
  module MaRuKu
23
-
24
- class MDElement
25
-
26
- # Strips all formatting from the string
27
- def to_s
28
- children_to_s
29
- end
30
-
31
- def children_to_s
32
- @children.join
33
- end
34
-
35
- # Generate an id for headers. Assumes @children is set.
36
- def generate_id
37
-
38
- title = children_to_s
39
- title.gsub!(/ /,'_')
40
- title.downcase!
41
- title.gsub!(/[^\w_]/,'')
42
- title.strip!
43
-
44
- if title.size == 0
45
- $uid ||= 0
46
- $uid += 1
47
- title = "id#{$uid}"
48
- end
49
2
 
50
- # random is a very bad idea
51
- # title << "_" + rand(10000).to_s
52
- title
53
- end
54
- end
3
+ class MDElement
4
+
5
+ # Strips all formatting from the string
6
+ def to_s
7
+ warn "Maruku#to_s is deprecated and will be removed or changed in a near-future version of Maruku."
8
+ children_to_s
9
+ end
55
10
 
11
+ def children_to_s
12
+ @children.join
13
+ end
14
+ end
56
15
  end
@@ -1,191 +1,141 @@
1
- #--
2
- # Copyright (C) 2006 Andrea Censi <andrea (at) rubyforge.org>
3
- #
4
- # This file is part of Maruku.
5
- #
6
- # Maruku is free software; you can redistribute it and/or modify
7
- # it under the terms of the GNU General Public License as published by
8
- # the Free Software Foundation; either version 2 of the License, or
9
- # (at your option) any later version.
10
- #
11
- # Maruku is distributed in the hope that it will be useful,
12
- # but WITHOUT ANY WARRANTY; without even the implied warranty of
13
- # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14
- # GNU General Public License for more details.
15
- #
16
- # You should have received a copy of the GNU General Public License
17
- # along with Maruku; if not, write to the Free Software
18
- # Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
19
- #++
1
+ require 'strscan'
20
2
 
3
+ module MaRuKu
4
+ # Utility functions for dealing with strings.
5
+ module Strings
6
+ TAB_SIZE = 4
21
7
 
22
- # Boring stuff with strings.
23
- module MaRuKu; module Strings
24
-
25
- def add_tabs(s,n=1,char="\t")
26
- s.split("\n").map{|x| char*n+x }.join("\n")
27
- end
28
-
29
- TabSize = 4;
30
-
31
- def split_lines(s)
32
- s.gsub("\r","").split("\n")
33
- end
34
-
35
- # This parses email headers. Returns an hash.
36
- #
37
- # +hash['data']+ is the message.
38
- #
39
- # Keys are downcased, space becomes underscore, converted to symbols.
40
- #
41
- # My key: true
42
- #
43
- # becomes:
44
- #
45
- # {:my_key => true}
46
- #
47
- def parse_email_headers(s)
48
- keys={}
49
- match = (s =~ /\A((\w[\w\s\_\-]+: .*\n)+)\s*\n/)
50
- if match != 0
51
- keys[:data] = s
52
- else
53
- keys[:data] = $'
54
- headers = $1
55
- headers.split("\n").each do |l|
56
- # Fails if there are other ':' characters.
57
- # k, v = l.split(':')
58
- k, v = l.split(':', 2)
59
- k, v = normalize_key_and_value(k, v)
60
- k = k.to_sym
61
- # puts "K = #{k}, V=#{v}"
62
- keys[k] = v
63
- end
64
- end
65
- keys
66
- end
8
+ # Split a string into multiple lines,
9
+ # on line feeds and/or carriage returns.
10
+ #
11
+ # @param s [String]
12
+ # @return [String]
13
+ def split_lines(s)
14
+ s.split(/\r\n|\r|\n/)
15
+ end
67
16
 
68
- # Keys are downcased, space becomes underscore, converted to symbols.
69
- def normalize_key_and_value(k,v)
70
- v = v ? v.strip : true # no value defaults to true
71
- k = k.strip
72
-
73
- # check synonyms
74
- v = true if ['yes','true'].include?(v.to_s.downcase)
75
- v = false if ['no','false'].include?(v.to_s.downcase)
76
-
77
- k = k.downcase.gsub(' ','_')
78
- return k, v
79
- end
80
-
81
- # Returns the number of leading spaces, considering that
82
- # a tab counts as `TabSize` spaces.
83
- def number_of_leading_spaces(s)
84
- n=0; i=0;
85
- while i < s.size
86
- c = s[i,1]
87
- if c == ' '
88
- i+=1; n+=1;
89
- elsif c == "\t"
90
- i+=1; n+=TabSize;
91
- else
92
- break
93
- end
94
- end
95
- n
96
- end
17
+ # Parses email headers, returning a hash.
18
+ # `hash[:data]` is the message;
19
+ # that is, anything past the headers.
20
+ #
21
+ # Keys are downcased and converted to symbols;
22
+ # spaces become underscores. For example:
23
+ #
24
+ # !!!plain
25
+ # My key: true
26
+ #
27
+ # becomes:
28
+ #
29
+ # {:my_key => true}
30
+ #
31
+ # @param s [String] The email
32
+ # @return [Symbol => String] The header values
33
+ def parse_email_headers(s)
34
+ headers = {}
35
+ scanner = StringScanner.new(s)
97
36
 
98
- # This returns the position of the first real char in a list item
99
- #
100
- # For example:
101
- # '*Hello' # => 1
102
- # '* Hello' # => 2
103
- # ' * Hello' # => 3
104
- # ' * Hello' # => 5
105
- # '1.Hello' # => 2
106
- # ' 1. Hello' # => 5
107
-
108
- def spaces_before_first_char(s)
109
- case s.md_type
110
- when :ulist
111
- i=0;
112
- # skip whitespace if present
113
- while s[i,1] =~ /\s/; i+=1 end
114
- # skip indicator (+, -, *)
115
- i+=1
116
- # skip optional whitespace
117
- while s[i,1] =~ /\s/; i+=1 end
118
- return i
119
- when :olist
120
- i=0;
121
- # skip whitespace
122
- while s[i,1] =~ /\s/; i+=1 end
123
- # skip digits
124
- while s[i,1] =~ /\d/; i+=1 end
125
- # skip dot
126
- i+=1
127
- # skip whitespace
128
- while s[i,1] =~ /\s/; i+=1 end
129
- return i
130
- else
131
- tell_user "BUG (my bad): '#{s}' is not a list"
132
- 0
133
- end
134
- end
37
+ while scanner.scan(/(\w[\w\s\-]+): +(.*)\n/)
38
+ k, v = normalize_key_and_value(scanner[1], scanner[2])
39
+ headers[k.to_sym] = v
40
+ end
135
41
 
136
- # Counts the number of leading '#' in the string
137
- def num_leading_hashes(s)
138
- i=0;
139
- while i<(s.size-1) && (s[i,1]=='#'); i+=1 end
140
- i
141
- end
142
-
143
- # Strips initial and final hashes
144
- def strip_hashes(s)
145
- s = s[num_leading_hashes(s), s.size]
146
- i = s.size-1
147
- while i > 0 && (s[i,1] =~ /(#|\s)/); i-=1; end
148
- s[0, i+1].strip
149
- end
150
-
151
- # change space to "_" and remove any non-word character
152
- def sanitize_ref_id(x)
153
- x.strip.downcase.gsub(' ','_').gsub(/[^\w]/,'')
154
- end
42
+ headers[:data] = scanner.rest
43
+ headers
44
+ end
155
45
 
46
+ # This returns the position of the first non-list character
47
+ # in a list item.
48
+ #
49
+ # @example
50
+ # spaces_before_first_char('*Hello') #=> 1
51
+ # spaces_before_first_char('* Hello') #=> 2
52
+ # spaces_before_first_char(' * Hello') #=> 3
53
+ # spaces_before_first_char(' * Hello') #=> 5
54
+ # spaces_before_first_char('1.Hello') #=> 2
55
+ # spaces_before_first_char(' 1. Hello') #=> 5
56
+ #
57
+ # @param s [String]
58
+ # @return [Fixnum]
59
+ def spaces_before_first_char(s)
60
+ match =
61
+ case s.md_type
62
+ when :ulist
63
+ # whitespace, followed by ('*'|'+'|'-') followed by
64
+ # more whitespace, followed by an optional IAL, followed
65
+ # by yet more whitespace
66
+ s[/^\s*(\*|\+|\-)\s*(\{[:#\.].*?\})?\s*/]
67
+ when :olist
68
+ # whitespace, followed by a number, followed by a period,
69
+ # more whitespace, an optional IAL, and more whitespace
70
+ s[/^\s*\d+\.\s*(\{[:#\.].*?\})?\s*/]
71
+ else
72
+ tell_user "BUG (my bad): '#{s}' is not a list"
73
+ ''
74
+ end
75
+ f = /\{(.*?)\}/.match(match)
76
+ ial = f[1] if f
77
+ [match.length, ial]
78
+ end
156
79
 
157
- # removes initial quote
158
- def unquote(s)
159
- s.gsub(/^>\s?/,'')
160
- end
80
+ # Normalize a link reference.
81
+ #
82
+ # @param s [String]
83
+ # @return [String]
84
+ def sanitize_ref_id(s)
85
+ s.downcase.gsub(/\s+/, ' ')
86
+ end
161
87
 
162
- # toglie al massimo n caratteri
163
- def strip_indent(s, n)
164
- i = 0
165
- while i < s.size && n>0
166
- c = s[i,1]
167
- if c == ' '
168
- n-=1;
169
- elsif c == "\t"
170
- n-=TabSize;
171
- else
172
- break
173
- end
174
- i+=1
175
- end
176
- s[i, s.size]
177
- end
88
+ # Remove line-initial `>` characters for a quotation.
89
+ #
90
+ # @param s [String]
91
+ # @return [String]
92
+ def unquote(s)
93
+ s.gsub(/^>\s?/, '')
94
+ end
178
95
 
179
- def dbg_describe_ary(a, prefix='')
180
- i = 0
181
- a.each do |l|
182
- puts "#{prefix} (#{i+=1})# #{l.inspect}"
183
- end
184
- end
96
+ # Removes indentation from the beginning of `s`,
97
+ # up to at most `n` spaces.
98
+ # Tabs are counted as {TAB_SIZE} spaces.
99
+ #
100
+ # @param s [String]
101
+ # @param n [Fixnum]
102
+ # @return [String]
103
+ def strip_indent(s, n)
104
+ while n > 0
105
+ case s[0, 1]
106
+ when ' '
107
+ n -= 1
108
+ when "\t"
109
+ n -= TAB_SIZE
110
+ else
111
+ break
112
+ end
113
+ s = s[1..-1]
114
+ end
185
115
 
186
- def force_linebreak?(l)
187
- l =~ / $/
188
- end
116
+ MDLine.new(s)
117
+ end
189
118
 
190
- end
119
+ private
120
+
121
+ # Normalize the key/value pairs for email headers.
122
+ # Keys are downcased and converted to symbols;
123
+ # spaces become underscores.
124
+ #
125
+ # Values of `"yes"`, `"true"`, `"no"`, and `"false"`
126
+ # are converted to appropriate booleans.
127
+ #
128
+ # @param k [String]
129
+ # @param v [String]
130
+ # @return [Array(String, String or Boolean)]
131
+ def normalize_key_and_value(k, v)
132
+ k = k.strip.downcase.gsub(/\s+/, '_').to_sym
133
+ v = v.strip
134
+
135
+ # check synonyms
136
+ return k, true if %w[yes true].include?(v.downcase)
137
+ return k, false if %w[no false].include?(v.downcase)
138
+ return k, v
139
+ end
140
+ end
191
141
  end