ultimate-jekyll-manager 1.7.2 → 1.8.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 (85) hide show
  1. package/.claude/scheduled_tasks.lock +1 -0
  2. package/CHANGELOG.md +61 -1
  3. package/CLAUDE.md +36 -15
  4. package/README.md +4 -2
  5. package/TODO-AUTH-TESTING.md +1 -1
  6. package/dist/assets/themes/newsflash/README.md +58 -0
  7. package/dist/assets/themes/newsflash/_config.scss +138 -0
  8. package/dist/assets/themes/newsflash/_theme.js +27 -0
  9. package/dist/assets/themes/newsflash/_theme.scss +37 -0
  10. package/dist/assets/themes/newsflash/css/base/_mixins.scss +50 -0
  11. package/dist/assets/themes/newsflash/css/base/_root.scss +134 -0
  12. package/dist/assets/themes/newsflash/css/base/_typography.scss +49 -0
  13. package/dist/assets/themes/newsflash/css/base/_utilities.scss +58 -0
  14. package/dist/assets/themes/newsflash/css/components/_badges.scss +65 -0
  15. package/dist/assets/themes/newsflash/css/components/_buttons.scss +139 -0
  16. package/dist/assets/themes/newsflash/css/components/_cards.scss +52 -0
  17. package/dist/assets/themes/newsflash/css/components/_editorial.scss +182 -0
  18. package/dist/assets/themes/newsflash/css/components/_forms.scss +75 -0
  19. package/dist/assets/themes/newsflash/css/components/_infinite-scroll.scss +102 -0
  20. package/dist/assets/themes/newsflash/css/components/_panels.scss +91 -0
  21. package/dist/assets/themes/newsflash/css/components/_ticker.scss +70 -0
  22. package/dist/assets/themes/newsflash/css/layout/_general.scss +264 -0
  23. package/dist/assets/themes/newsflash/css/layout/_navigation.scss +164 -0
  24. package/dist/assets/themes/newsflash/js/initialize-tooltips.js +20 -0
  25. package/dist/assets/themes/newsflash/js/masthead-scroll.js +29 -0
  26. package/dist/assets/themes/newsflash/pages/404/index.scss +27 -0
  27. package/dist/assets/themes/newsflash/pages/about/index.scss +70 -0
  28. package/dist/assets/themes/newsflash/pages/blog/index.scss +17 -0
  29. package/dist/assets/themes/newsflash/pages/blog/post.js +29 -0
  30. package/dist/assets/themes/newsflash/pages/blog/post.scss +164 -0
  31. package/dist/assets/themes/newsflash/pages/index.scss +159 -0
  32. package/dist/assets/themes/newsflash/pages/pricing/index.scss +194 -0
  33. package/dist/assets/themes/newsflash/pages/test/libraries/layers/index.js +9 -0
  34. package/dist/assets/themes/newsflash/pages/test/libraries/layers/index.scss +7 -0
  35. package/dist/commands/blogify.js +6 -3
  36. package/dist/commands/test.js +34 -5
  37. package/dist/defaults/CLAUDE.md +17 -4
  38. package/dist/defaults/dist/_includes/core/pricing/resolve-plan.html +59 -0
  39. package/dist/defaults/dist/_includes/themes/classy/frontend/sections/footer.html +20 -3
  40. package/dist/defaults/dist/_layouts/themes/classy/admin/core/minimal-viewport-locked.html +1 -1
  41. package/dist/defaults/dist/_layouts/themes/classy/admin/core/minimal.html +1 -1
  42. package/dist/defaults/dist/_layouts/themes/classy/frontend/pages/pricing.html +5 -40
  43. package/dist/defaults/dist/_layouts/themes/neobrutalism/frontend/pages/pricing.html +33 -34
  44. package/dist/defaults/dist/_layouts/themes/newsflash/frontend/core/base.html +61 -0
  45. package/dist/defaults/dist/_layouts/themes/newsflash/frontend/pages/404.html +86 -0
  46. package/dist/defaults/dist/_layouts/themes/newsflash/frontend/pages/about.html +353 -0
  47. package/dist/defaults/dist/_layouts/themes/newsflash/frontend/pages/blog/categories/category.html +105 -0
  48. package/dist/defaults/dist/_layouts/themes/newsflash/frontend/pages/blog/categories/index.html +93 -0
  49. package/dist/defaults/dist/_layouts/themes/newsflash/frontend/pages/blog/index.html +373 -0
  50. package/dist/defaults/dist/_layouts/themes/newsflash/frontend/pages/blog/post.html +289 -0
  51. package/dist/defaults/dist/_layouts/themes/newsflash/frontend/pages/blog/tags/index.html +90 -0
  52. package/dist/defaults/dist/_layouts/themes/newsflash/frontend/pages/blog/tags/tag.html +107 -0
  53. package/dist/defaults/dist/_layouts/themes/newsflash/frontend/pages/contact.html +340 -0
  54. package/dist/defaults/dist/_layouts/themes/newsflash/frontend/pages/index.html +522 -0
  55. package/dist/defaults/dist/_layouts/themes/newsflash/frontend/pages/pricing.html +485 -0
  56. package/dist/defaults/dist/_layouts/themes/newsflash/frontend/pages/team/index.html +207 -0
  57. package/dist/defaults/dist/_layouts/themes/newsflash/frontend/pages/team/member.html +134 -0
  58. package/dist/defaults/test/README.md +4 -0
  59. package/dist/gulp/tasks/jekyll.js +4 -2
  60. package/dist/test/runner.js +50 -3
  61. package/dist/test/suites/build/attach-log-file.test.js +102 -0
  62. package/dist/test/suites/build/theme-contract.test.js +173 -0
  63. package/dist/test/utils/extended-mode-warning.js +13 -0
  64. package/dist/utils/attach-log-file.js +70 -43
  65. package/docs/appearance.md +1 -0
  66. package/docs/assets.md +9 -0
  67. package/docs/audit.md +27 -7
  68. package/docs/build-system.md +57 -0
  69. package/docs/common-mistakes.md +15 -0
  70. package/docs/{project-structure.md → directory-structure.md} +1 -1
  71. package/docs/environment-detection.md +1 -1
  72. package/docs/javascript-libraries.md +38 -1
  73. package/docs/layouts-and-pages.md +146 -0
  74. package/docs/local-development.md +1 -8
  75. package/docs/logging.md +30 -0
  76. package/docs/migration.md +131 -0
  77. package/docs/no-inline-scripts.md +304 -0
  78. package/docs/purgecss.md +164 -0
  79. package/docs/seo.md +131 -4
  80. package/docs/templating.md +23 -0
  81. package/docs/test-boot-layer.md +1 -1
  82. package/docs/test-framework.md +56 -8
  83. package/docs/themes.md +254 -13
  84. package/logs/test.log +111 -0
  85. package/package.json +1 -1
@@ -0,0 +1,164 @@
1
+ // Newsflash Theme — Navigation
2
+ // The inherited nav markup (.navbar-wrapper > .navbar.navbar-floating) is a
3
+ // floating glass pill in Classy. Here it becomes the MASTHEAD: a sticky,
4
+ // blurred-paper bar closed by a hairline ink rule, serif brand on the left,
5
+ // uppercase pill links in the middle. The ticker (in base.html) sits above it
6
+ // in-flow and scrolls away; the masthead stays.
7
+
8
+ .navbar-wrapper {
9
+ position: sticky;
10
+ top: 0;
11
+ left: 0;
12
+ right: 0;
13
+ z-index: 1030;
14
+
15
+ .navbar {
16
+ width: 100%;
17
+ max-width: 100%;
18
+ margin: 0;
19
+ padding-left: clamp(1rem, 4vw, 3rem);
20
+ padding-right: clamp(1rem, 4vw, 3rem);
21
+ }
22
+ }
23
+
24
+ .navbar.navbar-floating {
25
+ border-radius: 0;
26
+ padding-top: 0.75rem;
27
+ padding-bottom: 0.75rem;
28
+ background: var(--nf-paper-translucent) !important;
29
+ backdrop-filter: blur(12px);
30
+ -webkit-backdrop-filter: blur(12px);
31
+ border: 0;
32
+ border-bottom: var(--nf-border);
33
+ transition: box-shadow 0.25s ease;
34
+
35
+ // Soft shadow only once scrolled (set by js/masthead-scroll.js)
36
+ &.scrolled {
37
+ box-shadow: 0 8px 24px -16px rgba(23, 19, 16, 0.4);
38
+ }
39
+
40
+ .container,
41
+ .container-fluid {
42
+ padding: 0;
43
+ }
44
+ }
45
+
46
+ // Brand: the serif masthead title
47
+ .navbar-brand {
48
+ font-family: $nf-font-display;
49
+ font-optical-sizing: auto;
50
+ font-weight: 600;
51
+ font-size: 1.5rem;
52
+ letter-spacing: -0.02em;
53
+
54
+ .brand-logo { height: 32px; width: auto; margin-right: 0.5rem; }
55
+ }
56
+
57
+ // Nav links: uppercase grotesk pills. Hover fills ink; active fills vermilion.
58
+ .navbar-nav .nav-link {
59
+ font-weight: 700;
60
+ font-size: 0.82rem;
61
+ text-transform: uppercase;
62
+ letter-spacing: 0.05em;
63
+ padding: 0.55rem 0.9rem;
64
+ margin: 0 0.1rem;
65
+ border-radius: 50rem;
66
+ color: var(--bs-body-color);
67
+ transition: $nf-transition;
68
+
69
+ // Hover + active need !important on color: the nav include puts Bootstrap's
70
+ // .text-body utility (!important) on every link, which otherwise wins and
71
+ // leaves ink text on the ink hover fill (unreadable).
72
+ &:hover {
73
+ background: var(--nf-ink);
74
+ color: var(--nf-paper) !important;
75
+ }
76
+
77
+ // Active = vermilion pill.
78
+ &.active,
79
+ &.active.text-body {
80
+ background: var(--nf-accent-interactive) !important;
81
+ color: var(--nf-accent-interactive-ink) !important;
82
+ }
83
+ }
84
+
85
+ // Mobile toggle: a pill ink-framed button
86
+ .navbar-toggler {
87
+ border-radius: 50rem;
88
+ padding: 0.35rem 0.6rem;
89
+ background: transparent;
90
+ @include nf-border();
91
+ transition: $nf-transition;
92
+
93
+ &:hover { background: var(--nf-paper-2); }
94
+ &:focus { box-shadow: 0 0 0 3px var(--nf-volt); }
95
+
96
+ .navbar-toggler-icon {
97
+ width: 1.25em;
98
+ height: 1.25em;
99
+ background-image: url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 30 30'%3e%3cpath stroke='rgba%2823,19,16,1%29' stroke-linecap='round' stroke-miterlimit='10' stroke-width='2.5' d='M4 7h22M4 15h22M4 23h22'/%3e%3c/svg%3e");
100
+ }
101
+
102
+ [data-bs-theme="dark"] & .navbar-toggler-icon {
103
+ background-image: url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 30 30'%3e%3cpath stroke='rgba%28242,232,217,1%29' stroke-linecap='round' stroke-miterlimit='10' stroke-width='2.5' d='M4 7h22M4 15h22M4 23h22'/%3e%3c/svg%3e");
104
+ }
105
+ }
106
+
107
+ // Mobile collapsed menu becomes a framed paper drawer
108
+ @media (max-width: 991.98px) {
109
+ .navbar-collapse {
110
+ margin-top: 0.75rem;
111
+ padding: 0.85rem;
112
+ background: var(--bs-card-bg);
113
+ border-radius: var(--bs-border-radius-lg);
114
+ @include nf-border();
115
+ @include nf-shadow-pop();
116
+ }
117
+ }
118
+
119
+ // ============================================
120
+ // Dropdown menus — framed paper panels
121
+ // ============================================
122
+ // Doubled selector: page bundles re-emit Bootstrap's .dropdown-menu AFTER the
123
+ // main bundle, and its `--bs-dropdown-padding-x: 0` strips the inset — the
124
+ // highlighted item pills end up pressed edge-to-edge against the panel.
125
+ .dropdown-menu.dropdown-menu {
126
+ background: var(--bs-card-bg);
127
+ border-radius: var(--bs-border-radius);
128
+ @include nf-border();
129
+ @include nf-shadow-pop();
130
+ padding: 0.4rem;
131
+ margin-top: 0.6rem;
132
+
133
+ .dropdown-item {
134
+ border-radius: 50rem;
135
+ font-weight: 600;
136
+ padding: 0.5rem 0.9rem;
137
+ color: var(--bs-body-color);
138
+
139
+ // !important: dropdown items (account dropdown, nav dropdowns) carry
140
+ // text-color utilities from the shared includes — same trap as nav links.
141
+ &:hover,
142
+ &:focus {
143
+ background: var(--nf-ink);
144
+ color: var(--nf-paper) !important;
145
+
146
+ // Child text spans with their own utility colors flip with the item
147
+ [class*="text-"] {
148
+ color: inherit !important;
149
+ }
150
+ }
151
+
152
+ &.active,
153
+ &:active {
154
+ background: var(--nf-accent-interactive);
155
+ color: var(--nf-accent-interactive-ink) !important;
156
+ }
157
+ }
158
+
159
+ .dropdown-divider {
160
+ border-top: 1px solid var(--nf-line);
161
+ opacity: 1;
162
+ margin: 0.4rem 0;
163
+ }
164
+ }
@@ -0,0 +1,20 @@
1
+ /**
2
+ * Initialize Bootstrap Tooltips
3
+ * Finds all elements with data-bs-toggle="tooltip" and initializes them
4
+ */
5
+ export default function initializeTooltips() {
6
+ const $tooltipTriggers = document.querySelectorAll('[data-bs-toggle="tooltip"]');
7
+
8
+ // If no tooltips found, exit early
9
+ if ($tooltipTriggers.length === 0) {
10
+ return;
11
+ }
12
+
13
+ // Log the number of tooltips being initialized
14
+ console.log(`Initializing ${$tooltipTriggers.length} tooltips`);
15
+
16
+ // Initialize each tooltip
17
+ $tooltipTriggers.forEach(($el) => {
18
+ new bootstrap.Tooltip($el);
19
+ });
20
+ }
@@ -0,0 +1,29 @@
1
+ // Masthead scroll effect for the Newsflash theme.
2
+ // Toggles a `.scrolled` class on the sticky masthead once the page is scrolled
3
+ // past a threshold; the SCSS turns that into a soft shadow under the bar.
4
+ // Threshold is configurable via the data-nf-scroll-threshold attribute on the navbar.
5
+ export default function setupMastheadScroll() {
6
+ const $navbar = document.querySelector('.navbar-floating');
7
+ if (!$navbar) {
8
+ return;
9
+ }
10
+
11
+ const threshold = parseInt($navbar.dataset.nfScrollThreshold, 10) || 8;
12
+
13
+ let ticking = false;
14
+ function update() {
15
+ $navbar.classList.toggle('scrolled', window.scrollY > threshold);
16
+ ticking = false;
17
+ }
18
+
19
+ function onScroll() {
20
+ if (!ticking) {
21
+ ticking = true;
22
+ window.requestAnimationFrame(update);
23
+ }
24
+ }
25
+
26
+ // Initial state + listener
27
+ update();
28
+ window.addEventListener('scroll', onScroll, { passive: true });
29
+ }
@@ -0,0 +1,27 @@
1
+ // Newsflash Theme — 404 page-specific CSS
2
+ // The "correction notice" treatment for
3
+ // (_layouts/themes/newsflash/frontend/pages/404.html).
4
+ // Compiles standalone, so it pulls in the theme tokens + mixins via loadPaths.
5
+ @use 'config' as *;
6
+ @import 'css/base/mixins';
7
+
8
+ // Oversized stroked serif numerals
9
+ .error-code {
10
+ font-family: $nf-font-display;
11
+ font-style: italic;
12
+ font-weight: 900;
13
+ font-size: clamp(5rem, 16vw, 8rem);
14
+ line-height: 1;
15
+ color: transparent;
16
+ -webkit-text-stroke: 2px var(--nf-ink);
17
+ }
18
+
19
+ // The rotated "Correction" chip pinned to the notice
20
+ .error-stamp {
21
+ position: absolute;
22
+ top: -0.85rem;
23
+ left: 50%;
24
+ transform: translateX(-50%) rotate(-3deg);
25
+ z-index: 1;
26
+ white-space: nowrap;
27
+ }
@@ -0,0 +1,70 @@
1
+ // Newsflash Theme — About page-specific CSS
2
+ // The editorial timeline for
3
+ // (_layouts/themes/newsflash/frontend/pages/about.html).
4
+ // Compiles standalone, so it pulls in the theme tokens + mixins via loadPaths.
5
+ @use 'config' as *;
6
+ @import 'css/base/mixins';
7
+
8
+ // Single-rail editorial timeline: an ink rule down the left, volt year chips
9
+ // hanging on it, entries stepping down the page.
10
+ .timeline {
11
+ position: relative;
12
+ padding-left: 1.5rem;
13
+ border-left: var(--nf-border);
14
+ }
15
+
16
+ .timeline-item {
17
+ position: relative;
18
+ display: flex;
19
+ flex-direction: column;
20
+ align-items: flex-start;
21
+ gap: 0.6rem;
22
+ padding-bottom: 2.25rem;
23
+
24
+ &:last-child {
25
+ padding-bottom: 0;
26
+ }
27
+
28
+ // The rule marker — a vermilion dot pinned to the rail
29
+ &::before {
30
+ content: "";
31
+ position: absolute;
32
+ left: calc(-1.5rem - 5.75px); // centers the dot on the 1.5px rail
33
+ top: 0.45rem;
34
+ width: 10px;
35
+ height: 10px;
36
+ border-radius: 50%;
37
+ background: var(--bs-primary);
38
+ border: var(--nf-border);
39
+ }
40
+ }
41
+
42
+ .timeline-year {
43
+ transform: rotate(-2deg);
44
+ }
45
+
46
+ // ============================================
47
+ // Reader quotes — letters to the editor
48
+ // ============================================
49
+ .quote-card {
50
+ &::before {
51
+ content: "\201C";
52
+ display: block;
53
+ font-family: $nf-font-display;
54
+ font-weight: 900;
55
+ font-size: 3rem;
56
+ line-height: 0.5;
57
+ color: var(--bs-primary);
58
+ margin-bottom: 0.5rem;
59
+ }
60
+
61
+ p {
62
+ font-family: $nf-font-display;
63
+ font-optical-sizing: auto;
64
+ font-style: italic;
65
+ font-weight: 550;
66
+ font-size: 1.15rem;
67
+ letter-spacing: -0.01em;
68
+ line-height: 1.45;
69
+ }
70
+ }
@@ -0,0 +1,17 @@
1
+ // Newsflash Theme — Blog index page-specific CSS
2
+ // Small accents for the newspaper front page
3
+ // (_layouts/themes/newsflash/frontend/pages/blog/index.html).
4
+ // Compiles standalone, so it pulls in the theme tokens + mixins via loadPaths.
5
+ @use 'config' as *;
6
+ @import 'css/base/mixins';
7
+
8
+ // The lead-story splash stays planted — only its framed image zooms
9
+ .story-card--lead {
10
+ &:hover {
11
+ transform: none;
12
+ }
13
+
14
+ .art-frame {
15
+ aspect-ratio: 16 / 10;
16
+ }
17
+ }
@@ -0,0 +1,29 @@
1
+ // Newsflash Theme — Blog post page JS (the #theme layer)
2
+ // Drives the reading-progress bar: fills the fixed top rule as the reader
3
+ // scrolls through the page. NOTE: flat file shape — the post layout sets
4
+ // `asset_path: blog/post`, so this loads as pages/blog/post.js.
5
+ export default ({ manager, options }) => {
6
+ const $bar = document.querySelector('.reading-progress > span');
7
+ if (!$bar) {
8
+ return;
9
+ }
10
+
11
+ let ticking = false;
12
+ function update() {
13
+ const $doc = document.documentElement;
14
+ const progress = $doc.scrollTop / ($doc.scrollHeight - $doc.clientHeight);
15
+ $bar.style.transform = `scaleX(${Math.min(Math.max(progress, 0), 1)})`;
16
+ ticking = false;
17
+ }
18
+
19
+ function onScroll() {
20
+ if (!ticking) {
21
+ ticking = true;
22
+ window.requestAnimationFrame(update);
23
+ }
24
+ }
25
+
26
+ // Initial state + listener
27
+ update();
28
+ window.addEventListener('scroll', onScroll, { passive: true });
29
+ };
@@ -0,0 +1,164 @@
1
+ // Newsflash Theme — Blog post page-specific CSS
2
+ // The editorial article treatment for
3
+ // (_layouts/themes/newsflash/frontend/pages/blog/post.html): reading-progress
4
+ // bar, drop cap, serif crossheads with the vermilion dash, framed in-content
5
+ // images, and the centered pullquote. NOTE: flat file shape — the post layout
6
+ // sets `asset_path: blog/post`, so this compiles to pages/blog/post.<id>.bundle.css.
7
+ // Compiles standalone, so it pulls in the theme tokens + mixins via loadPaths.
8
+ @use 'config' as *;
9
+ @import 'css/base/mixins';
10
+
11
+ // ============================================
12
+ // Reading progress — fixed vermilion rule across the very top
13
+ // ============================================
14
+ // Sits above the sticky masthead (z-index 1030); driven by pages/blog/post.js.
15
+ .reading-progress {
16
+ position: fixed;
17
+ top: 0;
18
+ left: 0;
19
+ right: 0;
20
+ height: 4px;
21
+ z-index: 1040;
22
+ pointer-events: none;
23
+ background: transparent;
24
+
25
+ span {
26
+ display: block;
27
+ height: 100%;
28
+ background: var(--bs-primary);
29
+ transform: scaleX(0);
30
+ transform-origin: left;
31
+ }
32
+ }
33
+
34
+ // ============================================
35
+ // Article hero — wide cinematic frame
36
+ // ============================================
37
+ .article-hero {
38
+ aspect-ratio: 21 / 10;
39
+
40
+ img {
41
+ height: 100%;
42
+ // Lift the framework's generic .blog-post-image cap (max-height: 480px in
43
+ // the main bundle) — the 21/10 frame is the size authority here, and the
44
+ // cap leaves a blank strip inside the frame on wide viewports.
45
+ max-height: none;
46
+ }
47
+ }
48
+
49
+ // ============================================
50
+ // Article body — the editorial reading column
51
+ // ============================================
52
+ .blog-post-content {
53
+ font-size: 1.13rem;
54
+ line-height: 1.78;
55
+
56
+ p {
57
+ margin-bottom: 1.5em;
58
+ }
59
+
60
+ // Drop cap on the opening paragraph
61
+ > p:first-of-type::first-letter {
62
+ font-family: $nf-font-display;
63
+ font-weight: 600;
64
+ font-size: 4.2rem;
65
+ line-height: 0.82;
66
+ color: var(--bs-primary);
67
+ float: left;
68
+ padding: 8px 12px 0 0;
69
+ }
70
+
71
+ // Serif crossheads with the vermilion dash
72
+ h2, h3 {
73
+ display: flex;
74
+ align-items: center;
75
+ gap: 0.5em;
76
+ font-size: 1.7rem;
77
+ letter-spacing: -0.014em;
78
+ line-height: 1.25;
79
+ margin: 2em 0 0.8em;
80
+
81
+ &::before {
82
+ content: "";
83
+ width: 0.55em;
84
+ height: 0.18em;
85
+ background: var(--bs-primary);
86
+ border-radius: 50rem;
87
+ flex: none;
88
+ }
89
+ }
90
+
91
+ h3 {
92
+ font-size: 1.35rem;
93
+ }
94
+
95
+ // In-content images get the editorial frame
96
+ img {
97
+ border: var(--nf-border);
98
+ border-radius: $nf-radius;
99
+ }
100
+
101
+ figcaption {
102
+ font-size: 0.78rem;
103
+ color: var(--bs-secondary-color);
104
+ padding-top: 10px;
105
+ text-align: right;
106
+ }
107
+
108
+ // Pullquote — centered italic serif with the oversized quote mark
109
+ blockquote {
110
+ margin: 2.4em 0;
111
+ padding: 0 1em;
112
+ text-align: center;
113
+ border: 0;
114
+
115
+ &::before {
116
+ content: "\201C";
117
+ display: block;
118
+ font-family: $nf-font-display;
119
+ font-weight: 900;
120
+ font-size: 4rem;
121
+ line-height: 0.6;
122
+ color: var(--bs-primary);
123
+ margin-bottom: 0.25em;
124
+ }
125
+
126
+ p {
127
+ font-family: $nf-font-display;
128
+ font-style: italic;
129
+ font-weight: 550;
130
+ font-size: clamp(1.4rem, 2.6vw, 1.9rem);
131
+ letter-spacing: -0.01em;
132
+ line-height: 1.3;
133
+ margin: 0;
134
+ }
135
+
136
+ cite {
137
+ display: block;
138
+ margin-top: 1.1em;
139
+ font-family: $font-family-sans-serif;
140
+ font-style: normal;
141
+ font-weight: 700;
142
+ font-size: 0.78rem;
143
+ letter-spacing: 0.12em;
144
+ text-transform: uppercase;
145
+ color: var(--bs-secondary-color);
146
+ }
147
+ }
148
+
149
+ // List markers pick up the accent
150
+ li::marker {
151
+ color: var(--bs-primary);
152
+ }
153
+ }
154
+
155
+ // Tag row sits on a hairline rule
156
+ .tag-row {
157
+ border-top: var(--nf-border);
158
+ }
159
+
160
+ @media (max-width: 767.98px) {
161
+ .blog-post-content {
162
+ font-size: 1.05rem;
163
+ }
164
+ }
@@ -0,0 +1,159 @@
1
+ // Newsflash Theme — Homepage page-specific CSS
2
+ // Styles the editorial front-page override
3
+ // (_layouts/themes/newsflash/frontend/pages/index.html).
4
+ //
5
+ // Class names are UNIVERSAL (section-hero, hero-title, feed-num, rail-title,
6
+ // mostread, stat-num, cta-panel, Bootstrap .card/.badge …) — no theme prefix —
7
+ // so the same markup is swappable across themes. This file gives those classes
8
+ // the newsflash look. Compiles standalone, so it pulls in the theme tokens +
9
+ // mixins via loadPaths.
10
+ @use 'config' as *;
11
+ @import 'css/base/mixins';
12
+
13
+ // ============================================
14
+ // Hero — the front-page lead
15
+ // ============================================
16
+ .section-hero {
17
+ padding-top: clamp(2.5rem, 5vw, 4rem);
18
+ }
19
+
20
+ .hero-title {
21
+ font-size: clamp(2.6rem, 5.4vw, 4.4rem);
22
+ font-weight: 550;
23
+ letter-spacing: -0.022em;
24
+ line-height: 1.04;
25
+ }
26
+
27
+ .hero-art {
28
+ .art-frame {
29
+ aspect-ratio: 4 / 3;
30
+ @include nf-shadow-pop();
31
+ }
32
+
33
+ .hero-art-chip {
34
+ position: absolute;
35
+ top: 18px;
36
+ left: -14px;
37
+ transform: rotate(-4deg);
38
+ z-index: 2;
39
+ }
40
+ }
41
+
42
+ // Decorative cover art (pre-content fallback when the site has no posts yet):
43
+ // vermilion-to-orange wash with a blue corner glow — pure CSS, no asset.
44
+ .cover-art {
45
+ background:
46
+ radial-gradient(110% 90% at 88% 8%, #FFB36B 0%, rgba(255, 179, 107, 0) 52%),
47
+ radial-gradient(120% 110% at 8% 95%, var(--nf-blue) 0%, rgba(39, 66, 245, 0) 56%),
48
+ linear-gradient(155deg, var(--nf-vermilion) 10%, #FF7A3D 90%);
49
+ }
50
+
51
+ // ============================================
52
+ // The rundown — stroked step numerals on dashed rows
53
+ // ============================================
54
+ // (The latest feed uses .feed-item's BASE layout from _editorial.scss —
55
+ // square art thumb + text. Only the rundown swaps the thumb for a numeral.)
56
+ .feed-num {
57
+ font-family: $nf-font-display;
58
+ font-style: italic;
59
+ font-weight: 800;
60
+ font-size: 3.2rem;
61
+ line-height: 1;
62
+ color: transparent;
63
+ -webkit-text-stroke: 1.5px var(--nf-ink);
64
+ }
65
+
66
+ // On rundown rows the numeral replaces the thumbnail — shrink its column
67
+ .feed-item .feed-num {
68
+ width: 5rem;
69
+ }
70
+ .section-rundown .feed-item {
71
+ grid-template-columns: 5rem 1fr;
72
+ }
73
+
74
+ // ============================================
75
+ // The rail (sticky sidebar)
76
+ // ============================================
77
+ .rail-stack {
78
+ position: sticky;
79
+ top: 5.75rem; // clears the sticky masthead
80
+ }
81
+
82
+ .rail-title {
83
+ display: flex;
84
+ align-items: center;
85
+ gap: 0.6em;
86
+ font-weight: 800;
87
+ font-size: 0.8rem;
88
+ letter-spacing: 0.14em;
89
+ text-transform: uppercase;
90
+ margin-bottom: 1rem;
91
+
92
+ &::after {
93
+ content: "";
94
+ flex: 1;
95
+ height: var(--nf-border-width);
96
+ background: var(--nf-border-color);
97
+ }
98
+ }
99
+
100
+ // Most-read list — stroked counter numerals that ink in on hover
101
+ .mostread {
102
+ counter-reset: mostread;
103
+
104
+ li {
105
+ counter-increment: mostread;
106
+ display: flex;
107
+ gap: 1rem;
108
+ align-items: flex-start;
109
+ padding: 0.8rem 0;
110
+ border-bottom: 1px solid var(--nf-line);
111
+
112
+ &:first-child { padding-top: 0; }
113
+ &:last-child { border-bottom: 0; padding-bottom: 0; }
114
+
115
+ &::before {
116
+ content: counter(mostread);
117
+ font-family: $nf-font-display;
118
+ font-style: italic;
119
+ font-weight: 900;
120
+ font-size: 2rem;
121
+ line-height: 1;
122
+ color: transparent;
123
+ -webkit-text-stroke: 1.3px var(--nf-ink);
124
+ flex: none;
125
+ width: 1.2em;
126
+ transition: $nf-transition;
127
+ }
128
+
129
+ &:hover::before {
130
+ color: var(--bs-primary);
131
+ -webkit-text-stroke-color: var(--bs-primary);
132
+ }
133
+ }
134
+
135
+ a {
136
+ font-weight: 700;
137
+ font-size: 0.95rem;
138
+ line-height: 1.35;
139
+ color: inherit;
140
+ text-decoration: none;
141
+
142
+ &:hover {
143
+ color: var(--bs-primary);
144
+ }
145
+ }
146
+ }
147
+
148
+ // Newsletter rail — the vermilion slab gets the hard offset shadow
149
+ .rail-stack .card.bg-primary {
150
+ box-shadow: var(--nf-shadow-hard-hover) !important;
151
+ }
152
+
153
+ // (Feature icon chips, stats numerals + the CTA band live in the main bundle — _panels.scss —
154
+ // because pricing/about reuse them. Reader quote-cards live in pages/about/index.scss —
155
+ // the testimonials section moved to the about page.)
156
+
157
+ @media (max-width: 991.98px) {
158
+ .rail-stack { position: static; }
159
+ }