asciidoctor-mathematical 0.0.5 → 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 7314ce3eb4a07303f58434c05e7b40d00b532ecb
4
- data.tar.gz: 769f69516c2d5a113ad67cbbd8720098f860c00f
3
+ metadata.gz: c60e640244d19ad2679b5117d86aa6b71ea3068d
4
+ data.tar.gz: a872640167565771f597fdd7868db7103a626a82
5
5
  SHA512:
6
- metadata.gz: baa9e15e5cdaeda7b3048470cd813c7647825ca35adb8816d9691b64743b357fc7e8b36017febefc147aa45ad3c0efb48751c1fb2c5964b7c5651891321c144b
7
- data.tar.gz: fbb01d534e647733b86b756f45d6598013c28560635a7d9aaa1cc26f46ced269687476d6053a618f63d9eb7a8494a07f18ee6ae1d08741801de07aee3c22389e
6
+ metadata.gz: b13a97f6910f9936f965eddc9eec2764bff84d15f81f27dfa1dfa2c8abe7c67c15a47072bdc620d10bd10a14ab82e761df2acc78cbba2695cb922401fa45b081
7
+ data.tar.gz: 8a1e50165d18cb99a763b8ca769fe970c5b1fdd683350cedc2d2b7c08abc881983d436be412bc07829868d743fdd5995ebf1da660f33e7adba1ae6db48447254
@@ -1,6 +1,5 @@
1
- RUBY_ENGINE == 'opal' ? (require 'asciidoctor-mathematical/extension') : (require_relative 'asciidoctor-mathematical/extension')
1
+ require_relative 'asciidoctor-mathematical/extension'
2
2
 
3
- Extensions.register do
4
- preprocessor MathematicalPreprocessor
3
+ Asciidoctor::Extensions.register do
5
4
  treeprocessor MathematicalTreeprocessor
6
5
  end
@@ -1,43 +1,35 @@
1
- require 'asciidoctor'
1
+ require 'pathname'
2
2
  require 'asciidoctor/extensions'
3
- require 'mathematical'
4
3
 
5
4
  autoload :Digest, 'digest'
5
+ autoload :Mathematical, 'mathematical'
6
6
 
7
- include ::Asciidoctor
7
+ class MathematicalTreeprocessor < Asciidoctor::Extensions::Treeprocessor
8
+ LineFeed = %(\n)
9
+ StemInlineMacroRx = /\\?(?:stem|latexmath):([a-z,]*)\[(.*?[^\\])\]/m
10
+ LatexmathInlineMacroRx = /\\?latexmath:([a-z,]*)\[(.*?[^\\])\]/m
8
11
 
9
- class MathematicalTreeprocessor < Extensions::Treeprocessor
10
12
  def process document
11
- if (stem_blocks = document.find_by context: :stem)
13
+ to_html = document.basebackend? 'html'
14
+ format = ((document.attr 'mathematical-format') || 'png').to_sym
15
+ if format != :png and format != :svg
16
+ warn %(Unknown format '#{format}', retreat to 'png')
12
17
  format = :png
13
- if document.attributes['mathematical-format']
14
- format_str = document.attributes['mathematical-format']
15
- if format_str == 'png'
16
- format = :png
17
- elsif format_str == 'svg'
18
- format = :svg
19
- end
20
- end
21
- image_postfix = ".#{format}"
22
- scale = 1.0
23
- if format == :png
24
- scale = 72.0/300.0
25
- end
26
- ppi = 72.0
27
- if format == :png
28
- ppi = 300.0
29
- end
30
- # The no-args constructor defaults to SVG and standard delimiters ($..$ for inline, $$..$$ for block)
31
- mathematical = ::Mathematical.new({ :format => format, :ppi => ppi })
32
- image_output_dir = resolve_image_output_dir document
33
- image_target_dir = document.attr 'imagesoutdir', (document.attr 'imagesdir')
34
- image_target_dir = '.' if image_target_dir.nil_or_empty?
35
- ::FileUtils.mkdir_p image_output_dir unless ::File.directory? image_output_dir
18
+ end
19
+ image_ext = %(.#{format})
20
+ ppi = ((document.attr 'mathematical-ppi') || '300.0').to_f
21
+ ppi = format == :png ? ppi : 72.0
22
+ # The no-args constructor defaults to SVG and standard delimiters ($..$ for inline, $$..$$ for block)
23
+ mathematical = ::Mathematical.new format: format, ppi: ppi
24
+ image_output_dir, image_target_dir = image_output_and_target_dir document
25
+
26
+ unless (stem_blocks = document.find_by context: :stem).nil_or_empty?
27
+ ::Asciidoctor::Helpers.mkdir_p image_output_dir unless ::File.directory? image_output_dir
36
28
 
37
29
  stem_blocks.each do |stem|
38
- equation_data = %($$#{stem.content}$$)
39
30
  equation_type = stem.style.to_sym
40
31
  next unless equation_type == :latexmath
32
+ equation_data = %($$#{stem.content}$$)
41
33
 
42
34
  # FIXME auto-generate id if one is not provided
43
35
  unless (stem_id = stem.id)
@@ -46,7 +38,7 @@ class MathematicalTreeprocessor < Extensions::Treeprocessor
46
38
 
47
39
  alt_text = stem.attr 'alt', equation_data
48
40
 
49
- image_target = %(#{stem_id}#{image_postfix})
41
+ image_target = %(#{stem_id}#{image_ext})
50
42
  image_file = ::File.join image_output_dir, image_target
51
43
  image_target = ::File.join image_target_dir, image_target unless image_target_dir == '.'
52
44
 
@@ -56,8 +48,8 @@ class MathematicalTreeprocessor < Extensions::Treeprocessor
56
48
 
57
49
  attrs = { 'target' => image_target, 'alt' => alt_text, 'align' => 'center' }
58
50
  if format == :png
59
- attrs['width'] = "#{result[:width]}pt"
60
- attrs['height'] = "#{result[:height]}pt"
51
+ attrs['width'] = %(#{result[:width]})
52
+ attrs['height'] = %(#{result[:height]})
61
53
  end
62
54
  parent = stem.parent
63
55
  stem_image = create_image_block parent, attrs
@@ -68,94 +60,85 @@ class MathematicalTreeprocessor < Extensions::Treeprocessor
68
60
  parent.blocks[parent.blocks.index stem] = stem_image
69
61
  end
70
62
  end
71
- nil
72
- end
73
-
74
- def resolve_image_output_dir doc
75
- if (images_dir = doc.attr 'imagesoutdir')
76
- base_dir = nil
77
- else
78
- base_dir = (doc.attr 'outdir') || ((doc.respond_to? :options) && doc.options[:to_dir])
79
- images_dir = doc.attr 'imagesdir'
80
- end
81
-
82
- doc.normalize_system_path images_dir, base_dir
83
- end
84
- end
85
-
86
- class MathematicalPreprocessor < Extensions::Preprocessor
87
- LATEXMATH_PTN = /latexmath:\[([^\]]+)\]/
88
63
 
89
- SPECIAL_CHARS = {
90
- '&' => '&amp;',
91
- '<' => '&lt;',
92
- '>' => '&gt;'
93
- }
94
-
95
- SPECIAL_CHARS_PATTERN = /[#{SPECIAL_CHARS.keys.join}]/
96
-
97
- # FIXME: I don't understand why I can not simply use sub_specialchars from
98
- # Asciidoctor. It just crashes with 'unknown method name'. So I copy the
99
- # code here.
100
- def sub_specialchars text
101
- text.gsub(SPECIAL_CHARS_PATTERN, SPECIAL_CHARS)
102
- end
103
-
104
- def process document, reader
105
- # Setup image format information
106
- format = :png
107
- if document.attributes['mathematical-format']
108
- format_str = document.attributes['mathematical-format']
109
- if format_str == 'png'
110
- format = :png
111
- elsif format_str == 'svg'
112
- format = :svg
64
+ unless (prose_blocks = document.find_by {|b|
65
+ (b.content_model == :simple && (b.subs.include? :macros)) || b.context == :list_item
66
+ }).nil_or_empty?
67
+ support_stem_prefix = document.attr? 'stem', 'latexmath'
68
+ ::Asciidoctor::Helpers.mkdir_p image_output_dir unless ::File.directory? image_output_dir
69
+ stem_rx = support_stem_prefix ? StemInlineMacroRx : LatexmathInlineMacroRx
70
+
71
+ prose_blocks.each do |block|
72
+ source_modified = false
73
+ source = block.context == :list_item ? (block.instance_variable_get :@text) : (block.lines * LineFeed)
74
+ # TODO skip passthroughs in the source (e.g., +stem:[x^2]+)
75
+ source.gsub!(stem_rx) {
76
+ if (m = $~)[0].start_with? '\\'
77
+ next m[0][1..-1]
78
+ end
79
+
80
+ if (eq_data = m[2].rstrip).empty?
81
+ next
82
+ else
83
+ source_modified = true
84
+ end
85
+
86
+ eq_data.gsub! '\]', ']'
87
+ subs = m[1].nil_or_empty? ? (to_html ? [:specialcharacters] : []) : (block.resolve_pass_subs m[1])
88
+ eq_data = block.apply_subs eq_data, subs unless subs.empty?
89
+
90
+ eq_id = %(stem-#{::Digest::MD5.hexdigest eq_data})
91
+ eq_input = %($#{eq_data}$)
92
+
93
+ img_target = %(#{eq_id}#{image_ext})
94
+ img_file = ::File.join image_output_dir, img_target
95
+ img_target = ::File.join image_target_dir, img_target unless image_target_dir == '.'
96
+
97
+ eq_result = mathematical.parse eq_input
98
+
99
+ ::IO.write img_file, eq_result[:data]
100
+ %(image:#{img_target}[width=#{eq_result[:width]},height=#{eq_result[:height]}])
101
+ } if (source.include? ':') && ((support_stem_prefix && (source.include? 'stem:')) || (source.include? 'latexmath:'))
102
+
103
+ if source_modified
104
+ if block.context == :list_item
105
+ block.instance_variable_set :@text, source
106
+ else
107
+ block.lines = source.split LineFeed
108
+ end
109
+ end
113
110
  end
114
111
  end
115
- image_postfix = ".#{format}"
116
- scale = 1.0
117
- if format == :png
118
- scale = 72.0/300.0
119
- end
120
- ppi = 72.0
121
- if format == :png
122
- ppi = 300.0
123
- end
124
112
 
125
- # Since at preprocessing stage, we have no document attribute avaliable,
126
- # so fix the image output dir to be simple.
127
- image_output_dir = './images'
128
- image_target_dir = './images'
129
- ::FileUtils.mkdir_p image_output_dir unless ::File.directory? image_output_dir
130
-
131
- mathematical = ::Mathematical.new({ :format => format, :ppi => ppi })
132
-
133
- lines = reader.readlines
134
- lines.each do |line|
135
- md = LATEXMATH_PTN.match line
136
- while md
137
- stem_content = md[1]
138
- # NOTE: It seems that we need to escape '<>&' to make mathematical
139
- # work. This is weired but verified. So we escape them here.
140
- stem_content = sub_specialchars stem_content
141
- equation_data = %($#{stem_content}$)
142
- stem_id = %(stem-#{::Digest::MD5.hexdigest stem_content})
143
-
144
- image_target = %(#{stem_id}#{image_postfix})
145
- image_file = ::File.join image_output_dir, image_target
146
- image_target = ::File.join image_target_dir, image_target unless image_target_dir == '.'
113
+ nil
114
+ end
147
115
 
148
- # TODO check for error
149
- result = mathematical.parse equation_data
150
- ::IO.write image_file, result[:data]
116
+ def image_output_and_target_dir(parent)
117
+ document = parent.document
151
118
 
152
- subst = %(image:#{image_target}[width=#{result[:width]}pt])
153
- line.gsub! md[0], subst
154
- md = LATEXMATH_PTN.match md.post_match
119
+ output_dir = parent.attr('imagesoutdir')
120
+ if output_dir
121
+ base_dir = nil
122
+ if parent.attr('imagesdir').nil_or_empty?
123
+ target_dir = output_dir
124
+ else
125
+ # When imagesdir attribute is set, every relative path is prefixed with it. So the real target dir shall then be relative to the imagesdir, instead of being relative to document root.
126
+ doc_outdir = parent.attr('outdir') || (document.respond_to?(:options) && document.options[:to_dir])
127
+ abs_imagesdir = parent.normalize_system_path(parent.attr('imagesdir'), doc_outdir)
128
+ abs_outdir = parent.normalize_system_path(output_dir, base_dir)
129
+ p1 = ::Pathname.new abs_outdir
130
+ p2 = ::Pathname.new abs_imagesdir
131
+ target_dir = p1.relative_path_from(p2).to_s
155
132
  end
133
+ else
134
+ base_dir = parent.attr('outdir') || (document.respond_to?(:options) && document.options[:to_dir])
135
+ output_dir = parent.attr('imagesdir')
136
+ # since we store images directly to imagesdir, target dir shall be NULL and asciidoctor converters will prefix imagesdir.
137
+ target_dir = "."
156
138
  end
157
139
 
158
- reader.unshift_lines lines
159
- reader
140
+ output_dir = parent.normalize_system_path(output_dir, base_dir)
141
+ return [output_dir, target_dir]
160
142
  end
143
+
161
144
  end
metadata CHANGED
@@ -1,15 +1,16 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: asciidoctor-mathematical
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.5
4
+ version: 0.1.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Tobias Stumm
8
8
  - Zhang Yang
9
+ - Dan Allen
9
10
  autorequire:
10
11
  bindir: bin
11
12
  cert_chain: []
12
- date: 2015-09-22 00:00:00.000000000 Z
13
+ date: 2016-08-21 00:00:00.000000000 Z
13
14
  dependencies:
14
15
  - !ruby/object:Gem::Dependency
15
16
  name: ruby-enum
@@ -65,7 +66,7 @@ dependencies:
65
66
  - - ">="
66
67
  - !ruby/object:Gem::Version
67
68
  version: 1.5.0
68
- description: Converts latexmath equations in Asciidoctor to SVG
69
+ description: An Asciidoctor extension to converts latexmath equations to SVG or PNGs
69
70
  email: tstumm@users.noreply.github.com
70
71
  executables: []
71
72
  extensions: []
@@ -93,8 +94,8 @@ required_rubygems_version: !ruby/object:Gem::Requirement
93
94
  version: '0'
94
95
  requirements: []
95
96
  rubyforge_project:
96
- rubygems_version: 2.4.5.1
97
+ rubygems_version: 2.5.1
97
98
  signing_key:
98
99
  specification_version: 4
99
- summary: Wrapper for Mathematical
100
+ summary: Asciidoctor STEM processor based on Mathematical
100
101
  test_files: []