| 1 | /* ------------------------------------------------------------------ */ |
| 2 | /* Home — paper above, sea below */ |
| 3 | /* ------------------------------------------------------------------ */ |
| 4 | /* |
| 5 | * Paper holds the promise and the install command. The live whale rests on |
| 6 | * one horizon line where the paper meets the sea; the real terminal floats |
| 7 | * in the deep water just under it. The reading sections return to paper, |
| 8 | * and the page ends in the sea with the install command, which runs on into |
| 9 | * the footer. Two sea moments, one horizon each; nothing else decorates. |
| 10 | */ |
| 11 | |
| 12 | .home { --home-measure: 36rem; } |
| 13 | |
| 14 | /* ---------- paper: the hero ---------- */ |
| 15 | .home-hero { |
| 16 | position: relative; |
| 17 | padding-block: clamp(3.5rem, 9vw, 7.5rem) 0; |
| 18 | background: var(--bg); |
| 19 | } |
| 20 | |
| 21 | .home-hero-inner { |
| 22 | display: grid; |
| 23 | grid-template-columns: minmax(0, 1.25fr) minmax(0, 0.75fr); |
| 24 | align-items: end; |
| 25 | gap: var(--space-6) clamp(2rem, 6vw, 5rem); |
| 26 | width: var(--container); |
| 27 | margin-inline: auto; |
| 28 | } |
| 29 | |
| 30 | .home-hero-copy { |
| 31 | display: grid; |
| 32 | gap: var(--space-5); |
| 33 | padding-bottom: clamp(3rem, 7vw, 5.5rem); |
| 34 | min-width: 0; |
| 35 | } |
| 36 | |
| 37 | /* Type is the hero's structure: large, tight, set in the brand face. */ |
| 38 | /* Measured in em, not ch, so CJK and long compound words wrap the same as |
| 39 | English; hyphenation lets German compounds break at syllables. */ |
| 40 | .home-title { |
| 41 | max-width: 9.5em; |
| 42 | font-size: clamp(2.5rem, 1.4rem + 4.4vw, 5rem); |
| 43 | hyphens: auto; |
| 44 | font-weight: 650; |
| 45 | line-height: 0.98; |
| 46 | letter-spacing: -0.035em; |
| 47 | text-wrap: balance; |
| 48 | color: var(--text); |
| 49 | } |
| 50 | |
| 51 | .home-lede { |
| 52 | max-width: var(--home-measure); |
| 53 | color: var(--muted); |
| 54 | font-size: clamp(1.0625rem, 1rem + 0.35vw, 1.25rem); |
| 55 | line-height: 1.55; |
| 56 | text-wrap: pretty; |
| 57 | } |
| 58 | .home-lede strong { color: var(--text); font-weight: 600; } |
| 59 | |
| 60 | /* CJK headlines carry more meaning per glyph: a step smaller, wider measure, |
| 61 | and no breaks inside words (Korean) or mid-phrase where avoidable. */ |
| 62 | :lang(zh) .home-title, |
| 63 | :lang(ja) .home-title, |
| 64 | :lang(ko) .home-title { |
| 65 | max-width: 11em; |
| 66 | font-size: clamp(2.125rem, 1.2rem + 3.4vw, 4rem); |
| 67 | line-height: 1.12; |
| 68 | letter-spacing: -0.01em; |
| 69 | word-break: keep-all; |
| 70 | line-break: strict; |
| 71 | } |
| 72 | |
| 73 | .home-hero-copy .hero-install { max-width: 32rem; margin-top: var(--space-2); } |
| 74 | .home-hero-copy .actions { margin-top: calc(var(--space-2) * -1); } |
| 75 | |
| 76 | /* The whale rests on the horizon: its lowest point meets the line. */ |
| 77 | .home-whale { |
| 78 | display: flex; |
| 79 | justify-content: center; |
| 80 | align-self: end; |
| 81 | min-width: 0; |
| 82 | } |
| 83 | .home-whale .whale-live { |
| 84 | --whale-size: clamp(18rem, 40vw, 34rem); |
| 85 | width: var(--whale-size); |
| 86 | /* The rig fills the middle 72% of the canvas; drop its belly onto the |
| 87 | waterline where the tide begins. */ |
| 88 | margin-bottom: calc(var(--whale-size) * -0.26); |
| 89 | position: relative; |
| 90 | z-index: 2; |
| 91 | } |
| 92 | |
| 93 | /* ---------- the live whale ---------- */ |
| 94 | .whale-live { |
| 95 | position: relative; |
| 96 | aspect-ratio: 1; |
| 97 | } |
| 98 | .whale-live > .whale-live-poster, |
| 99 | .whale-live > .whale-live-canvas { |
| 100 | position: absolute; |
| 101 | inset: 0; |
| 102 | width: 100%; |
| 103 | height: 100%; |
| 104 | } |
| 105 | /* The phase, in a word: a small point of light and a label, above the |
| 106 | whale's back. Light means live work (DIRECTION.md). */ |
| 107 | .whale-live-state { |
| 108 | position: absolute; |
| 109 | inset-inline-start: 50%; |
| 110 | top: 8%; |
| 111 | translate: -50% 0; |
| 112 | display: inline-flex; |
| 113 | align-items: center; |
| 114 | gap: var(--space-2); |
| 115 | padding: 0.3rem 0.75rem; |
| 116 | border: 1px solid var(--line); |
| 117 | border-radius: var(--radius-pill); |
| 118 | background: var(--panel); |
| 119 | color: var(--text); |
| 120 | font-size: var(--text-caption); |
| 121 | font-weight: 500; |
| 122 | white-space: nowrap; |
| 123 | box-shadow: 0 6px 18px -10px rgb(11 72 187 / 0.35); |
| 124 | } |
| 125 | .whale-live-dot { |
| 126 | width: 0.45rem; |
| 127 | height: 0.45rem; |
| 128 | border-radius: var(--radius-pill); |
| 129 | background: var(--brand-light); |
| 130 | } |
| 131 | .whale-live-state[data-state="done"] .whale-live-dot { background: var(--live); } |
| 132 | .whale-live-state[data-state="rest"] .whale-live-dot { background: var(--muted); } |
| 133 | @media (prefers-reduced-motion: no-preference) { |
| 134 | .whale-live-state:not([data-state="rest"]):not([data-state="done"]) .whale-live-dot { |
| 135 | animation: whale-pulse 1.4s var(--ease-out) infinite; |
| 136 | } |
| 137 | } |
| 138 | @keyframes whale-pulse { |
| 139 | 0% { box-shadow: 0 0 0 0 rgb(30 143 216 / 0.55); } |
| 140 | 100% { box-shadow: 0 0 0 0.5rem rgb(30 143 216 / 0); } |
| 141 | } |
| 142 | .whale-live-poster { --pose-size: 100%; padding: 14%; box-sizing: border-box; } |
| 143 | .whale-live-canvas { opacity: 0; } |
| 144 | .whale-live[data-ready] .whale-live-canvas { opacity: 1; } |
| 145 | .whale-live[data-ready] .whale-live-poster { visibility: hidden; } |
| 146 | |
| 147 | /* ---------- the sea: the terminal ---------- */ |
| 148 | /* The tide: paper fades through light aqua into cobalt and the deep, like |
| 149 | the merch's Tide ombré (light at the top, navy at the hem). No hard edge; |
| 150 | the whale rests where the water begins, and the terminal floats in calm, |
| 151 | dark water below. */ |
| 152 | .home-terminal { |
| 153 | position: relative; |
| 154 | background: var(--tide), var(--ocean-floor); |
| 155 | } |
| 156 | |
| 157 | /* The install band ends the page in the sea: one line of light at its top, |
| 158 | and water that reaches the floor colour by its own bottom edge, so it runs |
| 159 | into the footer without a seam. */ |
| 160 | .home-install { |
| 161 | position: relative; |
| 162 | background: var(--sea-band), var(--ocean-floor); |
| 163 | } |
| 164 | .home-install::before { |
| 165 | content: ""; |
| 166 | position: absolute; |
| 167 | inset: 0 0 auto; |
| 168 | height: 1px; |
| 169 | background: var(--horizon-light); |
| 170 | } |
| 171 | |
| 172 | .home-terminal-inner { |
| 173 | display: grid; |
| 174 | gap: var(--space-6); |
| 175 | width: min(var(--container), 64rem); |
| 176 | margin-inline: auto; |
| 177 | padding-block: clamp(9rem, 16vw, 13rem) clamp(4rem, 8vw, 6.5rem); |
| 178 | } |
| 179 | |
| 180 | .home-terminal-title { |
| 181 | max-width: 22ch; |
| 182 | font-size: var(--text-section); |
| 183 | font-weight: 600; |
| 184 | line-height: 1.1; |
| 185 | letter-spacing: -0.02em; |
| 186 | color: var(--text); |
| 187 | text-wrap: balance; |
| 188 | } |
| 189 | |
| 190 | .home-shot .figure-frame { |
| 191 | border: 0; |
| 192 | box-shadow: |
| 193 | 0 0 0 1px rgb(var(--gpui-dark-primary-rgb) / 0.14), |
| 194 | 0 40px 80px -40px rgb(0 0 0 / 0.75); |
| 195 | } |
| 196 | .home-shot figcaption { |
| 197 | display: flex; |
| 198 | flex-wrap: wrap; |
| 199 | justify-content: space-between; |
| 200 | gap: var(--space-2) var(--space-4); |
| 201 | } |
| 202 | |
| 203 | /* ---------- paper: the reading sections ---------- */ |
| 204 | .home-body { |
| 205 | width: var(--container); |
| 206 | margin-inline: auto; |
| 207 | padding-block: clamp(4.5rem, 9vw, 7rem); |
| 208 | } |
| 209 | .home-body > .home-section { padding-block: 0; } |
| 210 | .home-body > .home-section + .home-section { |
| 211 | margin-top: clamp(2.5rem, 6vw, 5rem); |
| 212 | padding-top: clamp(2.5rem, 6vw, 5rem); |
| 213 | border-top: 1px solid var(--line); |
| 214 | } |
| 215 | |
| 216 | /* Terms read as words, not as code: the brand face, a little weight. */ |
| 217 | .home-body .ruled-list dt { |
| 218 | font-family: var(--font-body); |
| 219 | font-size: var(--text-body); |
| 220 | font-weight: 600; |
| 221 | letter-spacing: 0; |
| 222 | color: var(--text); |
| 223 | } |
| 224 | .home-modes dt { font-family: var(--font-body); } |
| 225 | |
| 226 | .product-start-links { display: flex; flex-wrap: wrap; gap: var(--space-3) var(--space-5); margin-top: var(--space-5); } |
| 227 | |
| 228 | /* ---------- the sea: install, into the footer ---------- */ |
| 229 | .home-install-inner { |
| 230 | display: grid; |
| 231 | gap: var(--space-6); |
| 232 | grid-template-columns: minmax(0, 1fr); |
| 233 | align-items: center; |
| 234 | width: var(--container); |
| 235 | margin-inline: auto; |
| 236 | padding-block: clamp(4.5rem, 9vw, 7rem) clamp(2.5rem, 5vw, 4rem); |
| 237 | } |
| 238 | @media (min-width: 900px) { |
| 239 | .home-install-inner { grid-template-columns: minmax(0, 0.9fr) minmax(0, 1.1fr); } |
| 240 | } |
| 241 | .home-install-channels { color: var(--muted); font-size: var(--text-ui); line-height: 1.6; } |
| 242 | |
| 243 | /* ---------- narrow screens ---------- */ |
| 244 | @media (max-width: 900px) { |
| 245 | .home-hero-inner { grid-template-columns: minmax(0, 1fr); } |
| 246 | .home-hero-copy { padding-bottom: var(--space-4); } |
| 247 | .home-whale { justify-content: flex-end; } |
| 248 | .home-whale .whale-live { --whale-size: clamp(14rem, 70vw, 20rem); margin-inline: auto; } |
| 249 | } |
| 250 | |
| 251 | @media (forced-colors: active) { |
| 252 | .home-install::before { background: CanvasText; } |
| 253 | } |
| 254 |