datalog-theme 0.7.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 (203) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +188 -0
  3. data/CITATION.cff +2 -2
  4. data/README.md +25 -17
  5. data/_data/cdn-integrity.yml +0 -30
  6. data/_data/i18n/en.yml +297 -0
  7. data/_data/i18n/es.yml +297 -0
  8. data/_data/i18n/pt.yml +297 -0
  9. data/_data/js_manifest.json +16 -0
  10. data/_includes/analytics/dashboard.html +3 -1
  11. data/_includes/components/api-function.html +20 -1
  12. data/_includes/components/author-bio.html +21 -11
  13. data/_includes/components/author-list.html +32 -0
  14. data/_includes/components/citation-tools.html +33 -25
  15. data/_includes/components/comments-thread.html +90 -0
  16. data/_includes/components/contact-form.html +120 -0
  17. data/_includes/components/correction-report.html +82 -0
  18. data/_includes/components/enhanced-code-block.html +1 -1
  19. data/_includes/components/enhanced-toc.html +6 -7
  20. data/_includes/components/license-link.html +13 -0
  21. data/_includes/components/license-notice.html +28 -0
  22. data/_includes/components/moderation-inbox.html +139 -0
  23. data/_includes/components/reactions.html +49 -0
  24. data/_includes/components/reading-list.html +31 -0
  25. data/_includes/components/reading-mode-toggle.html +65 -0
  26. data/_includes/components/reading-state-bookmark.html +27 -0
  27. data/_includes/components/reading-state-panel.html +71 -0
  28. data/_includes/components/reproducibility.html +61 -0
  29. data/_includes/components/responsive-image.html +3 -3
  30. data/_includes/components/revision-history.html +39 -0
  31. data/_includes/components/revision-notice.html +35 -0
  32. data/_includes/components/series-nav.html +64 -0
  33. data/_includes/components/subscribe-form.html +88 -0
  34. data/_includes/components/subscription-manage.html +68 -0
  35. data/_includes/components/webmentions.html +48 -0
  36. data/_includes/csp-meta.html +135 -11
  37. data/_includes/footer.html +22 -20
  38. data/_includes/head.html +111 -63
  39. data/_includes/header/navigation.html +12 -15
  40. data/_includes/header.html +28 -19
  41. data/_includes/layouts/default/article.html +9 -7
  42. data/_includes/meta/dynamic-services-config.html +14 -0
  43. data/_includes/meta/math-config.html +18 -10
  44. data/_includes/meta/person-json.html +27 -0
  45. data/_includes/meta/publisher.html +45 -0
  46. data/_includes/meta/schema.html +67 -30
  47. data/_includes/meta/scholarly.html +121 -0
  48. data/_includes/meta/scripts-loader.html +18 -32
  49. data/_includes/meta/webmention-discovery.html +14 -0
  50. data/_includes/post/related-posts.html +4 -7
  51. data/_includes/scripts.html +57 -0
  52. data/_includes/search/index-data.json +9 -34
  53. data/_layouts/dataset.html +5 -3
  54. data/_layouts/default.html +16 -8
  55. data/_layouts/notebook.html +1 -0
  56. data/_layouts/package.html +4 -2
  57. data/_layouts/page.html +15 -0
  58. data/_layouts/portfolio.html +1 -0
  59. data/_layouts/post.html +102 -23
  60. data/_layouts/project.html +4 -3
  61. data/_layouts/research.html +20 -8
  62. data/_plugins/analytics_dashboard.rb +9 -3
  63. data/_plugins/authors.rb +133 -0
  64. data/_plugins/config_validator.rb +231 -23
  65. data/_plugins/critical_css_check.rb +42 -0
  66. data/_plugins/csp_generator.rb +18 -28
  67. data/_plugins/datalog_bibliography.rb +9 -7
  68. data/_plugins/datalog_comments.rb +8 -5
  69. data/_plugins/datalog_slides.rb +9 -8
  70. data/_plugins/i18n.rb +13 -12
  71. data/_plugins/image_optimizer.rb +241 -178
  72. data/_plugins/licenses.rb +135 -0
  73. data/_plugins/math_preprocessor.rb +59 -7
  74. data/_plugins/notebook_converter.rb +23 -4
  75. data/_plugins/plugin_loader.rb +3 -1
  76. data/_plugins/publications_generator.rb +8 -2
  77. data/_plugins/references.rb +238 -0
  78. data/_plugins/reproducibility.rb +150 -0
  79. data/_plugins/revisions.rb +101 -0
  80. data/_plugins/rouge_highlight_filter.rb +42 -0
  81. data/_plugins/scholarly.rb +50 -0
  82. data/_plugins/search_code_blocks.rb +30 -0
  83. data/_plugins/search_normalizer.rb +15 -53
  84. data/_plugins/search_pages.rb +3 -4
  85. data/_plugins/series.rb +104 -0
  86. data/_plugins/statements.rb +87 -0
  87. data/_sass/_academic-dashboard.scss +262 -0
  88. data/_sass/_base.scss +20 -1
  89. data/_sass/_comments-thread.scss +159 -0
  90. data/_sass/_components.scss +64 -1153
  91. data/_sass/_features.scss +17 -0
  92. data/_sass/_layout.scss +385 -1
  93. data/_sass/_mathematical.scss +27 -0
  94. data/_sass/_moderation.scss +222 -0
  95. data/_sass/_notebooks.scss +322 -0
  96. data/_sass/_open-science-badges.scss +56 -0
  97. data/_sass/{_phase1-enhancements.scss → _post-components.scss} +5 -3
  98. data/_sass/_print.scss +291 -0
  99. data/_sass/_reactions.scss +89 -0
  100. data/_sass/_reading-state.scss +290 -0
  101. data/_sass/_search-page.scss +530 -0
  102. data/_sass/_search.scss +46 -0
  103. data/_sass/_service-forms.scss +204 -0
  104. data/_sass/_subscriptions.scss +140 -0
  105. data/_sass/_syntax-highlighting.scss +212 -97
  106. data/_sass/_theme.scss +40 -19
  107. data/_sass/_typography.scss +130 -0
  108. data/_sass/_utilities.scss +5 -0
  109. data/_sass/_variables.scss +6 -0
  110. data/_sass/_webmentions.scss +125 -0
  111. data/assets/css/main.scss +14 -0
  112. data/assets/js/dist/academic.js +1 -1
  113. data/assets/js/dist/analytics-dashboard.js +1 -1
  114. data/assets/js/dist/chunks/chunk-2DYDWUFX.js +1 -0
  115. data/assets/js/dist/chunks/chunk-PATLC23F.js +1 -0
  116. data/assets/js/dist/chunks/chunk-V7734B2G.js +1 -0
  117. data/assets/js/dist/comments.js +2 -0
  118. data/assets/js/dist/contact.js +1 -0
  119. data/assets/js/dist/core.js +1 -1
  120. data/assets/js/dist/corrections.js +1 -0
  121. data/assets/js/dist/loader.js +1 -1
  122. data/assets/js/dist/math.js +1 -1
  123. data/assets/js/dist/moderation.js +1 -0
  124. data/assets/js/dist/notebook.js +1 -1
  125. data/assets/js/dist/reactions.js +1 -0
  126. data/assets/js/dist/reading-state.js +1 -0
  127. data/assets/js/dist/search.js +1 -1
  128. data/assets/js/dist/sources.json +52 -0
  129. data/assets/js/dist/subscriptions.js +1 -0
  130. data/assets/js/dist/visualizations.js +11 -2
  131. data/assets/js/dist/webmentions.js +1 -0
  132. data/assets/js/loader.js +37 -1
  133. data/datalog-theme.gemspec +35 -23
  134. data/lib/datalog/cli.rb +43 -15
  135. data/lib/datalog/critical_css.rb +168 -0
  136. data/lib/datalog/plugin_system/dependency_resolver.rb +0 -2
  137. data/lib/datalog/plugins/comments.rb +33 -3
  138. data/lib/datalog/theme/installed_files.rb +113 -0
  139. data/lib/datalog/theme/package.rb +57 -0
  140. data/lib/datalog/theme/repository_checkout.rb +94 -0
  141. data/lib/datalog/theme/version.rb +5 -1
  142. data/lib/datalog/warning_filter.rb +5 -11
  143. data/lib/datalog-theme.rb +6 -0
  144. metadata +96 -147
  145. data/_data/academic.yml +0 -217
  146. data/_data/config/author.yml +0 -121
  147. data/_data/datasets.yml +0 -28
  148. data/_data/js_meta.json +0 -371
  149. data/_data/navigation.yml +0 -145
  150. data/_data/projects.yml +0 -41
  151. data/_data/publications.yml +0 -28
  152. data/_data/social.yml +0 -73
  153. data/_data/visualizations.yml +0 -51
  154. data/_includes/components/advanced-search.html +0 -682
  155. data/_includes/components/bookmark-system.html +0 -96
  156. data/_includes/components/comments.html +0 -244
  157. data/_includes/components/content-recommendations.html +0 -228
  158. data/_includes/components/email-preferences.html +0 -200
  159. data/_includes/components/enhanced-metadata.html +0 -228
  160. data/_includes/components/language-switcher.html +0 -396
  161. data/_includes/components/navigation-enhancements.html +0 -454
  162. data/_includes/components/newsletter-signup.html +0 -178
  163. data/_includes/components/popular-posts.html +0 -233
  164. data/_includes/components/reading-progress.html +0 -133
  165. data/_includes/components/reading-time.html +0 -121
  166. data/_includes/components/series-navigation.html +0 -124
  167. data/_includes/components/social-proof.html +0 -34
  168. data/_includes/components/user-preferences.html +0 -566
  169. data/_includes/meta/syntax-config.html +0 -19
  170. data/_layouts/archive.html +0 -282
  171. data/_layouts/post-sidebar.html +0 -183
  172. data/_sass/_phase3-enhancements.scss +0 -874
  173. data/_sass/_phase4-enhancements.scss +0 -1214
  174. data/_sass/_phase5-enhancements.scss +0 -414
  175. data/assets/js/academic.js +0 -262
  176. data/assets/js/analytics-dashboard.js +0 -382
  177. data/assets/js/core/dark-mode.js +0 -79
  178. data/assets/js/core/github-cards.js +0 -123
  179. data/assets/js/core/language-filter.js +0 -69
  180. data/assets/js/core/navigation.js +0 -184
  181. data/assets/js/core/scroll-progress.js +0 -45
  182. data/assets/js/core/search-hotkeys.js +0 -62
  183. data/assets/js/core/skip-links.js +0 -62
  184. data/assets/js/dist/manifest.json +0 -22
  185. data/assets/js/dist/meta.json +0 -371
  186. data/assets/js/main.js +0 -23
  187. data/assets/js/math.js +0 -818
  188. data/assets/js/notebook.js +0 -158
  189. data/assets/js/search/analytics.js +0 -91
  190. data/assets/js/search/app.js +0 -271
  191. data/assets/js/search/autocomplete.js +0 -120
  192. data/assets/js/search/engine.js +0 -260
  193. data/assets/js/search/filters.js +0 -45
  194. data/assets/js/search/render.js +0 -217
  195. data/assets/js/search/utils.js +0 -99
  196. data/assets/js/search.js +0 -354
  197. data/assets/js/visualizations.js +0 -816
  198. data/assets/publications/datalog-publications.bib +0 -8
  199. data/assets/publications/datalog-publications.ris +0 -9
  200. data/assets/publications/publications.bib +0 -30
  201. data/assets/templates/diogo-ribeiro-cv.md +0 -31
  202. data/assets/templates/diogo-ribeiro-cv.tex +0 -32
  203. data/lib/datalog/theme/theme.rb +0 -18
@@ -1,184 +0,0 @@
1
- /**
2
- * @fileoverview Navigation module for responsive site navigation.
3
- * Handles mobile menu toggling, smooth scrolling, and keyboard navigation.
4
- * @module core/navigation
5
- */
6
-
7
- /** @constant {string} Media query for desktop viewport */
8
- const DESKTOP_MEDIA = "(min-width: 48rem)";
9
- /** @constant {string} Selector for the main navigation element */
10
- const NAV_SELECTOR = "#site-nav";
11
- /** @constant {string} Selector for the navigation toggle button */
12
- const TOGGLE_SELECTOR = ".nav-toggle";
13
- /** @constant {string} Class applied to body when nav is open */
14
- const NAV_OPEN_CLASS = "nav-open";
15
-
16
- /**
17
- * Normalizes a URL path by removing trailing slashes and index.html.
18
- * @param {string} path - The path to normalize
19
- * @returns {string} Normalized path
20
- */
21
- function normalizePath(path) {
22
- return path.replace(/index\.html$/, "").replace(/\/$/, "");
23
- }
24
-
25
- function getAnchorTarget(link) {
26
- const href = link.getAttribute("href");
27
- if (!href) {
28
- return null;
29
- }
30
- try {
31
- const destination = new URL(href, window.location.origin);
32
- if (!destination.hash) {
33
- return null;
34
- }
35
- const current = new URL(window.location.href);
36
- if (normalizePath(destination.pathname) !== normalizePath(current.pathname)) {
37
- return null;
38
- }
39
- return destination.hash.replace("#", "");
40
- } catch (error) {
41
- return null;
42
- }
43
- }
44
-
45
- function smoothScrollToId(id) {
46
- if (!id) {
47
- return false;
48
- }
49
- const target = document.getElementById(id);
50
- if (!target) {
51
- return false;
52
- }
53
- target.scrollIntoView({ behavior: "smooth", block: "start" });
54
- return true;
55
- }
56
-
57
- /**
58
- * Initializes the navigation system including mobile toggle,
59
- * smooth scrolling for anchor links, and keyboard accessibility.
60
- * @returns {void}
61
- */
62
- export function initNavigation() {
63
- const siteNav = document.querySelector(NAV_SELECTOR);
64
- if (!siteNav) {
65
- return;
66
- }
67
-
68
- const navToggle = document.querySelector(TOGGLE_SELECTOR);
69
- const body = document.body;
70
- const navMediaQuery = window.matchMedia(DESKTOP_MEDIA);
71
-
72
- const syncNavForViewport = (isDesktop) => {
73
- if (isDesktop) {
74
- siteNav.dataset.open = "true";
75
- body.classList.remove(NAV_OPEN_CLASS);
76
- if (navToggle) {
77
- navToggle.setAttribute("aria-expanded", "false");
78
- navToggle.classList.remove("is-active");
79
- }
80
- return;
81
- }
82
-
83
- const isOpen = siteNav.dataset.open === "true";
84
- if (!isOpen) {
85
- siteNav.dataset.open = "false";
86
- }
87
- if (navToggle) {
88
- navToggle.setAttribute("aria-expanded", String(isOpen));
89
- navToggle.classList.toggle("is-active", isOpen);
90
- }
91
- };
92
-
93
- const closeNav = ({ focusToggle = false } = {}) => {
94
- if (navMediaQuery.matches) {
95
- return;
96
- }
97
- siteNav.dataset.open = "false";
98
- body.classList.remove(NAV_OPEN_CLASS);
99
- if (navToggle) {
100
- navToggle.setAttribute("aria-expanded", "false");
101
- navToggle.classList.remove("is-active");
102
- if (focusToggle) {
103
- navToggle.focus();
104
- }
105
- }
106
- };
107
-
108
- const openNav = () => {
109
- if (navMediaQuery.matches) {
110
- return;
111
- }
112
- siteNav.dataset.open = "true";
113
- body.classList.add(NAV_OPEN_CLASS);
114
- if (navToggle) {
115
- navToggle.setAttribute("aria-expanded", "true");
116
- navToggle.classList.add("is-active");
117
- }
118
- };
119
-
120
- const toggleNav = () => {
121
- if (navMediaQuery.matches) {
122
- return;
123
- }
124
- if (siteNav.dataset.open === "true") {
125
- closeNav();
126
- } else {
127
- openNav();
128
- }
129
- };
130
-
131
- if (!navMediaQuery.matches) {
132
- siteNav.dataset.open = "false";
133
- }
134
-
135
- syncNavForViewport(navMediaQuery.matches);
136
- navMediaQuery.addEventListener("change", (event) => {
137
- if (event.matches) {
138
- syncNavForViewport(true);
139
- } else {
140
- closeNav();
141
- siteNav.dataset.open = "false";
142
- syncNavForViewport(false);
143
- }
144
- });
145
-
146
- const navLinks = siteNav.querySelectorAll(".nav-link");
147
- navLinks.forEach((link) => {
148
- const anchorId = getAnchorTarget(link);
149
- link.addEventListener("click", (event) => {
150
- if (!navMediaQuery.matches) {
151
- closeNav();
152
- }
153
- if (anchorId && smoothScrollToId(anchorId)) {
154
- event.preventDefault();
155
- }
156
- });
157
- });
158
-
159
- if (navToggle) {
160
- navToggle.addEventListener("click", () => {
161
- toggleNav();
162
- });
163
- }
164
-
165
- document.addEventListener("keydown", (event) => {
166
- if (event.key === "Escape") {
167
- closeNav({ focusToggle: true });
168
- }
169
- });
170
-
171
- document.addEventListener("click", (event) => {
172
- if (navMediaQuery.matches || siteNav.dataset.open !== "true") {
173
- return;
174
- }
175
- const target = event.target;
176
- if (!target || typeof target.closest !== "function") {
177
- return;
178
- }
179
- if (target.closest(NAV_SELECTOR) || (navToggle && target.closest(TOGGLE_SELECTOR))) {
180
- return;
181
- }
182
- closeNav();
183
- });
184
- }
@@ -1,45 +0,0 @@
1
- /**
2
- * @fileoverview Scroll progress indicator.
3
- * Shows reading progress as user scrolls through content.
4
- * @module core/scroll-progress
5
- */
6
-
7
- /**
8
- * Calculates and updates the scroll progress indicator.
9
- * @param {HTMLElement} progressBar - The progress bar element
10
- * @param {HTMLElement|null} progressValue - Optional element to display percentage
11
- */
12
- function calculateProgress(progressBar, progressValue) {
13
- const scrollTop = window.pageYOffset || document.documentElement.scrollTop;
14
- const docHeight = document.documentElement.scrollHeight - window.innerHeight;
15
- const progress = docHeight > 0 ? Math.min((scrollTop / docHeight) * 100, 100) : 0;
16
-
17
- if (progressBar.tagName === "PROGRESS") {
18
- progressBar.setAttribute("value", String(progress));
19
- } else {
20
- progressBar.style.setProperty("--progress", `${progress}%`);
21
- }
22
-
23
- if (progressValue) {
24
- progressValue.textContent = Math.round(progress);
25
- }
26
- }
27
-
28
- /**
29
- * Initializes the scroll progress indicator.
30
- * Listens to scroll and resize events to update progress.
31
- * @returns {void}
32
- */
33
- export function initScrollProgress() {
34
- const progressBar = document.querySelector("[data-scroll-progress]");
35
- if (!progressBar) {
36
- return;
37
- }
38
-
39
- const progressValue = document.querySelector("[data-scroll-progress-value]");
40
- const updateProgress = () => calculateProgress(progressBar, progressValue);
41
-
42
- updateProgress();
43
- window.addEventListener("scroll", updateProgress, { passive: true });
44
- window.addEventListener("resize", updateProgress);
45
- }
@@ -1,62 +0,0 @@
1
- /**
2
- * @fileoverview Search keyboard shortcuts.
3
- * Enables "/" and Cmd/Ctrl+K hotkeys to focus search.
4
- * @module core/search-hotkeys
5
- */
6
-
7
- /**
8
- * Focuses the global search input or navigates to search page.
9
- * @param {HTMLElement} siteSearchForm - The search form element
10
- */
11
- function focusGlobalSearch(siteSearchForm) {
12
- if (!siteSearchForm) {
13
- return;
14
- }
15
- const siteSearchInput = siteSearchForm.querySelector("input[type='search']");
16
- const searchDestination = siteSearchForm.getAttribute("action");
17
-
18
- if (siteSearchInput) {
19
- siteSearchInput.focus();
20
- siteSearchInput.select();
21
- } else if (searchDestination) {
22
- window.location.href = searchDestination;
23
- }
24
- }
25
-
26
- function shouldIgnoreHotkey(activeElement) {
27
- if (!activeElement) {
28
- return false;
29
- }
30
- if (activeElement.isContentEditable) {
31
- return true;
32
- }
33
- const tag = activeElement.tagName;
34
- return tag === "INPUT" || tag === "TEXTAREA" || tag === "SELECT";
35
- }
36
-
37
- /**
38
- * Initializes search keyboard shortcuts (/ and Cmd/Ctrl+K).
39
- * @returns {void}
40
- */
41
- export function initSearchHotkeys() {
42
- const siteSearchForm = document.querySelector(".site-search");
43
- if (!siteSearchForm) {
44
- return;
45
- }
46
-
47
- document.addEventListener("keydown", (event) => {
48
- if (shouldIgnoreHotkey(document.activeElement)) {
49
- return;
50
- }
51
-
52
- if (event.key === "/" && !event.ctrlKey && !event.metaKey && !event.altKey) {
53
- event.preventDefault();
54
- focusGlobalSearch(siteSearchForm);
55
- }
56
-
57
- if ((event.key === "k" || event.key === "K") && (event.ctrlKey || event.metaKey)) {
58
- event.preventDefault();
59
- focusGlobalSearch(siteSearchForm);
60
- }
61
- });
62
- }
@@ -1,62 +0,0 @@
1
- /**
2
- * @fileoverview Skip links for keyboard accessibility.
3
- * Allows users to skip to main content areas.
4
- * @module core/skip-links
5
- */
6
-
7
- /**
8
- * Focuses a target element, temporarily making it focusable if needed.
9
- * @param {HTMLElement|null} target - The element to focus
10
- */
11
- function focusTarget(target) {
12
- if (!target) {
13
- return;
14
- }
15
-
16
- const previousTabIndex = target.getAttribute("tabindex");
17
- if (previousTabIndex === null) {
18
- target.setAttribute("tabindex", "-1");
19
- target.dataset.skipLinkTempTabindex = "true";
20
- }
21
-
22
- target.addEventListener(
23
- "blur",
24
- () => {
25
- if (target.dataset.skipLinkTempTabindex) {
26
- target.removeAttribute("tabindex");
27
- delete target.dataset.skipLinkTempTabindex;
28
- }
29
- },
30
- { once: true }
31
- );
32
-
33
- target.focus();
34
- }
35
-
36
- /**
37
- * Initializes skip link functionality for accessibility.
38
- * Enhances focus management when skip links are activated.
39
- * @returns {void}
40
- */
41
- export function initSkipLinks() {
42
- const skipLinks = document.querySelectorAll(".skip-link[href^='#']");
43
- if (!skipLinks.length) {
44
- return;
45
- }
46
-
47
- skipLinks.forEach((link) => {
48
- link.addEventListener("click", (event) => {
49
- const href = link.getAttribute("href") || "";
50
- const targetId = href.slice(1);
51
- if (!targetId) {
52
- return;
53
- }
54
- const target = document.getElementById(targetId);
55
- if (!target) {
56
- return;
57
- }
58
- event.preventDefault();
59
- focusTarget(target);
60
- });
61
- });
62
- }
@@ -1,22 +0,0 @@
1
- {
2
- "core": "/assets/js/dist/core.js",
3
- "loader": "/assets/js/dist/loader.js",
4
- "features": {
5
- "search": "/assets/js/dist/search.js",
6
- "math": "/assets/js/dist/math.js",
7
- "visualizations": "/assets/js/dist/visualizations.js",
8
- "notebook": "/assets/js/dist/notebook.js",
9
- "academic": "/assets/js/dist/academic.js",
10
- "analytics-dashboard": "/assets/js/dist/analytics-dashboard.js"
11
- },
12
- "entrypoints": {
13
- "core": "/assets/js/dist/core.js",
14
- "loader": "/assets/js/dist/loader.js",
15
- "search": "/assets/js/dist/search.js",
16
- "math": "/assets/js/dist/math.js",
17
- "visualizations": "/assets/js/dist/visualizations.js",
18
- "notebook": "/assets/js/dist/notebook.js",
19
- "academic": "/assets/js/dist/academic.js",
20
- "analytics-dashboard": "/assets/js/dist/analytics-dashboard.js"
21
- }
22
- }