kramdown-man 0.1.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
data/.document ADDED
@@ -0,0 +1,4 @@
1
+ -
2
+ ChangeLog.md
3
+ LICENSE.txt
4
+ man/kramdown-man.1.md
data/.gitignore ADDED
@@ -0,0 +1,2 @@
1
+ doc/
2
+ pkg/
data/.rspec ADDED
@@ -0,0 +1 @@
1
+ --colour --format documentation
data/.travis.yml ADDED
@@ -0,0 +1,11 @@
1
+ language: ruby
2
+ before_install:
3
+ - gem install ffi rubygems-tasks rspec yard kramdown
4
+ rvm:
5
+ - 1.9.3
6
+ - 2.0.0
7
+ - jruby-18mode
8
+ - jruby-19mode
9
+ - rbx-18mode
10
+ - rbx-19mode
11
+ script: rake spec
data/.yardopts ADDED
@@ -0,0 +1 @@
1
+ --markup markdown --markup-provider kramdown --title "kramdown-man Documentation" --protected
data/ChangeLog.md ADDED
@@ -0,0 +1,20 @@
1
+ ### 0.1.3 / 2013-05-05
2
+
3
+ * Initial release:
4
+ * Converts markdown to [roff]:
5
+ * Supports codespans, emphasis and strong fonts.
6
+ * Supports normal and tagged paragraphs.
7
+ * Supports bullet lists.
8
+ * Supports multi-paragraph list items and blockquotes.
9
+ * Supports horizontal rules.
10
+ * Supports converting `[bash](man:bash(1))` links into man page references.
11
+ * Provides Rake task for converting `man/*.md` into man pages.
12
+ * Uses the pure-Ruby [Kramdown][kramdown] markdown parser.
13
+ * Supports [Ruby] 1.8.x, 1.9.x, 2.0.x, [JRuby], [Rubinius].
14
+
15
+ [kramdown]: http://kramdown.rubyforge.org/
16
+ [roff]: http://en.wikipedia.org/wiki/Roff
17
+
18
+ [Ruby]: http://www.ruby-lang.org/
19
+ [JRuby]: http://jruby.org/
20
+ [Rubinius]: http://rubini.us/
data/LICENSE.txt ADDED
@@ -0,0 +1,20 @@
1
+ Copyright (c) 2013 Hal Brodigan
2
+
3
+ Permission is hereby granted, free of charge, to any person obtaining
4
+ a copy of this software and associated documentation files (the
5
+ "Software"), to deal in the Software without restriction, including
6
+ without limitation the rights to use, copy, modify, merge, publish,
7
+ distribute, sublicense, and/or sell copies of the Software, and to
8
+ permit persons to whom the Software is furnished to do so, subject to
9
+ the following conditions:
10
+
11
+ The above copyright notice and this permission notice shall be
12
+ included in all copies or substantial portions of the Software.
13
+
14
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
15
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
17
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
18
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
19
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,178 @@
1
+ # kramdown-man
2
+
3
+ * [Homepage](https://github.com/postmodern/kramdown-man#readme)
4
+ * [Issues](https://github.com/postmodern/kramdown-man/issues)
5
+ * [Documentation](http://rubydoc.info/gems/kramdown-man/frames)
6
+ * [Email](mailto:postmodern.mod3 at gmail.com)
7
+
8
+ [![Build Status](https://secure.travis-ci.org/postmodern/kramdown-man.png?branch=master)](https://travis-ci.org/postmodern/kramdown-man)
9
+
10
+ ## Description
11
+
12
+ A [Kramdown][kramdown] convert for converting Markdown files into man pages.
13
+
14
+ ## Features
15
+
16
+ * Converts markdown to [roff]:
17
+ * Supports codespans, emphasis and strong fonts.
18
+ * Supports normal and tagged paragraphs.
19
+ * Supports bullet lists.
20
+ * Supports multi-paragraph list items and blockquotes.
21
+ * Supports horizontal rules.
22
+ * Supports converting `[bash](man:bash(1))` links into man page references.
23
+ * Provides Rake task for converting `man/*.md` into man pages.
24
+ * Uses the pure-Ruby [Kramdown][kramdown] markdown parser.
25
+ * Supports [Ruby] 1.8.x, 1.9.x, 2.0.x, [JRuby], [Rubinius].
26
+
27
+ ## Synopsis
28
+
29
+ Render a man page from markdown:
30
+
31
+ $ kramdown-man <man/myprog.1.md >man/myprog.1
32
+
33
+ ## Examples
34
+
35
+ Render a man page from a markdown file:
36
+
37
+ require 'kramdown/man'
38
+
39
+ doc = Kramdown::Document.new(File.read('man/kramdown-man.1.md'))
40
+ File.write('man/kramdown-man.1',doc.to_man)
41
+
42
+ system 'man', 'man/kramdown-man.1'
43
+
44
+ Define a `man` and file tasks which render all `*.md` files within the
45
+ `man/` directory:
46
+
47
+ require 'kramdown/man/task'
48
+ Kramdown::Man::Task.new
49
+
50
+ ## Syntax
51
+
52
+ ### Formatting
53
+
54
+ `code`
55
+
56
+ `code`
57
+
58
+ *emphasis*
59
+
60
+ *emphasis*
61
+
62
+ **strong**
63
+
64
+ **strong**
65
+
66
+ ### Paragraphs
67
+
68
+ Normal paragraph.
69
+
70
+ Normal paragraph.
71
+
72
+ `--tagged`
73
+ Text here.
74
+
75
+ `--tagged`
76
+ Text here.
77
+
78
+ ### Links
79
+
80
+ [website](http://example.com/)
81
+
82
+ [website](http://example.com/)
83
+
84
+ [bash](man:bash(1))
85
+
86
+ [bash](man:bash(1))
87
+
88
+ Email <bob@example.com>
89
+
90
+ Email <bob@example.com>
91
+
92
+ ### Lists
93
+
94
+ * one
95
+ * two
96
+ * three
97
+
98
+ extra paragraph
99
+
100
+
101
+ * one
102
+ * two
103
+ * three
104
+
105
+ extra paragraph
106
+
107
+ 1. one
108
+ 2. two
109
+ 3. three
110
+
111
+ extra paragraph
112
+
113
+ 1. one
114
+ 2. two
115
+ 3. three
116
+
117
+ extra paragraph
118
+
119
+ ### Horizontal Rule
120
+
121
+ -------------------------------------------------------------------------------
122
+
123
+ -------------------------------------------------------------------------------
124
+
125
+ ### Blockquotes
126
+
127
+ > Perfection is achieved, not when there is nothing more to add, but when there is nothing left to take away.
128
+ >
129
+ > --Antoine de Saint-Exupéry
130
+
131
+ > Perfection is achieved, not when there is nothing more to add, but when there is nothing left to take away.
132
+ >
133
+ > --Antoine de Saint-Exupéry
134
+
135
+ ### Code Blocks
136
+
137
+ #include <stdio.h>
138
+
139
+ int main()
140
+ {
141
+ printf("hello world\n");
142
+ return 0;
143
+ }
144
+
145
+ #include <stdio.h>
146
+
147
+ int main()
148
+ {
149
+ printf("hello world\n");
150
+ return 0;
151
+ }
152
+
153
+ ## Requirements
154
+
155
+ * [kramdown] ~> 1.0
156
+
157
+ ## Install
158
+
159
+ $ gem install kramdown-man
160
+
161
+ ## Alternatives
162
+
163
+ * [Redcarpet::Render::ManPage](http://rubydoc.info/gems/redcarpet/Redcarpet/Render/ManPage)
164
+ * [ronn](https://github.com/rtomayko/ronn#readme)
165
+ * [md2man](https://github.com/sunaku/md2man#readme)
166
+
167
+ ## Copyright
168
+
169
+ Copyright (c) 2013 Hal Brodigan
170
+
171
+ See {file:LICENSE.txt} for details.
172
+
173
+ [kramdown]: http://kramdown.rubyforge.org/
174
+ [roff]: http://en.wikipedia.org/wiki/Roff
175
+
176
+ [Ruby]: http://www.ruby-lang.org/
177
+ [JRuby]: http://jruby.org/
178
+ [Rubinius]: http://rubini.us/
data/Rakefile ADDED
@@ -0,0 +1,45 @@
1
+ # encoding: utf-8
2
+
3
+ require 'rubygems'
4
+ require 'rake'
5
+
6
+ begin
7
+ gem 'rubygems-tasks', '~> 0.2'
8
+ require 'rubygems/tasks'
9
+
10
+ Gem::Tasks.new
11
+ rescue LoadError => e
12
+ warn e.message
13
+ warn "Run `gem install rubygems-tasks` to install Gem::Tasks."
14
+ end
15
+
16
+ begin
17
+ gem 'rspec', '~> 2.4'
18
+ require 'rspec/core/rake_task'
19
+
20
+ RSpec::Core::RakeTask.new
21
+ rescue LoadError => e
22
+ task :spec do
23
+ abort "Please run `gem install rspec` to install RSpec."
24
+ end
25
+ end
26
+
27
+ task :test => :spec
28
+ task :default => :spec
29
+
30
+ begin
31
+ gem 'yard', '~> 0.8'
32
+ require 'yard'
33
+
34
+ YARD::Rake::YardocTask.new
35
+ rescue LoadError => e
36
+ task :yard do
37
+ abort "Please run `gem install yard` to install YARD."
38
+ end
39
+ end
40
+ task :doc => :yard
41
+
42
+ $LOAD_PATH.unshift(File.expand_path('lib'))
43
+
44
+ require 'kramdown/man/tasks'
45
+ Kramdown::Man::Tasks.new
data/bin/kramdown-man ADDED
@@ -0,0 +1,16 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ lib_dir = File.expand_path('../lib',File.dirname(__FILE__))
4
+ $LOAD_PATH.unshift(lib_dir) unless $LOAD_PATH.include?(lib_dir)
5
+
6
+ require 'kramdown'
7
+ require 'kramdown/man'
8
+
9
+ case ARGV[0]
10
+ when '-h', '--help'
11
+ warn "usage: #{File.dirname($0)} <INPUT.md >OUTPUT"
12
+ exit
13
+ end
14
+
15
+ doc = Kramdown::Document.new(ARGF.read)
16
+ puts doc.to_man
data/gemspec.yml ADDED
@@ -0,0 +1,15 @@
1
+ name: kramdown-man
2
+ summary: Converts markdown to man pages
3
+ description: A Kramdown converter for converting Markdown files into man pages.
4
+ license: MIT
5
+ authors: Postmodern
6
+ email: postmodern.mod3@gmail.com
7
+ homepage: https://github.com/postmodern/kramdown-man#readme
8
+
9
+ dependencies:
10
+ kramdown: ~> 1.0
11
+
12
+ development_dependencies:
13
+ rspec: ~> 2.4
14
+ rubygems-tasks: ~> 0.2
15
+ yard: ~> 0.8
@@ -0,0 +1,60 @@
1
+ # encoding: utf-8
2
+
3
+ require 'yaml'
4
+
5
+ Gem::Specification.new do |gem|
6
+ gemspec = YAML.load_file('gemspec.yml')
7
+
8
+ gem.name = gemspec.fetch('name')
9
+ gem.version = gemspec.fetch('version') do
10
+ lib_dir = File.join(File.dirname(__FILE__),'lib')
11
+ $LOAD_PATH << lib_dir unless $LOAD_PATH.include?(lib_dir)
12
+
13
+ require 'kramdown/man/version'
14
+ Kramdown::Man::VERSION
15
+ end
16
+
17
+ gem.summary = gemspec['summary']
18
+ gem.description = gemspec['description']
19
+ gem.licenses = Array(gemspec['license'])
20
+ gem.authors = Array(gemspec['authors'])
21
+ gem.email = gemspec['email']
22
+ gem.homepage = gemspec['homepage']
23
+
24
+ glob = lambda { |patterns| gem.files & Dir[*patterns] }
25
+
26
+ gem.files = `git ls-files`.split($/)
27
+ gem.files = glob[gemspec['files']] if gemspec['files']
28
+
29
+ gem.executables = gemspec.fetch('executables') do
30
+ glob['bin/*'].map { |path| File.basename(path) }
31
+ end
32
+ gem.default_executable = gem.executables.first if Gem::VERSION < '1.7.'
33
+
34
+ gem.extensions = glob[gemspec['extensions'] || 'ext/**/extconf.rb']
35
+ gem.test_files = glob[gemspec['test_files'] || '{test/{**/}*_test.rb']
36
+ gem.extra_rdoc_files = glob[gemspec['extra_doc_files'] || '*.{txt,md}']
37
+
38
+ gem.require_paths = Array(gemspec.fetch('require_paths') {
39
+ %w[ext lib].select { |dir| File.directory?(dir) }
40
+ })
41
+
42
+ gem.requirements = gemspec['requirements']
43
+ gem.required_ruby_version = gemspec['required_ruby_version']
44
+ gem.required_rubygems_version = gemspec['required_rubygems_version']
45
+ gem.post_install_message = gemspec['post_install_message']
46
+
47
+ split = lambda { |string| string.split(/,\s*/) }
48
+
49
+ if gemspec['dependencies']
50
+ gemspec['dependencies'].each do |name,versions|
51
+ gem.add_dependency(name,split[versions])
52
+ end
53
+ end
54
+
55
+ if gemspec['development_dependencies']
56
+ gemspec['development_dependencies'].each do |name,versions|
57
+ gem.add_development_dependency(name,split[versions])
58
+ end
59
+ end
60
+ end
@@ -0,0 +1,439 @@
1
+ # encoding: utf-8
2
+ require 'kramdown/man/version'
3
+
4
+ require 'kramdown/converter/base'
5
+
6
+ module Kramdown
7
+ module Converter
8
+ #
9
+ # Converts markdown into a roff man-page.
10
+ #
11
+ class Man < Base
12
+
13
+ # Comment header
14
+ HEADER = [
15
+ ".\\\" Generated by kramdown-man #{::Kramdown::Man::VERSION}",
16
+ ".\\\" https://github.com/postmodern/kramdown-roff#readme"
17
+ ].join("\n")
18
+
19
+ # Typographic Symbols and their UTF8 chars
20
+ TYPOGRAPHIC_SYMS = {
21
+ :ndash => "--",
22
+ :mdash => "—",
23
+ :hellip => "…",
24
+ :laquo => "«",
25
+ :raquo => "»",
26
+ :laquo_space => "«",
27
+ :raquo_space => "»"
28
+ }
29
+
30
+ # Smart Quotes and their UTF8 chars
31
+ SMART_QUOTES = {
32
+ :lsquo => "‘",
33
+ :rsquo => "’",
34
+ :ldquo => "“",
35
+ :rdquo => "”"
36
+ }
37
+
38
+ #
39
+ # Initializes the converter.
40
+ #
41
+ # @param [Kramdown::Element] root
42
+ # The root of the markdown document.
43
+ #
44
+ # @param [Hash] options
45
+ # Markdown options.
46
+ #
47
+ def initialize(root,options)
48
+ super(root,options)
49
+
50
+ @ol_index = 0
51
+ end
52
+
53
+ #
54
+ # Converts the markdown document into a man-page.
55
+ #
56
+ # @param [Kramdown::Element] root
57
+ # The root of a markdown document.
58
+ #
59
+ # @return [String]
60
+ # The roff output.
61
+ #
62
+ def convert(root)
63
+ "#{HEADER}\n#{convert_root(root)}"
64
+ end
65
+
66
+ #
67
+ # Converts the root of a markdown document.
68
+ #
69
+ # @param [Kramdown::Element] root
70
+ # The root of the markdown document.
71
+ #
72
+ # @return [String]
73
+ # The roff output.
74
+ #
75
+ def convert_root(root)
76
+ root.children.map { |child|
77
+ convert_element(child)
78
+ }.compact.join("\n")
79
+ end
80
+
81
+ #
82
+ # Converts an element.
83
+ #
84
+ # @param [Kramdown::Element] element
85
+ # An arbitrary element within the markdown document.
86
+ #
87
+ # @return [String]
88
+ # The roff output.
89
+ #
90
+ def convert_element(element)
91
+ method = "convert_#{element.type}"
92
+ send(method,element) if respond_to?(method)
93
+ end
94
+
95
+ #
96
+ # Converts a `kd:blank` element.
97
+ #
98
+ # @param [Kramdown::Element] blank
99
+ # A `kd:blank` element.
100
+ #
101
+ # @return [String]
102
+ # The roff output.
103
+ #
104
+ def convert_blank(blank)
105
+ '.LP'
106
+ end
107
+
108
+ #
109
+ # Converts a `kd:text` element.
110
+ #
111
+ # @param [Kramdown::Element] text
112
+ # A `kd:text` element.
113
+ #
114
+ # @return [String]
115
+ # The roff output.
116
+ #
117
+ def convert_text(text)
118
+ escape(text.value)
119
+ end
120
+
121
+ #
122
+ # Converts a `kd:typographic_sym` element.
123
+ #
124
+ # @param [Kramdown::Element] sym
125
+ # A `kd:typographic_sym` element.
126
+ #
127
+ # @return [String]
128
+ # The roff output.
129
+ #
130
+ def convert_typographic_sym(sym)
131
+ TYPOGRAPHIC_SYMS[sym.value]
132
+ end
133
+
134
+ #
135
+ # Converts a `kd:smart_quote` element.
136
+ #
137
+ # @param [Kramdown::Element] quote
138
+ # A `kd:smart_quote` element.
139
+ #
140
+ # @return [String]
141
+ # The roff output.
142
+ #
143
+ def convert_smart_quote(quote)
144
+ SMART_QUOTES[quote.value]
145
+ end
146
+
147
+ #
148
+ # Converts a `kd:header` element.
149
+ #
150
+ # @param [Kramdown::Element] header
151
+ # A `kd:header` element.
152
+ #
153
+ # @return [String]
154
+ # The roff output.
155
+ #
156
+ def convert_header(header)
157
+ text = header.options[:raw_text]
158
+
159
+ case header.options[:level]
160
+ when 1 then ".TH #{text}"
161
+ when 2 then ".SH #{text}"
162
+ else ".SS #{text}"
163
+ end
164
+ end
165
+
166
+ #
167
+ # Converts a `kd:hr` element.
168
+ #
169
+ # @param [Kramdown::Element] hr
170
+ # A `kd:hr` element.
171
+ #
172
+ # @return [String]
173
+ # The roff output.
174
+ #
175
+ def convert_hr(hr)
176
+ ".ti 0\n\\l'\\n(.lu'"
177
+ end
178
+
179
+ #
180
+ # Converts a `kd:ul` element.
181
+ #
182
+ # @param [Kramdown::Element] ul
183
+ # A `kd:ul` element.
184
+ #
185
+ # @return [String]
186
+ # The roff output.
187
+ #
188
+ def convert_ul(ul)
189
+ content = ul.children.map { |li| convert_ul_li(li) }.join("\n")
190
+
191
+ return ".RS\n#{content}\n.RE"
192
+ end
193
+
194
+ #
195
+ # Converts a `kd:li` element within a `kd:ul` list.
196
+ #
197
+ # @param [Kramdown::Element] li
198
+ # A `kd:li` element.
199
+ #
200
+ # @return [String]
201
+ # The roff output.
202
+ #
203
+ def convert_ul_li(li)
204
+ li.children.each_with_index.map { |child,index|
205
+ if child.type == :p
206
+ content = convert_children(child.children)
207
+
208
+ if index == 0 then ".IP \\(bu 2\n#{content}"
209
+ else ".IP \\( 2\n#{content}"
210
+ end
211
+ end
212
+ }.compact.join("\n")
213
+ end
214
+
215
+ #
216
+ # Converts a `kd:ol` element.
217
+ #
218
+ # @param [Kramdown::Element] ol
219
+ # A `kd:ol` element.
220
+ #
221
+ # @return [String]
222
+ # The roff output.
223
+ #
224
+ def convert_ol(ol)
225
+ @ol_index += 1
226
+
227
+ header = ".nr step#{@ol_index} 0 1"
228
+ content = ol.children.map { |li| convert_ol_li(li) }.join("\n")
229
+
230
+ return "#{header}\n.RS\n#{content}\n.RE"
231
+ end
232
+
233
+ #
234
+ # Converts a `kd:li` element within a `kd:ol` list.
235
+ #
236
+ # @param [Kramdown::Element] li
237
+ # A `kd:li` element.
238
+ #
239
+ # @return [String]
240
+ # The roff output.
241
+ #
242
+ def convert_ol_li(li)
243
+ li.children.each_with_index.map { |child,index|
244
+ if child.type == :p
245
+ content = convert_children(child.children)
246
+
247
+ if index == 0 then ".IP \\n+[step#{@ol_index}]\n#{content}"
248
+ else ".IP \\n\n#{content}"
249
+ end
250
+ end
251
+ }.compact.join("\n")
252
+ end
253
+
254
+ #
255
+ # Converts a `kd:abbreviation` element.
256
+ #
257
+ # @param [Kramdown::Element] abbr
258
+ # A `kd:abbreviation` element.
259
+ #
260
+ # @return [String]
261
+ # The roff output.
262
+ #
263
+ def convert_abbreviation(abbr)
264
+ escape(abbr.value)
265
+ end
266
+
267
+ #
268
+ # Converts a `kd:blockquote` element.
269
+ #
270
+ # @param [Kramdown::Element] blockquote
271
+ # A `kd:blockquote` element.
272
+ #
273
+ # @return [String]
274
+ # The roff output.
275
+ #
276
+ def convert_blockquote(blockquote)
277
+ content = blockquote.children.map { |child|
278
+ case child.type
279
+ when :p then convert_children(child.children)
280
+ else convert_element(child)
281
+ end
282
+ }.join("\n")
283
+
284
+ return ".PP\n.RS\n#{content}\n.RE"
285
+ end
286
+
287
+ #
288
+ # Converts a `kd:codeblock` element.
289
+ #
290
+ # @param [Kramdown::Element] codeblock
291
+ # A `kd:codeblock` element.
292
+ #
293
+ # @return [String]
294
+ # The roff output.
295
+ #
296
+ def convert_codeblock(codeblock)
297
+ ".nf\n#{escape(codeblock.value).rstrip}\n.fi"
298
+ end
299
+
300
+ #
301
+ # Converts a `kd:comment` element.
302
+ #
303
+ # @param [Kramdown::Element] comment
304
+ # A `kd:comment` element.
305
+ #
306
+ # @return [String]
307
+ # The roff output.
308
+ #
309
+ def convert_comment(comment)
310
+ comment.value.lines.map { |line|
311
+ ".\\\" #{line}"
312
+ }.join("\n")
313
+ end
314
+
315
+ #
316
+ # Converts a `kd:p` element.
317
+ #
318
+ # @param [Kramdown::Element] p
319
+ # A `kd:p` element.
320
+ #
321
+ # @return [String]
322
+ # The roff output.
323
+ #
324
+ def convert_p(p)
325
+ children = p.children
326
+
327
+ if (children.length >= 2) &&
328
+ (children[0].type == :em || children[0].type == :codespan) &&
329
+ (children[1].type == :text && children[1].value =~ /^( |\t)/)
330
+ [
331
+ '.TP',
332
+ convert_element(children[0]),
333
+ convert_text(children[1]).lstrip,
334
+ convert_children(children[2..-1])
335
+ ].join("\n").rstrip
336
+ else
337
+ ".PP\n#{convert_children(children)}"
338
+ end
339
+ end
340
+
341
+ #
342
+ # Converts a `kd:em` element.
343
+ #
344
+ # @param [Kramdown::Element] em
345
+ # A `kd:em` element.
346
+ #
347
+ # @return [String]
348
+ # The roff output.
349
+ #
350
+ def convert_em(em)
351
+ "\\fI#{convert_children(em.children)}\\fP"
352
+ end
353
+
354
+ #
355
+ # Converts a `kd:strong` element.
356
+ #
357
+ # @param [Kramdown::Element] strong
358
+ # A `kd:strong` element.
359
+ #
360
+ # @return [String]
361
+ # The roff output.
362
+ #
363
+ def convert_strong(strong)
364
+ "\\fB#{convert_children(strong.children)}\\fP"
365
+ end
366
+
367
+ #
368
+ # Converts a `kd:codespan` element.
369
+ #
370
+ # @param [Kramdown::Element] codespan
371
+ # A `kd:codespan` element.
372
+ #
373
+ # @return [String]
374
+ # The roff output.
375
+ #
376
+ def convert_codespan(codespan)
377
+ "\\fB\\fC#{codespan.value}\\fR"
378
+ end
379
+
380
+ #
381
+ # Converts a `kd:a` element.
382
+ #
383
+ # @param [Kramdown::Element] a
384
+ # A `kd:a` element.
385
+ #
386
+ # @return [String]
387
+ # The roff output.
388
+ #
389
+ def convert_a(a)
390
+ href = a.attr['href']
391
+ text = convert_children(a.children)
392
+
393
+ case href
394
+ when /^mailto:/
395
+ email = href[7..-1]
396
+
397
+ unless text == email then "#{text}\n.MT #{email}\n.ME"
398
+ else "\n.MT #{email}\n.ME"
399
+ end
400
+ when /^man:/
401
+ match = href.match(/man:([A-Za-z0-9_-]+)(?:\((\d[a-z]?)\))?/)
402
+
403
+ if match[2] then "\n.BR #{match[1]} (#{match[2]})"
404
+ else "\n.BR #{match[1]}"
405
+ end
406
+ else
407
+ "#{text}\n.UR #{href}\n.UE"
408
+ end
409
+ end
410
+
411
+ #
412
+ # Converts the children of an element.
413
+ #
414
+ # @param [Array<Kramdown::Element>] children
415
+ # The children of an element.
416
+ #
417
+ # @return [String]
418
+ # The roff output.
419
+ #
420
+ def convert_children(children)
421
+ children.map { |child| convert_element(child) }.join.strip
422
+ end
423
+
424
+ #
425
+ # Escapes text for roff.
426
+ #
427
+ # @param [String] text
428
+ # The unescaped text.
429
+ #
430
+ # @return [String]
431
+ # The escaped text.
432
+ #
433
+ def escape(text)
434
+ text.gsub('\\','\&\&').gsub('-','\\-')
435
+ end
436
+
437
+ end
438
+ end
439
+ end