metanorma-document 0.2.0 → 0.2.1
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 +4 -4
- data/README.adoc +59 -18
- data/data/stylesheets/components/bibliography.css +2 -2
- data/data/stylesheets/components/inline.css +11 -12
- data/docs/html-renderer.adoc +261 -0
- data/lib/metanorma/document/version.rb +1 -1
- data/lib/metanorma/html/base_renderer.rb +180 -219
- data/lib/metanorma/html/drops/admonition_drop.rb +26 -0
- data/lib/metanorma/html/drops/block_element_drop.rb +20 -0
- data/lib/metanorma/html/drops/example_drop.rb +35 -0
- data/lib/metanorma/html/drops/figure_drop.rb +53 -0
- data/lib/metanorma/html/drops/formula_drop.rb +44 -0
- data/lib/metanorma/html/drops/note_drop.rb +32 -0
- data/lib/metanorma/html/drops/sourcecode_drop.rb +37 -0
- data/lib/metanorma/html/drops.rb +7 -0
- data/lib/metanorma/html/iso_renderer.rb +96 -79
- data/lib/metanorma/html/ogc_renderer.rb +5 -5
- data/lib/metanorma/html/standard_renderer.rb +34 -28
- data/lib/metanorma/html/templates/_admonition.html.liquid +4 -0
- data/lib/metanorma/html/templates/_doc_title.html.liquid +1 -1
- data/lib/metanorma/html/templates/_example.html.liquid +3 -0
- data/lib/metanorma/html/templates/_figure.html.liquid +6 -0
- data/lib/metanorma/html/templates/_formula.html.liquid +6 -0
- data/lib/metanorma/html/templates/_iso_doc_title.html.liquid +2 -2
- data/lib/metanorma/html/templates/_note.html.liquid +3 -0
- data/lib/metanorma/html/templates/_sourcecode.html.liquid +4 -0
- metadata +16 -2
|
@@ -67,32 +67,32 @@ module Metanorma
|
|
|
67
67
|
end
|
|
68
68
|
end
|
|
69
69
|
|
|
70
|
-
def render(node, **
|
|
70
|
+
def render(node, **)
|
|
71
71
|
case node
|
|
72
72
|
when Metanorma::IsoDocument::Root
|
|
73
|
-
render_document(node, **
|
|
73
|
+
render_document(node, **)
|
|
74
74
|
when Metanorma::IsoDocument::Sections::IsoPreface
|
|
75
|
-
render_preface(node, **
|
|
75
|
+
render_preface(node, **)
|
|
76
76
|
when Metanorma::IsoDocument::Sections::IsoSections
|
|
77
|
-
render_sections(node, **
|
|
77
|
+
render_sections(node, **)
|
|
78
78
|
when Metanorma::IsoDocument::Sections::IsoClauseSection
|
|
79
|
-
render_clause(node, **
|
|
79
|
+
render_clause(node, **)
|
|
80
80
|
when Metanorma::IsoDocument::Sections::IsoAnnexSection
|
|
81
|
-
render_annex(node, **
|
|
81
|
+
render_annex(node, **)
|
|
82
82
|
when Metanorma::IsoDocument::Sections::IsoTermsSection
|
|
83
|
-
render_terms_section(node, **
|
|
83
|
+
render_terms_section(node, **)
|
|
84
84
|
when Metanorma::IsoDocument::Sections::IsoForewordSection
|
|
85
|
-
render_foreword(node, **
|
|
85
|
+
render_foreword(node, **)
|
|
86
86
|
when Metanorma::IsoDocument::Sections::IsoAbstractSection
|
|
87
|
-
render_abstract(node, **
|
|
87
|
+
render_abstract(node, **)
|
|
88
88
|
when Metanorma::IsoDocument::Terms::IsoTerm
|
|
89
|
-
render_term(node, **
|
|
89
|
+
render_term(node, **)
|
|
90
90
|
when Metanorma::IsoDocument::Terms::TermNote
|
|
91
|
-
render_term_note(node, **
|
|
91
|
+
render_term_note(node, **)
|
|
92
92
|
when Metanorma::IsoDocument::Terms::TermExample
|
|
93
|
-
render_term_example(node, **
|
|
93
|
+
render_term_example(node, **)
|
|
94
94
|
when Metanorma::IsoDocument::Boilerplate
|
|
95
|
-
render_boilerplate(node, **
|
|
95
|
+
render_boilerplate(node, **)
|
|
96
96
|
else
|
|
97
97
|
super
|
|
98
98
|
end
|
|
@@ -147,33 +147,35 @@ module Metanorma
|
|
|
147
147
|
|
|
148
148
|
# Extract English stage text, deduplicating duplicate language variants.
|
|
149
149
|
def extract_stage(bibdata)
|
|
150
|
-
return nil unless bibdata.status
|
|
150
|
+
return nil unless bibdata.status&.stage
|
|
151
151
|
|
|
152
152
|
stages = Array(bibdata.status.stage)
|
|
153
153
|
return nil if stages.empty?
|
|
154
154
|
|
|
155
155
|
# Prefer English-language stage
|
|
156
|
-
en_stage = stages.find
|
|
156
|
+
en_stage = stages.find do |s|
|
|
157
157
|
lang = safe_attr(s, :language)
|
|
158
158
|
lang == "en" if lang
|
|
159
|
-
|
|
160
|
-
return Array(en_stage.value).join.strip if en_stage
|
|
159
|
+
end
|
|
160
|
+
return Array(en_stage.value).join.strip if en_stage&.value
|
|
161
161
|
|
|
162
162
|
# Fallback: first non-empty, deduplicated
|
|
163
163
|
seen = Set.new
|
|
164
|
-
stage_text = stages.filter_map
|
|
164
|
+
stage_text = stages.filter_map do |s|
|
|
165
165
|
val = Array(s.value).join.strip
|
|
166
166
|
down = val.downcase
|
|
167
167
|
next if seen.include?(down)
|
|
168
|
+
|
|
168
169
|
seen << down
|
|
169
170
|
val.empty? ? nil : val
|
|
170
|
-
|
|
171
|
+
end.compact.join(" ")
|
|
171
172
|
stage_text.empty? ? nil : stage_text
|
|
172
173
|
end
|
|
173
174
|
|
|
174
175
|
# Extract document type from ext.doctype.
|
|
175
176
|
def extract_doctype(bibdata)
|
|
176
177
|
return nil unless bibdata.respond_to?(:ext)
|
|
178
|
+
|
|
177
179
|
ext = bibdata.ext
|
|
178
180
|
return nil unless ext
|
|
179
181
|
|
|
@@ -181,11 +183,11 @@ module Metanorma
|
|
|
181
183
|
return nil unless doctypes && !doctypes.empty?
|
|
182
184
|
|
|
183
185
|
# Prefer English-language doctype
|
|
184
|
-
en_dt = doctypes.find
|
|
186
|
+
en_dt = doctypes.find do |d|
|
|
185
187
|
lang = safe_attr(d, :language)
|
|
186
188
|
lang == "en" if lang
|
|
187
|
-
|
|
188
|
-
return en_dt.value.to_s if en_dt
|
|
189
|
+
end
|
|
190
|
+
return en_dt.value.to_s if en_dt&.value
|
|
189
191
|
|
|
190
192
|
# Fallback: first doctype
|
|
191
193
|
dt = doctypes.first
|
|
@@ -216,7 +218,7 @@ module Metanorma
|
|
|
216
218
|
all_items.each do |node|
|
|
217
219
|
next if node.is_a?(String)
|
|
218
220
|
next if is_title_element?(node, doc.sections)
|
|
219
|
-
|
|
221
|
+
|
|
220
222
|
render(node)
|
|
221
223
|
end
|
|
222
224
|
|
|
@@ -254,13 +256,13 @@ module Metanorma
|
|
|
254
256
|
stage_text = extract_stage(bibdata)
|
|
255
257
|
|
|
256
258
|
@output << render_liquid("_iso_cover.html.liquid", {
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
|
|
259
|
+
"publisher_logos" => logos,
|
|
260
|
+
"doc_id" => doc_id,
|
|
261
|
+
"pub_date" => pub_date,
|
|
262
|
+
"doctype" => doctype,
|
|
263
|
+
"title" => title_text,
|
|
264
|
+
"stage" => stage_text,
|
|
265
|
+
})
|
|
264
266
|
end
|
|
265
267
|
|
|
266
268
|
def render_doc_title(doc)
|
|
@@ -274,8 +276,8 @@ module Metanorma
|
|
|
274
276
|
return unless en_title
|
|
275
277
|
|
|
276
278
|
@output << render_liquid("_iso_doc_title.html.liquid", {
|
|
277
|
-
|
|
278
|
-
|
|
279
|
+
"title" => en_title.to_s,
|
|
280
|
+
})
|
|
279
281
|
end
|
|
280
282
|
|
|
281
283
|
def render_boilerplate_section(doc)
|
|
@@ -303,7 +305,7 @@ module Metanorma
|
|
|
303
305
|
fw_id = safe_attr(fw, :id)
|
|
304
306
|
title_text = extract_plain_text(title)
|
|
305
307
|
register_toc_entry(id: fw_id, level: level, text: title_text)
|
|
306
|
-
@output << "<h1 class=\"
|
|
308
|
+
@output << "<h1 class=\"foreword-title\">"
|
|
307
309
|
render_mixed_inline(title)
|
|
308
310
|
@output << "</h1>"
|
|
309
311
|
end
|
|
@@ -319,7 +321,7 @@ module Metanorma
|
|
|
319
321
|
sec_id = safe_attr(section, :id)
|
|
320
322
|
title_text = extract_plain_text(title)
|
|
321
323
|
register_toc_entry(id: sec_id, level: level, text: title_text)
|
|
322
|
-
@output << "<h1 class=\"
|
|
324
|
+
@output << "<h1 class=\"intro-title\">"
|
|
323
325
|
render_mixed_inline(title)
|
|
324
326
|
@output << "</h1>"
|
|
325
327
|
end
|
|
@@ -344,7 +346,7 @@ module Metanorma
|
|
|
344
346
|
# --- Clause rendering ---
|
|
345
347
|
|
|
346
348
|
def render_clause(clause, level: 1, **_opts)
|
|
347
|
-
attrs = element_attrs(id: safe_attr(clause, :id)
|
|
349
|
+
attrs = element_attrs(id: safe_attr(clause, :id))
|
|
348
350
|
tag("div", attrs) do
|
|
349
351
|
render_title(clause, level)
|
|
350
352
|
render_ordered_content(clause, level)
|
|
@@ -354,7 +356,7 @@ module Metanorma
|
|
|
354
356
|
# --- Annex rendering ---
|
|
355
357
|
|
|
356
358
|
def render_annex(annex, level: 1, **_opts)
|
|
357
|
-
attrs = element_attrs(id: safe_attr(annex, :id), class: "
|
|
359
|
+
attrs = element_attrs(id: safe_attr(annex, :id), class: "section-sub")
|
|
358
360
|
tag("div", attrs) do
|
|
359
361
|
render_annex_title(annex, level)
|
|
360
362
|
render_ordered_content(annex, level)
|
|
@@ -370,7 +372,7 @@ module Metanorma
|
|
|
370
372
|
register_toc_entry(id: annex_id, level: level, text: title_text)
|
|
371
373
|
|
|
372
374
|
h = "h#{[[level, 6].min, 1].max}"
|
|
373
|
-
@output << "<#{h} class=\"
|
|
375
|
+
@output << "<#{h} class=\"annex-title\">"
|
|
374
376
|
render_mixed_inline(title_element)
|
|
375
377
|
@output << "</#{h}>"
|
|
376
378
|
end
|
|
@@ -398,7 +400,7 @@ module Metanorma
|
|
|
398
400
|
# In presentation mode, use fmt_* elements
|
|
399
401
|
if term.fmt_name
|
|
400
402
|
# Render term number (e.g. "3.1")
|
|
401
|
-
@output << "<p class=\"
|
|
403
|
+
@output << "<p class=\"term-number\">"
|
|
402
404
|
render_inline_element(term.fmt_name)
|
|
403
405
|
@output << "</p>"
|
|
404
406
|
elsif term.term_number
|
|
@@ -408,7 +410,7 @@ module Metanorma
|
|
|
408
410
|
else
|
|
409
411
|
extract_text_value(tn)
|
|
410
412
|
end
|
|
411
|
-
@output << "<p class=\"
|
|
413
|
+
@output << "<p class=\"term-number\">#{escape_html(tn_text)}</p>"
|
|
412
414
|
end
|
|
413
415
|
|
|
414
416
|
# Preferred designations — use fmt-preferred if available
|
|
@@ -436,7 +438,7 @@ module Metanorma
|
|
|
436
438
|
# (fmt-definition already includes domain text in its content)
|
|
437
439
|
if term.domain && !term.fmt_definition
|
|
438
440
|
domain_text = safe_attr(term.domain, :text)
|
|
439
|
-
@output << "<p class=\"domain\"><#{escape_html(domain_text)}></p>" if domain_text
|
|
441
|
+
@output << "<p class=\"term-domain\"><#{escape_html(domain_text)}></p>" if domain_text
|
|
440
442
|
end
|
|
441
443
|
|
|
442
444
|
# Definition — use fmt-definition if available
|
|
@@ -458,7 +460,7 @@ module Metanorma
|
|
|
458
460
|
# Source references — use fmt-termsource if available
|
|
459
461
|
if term.fmt_termsource && !term.fmt_termsource.empty?
|
|
460
462
|
term.fmt_termsource.each do |fts|
|
|
461
|
-
@output << "<p class=\"source\">"
|
|
463
|
+
@output << "<p class=\"term-source\">"
|
|
462
464
|
render_mixed_inline(fts)
|
|
463
465
|
@output << "</p>"
|
|
464
466
|
end
|
|
@@ -485,7 +487,8 @@ module Metanorma
|
|
|
485
487
|
if term.preferred && !term.preferred.empty?
|
|
486
488
|
return extract_designation_name(term.preferred.first).to_s
|
|
487
489
|
end
|
|
488
|
-
|
|
490
|
+
|
|
491
|
+
safe_attr(term, :id).to_s.delete_prefix("term-")
|
|
489
492
|
end
|
|
490
493
|
|
|
491
494
|
def extract_term_definition(term)
|
|
@@ -502,11 +505,11 @@ module Metanorma
|
|
|
502
505
|
|
|
503
506
|
def strip_html(html)
|
|
504
507
|
html.gsub(/<[^>]+>/, "").gsub("<", "<").gsub(">", ">")
|
|
505
|
-
|
|
508
|
+
.gsub("&", "&").gsub(" ", " ")
|
|
506
509
|
end
|
|
507
510
|
|
|
508
511
|
def render_term_designation(designation, type)
|
|
509
|
-
css_class = type == "deprecated" ? "
|
|
512
|
+
css_class = type == "deprecated" ? "term-deprecated" : "term-name"
|
|
510
513
|
@output << "<p class=\"#{css_class}\" style=\"text-align:left;\">"
|
|
511
514
|
@output << "<del>" if type == "deprecated"
|
|
512
515
|
@output << "<b><dfn>"
|
|
@@ -583,10 +586,10 @@ module Metanorma
|
|
|
583
586
|
end
|
|
584
587
|
|
|
585
588
|
def render_term_note(note)
|
|
586
|
-
attrs = element_attrs(id: safe_attr(note, :id), class: "
|
|
589
|
+
attrs = element_attrs(id: safe_attr(note, :id), class: "note-block")
|
|
587
590
|
tag("div", attrs) do
|
|
588
591
|
label = extract_termnote_label(note)
|
|
589
|
-
@output << "<p><span class=\"
|
|
592
|
+
@output << "<p><span class=\"term-note-label\">#{escape_html(label)}: </span>"
|
|
590
593
|
note.p&.each { |para| render_mixed_inline(para) }
|
|
591
594
|
@output << "</p>"
|
|
592
595
|
note.ul&.each { |ul| render_unordered_list(ul) }
|
|
@@ -599,7 +602,7 @@ module Metanorma
|
|
|
599
602
|
attrs = element_attrs(id: safe_attr(example, :id), class: "example")
|
|
600
603
|
tag("div", attrs) do
|
|
601
604
|
label = extract_block_label(example, "EXAMPLE")
|
|
602
|
-
@output << "<p><span class=\"
|
|
605
|
+
@output << "<p><span class=\"example-label\">#{escape_html(label)}</span> "
|
|
603
606
|
example.p&.each { |para| render_mixed_inline(para) }
|
|
604
607
|
@output << "</p>"
|
|
605
608
|
example.ul&.each { |ul| render_unordered_list(ul) }
|
|
@@ -627,7 +630,13 @@ module Metanorma
|
|
|
627
630
|
.gsub(/<variant-title[^>]*>.*?<\/variant-title>/m, "")
|
|
628
631
|
.gsub(/<\/?(?:copyright-statement|clause)[^>]*>/, "")
|
|
629
632
|
|
|
630
|
-
|
|
633
|
+
# Remap XML class names to HTML-specific class names
|
|
634
|
+
boilerplate_doc = Nokogiri::HTML::DocumentFragment.parse(clean)
|
|
635
|
+
boilerplate_doc.css("[class]").each do |el|
|
|
636
|
+
el["class"] = el["class"].split(/\s+/).map { |c| html_class_for_span(c) }.join(" ")
|
|
637
|
+
end
|
|
638
|
+
|
|
639
|
+
@output << boilerplate_doc.inner_html.strip
|
|
631
640
|
|
|
632
641
|
@output << "</div>"
|
|
633
642
|
end
|
|
@@ -641,19 +650,19 @@ module Metanorma
|
|
|
641
650
|
next_sib = next_sib.next_sibling
|
|
642
651
|
end
|
|
643
652
|
|
|
644
|
-
display_text = if next_sib
|
|
645
|
-
|
|
646
|
-
|
|
647
|
-
|
|
648
|
-
|
|
649
|
-
|
|
650
|
-
|
|
651
|
-
|
|
652
|
-
|
|
653
|
-
|
|
654
|
-
display_text ||= target.to_s.
|
|
653
|
+
display_text = if next_sib&.element? && next_sib.name == "semx"
|
|
654
|
+
fmt_link = next_sib.at_css("fmt-link")
|
|
655
|
+
if fmt_link
|
|
656
|
+
fmt_target = fmt_link["target"] || fmt_link["href"] || target
|
|
657
|
+
display_text = fmt_target.to_s.delete_prefix("mailto:")
|
|
658
|
+
next_sib.remove
|
|
659
|
+
display_text
|
|
660
|
+
end
|
|
661
|
+
end
|
|
662
|
+
|
|
663
|
+
display_text ||= target.to_s.delete_prefix("mailto:")
|
|
655
664
|
a_tag = Nokogiri::HTML::DocumentFragment.parse(
|
|
656
|
-
"<a href=\"#{CGI.escapeHTML(target.to_s)}\">#{CGI.escapeHTML(display_text)}</a>"
|
|
665
|
+
"<a href=\"#{CGI.escapeHTML(target.to_s)}\">#{CGI.escapeHTML(display_text)}</a>",
|
|
657
666
|
)
|
|
658
667
|
link.replace(a_tag)
|
|
659
668
|
end
|
|
@@ -686,15 +695,20 @@ module Metanorma
|
|
|
686
695
|
%i[terms definitions].each do |attr|
|
|
687
696
|
val = safe_attr(section, attr)
|
|
688
697
|
next if val.nil?
|
|
698
|
+
|
|
689
699
|
Array(val).each do |v|
|
|
690
700
|
children << v unless children.include?(v)
|
|
691
701
|
end
|
|
692
702
|
end
|
|
693
703
|
|
|
694
704
|
# Sort by displayorder (non-nil first, then nil at end)
|
|
695
|
-
children.
|
|
705
|
+
children.compact!
|
|
696
706
|
children.sort_by do |node|
|
|
697
|
-
order =
|
|
707
|
+
order = begin
|
|
708
|
+
node.displayorder
|
|
709
|
+
rescue StandardError
|
|
710
|
+
nil
|
|
711
|
+
end
|
|
698
712
|
order &&= order.to_i
|
|
699
713
|
order || Float::INFINITY
|
|
700
714
|
end
|
|
@@ -710,46 +724,49 @@ module Metanorma
|
|
|
710
724
|
end
|
|
711
725
|
end
|
|
712
726
|
|
|
713
|
-
private
|
|
714
|
-
|
|
715
|
-
# Filter document title paragraphs that are rendered by render_doc_title
|
|
716
|
-
def is_doc_title_paragraph?(node)
|
|
717
|
-
return false unless node.respond_to?(:class_attr)
|
|
718
|
-
["zzSTDTitle1", "zzSTDTitle2"].include?(node.class_attr)
|
|
719
|
-
end
|
|
720
|
-
|
|
721
727
|
# Collect all document-level children (sections, normative refs, annexes,
|
|
722
728
|
# bibliography) sorted by displayorder for correct document order.
|
|
729
|
+
# Top-level paragraphs in sections (title paragraphs) are excluded —
|
|
730
|
+
# they are rendered separately by render_doc_title.
|
|
723
731
|
def collect_document_children(doc)
|
|
724
732
|
items = []
|
|
725
733
|
|
|
726
734
|
# Main sections children (clauses, terms, etc.)
|
|
727
735
|
if doc.sections
|
|
728
|
-
|
|
736
|
+
section_children = gather_element_order_children(doc.sections)
|
|
737
|
+
# Title paragraphs are ParagraphBlock objects at the top level of
|
|
738
|
+
# sections. They are rendered by render_doc_title, so skip them here.
|
|
739
|
+
section_children.reject! do |node|
|
|
740
|
+
node.is_a?(Metanorma::Document::Components::Paragraphs::ParagraphBlock)
|
|
741
|
+
end
|
|
742
|
+
items.concat(section_children)
|
|
729
743
|
# Also add typed attributes that may not be in element_order
|
|
730
744
|
%i[terms definitions].each do |attr|
|
|
731
745
|
val = safe_attr(doc.sections, attr)
|
|
732
746
|
next if val.nil?
|
|
747
|
+
|
|
733
748
|
Array(val).each { |v| items << v unless items.include?(v) }
|
|
734
749
|
end
|
|
735
750
|
end
|
|
736
751
|
|
|
737
752
|
# Normative references from bibliography (may have displayorder)
|
|
738
|
-
|
|
739
|
-
doc.bibliography.references.each { |r| items << r }
|
|
740
|
-
end
|
|
753
|
+
doc.bibliography&.references&.each { |r| items << r }
|
|
741
754
|
|
|
742
755
|
# Annexes
|
|
743
756
|
doc.annex&.each { |a| items << a }
|
|
744
757
|
|
|
745
758
|
# Non-normative bibliography (no displayorder = goes at end)
|
|
746
|
-
if doc.bibliography
|
|
759
|
+
if doc.bibliography&.references
|
|
747
760
|
# Already included above; filter normative vs non-normative below
|
|
748
761
|
end
|
|
749
762
|
|
|
750
763
|
items.compact!
|
|
751
764
|
items.sort_by do |node|
|
|
752
|
-
order =
|
|
765
|
+
order = begin
|
|
766
|
+
node.displayorder
|
|
767
|
+
rescue StandardError
|
|
768
|
+
nil
|
|
769
|
+
end
|
|
753
770
|
order &&= order.to_i
|
|
754
771
|
order || Float::INFINITY
|
|
755
772
|
end
|
|
@@ -797,7 +814,7 @@ module Metanorma
|
|
|
797
814
|
children
|
|
798
815
|
end
|
|
799
816
|
|
|
800
|
-
def publisher_logos_html(
|
|
817
|
+
def publisher_logos_html(_doc)
|
|
801
818
|
publishers = flavor_publishers(extract_primary_doc_id)
|
|
802
819
|
logo_map = publisher_logo_map
|
|
803
820
|
return [] if publishers.empty? && logo_map.empty?
|
|
@@ -811,8 +828,8 @@ module Metanorma
|
|
|
811
828
|
next unless svg
|
|
812
829
|
|
|
813
830
|
# White fill for dark cover background
|
|
814
|
-
svg = svg.gsub(
|
|
815
|
-
svg = svg.gsub(
|
|
831
|
+
svg = svg.gsub("fill:#00b1ff", "fill:white") if pub == "OGC"
|
|
832
|
+
svg = svg.gsub("fill:#e3000f", "fill:white") if pub == "ISO"
|
|
816
833
|
svg
|
|
817
834
|
end
|
|
818
835
|
end
|
|
@@ -46,7 +46,7 @@ module Metanorma
|
|
|
46
46
|
t.example_bg = "#e8f4fa"
|
|
47
47
|
t.example_color = "#004d73"
|
|
48
48
|
t.admonition_border = "#e8812e"
|
|
49
|
-
t.admonition_bg
|
|
49
|
+
t.admonition_bg = "#fff5eb"
|
|
50
50
|
t.admonition_color = "#c06a1a"
|
|
51
51
|
t.footer_border_color = "#00b1ff"
|
|
52
52
|
t.cover_separator_color = "rgba(0,177,255,0.25)"
|
|
@@ -69,13 +69,13 @@ module Metanorma
|
|
|
69
69
|
preface_clauses = preface.clause&.reject { |cl| cl.type == "toc" } || []
|
|
70
70
|
|
|
71
71
|
return if preface_clauses.empty? &&
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
72
|
+
!preface.foreword && !preface.introduction &&
|
|
73
|
+
!preface.abstract && !preface.acknowledgements &&
|
|
74
|
+
!preface.executivesummary
|
|
75
75
|
|
|
76
76
|
@output << "<div id=\"preface\" class=\"preface-section\">"
|
|
77
77
|
register_toc_entry(id: "preface", level: 1, text: "Preface")
|
|
78
|
-
@output << "<h1 class=\"
|
|
78
|
+
@output << "<h1 class=\"foreword-title\">Preface</h1>"
|
|
79
79
|
|
|
80
80
|
preface_clauses.each { |cl| render(cl, level: 2) }
|
|
81
81
|
|
|
@@ -5,34 +5,34 @@ module Metanorma
|
|
|
5
5
|
# Renders StandardDocument components to HTML.
|
|
6
6
|
# Extends BaseRenderer with terms, bibliography, and standard sections.
|
|
7
7
|
class StandardRenderer < BaseRenderer
|
|
8
|
-
def render(node, **
|
|
8
|
+
def render(node, **)
|
|
9
9
|
case node
|
|
10
10
|
when Metanorma::StandardDocument::Root
|
|
11
|
-
render_standard_document(node, **
|
|
11
|
+
render_standard_document(node, **)
|
|
12
12
|
when Metanorma::StandardDocument::Terms::Term
|
|
13
|
-
render_term(node, **
|
|
13
|
+
render_term(node, **)
|
|
14
14
|
when Metanorma::StandardDocument::Sections::TermsSection
|
|
15
|
-
render_terms_section(node, **
|
|
15
|
+
render_terms_section(node, **)
|
|
16
16
|
when Metanorma::StandardDocument::Sections::StandardReferencesSection
|
|
17
|
-
render_references_section(node, **
|
|
17
|
+
render_references_section(node, **)
|
|
18
18
|
when Metanorma::StandardDocument::Sections::BibliographySection
|
|
19
|
-
render_bibliography(node, **
|
|
19
|
+
render_bibliography(node, **)
|
|
20
20
|
when Metanorma::StandardDocument::Sections::ClauseSection
|
|
21
|
-
render_clause_section(node, **
|
|
21
|
+
render_clause_section(node, **)
|
|
22
22
|
when Metanorma::StandardDocument::Sections::AnnexSection
|
|
23
|
-
render_annex_section(node, **
|
|
23
|
+
render_annex_section(node, **)
|
|
24
24
|
when Metanorma::StandardDocument::Sections::StandardSection
|
|
25
|
-
render_standard_section(node, **
|
|
25
|
+
render_standard_section(node, **)
|
|
26
26
|
when Metanorma::StandardDocument::Sections::Abstract
|
|
27
|
-
render_abstract_section(node, **
|
|
27
|
+
render_abstract_section(node, **)
|
|
28
28
|
when Metanorma::StandardDocument::Sections::Foreword
|
|
29
|
-
render_foreword_section(node, **
|
|
29
|
+
render_foreword_section(node, **)
|
|
30
30
|
when Metanorma::StandardDocument::Sections::Introduction
|
|
31
|
-
render_introduction_section(node, **
|
|
31
|
+
render_introduction_section(node, **)
|
|
32
32
|
when Metanorma::StandardDocument::Sections::FloatingTitle
|
|
33
|
-
render_floating_title(node, **
|
|
33
|
+
render_floating_title(node, **)
|
|
34
34
|
when Metanorma::StandardDocument::Blocks::AmendBlock
|
|
35
|
-
render_amend_block(node, **
|
|
35
|
+
render_amend_block(node, **)
|
|
36
36
|
else
|
|
37
37
|
super
|
|
38
38
|
end
|
|
@@ -86,8 +86,10 @@ module Metanorma
|
|
|
86
86
|
cover_id = nil
|
|
87
87
|
bibdata.doc_identifier&.each do |di|
|
|
88
88
|
next unless safe_attr(di, :type) == "iso-reference"
|
|
89
|
+
|
|
89
90
|
id = extract_text_value(di)
|
|
90
91
|
next if id.to_s.empty?
|
|
92
|
+
|
|
91
93
|
cover_id = id
|
|
92
94
|
break
|
|
93
95
|
end
|
|
@@ -105,9 +107,9 @@ module Metanorma
|
|
|
105
107
|
end
|
|
106
108
|
|
|
107
109
|
@output << render_liquid("_cover.html.liquid", {
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
110
|
+
"doc_id" => cover_id,
|
|
111
|
+
"title" => title_text,
|
|
112
|
+
})
|
|
111
113
|
end
|
|
112
114
|
|
|
113
115
|
def render_doc_title(doc)
|
|
@@ -120,22 +122,24 @@ module Metanorma
|
|
|
120
122
|
elsif bibdata.is_a?(Metanorma::Document::Components::BibData::BibData)
|
|
121
123
|
titles = bibdata.title
|
|
122
124
|
return unless titles && !titles.empty?
|
|
125
|
+
|
|
123
126
|
en_title = titles.find { |t| t.language == "en" }
|
|
124
127
|
return unless en_title
|
|
128
|
+
|
|
125
129
|
en_title = extract_text_value(en_title)
|
|
126
130
|
else
|
|
127
131
|
return
|
|
128
132
|
end
|
|
129
133
|
|
|
130
134
|
@output << render_liquid("_doc_title.html.liquid", {
|
|
131
|
-
|
|
132
|
-
|
|
135
|
+
"title" => en_title,
|
|
136
|
+
})
|
|
133
137
|
end
|
|
134
138
|
|
|
135
139
|
# --- Section rendering ---
|
|
136
140
|
|
|
137
141
|
def render_clause_section(clause, level: 1, **_opts)
|
|
138
|
-
attrs = element_attrs(id: safe_attr(clause, :id)
|
|
142
|
+
attrs = element_attrs(id: safe_attr(clause, :id))
|
|
139
143
|
tag("div", attrs) do
|
|
140
144
|
render_standard_title(clause, level)
|
|
141
145
|
render_standard_section_blocks(clause, level)
|
|
@@ -324,11 +328,11 @@ module Metanorma
|
|
|
324
328
|
bibitemid = safe_attr(origin, :bibitemid)
|
|
325
329
|
|
|
326
330
|
if citeas && !citeas.to_s.empty?
|
|
327
|
-
if bibitemid && !bibitemid.to_s.empty?
|
|
328
|
-
|
|
329
|
-
|
|
330
|
-
|
|
331
|
-
|
|
331
|
+
@output << if bibitemid && !bibitemid.to_s.empty?
|
|
332
|
+
"<a href=\"##{escape_html(bibitemid.to_s)}\" class=\"bibref\">#{escape_html(citeas.to_s)}</a>"
|
|
333
|
+
else
|
|
334
|
+
escape_html(citeas.to_s)
|
|
335
|
+
end
|
|
332
336
|
else
|
|
333
337
|
render_mixed_inline(origin)
|
|
334
338
|
end
|
|
@@ -401,9 +405,11 @@ module Metanorma
|
|
|
401
405
|
def bibitem_url(item)
|
|
402
406
|
links = Array(item.link)
|
|
403
407
|
return nil if links.empty?
|
|
408
|
+
|
|
404
409
|
# Prefer src or citation type, skip RSS feeds
|
|
405
|
-
preferred = links.find { |l|
|
|
410
|
+
preferred = links.find { |l| ["src", "citation"].include?(l.type) }
|
|
406
411
|
return preferred.content.to_s if preferred && !preferred.content.to_s.empty?
|
|
412
|
+
|
|
407
413
|
# Fallback: first non-RSS link
|
|
408
414
|
non_rss = links.find { |l| !l.content.to_s.include?(".rss") && !l.content.to_s.empty? }
|
|
409
415
|
non_rss&.content&.to_s
|
|
@@ -421,10 +427,10 @@ module Metanorma
|
|
|
421
427
|
docids = Array(item.docidentifier)
|
|
422
428
|
# Skip bracket-number identifiers (e.g. "[1]") and iso-reference/URN variants;
|
|
423
429
|
# render only the primary doc identifier
|
|
424
|
-
primary = docids.find
|
|
430
|
+
primary = docids.find do |di|
|
|
425
431
|
val = extract_text_value(di).to_s
|
|
426
432
|
val.match?(/\A\[?\d+\]?\z/) ? false : !val.match?(/\A(?:iso-reference|URN)\s/)
|
|
427
|
-
|
|
433
|
+
end
|
|
428
434
|
if primary
|
|
429
435
|
id_val = extract_text_value(primary)
|
|
430
436
|
@output << "<span class=\"std-doc-number\">#{escape_html(id_val)}</span>" unless id_val.to_s.empty?
|
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
<div{% if block.id %} id="{{ block.id }}"{% endif %} class="{{ block.css_class }}">
|
|
2
|
+
{{ block.stem_html }}
|
|
3
|
+
{% if block.where_html %}<p class="formula-where">where</p>{% endif %}
|
|
4
|
+
{{ block.where_html }}
|
|
5
|
+
{% if block.number_html %}<span class="formula-number">{{ block.number_html }}</span>{% endif %}
|
|
6
|
+
</div>
|
|
@@ -1,3 +1,3 @@
|
|
|
1
|
-
<p class="
|
|
2
|
-
<span class="
|
|
1
|
+
<p class="doc-title">
|
|
2
|
+
<span class="title-text">{{ title | escape }}</span>
|
|
3
3
|
</p>
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
<div{% if block.id %} id="{{ block.id }}"{% endif %} class="{{ block.css_class }}">
|
|
2
|
+
{% if block.name_html %}<p class="code-name">{{ block.name_html }}</p>{% endif %}
|
|
3
|
+
<pre><code{% if block.lang %} lang="{{ block.lang }}"{% endif %}>{{ block.code_html }}</code></pre>
|
|
4
|
+
</div>
|