ultimate-jekyll-manager 1.4.3 → 1.6.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 (66) hide show
  1. package/CHANGELOG.md +36 -0
  2. package/CLAUDE-ATTRIBUTION.md +215 -0
  3. package/CLAUDE.md +7 -6
  4. package/README.md +1 -0
  5. package/dist/assets/css/pages/test/libraries/layers/index.scss +28 -0
  6. package/dist/assets/js/modules/redirect.js +5 -4
  7. package/dist/assets/js/pages/download/index.js +1 -1
  8. package/dist/assets/js/pages/feedback/index.js +1 -1
  9. package/dist/assets/js/pages/test/libraries/layers/index.js +11 -0
  10. package/dist/assets/themes/_template/README.md +50 -0
  11. package/dist/assets/themes/_template/_config.scss +60 -0
  12. package/dist/assets/themes/_template/_theme.js +13 -4
  13. package/dist/assets/themes/_template/_theme.scss +16 -4
  14. package/dist/assets/themes/_template/css/base/_root.scss +19 -0
  15. package/dist/assets/themes/_template/css/components/_components.scss +23 -0
  16. package/dist/assets/themes/classy/README.md +18 -6
  17. package/dist/assets/themes/neobrutalism/README.md +98 -0
  18. package/dist/assets/themes/neobrutalism/_config.scss +139 -0
  19. package/dist/assets/themes/neobrutalism/_theme.js +27 -0
  20. package/dist/assets/themes/neobrutalism/_theme.scss +33 -0
  21. package/dist/assets/themes/neobrutalism/css/base/_mixins.scss +46 -0
  22. package/dist/assets/themes/neobrutalism/css/base/_root.scss +80 -0
  23. package/dist/assets/themes/neobrutalism/css/base/_typography.scss +77 -0
  24. package/dist/assets/themes/neobrutalism/css/base/_utilities.scss +25 -0
  25. package/dist/assets/themes/neobrutalism/css/components/_buttons.scss +148 -0
  26. package/dist/assets/themes/neobrutalism/css/components/_cards.scss +69 -0
  27. package/dist/assets/themes/neobrutalism/css/components/_forms.scss +88 -0
  28. package/dist/assets/themes/neobrutalism/css/components/_infinite-scroll.scss +94 -0
  29. package/dist/assets/themes/neobrutalism/css/layout/_general.scss +200 -0
  30. package/dist/assets/themes/neobrutalism/css/layout/_navigation.scss +153 -0
  31. package/dist/assets/themes/neobrutalism/js/initialize-tooltips.js +20 -0
  32. package/dist/assets/themes/neobrutalism/js/navbar-scroll.js +29 -0
  33. package/dist/assets/themes/neobrutalism/pages/index.scss +227 -0
  34. package/dist/assets/themes/neobrutalism/pages/pricing/index.scss +267 -0
  35. package/dist/assets/themes/neobrutalism/pages/test/libraries/layers/index.js +9 -0
  36. package/dist/assets/themes/neobrutalism/pages/test/libraries/layers/index.scss +7 -0
  37. package/dist/build.js +2 -5
  38. package/dist/commands/install.js +1 -1
  39. package/dist/commands/setup.js +41 -0
  40. package/dist/defaults/CLAUDE.md +5 -1
  41. package/dist/defaults/dist/_includes/core/head.html +17 -0
  42. package/dist/defaults/dist/_includes/themes/classy/frontend/sections/footer.html +4 -4
  43. package/dist/defaults/dist/_layouts/themes/classy/frontend/pages/download.html +2 -0
  44. package/dist/defaults/dist/_layouts/themes/classy/frontend/pages/feedback.html +7 -3
  45. package/dist/defaults/dist/_layouts/themes/neobrutalism/frontend/core/base.html +31 -0
  46. package/dist/defaults/dist/_layouts/themes/neobrutalism/frontend/pages/index.html +345 -0
  47. package/dist/defaults/dist/_layouts/themes/neobrutalism/frontend/pages/pricing.html +483 -0
  48. package/dist/defaults/dist/pages/test/libraries/layers.html +57 -0
  49. package/dist/defaults/src/_config.yml +2 -0
  50. package/dist/defaults/test/_init.js +10 -0
  51. package/dist/gulp/tasks/defaults.js +8 -0
  52. package/dist/gulp/tasks/sass.js +43 -2
  53. package/dist/gulp/tasks/translation.js +11 -0
  54. package/dist/gulp/tasks/utils/manage-test-layers.js +97 -0
  55. package/dist/index.js +30 -4
  56. package/dist/test/runner.js +62 -0
  57. package/dist/test/suites/build/manager.test.js +11 -4
  58. package/dist/test/suites/build/mode-helpers.test.js +54 -2
  59. package/dist/utils/mode-helpers.js +65 -40
  60. package/docs/assets.md +6 -1
  61. package/docs/environment-detection.md +85 -0
  62. package/docs/test-framework.md +48 -3
  63. package/docs/themes.md +451 -0
  64. package/package.json +2 -1
  65. package/docs/cross-context-helpers.md +0 -75
  66. package/package copy.json +0 -75
@@ -2,21 +2,28 @@
2
2
 
3
3
  ## How to Customize in Your Consuming Project
4
4
 
5
- The Classy theme is designed to be fully customizable. All theme variables use `!default` which means you can override them BEFORE importing the theme.
5
+ The Classy theme is designed to be fully customizable. All theme variables use `!default` which means you can override them BEFORE the theme is imported.
6
+
7
+ > **How the import actually resolves:** Your project's `src/assets/css/main.scss`
8
+ > does `@use 'ultimate-jekyll-manager' as *;`. That entry point `@forward`s the
9
+ > theme, and UJM's SASS `loadPaths` resolve `theme` to whichever
10
+ > `src/assets/themes/<theme.id>/_theme.scss` wins — your project's copy first,
11
+ > then UJM's packaged copy. You never import the theme file by path directly.
12
+ > See [`docs/themes.md`](../../../../docs/themes.md) for the full mechanism.
6
13
 
7
14
  ### Example: Customizing Colors in Your Project
8
15
 
9
16
  In your consuming project's `src/assets/css/main.scss`:
10
17
 
11
18
  ```scss
12
- // 1. Override Classy theme variables BEFORE importing the theme
13
- $primary: #FF0000; // Change primary color to red
19
+ // 1. Override Classy theme variables FIRST (they are !default, so yours win)
20
+ $primary: #FF0000; // Change primary color to red
14
21
  $classy-bg-light: #F5F5F5; // Change light mode background
15
- $classy-bg-dark: #1A1A1A; // Change dark mode background
22
+ $classy-bg-dark: #1A1A1A; // Change dark mode background
16
23
  $font-family-sans-serif: 'Inter', sans-serif; // Change font
17
24
 
18
- // 2. Now import the Classy theme - it will use YOUR values
19
- @import '~ultimate-jekyll-manager/src/assets/themes/classy/theme';
25
+ // 2. Import the framework it loads the theme using YOUR values above
26
+ @use 'ultimate-jekyll-manager' as *;
20
27
 
21
28
  // 3. Add your custom styles below
22
29
  .my-custom-class {
@@ -24,6 +31,11 @@ $font-family-sans-serif: 'Inter', sans-serif; // Change font
24
31
  }
25
32
  ```
26
33
 
34
+ To customize beyond variables — change actual component styles or markup —
35
+ **shadow the theme**: create `src/assets/themes/classy/` in your project. UJM's
36
+ loadPaths resolve your copy before the packaged one. (To build a wholly new
37
+ look, author a new theme instead — see `docs/themes.md`.)
38
+
27
39
  ## Available Customizable Variables
28
40
 
29
41
  See `_config.scss` for the full list of variables you can override:
@@ -0,0 +1,98 @@
1
+ # Neobrutalism Theme
2
+
3
+ A bold, high-contrast UJM theme built on the neobrutalist design language:
4
+ **pure-ink borders, hard offset shadows (no blur), zero border-radius, chunky
5
+ grotesk display type, and flat saturated color blocks.** Buttons and cards
6
+ "press" into the page on interaction. Full light + dark mode support.
7
+
8
+ > See [`docs/themes.md`](../../../../docs/themes.md) for how the theme system
9
+ > works and how to author your own theme (inside UJM or in a consumer project).
10
+
11
+ ## Use it
12
+
13
+ In your consuming project's `src/_config.yml`:
14
+
15
+ ```yaml
16
+ theme:
17
+ id: "neobrutalism"
18
+ appearance: "light" # or "dark" / "system"
19
+ ```
20
+
21
+ That's it — every layout, nav, footer, and page is inherited from the shared
22
+ defaults (via the Classy layout fallback) and restyled in neobrutalist form.
23
+
24
+ ## Customize it (without editing the theme)
25
+
26
+ All design tokens are `!default` variables. Override them **before** the theme
27
+ is imported — in your project's `src/assets/css/main.scss`, set the variables,
28
+ then `@use 'ultimate-jekyll-manager' as *;`:
29
+
30
+ ```scss
31
+ // Change the accent + structure, then import the framework (which loads the theme)
32
+ $primary: #FF5C00; // your brand color
33
+ $nb-border-width: 4px; // chunkier borders
34
+ $nb-shadow-offset: 7px; // deeper hard shadow
35
+ $nb-accent-yellow: #D4FF00; // swap the signature highlight
36
+
37
+ @use 'ultimate-jekyll-manager' as *;
38
+ ```
39
+
40
+ ### Key tokens (see `_config.scss` for the full list)
41
+
42
+ | Token | Purpose | Default |
43
+ |---|---|---|
44
+ | `$primary` … `$danger` | Bootstrap semantic colors | electric blue, hot pink, etc. |
45
+ | `$nb-ink` / `$nb-paper` | Border/shadow color + page surface (light) | `#111` / `#FFFEF2` |
46
+ | `$nb-ink-dark` / `$nb-paper-dark` | Same, dark mode | `#F5F5F5` / `#16161A` |
47
+ | `$nb-border-width` | Standard border thickness | `3px` |
48
+ | `$nb-shadow-offset` | Hard shadow distance | `5px` |
49
+ | `$nb-accent-*` | Color-block palette | blue/pink/yellow/green/purple/orange |
50
+ | `$nb-font-display` | Heading font | `Archivo` |
51
+ | `$font-family-sans-serif` | Body font | `Space Grotesk` |
52
+
53
+ > Fonts are loaded via the theme's `head` block in the base layout. If you
54
+ > change the font tokens, update the Google Fonts `<link>` accordingly (in your
55
+ > page/layout `theme.head.content`, or by overriding the base layout).
56
+
57
+ ## No theme-prefixed classes
58
+
59
+ This theme deliberately uses **NO `nb-` prefixed classes in markup** — so the same
60
+ HTML is swappable across themes (change `theme.id`, done). It styles:
61
+
62
+ - **Standard Bootstrap classes** wherever they fit: `.card` (the canonical container —
63
+ gets the ink frame + hard shadow), `.btn` / `.btn-primary` / `.btn-warning` (yellow
64
+ accent), `.text-bg-{primary,secondary,success,warning,…}` (the color-block fills),
65
+ `.border`, `.shadow`, `.accordion`, `.badge`.
66
+ - **Universal semantic layout classes** for structures with no Bootstrap equivalent:
67
+ `.section-hero`, `.hero-title`, `.action-block`, `.logo-strip`, `.showcase-row`,
68
+ `.step-card`, `.stat-block`, `.cta-panel`, `.pricing-plan`, `.billing-toggle`,
69
+ `.kicker`, `.highlight`. Any theme can style these same names. See
70
+ [docs/themes.md → Universal layout classes](../../../../docs/themes.md).
71
+
72
+ The `nb-` prefix survives ONLY on SCSS internals (the `$nb-*` config tokens, `--nb-*`
73
+ CSS variables, and `@mixin nb-border/nb-shadow/nb-press`) — these never appear in HTML.
74
+
75
+ ## Structure
76
+
77
+ ```
78
+ neobrutalism/
79
+ ├── _config.scss ← all customizable tokens (!default) + Bootstrap forward
80
+ ├── _theme.scss ← entry point (config → mixins → root → base → layout → components → bootstrap overrides)
81
+ ├── _theme.js ← JS entry (Bootstrap UMD + behaviors on DOM ready)
82
+ ├── css/
83
+ │ ├── base/
84
+ │ │ ├── _mixins.scss ← nb-border / nb-shadow / nb-press (the SSOT for the look)
85
+ │ │ ├── _root.scss ← SCSS → CSS-variable bridge (light/dark)
86
+ │ │ ├── _typography.scss
87
+ │ │ └── _utilities.scss
88
+ │ ├── layout/
89
+ │ │ ├── _general.scss ← sections, hero, footer, gradient/accent overrides
90
+ │ │ └── _navigation.scss
91
+ │ └── components/
92
+ │ ├── _buttons.scss
93
+ │ ├── _cards.scss
94
+ │ └── _forms.scss
95
+ └── js/
96
+ ├── navbar-scroll.js
97
+ └── initialize-tooltips.js
98
+ ```
@@ -0,0 +1,139 @@
1
+ // Neobrutalism Theme Configuration
2
+ // ALL customizable variables are defined here with !default.
3
+ // Consuming projects override any of these BEFORE the theme is imported.
4
+ //
5
+ // Design language: raw, high-contrast color blocks; pure-black hard borders;
6
+ // hard offset shadows (no blur); zero border-radius; chunky grotesk type.
7
+ // This is NOT a recolored Classy — the shadow/border/press system is the identity.
8
+
9
+ // ============================================
10
+ // Bootstrap Color Overrides
11
+ // ============================================
12
+ // Loud, saturated, high-contrast. These map onto Bootstrap's semantic colors.
13
+ $primary: #2563EB !default; // electric blue
14
+ $secondary: #EC4899 !default; // hot pink
15
+ $success: #16A34A !default; // grass green
16
+ $info: #06B6D4 !default; // cyan
17
+ $warning: #FACC15 !default; // acid yellow
18
+ $danger: #EF4444 !default; // red
19
+ $light: #FFFEF2 !default; // paper white (warm off-white)
20
+ $dark: #111111 !default; // near-black
21
+
22
+ // ============================================
23
+ // Ink & Paper (the structural neutrals)
24
+ // ============================================
25
+ // "Ink" = the universal border/shadow color. "Paper" = the page surface.
26
+ $nb-ink: #111111 !default; // borders + hard shadows (light mode)
27
+ $nb-paper: #FFFEF2 !default; // body background (light mode)
28
+ $nb-surface: #FFFFFF !default; // cards / elevated surfaces (light mode)
29
+ $nb-surface-alt: #F4F1E4 !default; // alt sections / wells (light mode)
30
+
31
+ // Dark mode counterparts
32
+ $nb-ink-dark: #F5F5F5 !default; // borders + shadows become near-white
33
+ $nb-paper-dark: #16161A !default; // body background (dark mode)
34
+ $nb-surface-dark: #1F1F25 !default; // cards (dark mode)
35
+ $nb-surface-alt-dark: #25252D !default; // alt sections (dark mode)
36
+
37
+ // ============================================
38
+ // Accent Palette (for color-block sections, tags, highlights)
39
+ // ============================================
40
+ // Used directly as section backgrounds and decorative blocks.
41
+ $nb-accent-blue: #2563EB !default;
42
+ $nb-accent-pink: #EC4899 !default;
43
+ $nb-accent-yellow: #FACC15 !default;
44
+ $nb-accent-green: #16A34A !default;
45
+ $nb-accent-purple: #8B5CF6 !default;
46
+ $nb-accent-orange: #FB923C !default;
47
+
48
+ // ============================================
49
+ // Borders — the defining structural element
50
+ // ============================================
51
+ $nb-border-width: 3px !default; // standard border thickness
52
+ $nb-border-width-lg: 4px !default; // emphasis (hero buttons, feature cards)
53
+ $nb-border-width-sm: 2px !default; // small controls (inputs, tags)
54
+ $nb-border-color: $nb-ink !default; // remapped to ink-dark in dark mode via _root
55
+ $nb-border: $nb-border-width solid $nb-border-color !default;
56
+
57
+ // Zero radius everywhere — this is the neobrutalist signature.
58
+ $border-radius: 0 !default;
59
+ $border-radius-sm: 0 !default;
60
+ $border-radius-lg: 0 !default;
61
+ $border-radius-xl: 0 !default;
62
+ $border-radius-2xl: 0 !default;
63
+ $border-radius-pill: 0 !default;
64
+
65
+ // ============================================
66
+ // Hard Offset Shadows — the second defining element
67
+ // ============================================
68
+ // No blur, no spread — a solid block offset down-right in ink color.
69
+ $nb-shadow-offset: 5px !default; // default offset distance
70
+ $nb-shadow-offset-sm: 3px !default;
71
+ $nb-shadow-offset-lg: 8px !default;
72
+ $nb-shadow-color: $nb-ink !default; // remapped in dark mode via _root
73
+
74
+ $nb-shadow-sm: $nb-shadow-offset-sm $nb-shadow-offset-sm 0 $nb-shadow-color !default;
75
+ $nb-shadow: $nb-shadow-offset $nb-shadow-offset 0 $nb-shadow-color !default;
76
+ $nb-shadow-lg: $nb-shadow-offset-lg $nb-shadow-offset-lg 0 $nb-shadow-color !default;
77
+
78
+ // ============================================
79
+ // Typography
80
+ // ============================================
81
+ // Chunky geometric grotesk for display; clean grotesk for body.
82
+ $font-family-sans-serif: 'Space Grotesk', -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, 'Helvetica Neue', Arial, sans-serif !default;
83
+ $nb-font-display: 'Archivo', 'Space Grotesk', sans-serif !default;
84
+ $nb-font-mono: 'Space Mono', ui-monospace, SFMono-Regular, Menlo, monospace !default;
85
+
86
+ $headings-font-weight: 800 !default;
87
+ $nb-heading-letter-spacing: -0.02em !default;
88
+ $font-weight-bold: 700 !default;
89
+
90
+ // ============================================
91
+ // Motion — snappy, mechanical, no easing softness
92
+ // ============================================
93
+ // Neobrutalism favors instant/linear motion over smooth cubic-beziers.
94
+ $nb-transition-fast: all 0.08s ease-out !default;
95
+ $nb-transition: all 0.12s ease-out !default;
96
+
97
+ // ============================================
98
+ // Component Sizing
99
+ // ============================================
100
+ // Avatar sizes map (matches Classy so shared layouts/includes render correctly)
101
+ $avatar-sizes: (
102
+ null: 3rem,
103
+ 2xs: 0.5rem,
104
+ xs: 1.5rem,
105
+ sm: 2rem,
106
+ md: 2.5rem,
107
+ lg: 3.5rem,
108
+ xl: 5rem,
109
+ 2xl: 7.5rem,
110
+ 3xl: 10rem,
111
+ 4xl: 12.5rem,
112
+ 5xl: 15rem
113
+ ) !default;
114
+
115
+ // ============================================
116
+ // Forward Bootstrap with our configuration
117
+ // ============================================
118
+ @forward '../bootstrap/scss/bootstrap.scss' with (
119
+ $primary: $primary,
120
+ $secondary: $secondary,
121
+ $success: $success,
122
+ $info: $info,
123
+ $warning: $warning,
124
+ $danger: $danger,
125
+ $light: $light,
126
+ $dark: $dark,
127
+ $font-family-sans-serif: $font-family-sans-serif,
128
+ $headings-font-weight: $headings-font-weight,
129
+ $font-weight-bold: $font-weight-bold,
130
+ $border-radius: $border-radius,
131
+ $border-radius-sm: $border-radius-sm,
132
+ $border-radius-lg: $border-radius-lg,
133
+ // Neobrutalism uses solid borders everywhere, so Bootstrap's default
134
+ // border width is bumped and box-shadow softness is disabled.
135
+ $border-width: $nb-border-width,
136
+ $enable-rounded: false,
137
+ $enable-shadows: false,
138
+ $enable-negative-margins: true
139
+ );
@@ -0,0 +1,27 @@
1
+ // Neobrutalism Theme — JS entry point
2
+ // Loaded at runtime via webpack's __theme__ alias (import('__theme__/_theme.js')).
3
+ // Exposes Bootstrap globally and wires up theme behaviors on DOM ready.
4
+ import bootstrap from '__main_assets__/themes/bootstrap/js/index.umd.js';
5
+ import { ready as domReady } from 'web-manager/modules/dom.js';
6
+
7
+ // Make Bootstrap available globally (used by UJM utilities + components)
8
+ window.bootstrap = bootstrap;
9
+
10
+ /* @dev-only:start */
11
+ {
12
+ console.log('Neobrutalism theme loaded successfully (assets/themes/neobrutalism/_theme.js)');
13
+ }
14
+ /* @dev-only:end */
15
+
16
+ // Theme behaviors
17
+ import setupNavbarScroll from './js/navbar-scroll.js';
18
+ import initializeTooltips from './js/initialize-tooltips.js';
19
+
20
+ // Initialize when DOM is ready
21
+ domReady().then(() => {
22
+ // Neobrutalism behaviors
23
+ setupNavbarScroll();
24
+
25
+ // Generic Bootstrap initializations
26
+ initializeTooltips();
27
+ });
@@ -0,0 +1,33 @@
1
+ // Neobrutalism Theme — SCSS entry point
2
+ // Forwards config (so consuming projects can override vars), loads Bootstrap via
3
+ // config, then layers the neobrutalist system on top. Import order matters:
4
+ // config → mixins → root vars → base → layout → components → bootstrap overrides.
5
+
6
+ // Forward theme configuration (allows consuming project to override)
7
+ @forward 'config';
8
+ @use 'config' as *;
9
+
10
+ // Mixins must be available to every partial below.
11
+ // @import (not @use) so the mixins land in the global scope the @imports share.
12
+ @import 'css/base/mixins';
13
+
14
+ // CSS custom properties (light/dark bridge)
15
+ @import 'css/base/root';
16
+
17
+ // Base styles
18
+ @import 'css/base/typography';
19
+ @import 'css/base/utilities';
20
+
21
+ // Layout styles
22
+ @import 'css/layout/general';
23
+ @import 'css/layout/navigation';
24
+
25
+ // Component styles
26
+ @import 'css/components/buttons';
27
+ @import 'css/components/cards';
28
+ @import 'css/components/forms';
29
+ @import 'css/components/infinite-scroll';
30
+
31
+ // Universal Bootstrap overrides (shared across all UJ themes).
32
+ // Must come AFTER Bootstrap is loaded via config to use @extend.
33
+ @import '../bootstrap/overrides';
@@ -0,0 +1,46 @@
1
+ // Neobrutalism Theme — Mixins
2
+ // The shared building blocks of the neobrutalist look. Components @include these
3
+ // so the border/shadow/press system lives in ONE place (SSOT) rather than being
4
+ // copy-pasted across buttons, cards, inputs, etc.
5
+
6
+ // Hard border in the current ink color.
7
+ @mixin nb-border($width: var(--nb-border-width)) {
8
+ border: $width solid var(--nb-border-color);
9
+ }
10
+
11
+ // Hard offset shadow (no blur). $size: sm | md | lg.
12
+ @mixin nb-shadow($size: md) {
13
+ @if $size == sm {
14
+ box-shadow: var(--nb-shadow-sm);
15
+ } @else if $size == lg {
16
+ box-shadow: var(--nb-shadow-lg);
17
+ } @else {
18
+ box-shadow: var(--nb-shadow);
19
+ }
20
+ }
21
+
22
+ // The signature interaction: the element sits on a hard offset shadow, then
23
+ // "presses" toward the page on hover/active. THE INVARIANT: the element's
24
+ // translate distance + the shrunk shadow offset must always equal the RESTING
25
+ // shadow offset, so the bottom-right edge stays perfectly pinned (the face and
26
+ // shadow line up exactly when the press completes — no drift).
27
+ //
28
+ // $rest = the element's resting shadow offset. Pass the SAME size you gave
29
+ // nb-shadow() (default 5px = md; pass $nb-shadow-offset-lg for lg-shadow elements).
30
+ @mixin nb-press($rest: $nb-shadow-offset) {
31
+ transition: $nb-transition;
32
+
33
+ // Hover: press ~40% of the way in. shadow = rest - translate (stays pinned).
34
+ &:hover {
35
+ $hover-move: round($rest * 0.4);
36
+ $hover-shadow: $rest - $hover-move;
37
+ transform: translate($hover-move, $hover-move);
38
+ box-shadow: #{$hover-shadow} #{$hover-shadow} 0 var(--nb-shadow-color);
39
+ }
40
+
41
+ // Active: press fully in. translate == rest, shadow collapses to 0 → flush.
42
+ &:active {
43
+ transform: translate($rest, $rest);
44
+ box-shadow: 0 0 0 var(--nb-shadow-color);
45
+ }
46
+ }
@@ -0,0 +1,80 @@
1
+ // Neobrutalism Theme — CSS Custom Properties
2
+ // Bridges SCSS config into runtime CSS variables so light/dark mode switching
3
+ // works without recompilation. Components read these var(--nb-*) tokens, never
4
+ // the raw SCSS values, so dark mode is a single block of overrides.
5
+
6
+ // ============================================
7
+ // Light Mode (default)
8
+ // ============================================
9
+ :root,
10
+ [data-bs-theme="light"] {
11
+ // Structural tokens
12
+ --nb-ink: #{$nb-ink};
13
+ --nb-paper: #{$nb-paper};
14
+ --nb-surface: #{$nb-surface};
15
+ --nb-surface-alt: #{$nb-surface-alt};
16
+
17
+ // Height of the fixed navbar — the first section adds this to its top padding
18
+ // so content clears the overlapping nav (see _general.scss "Section rhythm").
19
+ --nb-navbar-height: 4.5rem;
20
+
21
+ // Border + shadow color follow the ink
22
+ --nb-border-color: var(--nb-ink);
23
+ --nb-shadow-color: var(--nb-ink);
24
+
25
+ // Border + shadow recipes (used by components)
26
+ --nb-border-width: #{$nb-border-width};
27
+ --nb-border: #{$nb-border-width} solid var(--nb-border-color);
28
+ --nb-shadow-sm: #{$nb-shadow-offset-sm} #{$nb-shadow-offset-sm} 0 var(--nb-shadow-color);
29
+ --nb-shadow: #{$nb-shadow-offset} #{$nb-shadow-offset} 0 var(--nb-shadow-color);
30
+ --nb-shadow-lg: #{$nb-shadow-offset-lg} #{$nb-shadow-offset-lg} 0 var(--nb-shadow-color);
31
+
32
+ // Accent palette (for color-block sections)
33
+ --nb-accent-blue: #{$nb-accent-blue};
34
+ --nb-accent-pink: #{$nb-accent-pink};
35
+ --nb-accent-yellow: #{$nb-accent-yellow};
36
+ --nb-accent-green: #{$nb-accent-green};
37
+ --nb-accent-purple: #{$nb-accent-purple};
38
+ --nb-accent-orange: #{$nb-accent-orange};
39
+
40
+ // INTERACTIVE accent — the single token every hover/active fill points at
41
+ // (nav links, footer links, dropdown items, body links, mobile toggler). It
42
+ // tracks the rendered primary blue (--bs-primary), NOT the yellow signature
43
+ // accent. Retune all interactive states from this one line. Yellow stays
44
+ // reserved for static signature blocks (kicker, highlight, hero, badges).
45
+ --nb-accent-interactive: var(--bs-primary);
46
+ --nb-accent-interactive-ink: #ffffff; // readable text on the interactive fill
47
+
48
+ // Map onto Bootstrap surfaces
49
+ --bs-body-bg: #{$nb-paper};
50
+ --bs-body-bg-rgb: #{red($nb-paper)}, #{green($nb-paper)}, #{blue($nb-paper)};
51
+ --bs-body-color: #{$nb-ink};
52
+ --bs-secondary-bg: #{$nb-surface};
53
+ --bs-tertiary-bg: #{$nb-surface-alt};
54
+ --bs-border-color: var(--nb-ink);
55
+ --bs-card-bg: #{$nb-surface};
56
+ --bs-emphasis-color: #{$nb-ink};
57
+ }
58
+
59
+ // ============================================
60
+ // Dark Mode
61
+ // ============================================
62
+ // Ink flips to near-white: borders and hard shadows become light on dark paper.
63
+ [data-bs-theme="dark"] {
64
+ --nb-ink: #{$nb-ink-dark};
65
+ --nb-paper: #{$nb-paper-dark};
66
+ --nb-surface: #{$nb-surface-dark};
67
+ --nb-surface-alt: #{$nb-surface-alt-dark};
68
+
69
+ --nb-border-color: var(--nb-ink);
70
+ --nb-shadow-color: var(--nb-ink);
71
+
72
+ --bs-body-bg: #{$nb-paper-dark};
73
+ --bs-body-bg-rgb: #{red($nb-paper-dark)}, #{green($nb-paper-dark)}, #{blue($nb-paper-dark)};
74
+ --bs-body-color: #{$nb-ink-dark};
75
+ --bs-secondary-bg: #{$nb-surface-dark};
76
+ --bs-tertiary-bg: #{$nb-surface-alt-dark};
77
+ --bs-border-color: var(--nb-ink);
78
+ --bs-card-bg: #{$nb-surface-dark};
79
+ --bs-emphasis-color: #{$nb-ink-dark};
80
+ }
@@ -0,0 +1,77 @@
1
+ // Neobrutalism Theme — Typography
2
+ // Chunky, confident, tightly-tracked headings; clean grotesk body.
3
+ // Fonts are loaded via the theme's `head` block in base.html (Google Fonts),
4
+ // NOT @import-ed here, to avoid render-blocking duplicate loads.
5
+
6
+ body {
7
+ font-family: $font-family-sans-serif;
8
+ font-weight: 400;
9
+ -webkit-font-smoothing: antialiased;
10
+ }
11
+
12
+ h1, h2, h3, h4, h5, h6,
13
+ .h1, .h2, .h3, .h4, .h5, .h6 {
14
+ font-family: $nb-font-display;
15
+ font-weight: $headings-font-weight;
16
+ letter-spacing: $nb-heading-letter-spacing;
17
+ line-height: 1.05;
18
+ text-wrap: balance;
19
+ }
20
+
21
+ // Display headings get extra weight + tighter tracking
22
+ .display-1, .display-2, .display-3, .display-4, .display-5, .display-6 {
23
+ font-family: $nb-font-display;
24
+ font-weight: 900;
25
+ letter-spacing: -0.03em;
26
+ line-height: 0.98;
27
+ }
28
+
29
+ // Monospace accents (kickers, labels, code-ish tags)
30
+ .font-mono,
31
+ code, kbd, samp, pre {
32
+ font-family: $nb-font-mono;
33
+ }
34
+
35
+ // Eyebrow / kicker label — universal "section kicker" above headlines.
36
+ .kicker {
37
+ display: inline-block;
38
+ font-family: $nb-font-mono;
39
+ font-weight: 700;
40
+ font-size: 0.8rem;
41
+ text-transform: uppercase;
42
+ letter-spacing: 0.08em;
43
+ padding: 0.35rem 0.65rem;
44
+ background: var(--nb-accent-yellow);
45
+ color: #111111;
46
+ @include nb-border($nb-border-width-sm);
47
+
48
+ // On a dark/ink panel (e.g. the CTA), keep the accent block readable.
49
+ &--invert { background: var(--nb-accent-yellow); color: #111111; }
50
+ }
51
+
52
+ // Highlighted inline text — marker-style background swipe.
53
+ .highlight {
54
+ background: var(--nb-accent-yellow);
55
+ color: #111111;
56
+ padding: 0 0.15em;
57
+ box-decoration-break: clone;
58
+ -webkit-box-decoration-break: clone;
59
+ }
60
+
61
+ // Links: bold, underlined, no fade — they look clickable and stay readable in both
62
+ // modes. Hover shifts to the interactive accent (blue), matching every other hover
63
+ // in the theme. Buttons/nav/dropdown/footer links opt out of this generic rule via
64
+ // their own higher-specificity hover, so this only catches plain in-content links.
65
+ a {
66
+ font-weight: 600;
67
+ text-underline-offset: 0.15em;
68
+ text-decoration-thickness: 2px;
69
+
70
+ &:hover { color: var(--nb-accent-interactive); }
71
+ }
72
+
73
+ // Buttons are <a> too, but set their text via --bs-btn-color. A direct `color` on
74
+ // `a:hover` would beat that var and turn button labels blue — exclude them so the
75
+ // button keeps its own (frozen) text color. Nav/dropdown/footer links already win
76
+ // on specificity with their explicit white hover, so they need no guard here.
77
+ a.btn:hover { color: var(--bs-btn-color); }
@@ -0,0 +1,25 @@
1
+ // Neobrutalism Theme — Base
2
+ // Body surface + neobrutalist treatment of Bootstrap's accent-block utilities.
3
+ // No theme-prefixed classes: the look comes from restyling STANDARD classes
4
+ // (.text-bg-*, .border, .shadow, .card) so markup stays swappable across themes.
5
+
6
+ // Body surface
7
+ body {
8
+ background-color: var(--nb-paper);
9
+ color: var(--bs-body-color);
10
+ }
11
+
12
+ // ============================================
13
+ // Accent blocks: .text-bg-* (Bootstrap) get the hard neobrutalist edge when
14
+ // used as full-bleed section/decorative blocks. Bootstrap already sets the
15
+ // background + a readable contrast color; we just square the corners.
16
+ // (Borders/shadows are added per-component where needed, e.g. .showcase-num.)
17
+ // ============================================
18
+ .text-bg-primary,
19
+ .text-bg-secondary,
20
+ .text-bg-success,
21
+ .text-bg-info,
22
+ .text-bg-warning,
23
+ .text-bg-danger {
24
+ border-radius: 0;
25
+ }