datalog-theme 0.8.0 → 0.9.0

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.
Files changed (111) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +63 -0
  3. data/CITATION.cff +2 -2
  4. data/README.md +4 -2
  5. data/_data/i18n/en.yml +297 -0
  6. data/_data/i18n/es.yml +297 -0
  7. data/_data/i18n/pt.yml +297 -0
  8. data/_data/js_manifest.json +16 -0
  9. data/_includes/components/author-bio.html +21 -11
  10. data/_includes/components/author-list.html +32 -0
  11. data/_includes/components/citation-tools.html +33 -25
  12. data/_includes/components/comments-thread.html +90 -0
  13. data/_includes/components/contact-form.html +120 -0
  14. data/_includes/components/correction-report.html +82 -0
  15. data/_includes/components/enhanced-toc.html +6 -7
  16. data/_includes/components/license-link.html +13 -0
  17. data/_includes/components/license-notice.html +28 -0
  18. data/_includes/components/moderation-inbox.html +139 -0
  19. data/_includes/components/reactions.html +49 -0
  20. data/_includes/components/reading-list.html +31 -0
  21. data/_includes/components/reading-mode-toggle.html +65 -0
  22. data/_includes/components/reading-state-bookmark.html +27 -0
  23. data/_includes/components/reading-state-panel.html +71 -0
  24. data/_includes/components/reproducibility.html +61 -0
  25. data/_includes/components/responsive-image.html +3 -3
  26. data/_includes/components/revision-history.html +39 -0
  27. data/_includes/components/revision-notice.html +35 -0
  28. data/_includes/components/series-nav.html +64 -0
  29. data/_includes/components/subscribe-form.html +88 -0
  30. data/_includes/components/subscription-manage.html +68 -0
  31. data/_includes/components/webmentions.html +48 -0
  32. data/_includes/csp-meta.html +21 -1
  33. data/_includes/footer.html +3 -0
  34. data/_includes/head.html +51 -40
  35. data/_includes/layouts/default/article.html +4 -6
  36. data/_includes/meta/dynamic-services-config.html +14 -0
  37. data/_includes/meta/math-config.html +9 -5
  38. data/_includes/meta/person-json.html +27 -0
  39. data/_includes/meta/publisher.html +45 -0
  40. data/_includes/meta/schema.html +62 -28
  41. data/_includes/meta/scholarly.html +121 -0
  42. data/_includes/meta/scripts-loader.html +2 -0
  43. data/_includes/meta/webmention-discovery.html +14 -0
  44. data/_includes/scripts.html +57 -0
  45. data/_layouts/dataset.html +4 -3
  46. data/_layouts/default.html +1 -1
  47. data/_layouts/package.html +3 -2
  48. data/_layouts/page.html +15 -0
  49. data/_layouts/post.html +82 -18
  50. data/_layouts/project.html +2 -2
  51. data/_layouts/research.html +20 -8
  52. data/_plugins/authors.rb +133 -0
  53. data/_plugins/config_validator.rb +223 -20
  54. data/_plugins/critical_css_check.rb +42 -0
  55. data/_plugins/i18n.rb +6 -4
  56. data/_plugins/image_optimizer.rb +224 -172
  57. data/_plugins/licenses.rb +135 -0
  58. data/_plugins/math_preprocessor.rb +32 -10
  59. data/_plugins/references.rb +238 -0
  60. data/_plugins/reproducibility.rb +150 -0
  61. data/_plugins/revisions.rb +101 -0
  62. data/_plugins/scholarly.rb +50 -0
  63. data/_plugins/series.rb +104 -0
  64. data/_plugins/statements.rb +87 -0
  65. data/_sass/_base.scss +8 -1
  66. data/_sass/_comments-thread.scss +159 -0
  67. data/_sass/_layout.scss +384 -0
  68. data/_sass/_mathematical.scss +27 -0
  69. data/_sass/_moderation.scss +222 -0
  70. data/_sass/_post-components.scss +4 -2
  71. data/_sass/_print.scss +291 -0
  72. data/_sass/_reactions.scss +89 -0
  73. data/_sass/_reading-state.scss +290 -0
  74. data/_sass/_service-forms.scss +204 -0
  75. data/_sass/_subscriptions.scss +140 -0
  76. data/_sass/_syntax-highlighting.scss +2 -2
  77. data/_sass/_theme.scss +11 -0
  78. data/_sass/_typography.scss +116 -0
  79. data/_sass/_utilities.scss +5 -0
  80. data/_sass/_variables.scss +6 -0
  81. data/_sass/_webmentions.scss +125 -0
  82. data/assets/js/dist/academic.js +1 -1
  83. data/assets/js/dist/analytics-dashboard.js +1 -1
  84. data/assets/js/dist/chunks/chunk-2DYDWUFX.js +1 -0
  85. data/assets/js/dist/chunks/chunk-PATLC23F.js +1 -0
  86. data/assets/js/dist/chunks/chunk-V7734B2G.js +1 -0
  87. data/assets/js/dist/comments.js +2 -0
  88. data/assets/js/dist/contact.js +1 -0
  89. data/assets/js/dist/core.js +1 -1
  90. data/assets/js/dist/corrections.js +1 -0
  91. data/assets/js/dist/loader.js +1 -1
  92. data/assets/js/dist/math.js +1 -1
  93. data/assets/js/dist/moderation.js +1 -0
  94. data/assets/js/dist/notebook.js +1 -1
  95. data/assets/js/dist/reactions.js +1 -0
  96. data/assets/js/dist/reading-state.js +1 -0
  97. data/assets/js/dist/search.js +1 -1
  98. data/assets/js/dist/sources.json +52 -0
  99. data/assets/js/dist/subscriptions.js +1 -0
  100. data/assets/js/dist/webmentions.js +1 -0
  101. data/assets/js/loader.js +34 -0
  102. data/datalog-theme.gemspec +1 -2
  103. data/lib/datalog/cli.rb +9 -1
  104. data/lib/datalog/critical_css.rb +168 -0
  105. data/lib/datalog/plugins/comments.rb +33 -3
  106. data/lib/datalog/theme/installed_files.rb +113 -0
  107. data/lib/datalog/theme/repository_checkout.rb +6 -2
  108. data/lib/datalog/theme/version.rb +5 -1
  109. data/lib/datalog-theme.rb +1 -0
  110. metadata +57 -23
  111. data/assets/js/dist/chunks/chunk-225H5YXE.js +0 -1
@@ -0,0 +1,121 @@
1
+ {%- comment -%}
2
+ ---
3
+ optional: []
4
+ ---
5
+ Scholarly discovery metadata for a page read as a research article: the
6
+ Highwire meta tags Google Scholar and reference managers read, and their
7
+ Dublin Core equivalents. Only a page the `scholarly` filter accepts gets them
8
+ (_plugins/scholarly.rb): a research article, a page with `scholarly: true`,
9
+ or every post when _config.yml sets `scholarly: true`. A field the page
10
+ lacks leaves its tag out. The authors are the page's (page_authors), as in
11
+ the byline, the JSON-LD and the citation exports; `citation_authors` names
12
+ the indexed authors alone.
13
+ {%- endcomment -%}
14
+ {%- assign is_scholarly = page | scholarly -%}
15
+ {%- if is_scholarly and page.title -%}
16
+ {%- include meta/publisher.html -%}
17
+ {%- assign scholarly_title = page.citation_title | default: page.title | strip_html | normalize_whitespace -%}
18
+ {%- assign scholarly_url = page.url | absolute_url -%}
19
+ {%- assign scholarly_authors = page | page_authors -%}
20
+ {%- assign scholarly_names = scholarly_authors | map: 'name' -%}
21
+ {%- assign scholarly_override = false -%}
22
+ {%- if page.citation_authors -%}
23
+ {%- assign scholarly_override = true -%}
24
+ {%- capture citation_source_json -%}{{ page.citation_authors | jsonify }}{%- endcapture -%}
25
+ {%- assign citation_source_first = citation_source_json | slice: 0, 1 -%}
26
+ {%- if citation_source_first == '[' -%}
27
+ {%- assign scholarly_names = page.citation_authors -%}
28
+ {%- else -%}
29
+ {%- assign scholarly_names = page.citation_authors | replace: ';', ',' | split: ',' -%}
30
+ {%- endif -%}
31
+ {%- endif -%}
32
+ {%- assign scholarly_pdf = page.pdf_url | default: page.citation_pdf -%}
33
+ {%- assign scholarly_journal = page.journal | default: page.publication -%}
34
+ {%- assign scholarly_issue = page.issue | default: page.number -%}
35
+ {%- assign scholarly_keywords = page.keywords | default: page.tags -%}
36
+ {%- assign scholarly_publisher = page.publisher | default: publisher_name -%}
37
+ {%- assign scholarly_language = page.lang | default: site.locale | default: 'en' | split: '_' | first | split: '-' | first -%}
38
+ {%- assign scholarly_license = page | page_license -%}
39
+ {%- assign scholarly_description = page.description | default: page.excerpt | strip_html | normalize_whitespace | truncate: 300 -%}
40
+ <meta name="citation_title" content="{{ scholarly_title | escape }}" />
41
+ {%- if scholarly_override %}
42
+ {%- for name in scholarly_names %}
43
+ <meta name="citation_author" content="{{ name | strip | escape }}" />
44
+ {%- endfor %}
45
+ {%- else %}
46
+ {%- for author in scholarly_authors %}
47
+ <meta name="citation_author" content="{{ author.name | strip | escape }}" />
48
+ {%- if author.affiliation %}
49
+ <meta name="citation_author_institution" content="{{ author.affiliation | strip | escape }}" />
50
+ {%- endif %}
51
+ {%- if author.orcid %}
52
+ <meta name="citation_author_orcid" content="{{ author.orcid | escape }}" />
53
+ {%- endif %}
54
+ {%- endfor %}
55
+ {%- endif %}
56
+ {%- if page.date %}
57
+ <meta name="citation_publication_date" content="{{ page.date | date: '%Y/%m/%d' }}" />
58
+ {%- endif %}
59
+ <meta name="citation_public_url" content="{{ scholarly_url }}" />
60
+ <meta name="citation_fulltext_html_url" content="{{ scholarly_url }}" />
61
+ {%- if scholarly_pdf %}
62
+ <meta name="citation_pdf_url" content="{{ scholarly_pdf | absolute_url }}" />
63
+ {%- endif %}
64
+ {%- if page.doi %}
65
+ <meta name="citation_doi" content="{{ page.doi | escape }}" />
66
+ {%- endif %}
67
+ {%- if scholarly_journal %}
68
+ <meta name="citation_journal_title" content="{{ scholarly_journal | escape }}" />
69
+ {%- endif %}
70
+ {%- if page.conference %}
71
+ <meta name="citation_conference_title" content="{{ page.conference | escape }}" />
72
+ {%- endif %}
73
+ {%- if page.volume %}
74
+ <meta name="citation_volume" content="{{ page.volume | escape }}" />
75
+ {%- endif %}
76
+ {%- if scholarly_issue %}
77
+ <meta name="citation_issue" content="{{ scholarly_issue | escape }}" />
78
+ {%- endif %}
79
+ {%- if page.pages %}
80
+ {%- assign page_range = page.pages | append: '' | replace: '–', '-' | replace: '—', '-' | split: '-' %}
81
+ <meta name="citation_firstpage" content="{{ page_range[0] | strip | escape }}" />
82
+ {%- if page_range.size > 1 %}
83
+ <meta name="citation_lastpage" content="{{ page_range[1] | strip | escape }}" />
84
+ {%- endif %}
85
+ {%- endif %}
86
+ {%- if page.issn %}
87
+ <meta name="citation_issn" content="{{ page.issn | escape }}" />
88
+ {%- endif %}
89
+ {%- if page.isbn %}
90
+ <meta name="citation_isbn" content="{{ page.isbn | escape }}" />
91
+ {%- endif %}
92
+ <meta name="citation_publisher" content="{{ scholarly_publisher | escape }}" />
93
+ <meta name="citation_language" content="{{ scholarly_language }}" />
94
+ {%- if scholarly_keywords and scholarly_keywords.size > 0 %}
95
+ <meta name="citation_keywords" content="{{ scholarly_keywords | join: '; ' | escape }}" />
96
+ {%- endif %}
97
+ <link rel="schema.DC" href="http://purl.org/dc/elements/1.1/" />
98
+ <meta name="DC.title" content="{{ scholarly_title | escape }}" />
99
+ {%- for name in scholarly_names %}
100
+ <meta name="DC.creator" content="{{ name | strip | escape }}" />
101
+ {%- endfor %}
102
+ {%- if page.date %}
103
+ <meta name="DC.date" content="{{ page.date | date: '%Y-%m-%d' }}" />
104
+ {%- endif %}
105
+ {%- if page.doi %}
106
+ {%- assign scholarly_identifier = page.doi -%}
107
+ {%- unless scholarly_identifier contains '://' -%}{%- assign scholarly_identifier = 'https://doi.org/' | append: page.doi -%}{%- endunless %}
108
+ <meta name="DC.identifier" content="{{ scholarly_identifier | escape }}" />
109
+ {%- else %}
110
+ <meta name="DC.identifier" content="{{ scholarly_url }}" />
111
+ {%- endif %}
112
+ <meta name="DC.type" content="Text" />
113
+ <meta name="DC.language" content="{{ scholarly_language }}" />
114
+ <meta name="DC.publisher" content="{{ scholarly_publisher | escape }}" />
115
+ {%- if scholarly_license.url %}
116
+ <meta name="DC.rights" content="{{ scholarly_license.url | escape }}" />
117
+ {%- endif %}
118
+ {%- if scholarly_description and scholarly_description != '' %}
119
+ <meta name="DC.description" content="{{ scholarly_description | escape }}" />
120
+ {%- endif %}
121
+ {%- endif -%}
@@ -34,4 +34,6 @@ highlighted by Rouge when the site builds, so the head renders nothing.
34
34
  <script nonce="{{ page.csp_nonce }}">
35
35
  window.DatalogIntegrations = {{ site.integrations | jsonify }};
36
36
  </script>
37
+ {%- comment -%} The dynamic services' public settings, on a site that has a backend. {%- endcomment -%}
38
+ {% include meta/dynamic-services-config.html %}
37
39
  {%- endif -%}
@@ -0,0 +1,14 @@
1
+ {%- comment -%}
2
+ ---
3
+ optional: []
4
+ ---
5
+ Webmention discovery (W3C Webmention, section 3.1.2): the receiver a site
6
+ names in `webmentions.endpoint` is advertised in every page's head, so a
7
+ website that links here can notify it. GitHub Pages cannot send the HTTP
8
+ Link header form, so the <link> form is the one the theme uses. Nothing is
9
+ advertised without an endpoint or with `webmentions.enabled: false`.
10
+ {%- endcomment -%}
11
+ {%- assign webmentions = site.webmentions -%}
12
+ {%- if webmentions.enabled != false and webmentions.endpoint and webmentions.endpoint != '' -%}
13
+ <link rel="webmention" href="{{ webmentions.endpoint }}" />
14
+ {%- endif -%}
@@ -31,6 +31,55 @@
31
31
  {% assign academic_flag = 'false' %}
32
32
  {% endif %}
33
33
 
34
+ {% if site.theme_options.reading_state.enabled == false %}
35
+ {% assign reading_state_flag = 'false' %}
36
+ {% else %}
37
+ {% assign reading_state_flag = 'auto' %}
38
+ {% endif %}
39
+
40
+ {%- comment -%} The correction-report form needs a backend with the feature on (components/correction-report.html). {%- endcomment -%}
41
+ {% assign corrections_flag = 'false' %}
42
+ {% if site.dynamic_services.base_url and site.dynamic_services.base_url != '' and site.dynamic_services.features.corrections != false and site.corrections.enabled != false %}
43
+ {% assign corrections_flag = 'auto' %}
44
+ {% endif %}
45
+
46
+ {%- comment -%} The contact form likewise (components/contact-form.html). {%- endcomment -%}
47
+ {% assign contact_flag = 'false' %}
48
+ {% if site.dynamic_services.base_url and site.dynamic_services.base_url != '' and site.dynamic_services.features.contact != false and site.contact.enabled != false %}
49
+ {% assign contact_flag = 'auto' %}
50
+ {% endif %}
51
+
52
+ {%- comment -%} The comments thread of the api provider (components/comments-thread.html), site-wide or for this page. {%- endcomment -%}
53
+ {% assign comments_flag = 'false' %}
54
+ {% assign comments_options = site.datalog_plugins.options['datalog-comments'] %}
55
+ {% if comments_options.provider == 'api' or page.datalog_comments.provider == 'api' %}
56
+ {% assign comments_flag = 'auto' %}
57
+ {% endif %}
58
+
59
+ {%- comment -%} "Was this useful?" needs a backend with the feature on (components/reactions.html). {%- endcomment -%}
60
+ {% assign reactions_flag = 'false' %}
61
+ {% if site.dynamic_services.base_url and site.dynamic_services.base_url != '' and site.dynamic_services.features.reactions != false and site.reactions.enabled != false %}
62
+ {% assign reactions_flag = 'auto' %}
63
+ {% endif %}
64
+
65
+ {%- comment -%} "Mentioned elsewhere" needs a backend with the feature on (components/webmentions.html). {%- endcomment -%}
66
+ {% assign webmentions_flag = 'false' %}
67
+ {% if site.dynamic_services.base_url and site.dynamic_services.base_url != '' and site.dynamic_services.features.webmentions != false and site.webmentions.enabled != false %}
68
+ {% assign webmentions_flag = 'auto' %}
69
+ {% endif %}
70
+
71
+ {%- comment -%} The newsletter form and its manage page need a backend with the feature on (components/subscribe-form.html). {%- endcomment -%}
72
+ {% assign subscriptions_flag = 'false' %}
73
+ {% if site.dynamic_services.base_url and site.dynamic_services.base_url != '' and site.dynamic_services.features.subscriptions != false and site.subscriptions.enabled != false %}
74
+ {% assign subscriptions_flag = 'auto' %}
75
+ {% endif %}
76
+
77
+ {%- comment -%} The moderation inbox is off unless the site turns it on (components/moderation-inbox.html). {%- endcomment -%}
78
+ {% assign moderation_flag = 'false' %}
79
+ {% if site.moderation.enabled == true %}
80
+ {% assign moderation_flag = 'auto' %}
81
+ {% endif %}
82
+
34
83
  <script nonce="{{ page.csp_nonce }}">
35
84
  (function () {
36
85
  const body = document.body;
@@ -42,6 +91,14 @@
42
91
  body.dataset.featureMath = "{{ math_flag }}";
43
92
  body.dataset.featureNotebook = "{{ notebook_flag }}";
44
93
  body.dataset.featureAcademic = "{{ academic_flag }}";
94
+ body.dataset.featureReadingState = "{{ reading_state_flag }}";
95
+ body.dataset.featureCorrections = "{{ corrections_flag }}";
96
+ body.dataset.featureContact = "{{ contact_flag }}";
97
+ body.dataset.featureComments = "{{ comments_flag }}";
98
+ body.dataset.featureReactions = "{{ reactions_flag }}";
99
+ body.dataset.featureWebmentions = "{{ webmentions_flag }}";
100
+ body.dataset.featureSubscriptions = "{{ subscriptions_flag }}";
101
+ body.dataset.featureModeration = "{{ moderation_flag }}";
45
102
  })();
46
103
  </script>
47
104
 
@@ -8,7 +8,8 @@ show_title: false # this layout renders the page's <h1>
8
8
  <header class="dataset-header">
9
9
  <h1>{{ page.title }}</h1>
10
10
  {% if page.updated %}<p class="dataset-meta"><strong>{% t 'dataset.last_updated' %}</strong> {{ page.updated | localize_date: date_format }}</p>{% endif %}
11
- {% if page.license %}<p class="dataset-meta"><strong>{% t 'dataset.license' %}</strong> {{ page.license }}</p>{% endif %}
11
+ {% assign dataset_license = page | page_license %}
12
+ {% if dataset_license %}<p class="dataset-meta"><strong>{% t 'dataset.license' %}</strong> {% include components/license-link.html license=dataset_license %}</p>{% endif %}
12
13
  </header>
13
14
  <div class="dataset-summary">
14
15
  {{ page.summary | default: page.excerpt }}
@@ -45,9 +46,9 @@ show_title: false # this layout renders the page's <h1>
45
46
  </section>
46
47
  {% endif %}
47
48
  {% assign citation_key = page.citation_key | default: page.slug | default: page.title | slugify %}
48
- {% assign citation_authors = page.authors | default: page.author | default: site.author.name %}
49
+ {% assign citation_authors = page | page_authors %}
49
50
  {% assign citation_date = page.date | default: page.updated %}
50
51
  {% assign citation_url = page.url | absolute_url %}
51
- {% include components/citation-tools.html title=page.title authors=citation_authors date=citation_date url=citation_url citation_key=citation_key publisher=site.author.affiliation citation_type='dataset' doi=page.doi %}
52
+ {% include components/citation-tools.html title=page.title authors=citation_authors date=citation_date url=citation_url citation_key=citation_key citation_type='dataset' doi=page.doi %}
52
53
  {% include components/open-science-badges.html %}
53
54
  </article>
@@ -34,7 +34,7 @@
34
34
  {% include components/math-fallback.html expressions=page.math_expressions %}
35
35
  {% include layouts/default/article.html page=page content=content date_format=date_format %}
36
36
  </main>
37
- {% include_cached footer.html %}
37
+ {% include_cached footer.html lang=page.lang %}
38
38
  <div class="visually-hidden" aria-live="polite" id="{{ math_status_id }}">{% t 'global.math_loading' %}</div>
39
39
  {% include meta/scripts-loader.html location='body' %}
40
40
  </body>
@@ -224,13 +224,14 @@ show_title: false # this layout renders the page's <h1>
224
224
  observer.observe(heading);
225
225
  });
226
226
 
227
- // Smooth scroll for anchor links
227
+ // Scroll to anchor targets. The stylesheet's scroll-behavior decides whether
228
+ // the scroll is smooth, so reduced-motion preferences are respected.
228
229
  document.querySelectorAll('.package-nav__link[href^="#"]').forEach(link => {
229
230
  link.addEventListener('click', (e) => {
230
231
  e.preventDefault();
231
232
  const target = document.querySelector(link.getAttribute('href'));
232
233
  if (target) {
233
- target.scrollIntoView({ behavior: 'smooth', block: 'start' });
234
+ target.scrollIntoView({ block: 'start' });
234
235
  history.pushState(null, null, link.getAttribute('href'));
235
236
  }
236
237
  });
data/_layouts/page.html CHANGED
@@ -11,6 +11,21 @@ layout: default
11
11
  {% endif %}
12
12
  <div class="page-content">
13
13
  {{ content }}
14
+ {%- if page.contact_form %}
15
+ {%- comment -%} The contact and collaboration form, or the email address without a backend {%- endcomment %}
16
+ {% include components/contact-form.html %}
17
+ {%- endif %}
18
+ {%- if page.subscription_manage %}
19
+ {%- comment -%} Where the newsletter's emails lead: confirm, change topics, unsubscribe {%- endcomment %}
20
+ {% include components/subscription-manage.html %}
21
+ {%- endif %}
22
+ {%- if page.subscribe_form %}
23
+ {% include components/subscribe-form.html where='page' %}
24
+ {%- endif %}
25
+ {%- if page.moderation_inbox %}
26
+ {%- comment -%} The moderation inbox: a shell; the service authenticates every request {%- endcomment %}
27
+ {% include components/moderation-inbox.html %}
28
+ {%- endif %}
14
29
  </div>
15
30
  </div>
16
31
  </section>
data/_layouts/post.html CHANGED
@@ -34,8 +34,8 @@ schema_type: TechnicalArticle
34
34
 
35
35
  {%- comment -%} Canonical URL & author info {%- endcomment -%}
36
36
  {% assign canonical_url = page.url | absolute_url %}
37
- {% assign author_name = page.author | default: site.author.name %}
38
- {% assign author_affiliation = page.author_affiliation | default: site.author.affiliation %}
37
+ {% assign authors = page | page_authors %}
38
+ {% assign contributors = page | page_contributors %}
39
39
 
40
40
  {%- comment -%} Tag/Category flags {%- endcomment -%}
41
41
  {% assign post_tags = page.tags %}
@@ -56,8 +56,8 @@ schema_type: TechnicalArticle
56
56
  {% if page.last_modified_at or page.updated %}
57
57
  <meta itemprop="dateModified" content="{{ page.last_modified_at | default: page.updated | date_to_xmlschema }}" />
58
58
  {% endif %}
59
- <meta itemprop="author" content="{{ author_name }}" />
60
- <meta itemprop="publisher" content="{{ site.author.affiliation | default: site.title }}" />
59
+ {% include meta/publisher.html %}
60
+ <meta itemprop="publisher" content="{{ publisher_name | escape }}" />
61
61
  <meta itemprop="timeRequired" content="{{ time_required }}" />
62
62
  {% if difficulty %}<meta itemprop="learningResourceType" content="{{ difficulty }}" />{% endif %}
63
63
  {% if has_tags %}<meta itemprop="keywords" content="{{ post_tags | join: ', ' }}" />{% endif %}
@@ -69,17 +69,28 @@ schema_type: TechnicalArticle
69
69
  <dt class="post-meta-term">{% t 'post.meta.published' %}</dt>
70
70
  <dd class="post-meta-definition">{{ page.date | localize_date: date_format }}</dd>
71
71
  </div>
72
+ {%- comment -%} The last change, when it fell on another day than the publication {%- endcomment -%}
73
+ {% assign modified = page.last_modified_at | default: page.updated %}
74
+ {% if modified %}
75
+ {% assign modified_day = modified | date: '%F' %}
76
+ {% assign published_day = page.date | date: '%F' %}
77
+ {% if modified_day != published_day %}
78
+ <div>
79
+ <dt class="post-meta-term">{% t 'post.meta.updated' %}</dt>
80
+ <dd class="post-meta-definition">{{ modified | localize_date: date_format }}</dd>
81
+ </div>
82
+ {% endif %}
83
+ {% endif %}
72
84
  <div>
73
- <dt class="post-meta-term">{% t 'post.meta.author' %}</dt>
74
- <dd class="post-meta-definition">
75
- <span itemprop="author" itemscope itemtype="https://schema.org/Person">
76
- <span itemprop="name">{{ author_name }}</span>
77
- {% if author_affiliation %}
78
- <span class="post-author-affiliation" itemprop="affiliation">{{ author_affiliation }}</span>
79
- {% endif %}
80
- </span>
81
- </dd>
85
+ <dt class="post-meta-term">{% if authors.size > 1 %}{% t 'post.meta.authors' %}{% else %}{% t 'post.meta.author' %}{% endif %}</dt>
86
+ <dd class="post-meta-definition">{% include components/author-list.html people=authors %}</dd>
82
87
  </div>
88
+ {% if contributors.size > 0 %}
89
+ <div>
90
+ <dt class="post-meta-term">{% t 'post.meta.contributors' %}</dt>
91
+ <dd class="post-meta-definition">{% include components/author-list.html people=contributors property='contributor' %}</dd>
92
+ </div>
93
+ {% endif %}
83
94
  <div>
84
95
  <dt class="post-meta-term">{% t 'post.meta.reading_time' %}</dt>
85
96
  <dd class="post-meta-definition"><span data-reading-time>{{ reading_label }}</span></dd>
@@ -111,6 +122,16 @@ schema_type: TechnicalArticle
111
122
  </dl>
112
123
  </section>
113
124
 
125
+ {%- comment -%} The reader's tools: save for later and reading mode; and the article's address on paper {%- endcomment -%}
126
+ <div class="post-tools">
127
+ {% include components/reading-state-bookmark.html %}
128
+ {% include components/reading-mode-toggle.html %}
129
+ </div>
130
+ <p class="post-print-source print-only">{% t 'post.print.source' %} {{ canonical_url }}{% if page.doi %} · DOI {{ page.doi | escape }}{% endif %}</p>
131
+
132
+ {%- comment -%} The newest correction or update, with a link to the revision history {%- endcomment -%}
133
+ {% include components/revision-notice.html page=page date_format=date_format %}
134
+
114
135
  {% if has_tags or has_categories %}
115
136
  <section class="post-taxonomy" aria-labelledby="post-taxonomy-heading">
116
137
  <h2 id="post-taxonomy-heading" class="visually-hidden">{% t 'post.topics_heading' %}</h2>
@@ -134,6 +155,9 @@ schema_type: TechnicalArticle
134
155
  {%- comment -%} Editorial provenance (why_this_exists, evidence, methodology, reviewed_at) {%- endcomment -%}
135
156
  {% include components/content-provenance.html page=page date_format=date_format %}
136
157
 
158
+ {%- comment -%} The article's series: every part in order, and the previous and next ones {%- endcomment -%}
159
+ {% include components/series-nav.html page=page %}
160
+
137
161
  {%- comment -%} Enhanced social sharing {%- endcomment -%}
138
162
  {% include components/social-share.html url=canonical_url title=page.title description=page.excerpt %}
139
163
 
@@ -148,6 +172,24 @@ schema_type: TechnicalArticle
148
172
  </div>
149
173
  </div>
150
174
 
175
+ {%- comment -%} The previous and next parts of the series, for a reader who has finished this one {%- endcomment -%}
176
+ {% include components/series-nav.html page=page compact=true %}
177
+
178
+ {%- comment -%} Was this useful? A reaction without a comment, on a site with a backend {%- endcomment -%}
179
+ {% include components/reactions.html %}
180
+
181
+ {%- comment -%} The reader's own: resume prompt, highlights and notes, kept in the browser {%- endcomment -%}
182
+ {% include components/reading-state-panel.html %}
183
+
184
+ {%- comment -%} The code, data and environment behind the analysis {%- endcomment -%}
185
+ {% include components/reproducibility.html page=page %}
186
+
187
+ {%- comment -%} Report an error: structured feedback to the author, on a site with a backend {%- endcomment -%}
188
+ {% include components/correction-report.html %}
189
+
190
+ {%- comment -%} What changed since publication (revisions in front matter) {%- endcomment -%}
191
+ {% include components/revision-history.html page=page date_format=date_format %}
192
+
151
193
  <section class="post-interactive" aria-label="{% t 'post.interactive.label' %}">
152
194
  {% if page.interactive_components and page.interactive_components.size > 0 %}
153
195
  <ul class="post-interactive-list">
@@ -195,22 +237,44 @@ schema_type: TechnicalArticle
195
237
  </section>
196
238
  {% endif %}
197
239
 
240
+ {%- comment -%} What other websites said about this article, apart from the comments hosted here {%- endcomment -%}
241
+ {% include components/webmentions.html %}
242
+
243
+ {%- comment -%} Reuse terms: the licence of the text and figures, and of the code samples {%- endcomment -%}
244
+ {% include components/license-notice.html page=page %}
245
+
198
246
  {%- comment -%} ===== Citation tools & badges ===== {%- endcomment -%}
199
247
  {% assign citation_key = page.citation_key | default: page.slug | default: page.title | slugify %}
200
- {% assign citation_authors = page.authors | default: page.author | default: author_name %}
201
248
  {% include components/citation-tools.html
202
249
  title=page.title
203
- authors=citation_authors
250
+ authors=authors
204
251
  date=page.date
205
252
  url=canonical_url
206
253
  citation_key=citation_key
207
- publisher=site.author.affiliation
208
254
  citation_type='article'
209
255
  doi=page.doi %}
210
256
  {% include components/open-science-badges.html %}
211
257
 
212
- {%- comment -%} Author bio card {%- endcomment -%}
213
- {% include components/author-bio.html author=author_name %}
258
+ {%- comment -%}
259
+ Author cards: a full card for a single author, or for each author with
260
+ `author_cards: detailed`; a compact card each for several authors;
261
+ none with `author_cards: false`.
262
+ {%- endcomment -%}
263
+ {% unless page.author_cards == false %}
264
+ {% assign detailed_cards = false %}
265
+ {% if authors.size == 1 or page.author_cards == 'detailed' %}{% assign detailed_cards = true %}{% endif %}
266
+ {% for author in authors %}
267
+ {% if detailed_cards %}
268
+ {% include components/author-bio.html person=author %}
269
+ {% else %}
270
+ {% include components/author-bio.html person=author compact=true %}
271
+ {% endif %}
272
+ {% endfor %}
273
+ {% endunless %}
274
+
275
+ {%- comment -%} The newsletter form at the end of the article, when subscriptions.placement says so {%- endcomment -%}
276
+ {% assign subscribe_placement = site.subscriptions.placement | default: 'footer' %}
277
+ {% if subscribe_placement contains 'post' %}{% include components/subscribe-form.html where='post' %}{% endif %}
214
278
 
215
279
  {%- comment -%} ===== Robust related posts (no where_exp, no nil sort) ===== {%- endcomment -%}
216
280
  {% include post/related-posts.html page=page date_format=date_format %}
@@ -209,10 +209,10 @@ show_title: false # this layout renders the page's <h1>
209
209
  {% endif %}
210
210
 
211
211
  {% assign citation_key = page.citation_key | default: page.slug | default: page.title | slugify %}
212
- {% assign citation_authors = page.authors | default: page.author | default: site.author.name %}
212
+ {% assign citation_authors = page | page_authors %}
213
213
  {% assign citation_date = page.date | default: page.last_updated %}
214
214
  {% assign citation_url = page.url | absolute_url %}
215
- {% include components/citation-tools.html title=page.title authors=citation_authors date=citation_date url=citation_url citation_key=citation_key publisher=site.author.affiliation citation_type='software' doi=page.doi %}
215
+ {% include components/citation-tools.html title=page.title authors=citation_authors date=citation_date url=citation_url citation_key=citation_key citation_type='software' doi=page.doi %}
216
216
 
217
217
  {% include components/open-science-badges.html %}
218
218
 
@@ -3,8 +3,7 @@ layout: default
3
3
  schema_type: ScholarlyArticle
4
4
  ---
5
5
  {% assign date_format = site.date_format | default: '%B %-d, %Y' %}
6
- {% assign authors_source = page.authors | default: page.author | default: site.author %}
7
- {% assign authors = authors_source | arrayify %}
6
+ {% assign authors = page | page_authors %}
8
7
  {% assign publication_name = page.publication | default: page.journal | default: page.conference %}
9
8
  {% assign publication_status = page.publication_status | default: page.status %}
10
9
  {% assign doi = page.doi %}
@@ -20,7 +19,13 @@ schema_type: ScholarlyArticle
20
19
  {% assign methodology_content = page.methodology %}
21
20
  {% assign results_content = page.results %}
22
21
  {% assign data_availability = page.data_availability %}
23
- {% assign reproducibility = page.reproducibility | default: page.reproducibility_notes %}
22
+ {%- comment -%} `reproducibility` is free text here, or a map of artifacts for the panel (components/reproducibility.html). {%- endcomment -%}
23
+ {% capture reproducibility_shape %}{{ page.reproducibility | jsonify | slice: 0, 1 }}{% endcapture %}
24
+ {% if reproducibility_shape == '{' %}
25
+ {% assign reproducibility = page.reproducibility_notes %}
26
+ {% else %}
27
+ {% assign reproducibility = page.reproducibility | default: page.reproducibility_notes %}
28
+ {% endif %}
24
29
  {% assign peer_review = page.peer_review | default: page.peer_review_notes %}
25
30
  {% assign version_history = page.version_history %}
26
31
  {% assign appendices = page.appendices %}
@@ -28,8 +33,8 @@ schema_type: ScholarlyArticle
28
33
  {% assign references = page.references %}
29
34
  {% assign references_array = references | arrayify %}
30
35
  {% assign funding = page.funding %}
31
- {% assign rights = page.rights | default: page.license %}
32
- {% assign affiliation_default = site.author.affiliation %}
36
+ {% assign rights = page.rights %}
37
+ {% assign research_license = page | page_license %}
33
38
  {% assign show_publications = page.show_publications | default: false %}
34
39
 
35
40
  <div class="research-wrapper" itemscope itemtype="https://schema.org/ScholarlyArticle">
@@ -57,9 +62,9 @@ schema_type: ScholarlyArticle
57
62
  <h2 class="visually-hidden">Authors</h2>
58
63
  <ul class="research-author-list">
59
64
  {% for author in authors %}
60
- {% assign author_name = author.name | default: author %}
61
- {% assign author_affiliation = author.affiliation | default: author.institution | default: affiliation_default %}
62
- {% assign author_orcid = author.orcid | default: site.author.orcid %}
65
+ {% assign author_name = author.name | escape %}
66
+ {% assign author_affiliation = author.affiliation | escape %}
67
+ {% assign author_orcid = author.orcid %}
63
68
  {% assign author_email = author.email | default: author.contact %}
64
69
  <li class="research-author" itemprop="author" itemscope itemtype="https://schema.org/Person">
65
70
  <span class="research-author-name" itemprop="name">{{ author_name }}</span>
@@ -125,6 +130,11 @@ schema_type: ScholarlyArticle
125
130
  <dt>Rights</dt>
126
131
  <dd>{{ rights }}</dd>
127
132
  </div>
133
+ {% elsif research_license %}
134
+ <div>
135
+ <dt>Rights</dt>
136
+ <dd>{% include components/license-link.html license=research_license %}</dd>
137
+ </div>
128
138
  {% endif %}
129
139
  </dl>
130
140
 
@@ -321,6 +331,8 @@ ER -
321
331
  </section>
322
332
  {% endif %}
323
333
 
334
+ {% include components/reproducibility.html page=page %}
335
+
324
336
  {% if supplementary or appendices %}
325
337
  <section class="research-appendices" aria-labelledby="appendix-heading">
326
338
  <h2 id="appendix-heading">Appendix and supplementary materials</h2>