Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
17 changes: 2 additions & 15 deletions src/components/Bento.astro
Original file line number Diff line number Diff line change
@@ -1,21 +1,8 @@
---
// The landing page's capabilities, as a grid of cards (BentoCard.astro) under one light that
// follows the pointer.
// The landing page's capabilities, as a grid of cards (BentoCard.astro).
---

<div class="bento not-content" data-bento><slot /></div>

<script>
for (const grid of document.querySelectorAll<HTMLElement>('[data-bento]')) {
grid.addEventListener('pointermove', (e) => {
for (const card of grid.querySelectorAll<HTMLElement>('.card')) {
const r = card.getBoundingClientRect();
card.style.setProperty('--mx', `${e.clientX - r.left}px`);
card.style.setProperty('--my', `${e.clientY - r.top}px`);
}
});
}
</script>
<div class="bento not-content"><slot /></div>

<style>
.bento {
Expand Down
40 changes: 7 additions & 33 deletions src/components/BentoCard.astro
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,6 @@ const proof = kind === 'e2e' ? `e2e · ${what}` : kind === 'cli' ? `spin ${what}
---

<a class:list={['card', size]} href={to}>
<span class="glow" aria-hidden="true"></span>
<span class="icon"><Icon name={icon} /></span>
<span class="title">{title}</span>
<span class="body"><slot /></span>
Expand Down Expand Up @@ -53,49 +52,37 @@ const proof = kind === 'e2e' ? `e2e · ${what}` : kind === 'cli' ? `spin ${what}
flex-direction: column;
gap: 0.6rem;
padding: 1.4rem 1.4rem 1.2rem;
border-radius: var(--spin-radius-lg);
border-radius: var(--spin-radius);
text-decoration: none;
color: var(--sl-color-gray-3);
background: color-mix(in srgb, var(--sl-color-gray-6) 70%, transparent);
border: 1px solid var(--sl-color-hairline-light);
overflow: hidden;
transition:
transform var(--spin-duration) var(--spin-ease),
border-color var(--spin-duration) var(--spin-ease),
box-shadow var(--spin-duration) var(--spin-ease);
transition: border-color var(--spin-duration) var(--spin-ease);
}
/* A card answers the pointer with its edge, and stays where it is. */
.card:hover,
.card:focus-visible {
transform: translateY(-4px);
border-color: color-mix(in srgb, var(--sl-color-accent) 50%, transparent);
box-shadow: 0 24px 60px -30px color-mix(in srgb, var(--spin-brand-blue) 80%, transparent);
border-color: var(--spin-border-strong);
}
.card:focus-visible {
outline: 2px solid var(--sl-color-accent);
outline-offset: 3px;
}
/* A light that follows the pointer across the grid (Bento.astro sets where it is). */
.glow {
position: absolute;
inset: 0;
z-index: -1;
background: radial-gradient(22rem circle at var(--mx, -100rem) var(--my, -100rem), color-mix(in srgb, var(--spin-brand-cyan) 16%, transparent), transparent 60%);
}
.icon {
display: inline-grid;
place-items: center;
width: 2.6rem;
height: 2.6rem;
border-radius: var(--spin-radius);
color: var(--spin-label);
background: linear-gradient(135deg, color-mix(in srgb, var(--spin-brand-cyan) 18%, transparent), color-mix(in srgb, var(--spin-brand-blue) 18%, transparent));
border: 1px solid color-mix(in srgb, var(--spin-brand-cyan) 28%, transparent);
background: var(--spin-raised);
}
.title {
font-size: 1.2rem;
font-weight: 600;
color: var(--sl-color-white);
letter-spacing: -0.01em;
letter-spacing: var(--spin-heading-tracking);
}
.body {
font-size: var(--sl-text-sm);
Expand Down Expand Up @@ -130,19 +117,6 @@ const proof = kind === 'e2e' ? `e2e · ${what}` : kind === 'cli' ? `spin ${what}
font-size: 12px;
fill: var(--sl-color-white);
}
.card:hover .r3 {
filter: drop-shadow(0 0 10px var(--spin-brand-cyan));
}
@media (prefers-reduced-motion: no-preference) {
.r3 {
animation: ring-breathe 1.6s ease-in-out 2 alternate;
}
@keyframes ring-breathe {
to {
fill: color-mix(in srgb, var(--spin-brand-cyan) 32%, transparent);
}
}
}
.art + .proof {
margin-top: 0;
}
Expand All @@ -151,7 +125,7 @@ const proof = kind === 'e2e' ? `e2e · ${what}` : kind === 'cli' ? `spin ${what}
padding-top: 0.8rem;
font-family: var(--sl-font-mono);
font-size: 0.72rem;
color: var(--sl-color-gray-4);
color: var(--spin-muted);
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
Expand Down
15 changes: 3 additions & 12 deletions src/components/Cta.astro
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
---
// The landing page's last word: where to go next, on the brand's gradient. Its Markdown twin is
// The landing page's last word: where to go next, on the navy. Its Markdown twin is
// the title and the links.
import { LinkButton } from '@astrojs/starlight/components';

Expand All @@ -11,7 +11,6 @@ const { title, links } = Astro.props;
---

<section class="cta not-content spin-dark">
<div class="mesh" aria-hidden="true"></div>
<h2>{title}</h2>
<p><slot /></p>
<div class="links">
Expand All @@ -32,27 +31,19 @@ const { title, links } = Astro.props;
overflow: hidden;
margin-block: 4rem 1rem;
padding: clamp(2.5rem, 2rem + 3vw, 4.5rem) clamp(1.5rem, 1rem + 3vw, 4rem);
border-radius: var(--spin-radius-lg);
border-radius: var(--spin-radius);
background: var(--spin-page);
color: var(--spin-text);
text-align: center;
border: 1px solid var(--spin-border);
}
.mesh {
position: absolute;
inset: -40%;
z-index: -1;
background: conic-gradient(from 180deg at 50% 50%, var(--spin-brand-deep), var(--spin-brand-blue), var(--spin-brand-cyan), var(--spin-brand-mint), var(--spin-brand-deep));
filter: blur(70px);
opacity: 0.55;
}
h2 {
margin: 0 auto;
max-width: 22ch;
font-family: var(--sl-font-mono);
font-size: clamp(1.8rem, 1.2rem + 2.4vw, 3rem);
line-height: 1.1;
letter-spacing: -0.035em;
letter-spacing: var(--spin-heading-tracking);
color: var(--spin-brand-frost);
}
p {
Expand Down
2 changes: 1 addition & 1 deletion src/components/Figure.astro
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@ const style = width ? `width: max(100%, ${width}px)` : 'width: 100%';
display: block;
background: #fff;
border: 1px solid var(--sl-color-hairline-light);
border-radius: 0.5rem;
border-radius: var(--spin-radius);
padding: 1rem;
overflow-x: auto;
}
Expand Down
2 changes: 1 addition & 1 deletion src/components/Footer.astro
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@ if (source) {
)
}
<p>
Documents spin <code>{reference.spin.release}</code>.
Documents Spinbox <code>{reference.spin.release}</code>.{' '}
<a href={`${base}${twinPath(id)}`}>This page as Markdown</a>, for a model or a terminal.
</p>
</div>
Expand Down
60 changes: 4 additions & 56 deletions src/components/Hero.astro
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
---
// The landing page's hero: Starlight's, with the drawing of a workspace's disk beside it and the
// project's name above the title. The title's second sentence - what Spinbox does, after what it
// is - carries the brand's gradient.
// is - is in the accent: one color, flat, as the console sets what matters.
import { LinkButton } from '@astrojs/starlight/components';
import LayerStack from './LayerStack.astro';

Expand Down Expand Up @@ -40,30 +40,16 @@ const rest = cut < 0 ? '' : title.slice(cut + 2);
align-items: center;
padding-block: 2rem 1rem;
}
/* The brand's three lights behind the hero, over a grid of dots that fades out towards the
edges: the colours of the mark, as a glow rather than as blocks. */
/* A grid of dots behind the hero, fading out towards the edges: a drawing board, not a glow. */
.backdrop {
position: absolute;
inset: -10rem calc(50% - 50vw) -6rem;
z-index: -1;
pointer-events: none;
background:
radial-gradient(38% 46% at 78% 42%, color-mix(in srgb, var(--spin-brand-blue) 34%, transparent), transparent 70%),
radial-gradient(30% 38% at 92% 18%, color-mix(in srgb, var(--spin-brand-cyan) 26%, transparent), transparent 70%),
radial-gradient(34% 40% at 12% 78%, color-mix(in srgb, var(--spin-brand-mint) 14%, transparent), transparent 70%);
filter: blur(8px);
}
.backdrop::after {
content: '';
position: absolute;
inset: 0;
background-image: radial-gradient(color-mix(in srgb, var(--sl-color-gray-3) 38%, transparent) 1px, transparent 1.5px);
background-size: 22px 22px;
mask-image: radial-gradient(60% 60% at 60% 45%, #000 20%, transparent 75%);
}
:global([data-theme='light']) .backdrop {
opacity: 0.55;
}
.copy {
display: flex;
flex-direction: column;
Expand All @@ -83,27 +69,18 @@ const rest = cut < 0 ? '' : title.slice(cut + 2);
height: 0.5rem;
border-radius: 50%;
background: var(--spin-label);
box-shadow: 0 0 0 0 color-mix(in srgb, var(--spin-label) 60%, transparent);
}
h1 {
font-family: var(--sl-font-mono);
font-size: clamp(2.3rem, 1rem + 3.6vw, 3.9rem);
line-height: 1.08;
letter-spacing: -0.03em;
letter-spacing: var(--spin-heading-tracking);
font-weight: 600;
color: var(--sl-color-white);
margin: 0;
}
.hl {
/* The mark's lights that may be text on the navy: cyan and mint, never its blue. */
background: linear-gradient(100deg, var(--spin-brand-cyan), var(--spin-brand-mint) 55%, var(--spin-brand-cyan));
background-size: 200% 100%;
-webkit-background-clip: text;
background-clip: text;
color: transparent;
}
:global([data-theme='light']) .hl {
background-image: linear-gradient(100deg, var(--spin-accent), var(--spin-brand-deep) 55%, var(--spin-accent));
color: var(--spin-accent-text);
}
.tagline {
font-size: var(--sl-text-lg);
Expand All @@ -117,16 +94,6 @@ const rest = cut < 0 ? '' : title.slice(cut + 2);
gap: 1rem 1.5rem;
align-items: center;
}
.actions :global(.sl-link-button.primary) {
box-shadow: 0 0 0 0 transparent;
transition:
box-shadow 200ms,
transform 200ms;
}
.actions :global(.sl-link-button.primary:hover) {
transform: translateY(-1px);
box-shadow: 0 8px 28px -6px color-mix(in srgb, var(--sl-color-accent) 70%, transparent);
}
.art {
display: flex;
justify-content: center;
Expand All @@ -150,30 +117,11 @@ const rest = cut < 0 ? '' : title.slice(cut + 2);
.copy > :nth-child(4) {
animation-delay: 240ms;
}
/* Once each (palette.toml's [motion]): the light crosses the title, the dot pulses three
times, and both stay as they end. */
.hl {
animation: hero-sheen 2.4s var(--spin-ease) 400ms both;
}
.dot {
animation: hero-pulse 1.6s ease-out 3;
}
@keyframes hero-rise {
from {
opacity: 0;
transform: translateY(14px);
}
}
@keyframes hero-sheen {
to {
background-position: 100% 0;
}
}
@keyframes hero-pulse {
70%,
100% {
box-shadow: 0 0 0 0.6rem transparent;
}
}
}
</style>
10 changes: 1 addition & 9 deletions src/components/LayerStack.astro
Original file line number Diff line number Diff line change
Expand Up @@ -51,7 +51,6 @@ const layers = [
.layer-stack {
width: 100%;
max-width: 34rem;
filter: drop-shadow(0 40px 60px color-mix(in srgb, var(--spin-brand-blue) 35%, transparent));
height: auto;
font-family: var(--sl-font-mono);
--ls-ink: var(--spin-label);
Expand Down Expand Up @@ -108,9 +107,7 @@ const layers = [
ls-fade var(--spin-duration-slow) ease-out both;
}
.live-top {
animation:
ls-write 1.6s linear 3,
ls-glow 2.4s ease-in-out 2 alternate;
animation: ls-write 1.6s linear 3;
}
@keyframes ls-drop {
from {
Expand All @@ -136,10 +133,5 @@ const layers = [
stroke-dashoffset: -22;
}
}
@keyframes ls-glow {
to {
fill: color-mix(in srgb, var(--ls-ink) 26%, transparent);
}
}
}
</style>
2 changes: 1 addition & 1 deletion src/components/PageTitle.astro
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,7 @@ const twin = `${base}${twinPath(Astro.locals.starlightRoute.id)}`;
min-height: 2rem;
padding: 0 0.75rem;
border: 1px solid var(--sl-color-hairline-light);
border-radius: 0.375rem;
border-radius: var(--spin-radius-sm);
background: transparent;
color: var(--sl-color-gray-2);
text-decoration: none;
Expand Down
Loading
Loading