isodoc 2.5.1 → 2.5.2

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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 23f98744bc0bb65ad60168ed537e14fe7c42222751d9beb5889ef3f6774c5b2a
4
- data.tar.gz: 126d7531a7f6dee506d40ec9495de1cbff43efbd8699c9913e3564698bce3b1e
3
+ metadata.gz: 35414cac7eab8ae893d39af33b9f3ecf591c33bd5013ea6340b13b26c23e73e1
4
+ data.tar.gz: b4820f7236dc69a3fadf213dcd7fef2eadddebbf85dc02a4ec7364c688baa4da
5
5
  SHA512:
6
- metadata.gz: 70045efc243c466f1ad330ce1d3a5cdb4a0ec76d5575913c47ab3043b1242d4b8fbb319fe7993db211dd7ff1c8d3cce9e501bf745ee9e861330c9e793a35ba1f
7
- data.tar.gz: bfba85e2ac12b48cc5f255a4f983201c6042f506590ac34300da79107892532a0266a6507eb93ca8c247c047ada4e3049f1ddfd410af0e521596d3341a6dcfc9
6
+ metadata.gz: 902033f59dc11d6f097e7477aa8ea44cc7eb199e085778a3eee2cfa771d7a40a85869176ff0c57e0cad88d1c270546a7d9419da2119fb3a6d435c629aeea6acc
7
+ data.tar.gz: 0f346f7277f8aab99189f29d2e1a35a6d36c593cfd52628d37f9245acb39e7ea0aa8761f6797e18dbb1b1069812ffbf2c2563f97e472cfa628047c6e84df0eb0
data/isodoc.gemspec CHANGED
@@ -29,10 +29,10 @@ Gem::Specification.new do |spec|
29
29
  spec.test_files = `git ls-files -- {spec}/*`.split("\n")
30
30
  spec.required_ruby_version = Gem::Requirement.new(">= 2.7.0")
31
31
 
32
- spec.add_dependency "html2doc", "~> 1.5.0"
32
+ spec.add_dependency "html2doc", "~> 1.5.3"
33
33
  spec.add_dependency "htmlentities", "~> 4.3.4"
34
34
  # spec.add_dependency "isodoc-i18n", "~> 1.1.0" # already in relaton-render and mn-requirements
35
- spec.add_dependency "liquid", "~> 4"
35
+ spec.add_dependency "liquid", "~> 5"
36
36
  spec.add_dependency "emf2svg"
37
37
  spec.add_dependency "plurimath"
38
38
  spec.add_dependency "relaton-cli"
@@ -63,109 +63,6 @@ module IsoDoc
63
63
  init_arrangement(@options)
64
64
  end
65
65
 
66
- def options_preprocess(options)
67
- options.merge!(default_fonts(options)) do |_, old, new|
68
- old || new
69
- end.merge!(default_file_locations(options)) do |_, old, new|
70
- old || new
71
- end
72
- options
73
- end
74
-
75
- def init_rendering(options)
76
- @ulstyle = options[:ulstyle]
77
- @olstyle = options[:olstyle]
78
- @datauriimage = options[:datauriimage]
79
- @suppressheadingnumbers = options[:suppressheadingnumbers]
80
- @break_up_urls_in_tables = options[:breakupurlsintables]
81
- @suppressasciimathdup = options[:suppressasciimathdup]
82
- @aligncrosselements = options[:aligncrosselements]
83
- @modspecidentifierbase = options[:modspecidentifierbase]
84
- @sourcehighlighter = options[:sourcehighlighter]
85
- end
86
-
87
- def init_arrangement(options)
88
- @sectionsplit = options[:sectionsplit] == "true"
89
- @bare = options[:bare]
90
- @semantic_xml_insert = options[:semanticxmlinsert] != "false"
91
- end
92
-
93
- def init_i18n(options)
94
- @i18nyaml = options[:i18nyaml]
95
- @lang = options[:language] || "en"
96
- @script = options[:script] || "Latn"
97
- @locale = options[:locale]
98
- @localizenumber = options[:localizenumber]
99
- end
100
-
101
- def init_locations(options)
102
- @libdir ||= File.dirname(__FILE__)
103
- @baseassetpath = options[:baseassetpath]
104
- @tmpimagedir_suffix = tmpimagedir_suffix
105
- @tmpfilesdir_suffix = tmpfilesdir_suffix
106
- @sourcefilename = options[:sourcefilename]
107
- @files_to_delete = []
108
- @tempfile_cache = []
109
- end
110
-
111
- def init_processing
112
- @termdomain = ""
113
- @termexample = false
114
- @note = false
115
- @sourcecode = false
116
- @footnotes = []
117
- @comments = []
118
- @in_footnote = false
119
- @in_comment = false
120
- @in_table = false
121
- @in_figure = false
122
- @seen_footnote = Set.new
123
- @c = HTMLEntities.new
124
- @openmathdelim = "`"
125
- @closemathdelim = "`"
126
- @maxwidth = 1200
127
- @maxheight = 800
128
- @bookmarks_allocated = { "X" => true }
129
- @fn_bookmarks = {}
130
- end
131
-
132
- def init_fonts(options)
133
- @normalfontsize = options[:normalfontsize]
134
- @smallerfontsize = options[:smallerfontsize]
135
- @monospacefontsize = options[:monospacefontsize]
136
- @footnotefontsize = options[:footnotefontsize]
137
- @fontist_fonts = options[:fonts]
138
- @fontlicenseagreement = options[:fontlicenseagreement]
139
- end
140
-
141
- def init_covers(options)
142
- @header = options[:header]
143
- @htmlcoverpage = options[:htmlcoverpage]
144
- @wordcoverpage = options[:wordcoverpage]
145
- @htmlintropage = options[:htmlintropage]
146
- @wordintropage = options[:wordintropage]
147
- @scripts = options[:scripts] ||
148
- File.join(File.dirname(__FILE__), "base_style", "scripts.html")
149
- @scripts_pdf = options[:scripts_pdf]
150
- @scripts_override = options[:scripts_override]
151
- end
152
-
153
- def init_stylesheets(options)
154
- @htmlstylesheet_name = options[:htmlstylesheet]
155
- @wordstylesheet_name = options[:wordstylesheet]
156
- @htmlstylesheet_override_name = options[:htmlstylesheet_override]
157
- @wordstylesheet_override_name = options[:wordstylesheet_override]
158
- @standardstylesheet_name = options[:standardstylesheet]
159
- end
160
-
161
- def init_toc(options)
162
- @htmlToClevels = 2
163
- @wordToClevels = 2
164
- @tocfigures = options[:tocfigures]
165
- @toctables = options[:toctables]
166
- @tocrecommendations = options[:tocrecommendations]
167
- end
168
-
169
66
  def tmpimagedir_suffix
170
67
  "_#{SecureRandom.hex(8)}_images"
171
68
  end
@@ -214,10 +111,27 @@ module IsoDoc
214
111
  convert_i18n_init(docxml)
215
112
  metadata_init(@lang, @script, @locale, @i18n)
216
113
  xref_init(@lang, @script, self, @i18n, { locale: @locale })
114
+ docxml = preprocess_xslt(docxml)
217
115
  toc_init(docxml)
218
116
  [docxml, filename, dir]
219
117
  end
220
118
 
119
+ def preprocess_xslt(docxml)
120
+ extract_preprocess_xslt(docxml).each do |x|
121
+ docxml = Nokogiri::XSLT(x).transform(docxml)
122
+ end
123
+ docxml
124
+ end
125
+
126
+ def extract_preprocess_xslt(docxml)
127
+ docxml.xpath(ns("//metanorma-extension/render/preprocess-xslt"))
128
+ .each_with_object([]) do |x, m|
129
+ formats = x["format"]&.split(",") || []
130
+ !formats.empty? && !formats.include?(@format.to_s) and next
131
+ m << x.children.to_xml
132
+ end
133
+ end
134
+
221
135
  def convert_i18n_init(docxml)
222
136
  convert_i18n_init1(docxml)
223
137
  i18n_init(@lang, @script, @locale)
@@ -242,8 +156,7 @@ module IsoDoc
242
156
  @openmathdelim, @closemathdelim = extract_delims(file)
243
157
  docxml, filename, dir = convert_init(file, input_filename, debug)
244
158
  result = convert1(docxml, filename, dir)
245
- return result if debug
246
-
159
+ debug and return result
247
160
  output_filename ||= "#{filename}.#{@suffix}"
248
161
  postprocess(result, output_filename, dir)
249
162
  FileUtils.rm_rf dir
@@ -76,6 +76,7 @@ module IsoDoc
76
76
  out.p **sourcecode_attrs(node) do |div|
77
77
  sourcecode_parse1(node, div)
78
78
  end
79
+ annotation_parse(node, out)
79
80
  sourcecode_name_parse(node, out, name)
80
81
  end
81
82
 
@@ -84,9 +85,10 @@ module IsoDoc
84
85
  node.at(ns(".//table[@class = 'rouge-line-table']")) ||
85
86
  node.at("./ancestor::xmlns:table[@class = 'rouge-line-table']") and
86
87
  @sourcecode = "table"
87
- # !node.ancestors("table").empty? and
88
- # @sourcecode = "table"
89
- node.children.each { |n| parse(n, div) unless n.name == "name" }
88
+ node.children.each do |n|
89
+ %w(name dl).include?(n.name) and next
90
+ parse(n, div)
91
+ end
90
92
  @sourcecode = false
91
93
  end
92
94
 
@@ -95,17 +97,12 @@ module IsoDoc
95
97
  end
96
98
 
97
99
  def annotation_parse(node, out)
100
+ dl = node.at(ns("./dl")) or return
98
101
  @sourcecode = false
99
- @annotation = true
102
+ # @annotation = true
100
103
  out.div class: "annotation" do |div|
101
- # node.at("./preceding-sibling::*[local-name() = 'annotation']") or
102
- # div << "<br/>"
103
- callout = node.at(ns("//callout[@target='#{node['id']}']"))
104
- div << "<span class='c'>&lt;#{callout.text}&gt;</span> "
105
- div << "<span class='c'>#{node.children&.text&.strip}</span>"
106
- node.at("./following-sibling::*[local-name() = 'annotation']") and
107
- div << "<br/>"
108
- @annotation = false
104
+ parse(dl, div)
105
+ # @annotation = false
109
106
  end
110
107
  end
111
108
 
@@ -203,6 +200,14 @@ module IsoDoc
203
200
  node.children.each { |n| parse(n, div) }
204
201
  end
205
202
  end
203
+
204
+ def source_parse(node, out)
205
+ out.div class: "BlockSource" do |d|
206
+ d.p do |p|
207
+ node.children.each { |n| parse(n, p) }
208
+ end
209
+ end
210
+ end
206
211
  end
207
212
  end
208
213
  end
@@ -194,11 +194,12 @@ module IsoDoc
194
194
  end
195
195
 
196
196
  def table_note_cleanup(docxml)
197
- docxml.xpath("//table[div[@class = 'Note' or " \
198
- "@class = 'TableFootnote']]").each do |t|
197
+ docxml.xpath("//table[dl or div[@class = 'Note' or @class = 'BlockSource' " \
198
+ "or @class = 'TableFootnote']]").each do |t|
199
199
  tfoot = table_get_or_make_tfoot(t)
200
200
  insert_here = new_fullcolspan_row(t, tfoot)
201
- t.xpath("div[@class = 'Note' or @class = 'TableFootnote']")
201
+ t.xpath("dl | div[@class = 'Note' or @class = 'BlockSource' or " \
202
+ "@class = 'TableFootnote']")
202
203
  .each do |d|
203
204
  d.parent = insert_here
204
205
  end
@@ -4,7 +4,7 @@ module IsoDoc
4
4
  def recommendation_name(name, out)
5
5
  return if name.nil?
6
6
 
7
- out.p **{ class: "RecommendationTitle" } do |p|
7
+ out.p class: "RecommendationTitle" do |p|
8
8
  name.children.each { |n| parse(n, p) }
9
9
  end
10
10
  end
@@ -38,8 +38,7 @@ module IsoDoc
38
38
  out.div **attr_code(annex_attrs(c)) do |s|
39
39
  c.elements.each do |c1|
40
40
  if c1.name == "title" then annex_name(c, c1, s)
41
- else
42
- parse(c1, s)
41
+ else parse(c1, s)
43
42
  end
44
43
  end
45
44
  end
@@ -20,10 +20,11 @@ module IsoDoc
20
20
  end
21
21
 
22
22
  def tbody_parse(node, table)
23
- tbody = node.at(ns("./tbody")) || return
23
+ tbody = node.at(ns("./tbody")) or return
24
+ rowcount = tbody.xpath(ns("./tr")).size
24
25
  table.tbody do |h|
25
26
  tbody.element_children.each_with_index do |n, i|
26
- tr_parse(n, h, i, tbody.xpath(ns("./tr")).size, false)
27
+ tr_parse(n, h, i, rowcount, false)
27
28
  end
28
29
  end
29
30
  end
@@ -76,12 +77,17 @@ module IsoDoc
76
77
  table_title_parse(node, out)
77
78
  out.table **table_attrs(node) do |t|
78
79
  table_parse_core(node, t)
79
- (dl = node.at(ns("./dl"))) && parse(dl, out)
80
- node.xpath(ns("./note")).each { |n| parse(n, out) }
80
+ table_parse_tail(node, t)
81
81
  end
82
82
  @in_table = false
83
83
  end
84
84
 
85
+ def table_parse_tail(node, out)
86
+ (dl = node.at(ns("./dl"))) && parse(dl, out)
87
+ node.xpath(ns("./source")).each { |n| parse(n, out) }
88
+ node.xpath(ns("./note")).each { |n| parse(n, out) }
89
+ end
90
+
85
91
  def table_parse_core(node, out)
86
92
  tcaption(node, out)
87
93
  colgroup(node, out)
@@ -12,7 +12,6 @@ module IsoDoc
12
12
 
13
13
  def deprecated_term_parse(node, out)
14
14
  out.p class: "DeprecatedTerms", style: "text-align:left;" do |p|
15
- p << l10n("#{@i18n.deprecated}: ")
16
15
  node.children.each { |c| parse(c, p) }
17
16
  end
18
17
  end
@@ -176,6 +176,7 @@ module IsoDoc
176
176
  when "fn" then footnote_parse(node, out)
177
177
  when "p" then para_parse(node, out)
178
178
  when "quote" then quote_parse(node, out)
179
+ when "source" then source_parse(node, out)
179
180
  when "tr" then tr_parse(node, out)
180
181
  when "note" then note_parse(node, out)
181
182
  when "review" then review_note_parse(node, out)
@@ -205,11 +206,6 @@ module IsoDoc
205
206
  when "recommendation" then recommendation_parse(node, out)
206
207
  when "permission" then permission_parse(node, out)
207
208
  when "div" then div_parse(node, out)
208
- # when "subject", "classification"
209
- # requirement_skip_parse(node, out)
210
- # when "inherit", "description", "specification", "measurement-target",
211
- # "verification", "import", "component"
212
- # requirement_component_parse(node, out)
213
209
  when "index" then index_parse(node, out)
214
210
  when "index-xref" then index_xref_parse(node, out)
215
211
  when "termref" then termrefelem_parse(node, out)
@@ -96,6 +96,7 @@ module IsoDoc
96
96
  out.send tag, **attr do |div|
97
97
  sourcecode_parse1(node, div)
98
98
  end
99
+ annotation_parse(node, out)
99
100
  sourcecode_name_parse(node, out, name)
100
101
  end
101
102
 
data/lib/isodoc/init.rb CHANGED
@@ -26,5 +26,108 @@ module IsoDoc
26
26
  n = docxml.at(ns(x.sub(/TOC/, "HTML TOC"))) and
27
27
  @htmlToClevels = n.text.to_i
28
28
  end
29
+
30
+ def options_preprocess(options)
31
+ options.merge!(default_fonts(options)) do |_, old, new|
32
+ old || new
33
+ end.merge!(default_file_locations(options)) do |_, old, new|
34
+ old || new
35
+ end
36
+ options
37
+ end
38
+
39
+ def init_rendering(options)
40
+ @ulstyle = options[:ulstyle]
41
+ @olstyle = options[:olstyle]
42
+ @datauriimage = options[:datauriimage]
43
+ @suppressheadingnumbers = options[:suppressheadingnumbers]
44
+ @break_up_urls_in_tables = options[:breakupurlsintables]
45
+ @suppressasciimathdup = options[:suppressasciimathdup]
46
+ @aligncrosselements = options[:aligncrosselements]
47
+ @modspecidentifierbase = options[:modspecidentifierbase]
48
+ @sourcehighlighter = options[:sourcehighlighter]
49
+ end
50
+
51
+ def init_arrangement(options)
52
+ @sectionsplit = options[:sectionsplit] == "true"
53
+ @bare = options[:bare]
54
+ @semantic_xml_insert = options[:semanticxmlinsert] != "false"
55
+ end
56
+
57
+ def init_i18n(options)
58
+ @i18nyaml = options[:i18nyaml]
59
+ @lang = options[:language] || "en"
60
+ @script = options[:script] || "Latn"
61
+ @locale = options[:locale]
62
+ @localizenumber = options[:localizenumber]
63
+ end
64
+
65
+ def init_locations(options)
66
+ @libdir ||= File.dirname(__FILE__)
67
+ @baseassetpath = options[:baseassetpath]
68
+ @tmpimagedir_suffix = tmpimagedir_suffix
69
+ @tmpfilesdir_suffix = tmpfilesdir_suffix
70
+ @sourcefilename = options[:sourcefilename]
71
+ @files_to_delete = []
72
+ @tempfile_cache = []
73
+ end
74
+
75
+ def init_processing
76
+ @termdomain = ""
77
+ @termexample = false
78
+ @note = false
79
+ @sourcecode = false
80
+ @footnotes = []
81
+ @comments = []
82
+ @in_footnote = false
83
+ @in_comment = false
84
+ @in_table = false
85
+ @in_figure = false
86
+ @seen_footnote = Set.new
87
+ @c = HTMLEntities.new
88
+ @openmathdelim = "`"
89
+ @closemathdelim = "`"
90
+ @maxwidth = 1200
91
+ @maxheight = 800
92
+ @bookmarks_allocated = { "X" => true }
93
+ @fn_bookmarks = {}
94
+ end
95
+
96
+ def init_fonts(options)
97
+ @normalfontsize = options[:normalfontsize]
98
+ @smallerfontsize = options[:smallerfontsize]
99
+ @monospacefontsize = options[:monospacefontsize]
100
+ @footnotefontsize = options[:footnotefontsize]
101
+ @fontist_fonts = options[:fonts]
102
+ @fontlicenseagreement = options[:fontlicenseagreement]
103
+ end
104
+
105
+ def init_covers(options)
106
+ @header = options[:header]
107
+ @htmlcoverpage = options[:htmlcoverpage]
108
+ @wordcoverpage = options[:wordcoverpage]
109
+ @htmlintropage = options[:htmlintropage]
110
+ @wordintropage = options[:wordintropage]
111
+ @scripts = options[:scripts] ||
112
+ File.join(File.dirname(__FILE__), "base_style", "scripts.html")
113
+ @scripts_pdf = options[:scripts_pdf]
114
+ @scripts_override = options[:scripts_override]
115
+ end
116
+
117
+ def init_stylesheets(options)
118
+ @htmlstylesheet_name = options[:htmlstylesheet]
119
+ @wordstylesheet_name = options[:wordstylesheet]
120
+ @htmlstylesheet_override_name = options[:htmlstylesheet_override]
121
+ @wordstylesheet_override_name = options[:wordstylesheet_override]
122
+ @standardstylesheet_name = options[:standardstylesheet]
123
+ end
124
+
125
+ def init_toc(options)
126
+ @htmlToClevels = 2
127
+ @wordToClevels = 2
128
+ @tocfigures = options[:tocfigures]
129
+ @toctables = options[:toctables]
130
+ @tocrecommendations = options[:tocrecommendations]
131
+ end
29
132
  end
30
133
  end
@@ -5,6 +5,7 @@ module IsoDoc
5
5
  def bibdata(docxml)
6
6
  toc_metadata(docxml)
7
7
  fonts_metadata(docxml)
8
+ preprocess_xslt_insert(docxml)
8
9
  docid_prefixes(docxml)
9
10
  a = bibdata_current(docxml) or return
10
11
  address_precompose(a)
@@ -14,11 +15,30 @@ module IsoDoc
14
15
  "</localized-strings>"
15
16
  end
16
17
 
18
+ def extension_insert(docxml, path = [])
19
+ ins = docxml.at(ns("//metanorma-extension")) ||
20
+ docxml.at(ns("//bibdata")).after("<metanorma-extension/>").next_element
21
+ path.each do |n|
22
+ ins = ins.at(ns("./#{n}")) || ins.add_child("<#{n}/>").first
23
+ end
24
+ ins
25
+ end
26
+
27
+ def preprocess_xslt_insert(docxml)
28
+ content = preprocess_xslt_read or return
29
+ ins = extension_insert(docxml, %w(render))
30
+ ins << File.read(content)
31
+ end
32
+
33
+ # read in from file, but with `<preprocess-xslt @format="">` wrapper
34
+ def preprocess_xslt_read
35
+ html_doc_path("preprocess.xslt")
36
+ end
37
+
17
38
  def toc_metadata(docxml)
18
39
  return unless @tocfigures || @toctables || @tocrecommendations
19
40
 
20
- ins = docxml.at(ns("//metanorma-extension")) ||
21
- docxml.at(ns("//bibdata")).after("<metanorma-extension/>").next_element
41
+ ins = extension_insert(docxml)
22
42
  @tocfigures and
23
43
  ins << "<toc type='figure'><title>#{@i18n.toc_figures}</title></toc>"
24
44
  @toctables and
@@ -178,5 +178,32 @@ module IsoDoc
178
178
  node.replace(@reqt_models.model(node["model"])
179
179
  .requirement_render1(node))
180
180
  end
181
+
182
+ def source(docxml)
183
+ docxml.xpath(ns("//source/modification")).each do |f|
184
+ source_modification(f)
185
+ end
186
+ docxml.xpath(ns("//table/source")).each { |f| tablesource(f) }
187
+ docxml.xpath(ns("//figure/source")).each { |f| figuresource(f) }
188
+ end
189
+
190
+ def tablesource(elem)
191
+ source1(elem)
192
+ end
193
+
194
+ def figuresource(elem)
195
+ source1(elem)
196
+ end
197
+
198
+ def source1(elem)
199
+ while elem&.next_element&.name == "source"
200
+ elem << "; #{to_xml(elem.next_element.remove.children)}"
201
+ end
202
+ elem.children = l10n("[#{@i18n.source}: #{to_xml(elem.children).strip}]")
203
+ end
204
+
205
+ def source_modification(mod)
206
+ termsource_modification(mod)
207
+ end
181
208
  end
182
209
  end
@@ -3,23 +3,26 @@ module IsoDoc
3
3
  def sourcehighlighter_css(docxml)
4
4
  ret = custom_css(docxml)
5
5
  ret.empty? and return
6
- ins = docxml.at(ns("//metanorma-extension")) ||
7
- docxml.at(ns("//bibdata")).after("<metanorma-extension/>").next_element
6
+ ins = extension_insert(docxml)
8
7
  ins << "<source-highlighter-css>#{ret}" \
9
8
  "</source-highlighter-css>"
10
9
  end
11
10
 
12
11
  def custom_css(docxml)
13
12
  ret = ""
14
- @sourcehighlighter and
15
- ret += File.read(File.join(File.dirname(__FILE__), "..", "base_style",
16
- "rouge.css"))
13
+ @sourcehighlighter and ret += rouge_css_location
17
14
  a = docxml.at(ns("//metanorma-extension/" \
18
15
  "clause[title = 'user-css']/sourcecode")) and
19
16
  ret += "\n#{to_xml(a.children)}"
20
17
  ret
21
18
  end
22
19
 
20
+ # replace in local gem rather than specify overrides of default
21
+ def rouge_css_location
22
+ File.read(File.join(File.dirname(__FILE__), "..", "base_style",
23
+ "rouge.css"))
24
+ end
25
+
23
26
  def sourcehighlighter
24
27
  @sourcehighlighter or return
25
28
  Rouge::Formatter.enable_escape!
@@ -29,9 +32,16 @@ module IsoDoc
29
32
  { formatter: f, formatter_line: f1 }
30
33
  end
31
34
 
35
+ def callouts(elem)
36
+ elem.xpath(ns(".//callout")).each do |c|
37
+ @callouts[c["target"]] = c.children.to_xml
38
+ end
39
+ end
40
+
32
41
  def sourcecode(docxml)
33
42
  sourcehighlighter_css(docxml)
34
43
  @highlighter = sourcehighlighter
44
+ @callouts = {}
35
45
  docxml.xpath(ns("//sourcecode")).each do |f|
36
46
  sourcecode1(f)
37
47
  end
@@ -40,6 +50,21 @@ module IsoDoc
40
50
  def sourcecode1(elem)
41
51
  source_highlight(elem)
42
52
  source_label(elem)
53
+ callouts(elem)
54
+ annotations(elem)
55
+ end
56
+
57
+ def annotations(elem)
58
+ elem.at(ns("./annotation")) or return
59
+ ret = ""
60
+ elem.xpath(ns("./annotation")).each do |a|
61
+ a.remove
62
+ ret += <<~OUT
63
+ <dt id='#{a['id']}'><span class='c'>#{@callouts[a['id']]}</span></dt>
64
+ <dd>#{a.children.to_xml}</dd>
65
+ OUT
66
+ end
67
+ elem << "<dl><name>#{@i18n.key}</name>#{ret}</dl>"
43
68
  end
44
69
 
45
70
  def source_highlight(elem)
@@ -65,7 +90,7 @@ module IsoDoc
65
90
  def source_remove_annotations(ret, elem)
66
91
  ret[:ann] = elem.xpath(ns("./annotation")).each(&:remove)
67
92
  ret[:call] = elem.xpath(ns("./callout")).each_with_object([]) do |c, m|
68
- m << { xml: c.remove.to_xml, line: c.line - elem.line }
93
+ m << { xml: c.remove, line: c.line - elem.line }
69
94
  end
70
95
  ret
71
96
  end
@@ -85,7 +110,7 @@ module IsoDoc
85
110
  text = to_xml(code)
86
111
  text.split(/[\n\r]/).each_with_index do |c, i|
87
112
  while !callouts.empty? && callouts[0][:line] == i
88
- c.sub!(/\s+$/, " <span class='c'>#{callouts[0][:xml]}</span> ")
113
+ c.sub!(/\s+$/, " #{reinsert_callout(callouts[0][:xml])} ")
89
114
  callouts.shift
90
115
  end
91
116
  end.join("\n")
@@ -95,12 +120,16 @@ module IsoDoc
95
120
  table.xpath(".//td[@class = 'rouge-code']/sourcecode")
96
121
  .each_with_index do |c, i|
97
122
  while !callouts.empty? && callouts[0][:line] == i
98
- c << " <span class='c'>#{callouts[0][:xml]}</span> "
123
+ c << " #{reinsert_callout(callouts[0][:xml])} "
99
124
  callouts.shift
100
125
  end
101
126
  end
102
127
  end
103
128
 
129
+ def reinsert_callout(xml)
130
+ "<span class='c'>#{to_xml(xml)}</span>"
131
+ end
132
+
104
133
  def sourcecode_table_to_elem(elem, tokens)
105
134
  r = Nokogiri::XML(@highlighter[:formatter_line].format(tokens)).root
106
135
  r.xpath(".//td[@class = 'rouge-code']/pre").each do |pre|
@@ -38,16 +38,13 @@ module IsoDoc
38
38
 
39
39
  def concept_render_init(node, defaults)
40
40
  opts = %i(bold ital ref linkref linkmention)
41
- .each_with_object({}) do |x, m|
42
- m[x] = node[x.to_s] || defaults[x]
43
- end
41
+ .each_with_object({}) { |x, m| m[x] = node[x.to_s] || defaults[x] }
44
42
  [opts, node.at(ns("./renderterm")),
45
43
  node.at(ns("./xref | ./eref | ./termref"))]
46
44
  end
47
45
 
48
46
  def concept1_linkmention(ref, renderterm, opts)
49
- (opts[:linkmention] == "true" &&
50
- !renderterm.nil? && !ref.nil?) or return
47
+ (opts[:linkmention] == "true" && !renderterm.nil? && !ref.nil?) or return
51
48
  ref2 = ref.clone
52
49
  r2 = renderterm.clone
53
50
  renderterm.replace(ref2).children = r2
@@ -65,11 +62,10 @@ module IsoDoc
65
62
  def concept1_ref_content(ref)
66
63
  prev = "["
67
64
  foll = "]"
68
- if non_locality_elems(ref).select do |c|
69
- !c.text? || /\S/.match(c)
70
- end.empty?
71
- prev, foll = @i18n.term_defined_in.split("%")
72
- end
65
+ non_locality_elems(ref).select do |c|
66
+ !c.text? || /\S/.match(c)
67
+ end.empty? and
68
+ (prev, foll = @i18n.term_defined_in.split("%"))
73
69
  ref.previous = prev
74
70
  ref.next = foll
75
71
  end
@@ -95,14 +91,20 @@ module IsoDoc
95
91
  docxml.xpath(ns("//term")).each { |t| merge_second_preferred(t) }
96
92
  docxml.xpath(ns("//preferred | //admitted | //deprecates"))
97
93
  .each { |p| designation1(p) }
94
+ docxml.xpath(ns("//deprecates")).each { |d| deprecates(d) }
95
+ docxml.xpath(ns("//admitted")).each { |d| admits(d) }
96
+ end
97
+
98
+ def deprecates(elem)
99
+ elem.children.first.previous = @i18n.l10n("#{@i18n.deprecated}: ")
98
100
  end
99
101
 
102
+ def admits(elem); end
103
+
100
104
  def merge_second_preferred(term)
101
105
  pref = nil
102
106
  term.xpath(ns("./preferred[expression/name]")).each_with_index do |p, i|
103
- if i.zero? then pref = p
104
- else merge_second_preferred1(pref, p)
105
- end
107
+ (i.zero? and pref = p) or merge_second_preferred1(pref, p)
106
108
  end
107
109
  end
108
110
 
@@ -226,9 +228,7 @@ module IsoDoc
226
228
  docxml.xpath(ns("//termsource/modification")).each do |f|
227
229
  termsource_modification(f)
228
230
  end
229
- docxml.xpath(ns("//termsource")).each do |f|
230
- termsource1(f)
231
- end
231
+ docxml.xpath(ns("//termsource")).each { |f| termsource1(f) }
232
232
  end
233
233
 
234
234
  def termsource1(elem)
@@ -58,6 +58,7 @@ module IsoDoc
58
58
  example docxml
59
59
  note docxml
60
60
  admonition docxml
61
+ source docxml
61
62
  ol docxml
62
63
  permission docxml
63
64
  requirement docxml
@@ -1,3 +1,3 @@
1
1
  module IsoDoc
2
- VERSION = "2.5.1".freeze
2
+ VERSION = "2.5.2".freeze
3
3
  end
@@ -43,14 +43,21 @@ module IsoDoc
43
43
  "#{ret}page-break-after:#{pb};"
44
44
  end
45
45
 
46
- def keep_rows_together(cell, rowmax, totalrows, opt)
46
+ def keep_rows_together(_cell, rowmax, totalrows, opt)
47
47
  opt[:header] and return true
48
- table_line_count(cell.parent.parent) > 15 and return false
48
+ @table_line_count > 15 and return false
49
49
  (totalrows <= 10 && rowmax < totalrows)
50
50
  end
51
51
 
52
+ def tbody_parse(node, table)
53
+ tbody = node.at(ns("./tbody")) or return
54
+ @table_line_count = table_line_count(tbody)
55
+ super
56
+ end
57
+
52
58
  def table_line_count(tbody)
53
59
  sum = 0
60
+ tbody.xpath(ns(".//tr")).size > 15 and return 16 # short-circuit
54
61
  tbody.xpath(ns(".//tr")).each do |r|
55
62
  i = 1
56
63
  r.xpath(ns(".//td | .//th")).each do |c|
@@ -70,7 +77,8 @@ module IsoDoc
70
77
  summary: node["summary"], width: node["width"],
71
78
  style: "mso-table-anchor-horizontal:column;mso-table-overlap:never;" \
72
79
  "#{bordered}#{keep_style(node)}",
73
- class: (node.text.length > 4000 ? "MsoISOTableBig" : "MsoISOTable") }
80
+ class: (node.text.length > 4000 ? "MsoISOTableBig" : "MsoISOTable")
81
+ }
74
82
  bordered or ret.delete(:class)
75
83
  super.merge(attr_code(ret))
76
84
  end
@@ -89,9 +97,8 @@ module IsoDoc
89
97
  table_title_parse(node, out)
90
98
  out.div align: "center", class: "table_container" do |div|
91
99
  div.table **table_attrs(node) do |t|
92
- table_parse_core(node, out)
93
- (dl = node.at(ns("./dl"))) && parse(dl, out)
94
- node.xpath(ns("./note")).each { |n| parse(n, out) }
100
+ table_parse_core(node, t)
101
+ table_parse_tail(node, t)
95
102
  end
96
103
  end
97
104
  @in_table = false
@@ -172,8 +172,8 @@ refer_list)
172
172
  c = Counter.new(list["start"] ? list["start"].to_i - 1 : 0)
173
173
  list.xpath(ns("./li")).each do |li|
174
174
  label = c.increment(li).listlabel(list, depth)
175
- label = "#{prev_label}) #{label}" unless prev_label.empty?
176
- label = "#{list_anchor[:xref]} #{label}" if refer_list
175
+ label = list_item_anchor_label(label, list_anchor, prev_label,
176
+ refer_list)
177
177
  li["id"] and @anchors[li["id"]] =
178
178
  { xref: "#{label})", type: "listitem", refer_list:
179
179
  refer_list, container: list_anchor[:container] }
@@ -183,6 +183,16 @@ refer_list)
183
183
  end
184
184
  end
185
185
 
186
+ def list_item_anchor_label(label, list_anchor, prev_label, refer_list)
187
+ prev_label.empty? or
188
+ label = @i18n.list_nested_xref.sub(/%1/, "#{prev_label})")
189
+ .sub(/%2/, label)
190
+ refer_list and
191
+ label = @i18n.list_nested_xref.sub(/%1/, list_anchor[:xref])
192
+ .sub(/%2/, label)
193
+ label
194
+ end
195
+
186
196
  def deflist_anchor_names(sections)
187
197
  sections.each do |s|
188
198
  notes = s.xpath(ns(".//dl")) - s.xpath(ns(".//clause//dl")) -
@@ -51,35 +51,40 @@ module IsoDoc
51
51
  ret.merge(@pdf_cmd_options)
52
52
  end
53
53
 
54
- def convert(input_filename, file = nil, debug = false,
55
- output_filename = nil)
56
- file = File.read(input_filename, encoding: "utf-8") if file.nil?
57
- input_filename, docxml, filename = input_xml_path(input_filename,
58
- file, debug)
54
+ # input_file: keep-alive tempfile
55
+ def convert(input_fname, file = nil, debug = false,
56
+ output_fname = nil)
57
+ file = File.read(input_fname, encoding: "utf-8") if file.nil?
58
+ input_file, docxml, filename =
59
+ input_xml_path(input_fname, file, debug)
59
60
  ::Metanorma::Output::XslfoPdf.new.convert(
60
- input_filename,
61
- output_filename || "#{filename}.#{@suffix}",
61
+ filename,
62
+ output_fname || output_filename(input_fname),
62
63
  File.join(@libdir, pdf_stylesheet(docxml)),
63
64
  pdf_options(docxml),
64
65
  )
65
66
  end
66
67
 
68
+ def output_filename(input_fname)
69
+ out = input_fname.sub(/\.presentation\.xml$/, ".xml")
70
+ File.join(File.dirname(input_fname),
71
+ "#{File.basename(out, '.*')}.#{@suffix}")
72
+ end
73
+
67
74
  def xref_parse(node, out)
68
- out.a(**{ href: target_pdf(node) }) { |l| l << get_linkend(node) }
75
+ out.a(href: target_pdf(node)) { |l| l << get_linkend(node) }
69
76
  end
70
77
 
71
78
  def input_xml_path(input_filename, xml_file, debug)
72
79
  docxml, filename, dir = convert_init(xml_file, input_filename, debug)
73
- unless /\.xml$/.match?(input_filename)
74
- input_filename = Tempfile.open([filename, ".xml"],
75
- encoding: "utf-8") do |f|
76
- f.write xml_file
77
- f.path
78
- end
80
+ input_filename = Tempfile.open([File.basename(filename), ".xml"],
81
+ encoding: "utf-8") do |f|
82
+ f.write xml_file
83
+ f
79
84
  end
80
85
  FileUtils.rm_rf dir
81
86
 
82
- [input_filename, docxml, filename]
87
+ [input_filename, docxml, input_filename.path]
83
88
  end
84
89
  end
85
90
  end
@@ -39,6 +39,7 @@ chain_or: "%1 او %2"
39
39
  chain_from: "%1 %من 2"
40
40
  chain_to: "من %1 إلى %2"
41
41
  nested_xref: "%1, %2"
42
+ list_nested_xref: "%1 %2"
42
43
  ordinal_keys: [gender]
43
44
  SpelloutRules:
44
45
  f: spellout-ordinal-feminine
@@ -41,6 +41,7 @@ chain_or: "%1 oder %2"
41
41
  chain_from: "%1 von %2"
42
42
  chain_to: "%1 bis %2"
43
43
  nested_xref: "%1, %2"
44
+ list_nested_xref: "%1 %2"
44
45
  ordinal_keys: [gender,number]
45
46
  SpelloutRules:
46
47
  m.sg: spellout-ordinal-r
@@ -47,6 +47,7 @@ chain_or: "%1 or %2"
47
47
  chain_from: "%1 from %2"
48
48
  chain_to: "%1 to %2"
49
49
  nested_xref: "%1, %2"
50
+ list_nested_xref: "%1 %2"
50
51
  ordinal_keys: []
51
52
  SpelloutRules: spellout-ordinal
52
53
  note: NOTE
@@ -43,6 +43,7 @@ chain_or: "%1 o %2"
43
43
  chain_from: "%1 del %2"
44
44
  chain_to: "%1 al %2"
45
45
  nested_xref: "%1, %2"
46
+ list_nested_xref: "%1 %2"
46
47
  ordinal_keys: [gender,number]
47
48
  SpelloutRules:
48
49
  m.sg: spellout-ordinal-masculine
@@ -40,6 +40,7 @@ chain_or: "%1 ou %2"
40
40
  chain_from: "%1 de %2"
41
41
  chain_to: "%1 à %2"
42
42
  nested_xref: "%1, %2"
43
+ list_nested_xref: "%1 %2"
43
44
  ordinal_keys: [gender,number]
44
45
  SpelloutRules:
45
46
  m.sg: spellout-ordinal-masculine
@@ -40,12 +40,13 @@ chain_or: "%1 or %2"
40
40
  chain_from: "%1 from %2"
41
41
  chain_to: "%1 to %2"
42
42
  nested_xref: "%1の%2"
43
+ list_nested_xref: "%1の%2"
43
44
  ordinal_keys: []
44
45
  SpelloutRules: spellout-ordinal
45
46
  note: 注記
46
47
  note_xref: 注記
47
48
  termnote: 注釈%
48
- list: List
49
+ list: リスト
49
50
  deflist: Definition List
50
51
  figure: 図
51
52
  diagram: Diagram
@@ -116,7 +117,7 @@ locality: {
116
117
  part: 部,
117
118
  paragraph: 段落,
118
119
  chapter: Chapter,
119
- page: Page,
120
+ page: ページ,
120
121
  table: 表,
121
122
  annex: 附属書,
122
123
  figure: 図,
@@ -46,6 +46,7 @@ chain_or: "%1 или %2"
46
46
  chain_from: "%1 от %2"
47
47
  chain_to: "%1 до %2"
48
48
  nested_xref: "%1, %2"
49
+ list_nested_xref: "%1 %2"
49
50
  ordinal_keys: [gender,number]
50
51
  SpelloutRules:
51
52
  m.sg: spellout-ordinal-masculine
@@ -42,6 +42,7 @@ chain_or: "%1或%2"
42
42
  chain_from: "%1从%2"
43
43
  chain_to: "%1到%2"
44
44
  nested_xref: "%1, %2"
45
+ list_nested_xref: "%1 %2"
45
46
  ordinal_keys: []
46
47
  SpelloutRules: spellout-ordinal
47
48
  note: 注
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: isodoc
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.5.1
4
+ version: 2.5.2
5
5
  platform: ruby
6
6
  authors:
7
7
  - Ribose Inc.
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2023-03-27 00:00:00.000000000 Z
11
+ date: 2023-04-10 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: html2doc
@@ -16,14 +16,14 @@ dependencies:
16
16
  requirements:
17
17
  - - "~>"
18
18
  - !ruby/object:Gem::Version
19
- version: 1.5.0
19
+ version: 1.5.3
20
20
  type: :runtime
21
21
  prerelease: false
22
22
  version_requirements: !ruby/object:Gem::Requirement
23
23
  requirements:
24
24
  - - "~>"
25
25
  - !ruby/object:Gem::Version
26
- version: 1.5.0
26
+ version: 1.5.3
27
27
  - !ruby/object:Gem::Dependency
28
28
  name: htmlentities
29
29
  requirement: !ruby/object:Gem::Requirement
@@ -44,14 +44,14 @@ dependencies:
44
44
  requirements:
45
45
  - - "~>"
46
46
  - !ruby/object:Gem::Version
47
- version: '4'
47
+ version: '5'
48
48
  type: :runtime
49
49
  prerelease: false
50
50
  version_requirements: !ruby/object:Gem::Requirement
51
51
  requirements:
52
52
  - - "~>"
53
53
  - !ruby/object:Gem::Version
54
- version: '4'
54
+ version: '5'
55
55
  - !ruby/object:Gem::Dependency
56
56
  name: emf2svg
57
57
  requirement: !ruby/object:Gem::Requirement