isodoc 1.1.4 → 1.2.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (45) hide show
  1. checksums.yaml +4 -4
  2. data/lib/isodoc-yaml/i18n-en.yaml +4 -1
  3. data/lib/isodoc-yaml/i18n-fr.yaml +4 -1
  4. data/lib/isodoc-yaml/i18n-zh-Hans.yaml +4 -1
  5. data/lib/isodoc.rb +1 -0
  6. data/lib/isodoc/common.rb +0 -2
  7. data/lib/isodoc/convert.rb +33 -27
  8. data/lib/isodoc/function/blocks.rb +10 -22
  9. data/lib/isodoc/function/blocks_example_note.rb +14 -15
  10. data/lib/isodoc/function/cleanup.rb +5 -4
  11. data/lib/isodoc/function/inline.rb +6 -76
  12. data/lib/isodoc/function/references.rb +10 -9
  13. data/lib/isodoc/function/reqt.rb +12 -11
  14. data/lib/isodoc/function/section.rb +39 -54
  15. data/lib/isodoc/function/table.rb +1 -6
  16. data/lib/isodoc/function/terms.rb +13 -6
  17. data/lib/isodoc/function/to_word_html.rb +1 -0
  18. data/lib/isodoc/function/utils.rb +4 -3
  19. data/lib/isodoc/html_function/html.rb +0 -1
  20. data/lib/isodoc/{function/i18n.rb → i18n.rb} +37 -36
  21. data/lib/isodoc/metadata.rb +4 -3
  22. data/lib/isodoc/metadata_date.rb +1 -1
  23. data/lib/isodoc/presentation_function/block.rb +138 -0
  24. data/lib/isodoc/presentation_function/inline.rb +131 -0
  25. data/lib/isodoc/presentation_function/section.rb +46 -0
  26. data/lib/isodoc/presentation_xml_convert.rb +38 -5
  27. data/lib/isodoc/version.rb +1 -1
  28. data/lib/isodoc/word_function/body.rb +12 -8
  29. data/lib/isodoc/word_function/inline.rb +3 -1
  30. data/lib/isodoc/xref.rb +5 -3
  31. data/lib/isodoc/xref/xref_sect_gen.rb +3 -3
  32. data/spec/assets/i18n.yaml +12 -1
  33. data/spec/isodoc/blocks_spec.rb +1101 -147
  34. data/spec/isodoc/cleanup_spec.rb +2 -2
  35. data/spec/isodoc/footnotes_spec.rb +2 -2
  36. data/spec/isodoc/i18n_spec.rb +679 -110
  37. data/spec/isodoc/inline_spec.rb +323 -142
  38. data/spec/isodoc/lists_spec.rb +2 -2
  39. data/spec/isodoc/postproc_spec.rb +1311 -1333
  40. data/spec/isodoc/ref_spec.rb +181 -3
  41. data/spec/isodoc/section_spec.rb +508 -680
  42. data/spec/isodoc/table_spec.rb +155 -4
  43. data/spec/isodoc/terms_spec.rb +111 -79
  44. data/spec/isodoc/xref_spec.rb +1569 -1186
  45. metadata +6 -3
@@ -16,16 +16,17 @@ module IsoDoc
16
16
  end
17
17
 
18
18
  def l10n(a, b, c)
19
- IsoDoc::Function::I18n::l10n(a, b, c)
19
+ @i18n.l10n(a, b, c)
20
20
  end
21
21
 
22
- def initialize(lang, script, labels, fonts_options = {})
22
+ def initialize(lang, script, i18n, fonts_options = {})
23
23
  @metadata = {}
24
24
  DATETYPES.each { |w| @metadata["#{w.gsub(/-/, '_')}date".to_sym] = 'XXX' }
25
25
  @lang = lang
26
26
  @script = script
27
27
  @c = HTMLEntities.new
28
- @labels = labels
28
+ @i18n = i18n
29
+ @labels = @i18n.get
29
30
  @fonts_options = fonts_options
30
31
  end
31
32
 
@@ -20,7 +20,7 @@ module IsoDoc
20
20
  def monthyr(isodate)
21
21
  m = /(?<yr>\d\d\d\d)-(?<mo>\d\d)/.match isodate
22
22
  return isodate unless m && m[:yr] && m[:mo]
23
- IsoDoc::Function::I18n::l10n("#{months[m[:mo].to_sym]} #{m[:yr]}",
23
+ l10n("#{months[m[:mo].to_sym]} #{m[:yr]}",
24
24
  @lang, @script)
25
25
  end
26
26
 
@@ -0,0 +1,138 @@
1
+ module IsoDoc
2
+ class PresentationXMLConvert < ::IsoDoc::Convert
3
+ def figure(docxml)
4
+ docxml.xpath(ns("//figure")).each do |f|
5
+ figure1(f)
6
+ end
7
+ end
8
+
9
+ def figure1(f)
10
+ return sourcecode1(f) if f["class"] == "pseudocode" ||
11
+ f["type"] == "pseudocode"
12
+ return if labelled_ancestor(f) && f.ancestors("figure").empty?
13
+ return if f.at(ns("./figure")) and !f.at(ns("./name"))
14
+ lbl = @xrefs.anchor(f['id'], :label, false) or return
15
+ prefix_name(f, "&nbsp;&mdash; ", l10n("#{@i18n.figure} #{lbl}"), "name")
16
+ end
17
+
18
+ def prefix_name(f, delim, number, elem)
19
+ return if number.nil? || number.empty?
20
+ unless name = f.at(ns("./#{elem}"))
21
+ f.children.empty? and f.add_child("<#{elem}></#{elem}>") or
22
+ f.children.first.previous = "<#{elem}></#{elem}>"
23
+ name = f.children.first
24
+ end
25
+ name.children.empty? ? name.add_child(number) :
26
+ ( name.children.first.previous = "#{number}#{delim}" )
27
+ end
28
+
29
+ def sourcecode(docxml)
30
+ docxml.xpath(ns("//sourcecode")).each do |f|
31
+ sourcecode1(f)
32
+ end
33
+ end
34
+
35
+ def sourcecode1(f)
36
+ return if labelled_ancestor(f)
37
+ return unless f.ancestors("example").empty?
38
+ lbl = @xrefs.anchor(f['id'], :label, false) or return
39
+ prefix_name(f, "&nbsp;&mdash; ", l10n("#{@i18n.figure} #{lbl}"), "name")
40
+ end
41
+
42
+ def formula(docxml)
43
+ docxml.xpath(ns("//formula")).each do |f|
44
+ formula1(f)
45
+ end
46
+ end
47
+
48
+ # introduce name element
49
+ def formula1(f)
50
+ lbl = @xrefs.anchor(f['id'], :label, false)
51
+ prefix_name(f, "", lbl, "name")
52
+ end
53
+
54
+ def example(docxml)
55
+ docxml.xpath(ns("//example")).each do |f|
56
+ example1(f)
57
+ end
58
+ end
59
+
60
+ def termexample(docxml)
61
+ docxml.xpath(ns("//termexample")).each do |f|
62
+ example1(f)
63
+ end
64
+ end
65
+
66
+ def example1(f)
67
+ n = @xrefs.get[f["id"]]
68
+ lbl = (n.nil? || n[:label].nil? || n[:label].empty?) ? @i18n.example :
69
+ l10n("#{@i18n.example} #{n[:label]}")
70
+ prefix_name(f, "&nbsp;&mdash; ", lbl, "name")
71
+ end
72
+
73
+ def note(docxml)
74
+ docxml.xpath(ns("//note")).each do |f|
75
+ note1(f)
76
+ end
77
+ end
78
+
79
+ # introduce name element
80
+ def note1(f)
81
+ return if f.parent.name == "bibitem"
82
+ n = @xrefs.get[f["id"]]
83
+ lbl = (@i18n.note if n.nil? || n[:label].nil? || n[:label].empty?) ?
84
+ @i18n.note : l10n("#{@i18n.note} #{n[:label]}")
85
+ prefix_name(f, "", lbl, "name")
86
+ end
87
+
88
+ def termnote(docxml)
89
+ docxml.xpath(ns("//termnote")).each do |f|
90
+ termnote1(f)
91
+ end
92
+ end
93
+
94
+ # introduce name element
95
+ def termnote1(f)
96
+ lbl = l10n(@xrefs.anchor(f['id'], :label) || '???')
97
+ prefix_name(f, "", lbl, "name")
98
+ end
99
+
100
+ def recommendation(docxml)
101
+ docxml.xpath(ns("//recommendation")).each do |f|
102
+ recommendation1(f, @i18n.recommendation)
103
+ end
104
+ end
105
+
106
+ def requirement(docxml)
107
+ docxml.xpath(ns("//requirement")).each do |f|
108
+ recommendation1(f, @i18n.requirement)
109
+ end
110
+ end
111
+
112
+ def permission(docxml)
113
+ docxml.xpath(ns("//permission")).each do |f|
114
+ recommendation1(f, @i18n.permission)
115
+ end
116
+ end
117
+
118
+ # introduce name element
119
+ def recommendation1(f, type)
120
+ n = @xrefs.anchor(f['id'], :label, false)
121
+ lbl = (n.nil? ? type : l10n("#{type} #{n}"))
122
+ prefix_name(f, "", lbl, "name")
123
+ end
124
+
125
+ def table(docxml)
126
+ docxml.xpath(ns("//table")).each do |f|
127
+ table1(f)
128
+ end
129
+ end
130
+
131
+ def table1(f)
132
+ return if labelled_ancestor(f)
133
+ return if f["unnumbered"] && !f.at(ns("./name"))
134
+ n = @xrefs.anchor(f['id'], :label, false)
135
+ prefix_name(f, "&nbsp;&mdash; ", l10n("#{@i18n.table} #{n}"), "name")
136
+ end
137
+ end
138
+ end
@@ -0,0 +1,131 @@
1
+ module IsoDoc
2
+ class PresentationXMLConvert < ::IsoDoc::Convert
3
+ def prefix_container(container, linkend, _target)
4
+ l10n(@xrefs.anchor(container, :xref) + ", " + linkend)
5
+ end
6
+
7
+ def anchor_linkend(node, linkend)
8
+ if node["citeas"].nil? && node["bibitemid"]
9
+ return @xrefs.anchor(node["bibitemid"] ,:xref) || "???"
10
+ elsif node["target"] && !/.#./.match(node["target"])
11
+ linkend = @xrefs.anchor(node["target"], :xref)
12
+ container = @xrefs.anchor(node["target"], :container, false)
13
+ (container && get_note_container_id(node) != container &&
14
+ @xrefs.get[node["target"]]) &&
15
+ linkend = prefix_container(container, linkend, node["target"])
16
+ linkend = capitalise_xref(node, linkend)
17
+ end
18
+ linkend || "???"
19
+ end
20
+
21
+ def capitalise_xref(node, linkend)
22
+ return linkend unless %w(Latn Cyrl Grek).include? @script
23
+ return linkend&.capitalize if node["case"] == "capital"
24
+ return linkend&.downcase if node["case"] == "lowercase"
25
+ return linkend if linkend[0,1].match(/\p{Upper}/)
26
+ prec = nearest_block_parent(node).xpath("./descendant-or-self::text()") &
27
+ node.xpath("./preceding::text()")
28
+ (prec.empty? || /(?!<[^.].)\.\s+$/.match(prec.map { |p| p.text }.join)) ?
29
+ linkend&.capitalize : linkend
30
+ end
31
+
32
+ def nearest_block_parent(node)
33
+ until %w(p title td th name formula
34
+ li dt dd sourcecode pre).include?(node.name)
35
+ node = node.parent
36
+ end
37
+ node
38
+ end
39
+
40
+ def non_locality_elems(node)
41
+ node.children.select do |c|
42
+ !%w{locality localityStack}.include? c.name
43
+ end
44
+ end
45
+
46
+ def get_linkend(node)
47
+ contents = non_locality_elems(node).select { |c| !c.text? || /\S/.match(c) }
48
+ return unless contents.empty?
49
+ link = anchor_linkend(node, docid_l10n(node["target"] || node["citeas"]))
50
+ link += eref_localities(node.xpath(ns("./locality | ./localityStack")), link)
51
+ non_locality_elems(node).each { |n| n.remove }
52
+ node.add_child(link)
53
+ end
54
+ # so not <origin bibitemid="ISO7301" citeas="ISO 7301">
55
+ # <locality type="section"><reference>3.1</reference></locality></origin>
56
+
57
+ def eref_localities(refs, target)
58
+ ret = ""
59
+ refs.each_with_index do |r, i|
60
+ delim = ","
61
+ delim = ";" if r.name == "localityStack" && i>0
62
+ if r.name == "localityStack"
63
+ r.elements.each_with_index do |rr, j|
64
+ ret += eref_localities0(rr, j, target, delim)
65
+ delim = ","
66
+ end
67
+ else
68
+ ret += eref_localities0(r, i, target, delim)
69
+ end
70
+ end
71
+ ret
72
+ end
73
+
74
+ def eref_localities0(r, i, target, delim)
75
+ if r["type"] == "whole" then l10n("#{delim} #{@i18n.wholeoftext}")
76
+ else
77
+ eref_localities1(target, r["type"], r.at(ns("./referenceFrom")),
78
+ r.at(ns("./referenceTo")), delim, @lang)
79
+ end
80
+ end
81
+
82
+ # TODO: move to localization file
83
+ def eref_localities1_zh(target, type, from, to, delim)
84
+ ret = "#{delim} 第#{from.text}" if from
85
+ ret += "&ndash;#{to.text}" if to
86
+ loc = (@i18n.locality[type] || type.sub(/^locality:/, "").capitalize )
87
+ ret += " #{loc}"
88
+ ret
89
+ end
90
+
91
+ # TODO: move to localization file
92
+ def eref_localities1(target, type, from, to, delim, lang = "en")
93
+ return "" if type == "anchor"
94
+ return l10n(eref_localities1_zh(target, type, from, to, delim)) if lang == "zh"
95
+ ret = delim
96
+ loc = @i18n.locality[type] || type.sub(/^locality:/, "").capitalize
97
+ ret += " #{loc}"
98
+ ret += " #{from.text}" if from
99
+ ret += "&ndash;#{to.text}" if to
100
+ l10n(ret)
101
+ end
102
+
103
+ def xref(docxml)
104
+ docxml.xpath(ns("//xref")).each do |f|
105
+ xref1(f)
106
+ end
107
+ end
108
+
109
+ def eref(docxml)
110
+ docxml.xpath(ns("//eref")).each do |f|
111
+ xref1(f)
112
+ end
113
+ end
114
+
115
+ def origin(docxml)
116
+ docxml.xpath(ns("//origin[not(termref)]")).each do |f|
117
+ xref1(f)
118
+ end
119
+ end
120
+
121
+ def quotesource(docxml)
122
+ docxml.xpath(ns("//quote/source")).each do |f|
123
+ xref1(f)
124
+ end
125
+ end
126
+
127
+ def xref1(f)
128
+ get_linkend(f)
129
+ end
130
+ end
131
+ end
@@ -0,0 +1,46 @@
1
+ module IsoDoc
2
+ class PresentationXMLConvert < ::IsoDoc::Convert
3
+ def clause(docxml)
4
+ docxml.xpath(ns("//clause | "\
5
+ "//terms | //definitions | //references")).
6
+ each do |f|
7
+ clause1(f)
8
+ end
9
+ end
10
+
11
+ def clause1(f)
12
+ level = @xrefs.anchor(f['id'], :level, false) || "1"
13
+ t = f.at(ns("./title")) and t["depth"] = level
14
+ return if !f.ancestors("boilerplate").empty?
15
+ return if @suppressheadingnumbers || f["unnumbered"]
16
+ lbl = @xrefs.anchor(f['id'], :label,
17
+ f.parent.name != "sections") or return
18
+ prefix_name(f, "<tab/>", "#{lbl}#{clausedelim}", "title")
19
+ end
20
+
21
+ def annex(docxml)
22
+ docxml.xpath(ns("//annex")).each do |f|
23
+ annex1(f)
24
+ end
25
+ end
26
+
27
+ def annex1(f)
28
+ lbl = @xrefs.anchor(f['id'], :label)
29
+ if t = f.at(ns("./title"))
30
+ t.children = "<strong>#{t.children.to_xml}</strong>"
31
+ end
32
+ prefix_name(f, "<br/><br/>", lbl, "title")
33
+ end
34
+
35
+ def term(docxml)
36
+ docxml.xpath(ns("//term")).each do |f|
37
+ term1(f)
38
+ end
39
+ end
40
+
41
+ def term1(f)
42
+ lbl = @xrefs.get[f["id"]][:label] or return
43
+ prefix_name(f, "", "#{lbl}#{clausedelim}", "name")
44
+ end
45
+ end
46
+ end
@@ -1,3 +1,7 @@
1
+ require_relative "presentation_function/block"
2
+ require_relative "presentation_function/inline"
3
+ require_relative "presentation_function/section"
4
+
1
5
  module IsoDoc
2
6
  class PresentationXMLConvert < ::IsoDoc::Convert
3
7
  def initialize(options)
@@ -9,21 +13,50 @@ module IsoDoc
9
13
  def convert1(docxml, filename, dir)
10
14
  @xrefs.parse docxml
11
15
  info docxml, nil
16
+ conversions(docxml)
12
17
  docxml.to_xml
13
18
  end
14
19
 
20
+ def conversions(docxml)
21
+ section docxml
22
+ block docxml
23
+ inline docxml
24
+ end
25
+
26
+ def section(docxml)
27
+ clause docxml
28
+ annex docxml
29
+ term docxml
30
+ end
31
+
32
+ def block(docxml)
33
+ table docxml
34
+ figure docxml
35
+ sourcecode docxml
36
+ formula docxml
37
+ example docxml
38
+ termexample docxml
39
+ note docxml
40
+ termnote docxml
41
+ permission docxml
42
+ requirement docxml
43
+ recommendation docxml
44
+ end
45
+
46
+ def inline(docxml)
47
+ xref docxml
48
+ eref docxml
49
+ origin docxml
50
+ quotesource docxml
51
+ end
52
+
15
53
  def postprocess(result, filename, dir)
16
- #result = from_xhtml(cleanup(to_xhtml(textcleanup(result))))
17
54
  toXML(result, filename)
18
55
  @files_to_delete.each { |f| FileUtils.rm_rf f }
19
56
  end
20
57
 
21
58
  def toXML(result, filename)
22
- #result = (from_xhtml(html_cleanup(to_xhtml(result))))
23
- #result = from_xhtml(move_images(to_xhtml(result)))
24
- #result = html5(script_cdata(inject_script(result)))
25
59
  File.open(filename, "w:UTF-8") { |f| f.write(result) }
26
60
  end
27
61
  end
28
62
  end
29
-
@@ -1,3 +1,3 @@
1
1
  module IsoDoc
2
- VERSION = "1.1.4".freeze
2
+ VERSION = "1.2.0".freeze
3
3
  end
@@ -111,7 +111,7 @@ module IsoDoc::WordFunction
111
111
  def figure_get_or_make_dl(t)
112
112
  dl = t.at(".//table[@class = 'dl']")
113
113
  if dl.nil?
114
- t.add_child("<p><b>#{@key_lbl}</b></p><table class='dl'></table>")
114
+ t.add_child("<p><b>#{@i18n.key}</b></p><table class='dl'></table>")
115
115
  dl = t.at(".//table[@class = 'dl']")
116
116
  end
117
117
  dl
@@ -132,9 +132,10 @@ module IsoDoc::WordFunction
132
132
  end
133
133
 
134
134
  def note_p_parse(node, div)
135
+ name = node&.at(ns("./name"))&.remove
135
136
  div.p **{ class: "Note" } do |p|
136
137
  p.span **{ class: "note_label" } do |s|
137
- s << note_label(node)
138
+ name and name.children.each { |n| parse(n, s) }
138
139
  end
139
140
  insert_tab(p, 1)
140
141
  node.first_element_child.children.each { |n| parse(n, p) }
@@ -143,9 +144,10 @@ module IsoDoc::WordFunction
143
144
  end
144
145
 
145
146
  def note_parse1(node, div)
147
+ name = node&.at(ns("./name"))&.remove
146
148
  div.p **{ class: "Note" } do |p|
147
149
  p.span **{ class: "note_label" } do |s|
148
- s << note_label(node)
150
+ name and name.children.each { |n| parse(n, s) }
149
151
  end
150
152
  insert_tab(p, 1)
151
153
  end
@@ -153,12 +155,14 @@ module IsoDoc::WordFunction
153
155
  end
154
156
 
155
157
  def termnote_parse(node, out)
158
+ name = node&.at(ns("./name"))&.remove
156
159
  out.div **note_attrs(node) do |div|
157
- first = node.first_element_child
158
160
  div.p **{ class: "Note" } do |p|
159
- anchor = @xrefs.get[node['id']]
160
- p << "#{anchor&.dig(:label) || '???'}: "
161
- para_then_remainder(first, node, p, div)
161
+ if name
162
+ name.children.each { |n| parse(n, p) }
163
+ p << l10n(": ")
164
+ end
165
+ para_then_remainder(node.first_element_child, node, p, div)
162
166
  end
163
167
  end
164
168
  end
@@ -186,7 +190,7 @@ module IsoDoc::WordFunction
186
190
 
187
191
  def formula_where(dl, out)
188
192
  return unless dl
189
- out.p { |p| p << @where_lbl }
193
+ out.p { |p| p << @i18n.where }
190
194
  parse(dl, out)
191
195
  out.parent.at("./table")["class"] = "formula_dl"
192
196
  end