14islands extraído de 14islands.com Ver sitio ↗
Design & Technology
Creative agency

We design and build premium digital products, brands, and experiences.

Un lienzo gris pálido, tinta casi negra y tipografía de 314px componiendo el logo de la página. El estudio que escribió r3f-scroll-rig esconde un motor WebGL debajo de lo que parece un PDF elegante.

Un solo peso tipográfico (400) en todo el sitio: el énfasis se hace con la escala (de 13px a 314px, un salto de 24x), con la itálica o con el highlight beige que subraya palabras al hacer scroll. Los neutros de apoyo son arenas cálidas y el color saturado entra solo por proyecto. Cero sombras: la profundidad es física, no óptica.

light mode neutro cálido 1 peso tipográfico salto de escala 24x 0 sombras canvas WebGL global lenis + scroll-rig
↓ Scroll
14islands.com
Captura del hero de 14islands: Design & Technology en tipografía gigante escalonada sobre gris pálido
Los escalones"Design" arriba a la izquierda, el ampersand en gris #A2A2A9 debajo, "Technology" entrando desde la derecha. La composición asimétrica es el logo.
El contrapesoCada pieza gigante lleva su label diminuto: "CREATIVE AGENCY" a 13px uppercase ancla la esquina mientras el display ocupa el viewport.
El motor invisibleLas clases reales del html (js-has-global-canvas, lenis-smooth) delatan un canvas WebGL único que persigue las imágenes del DOM para distorsionarlas con el scroll.
01

Color

light · neutro cálido · el color es del proyecto
El sistema (variables reales del :root)
#070707
Casi negro
--color-almost-black: la tinta universal. Siete puntos de gris la separan del #000: esa es la suavidad del sistema
sobre #F2F2F2: 18:1 AAA · sobre blanco: 20.2:1 AAA
#F2F2F2
Fondo
--color-background: el lienzo del sitio, un gris pálido que nunca compite con el trabajo
tinta encima: 18:1 AAA
#FFFFFF
Blanco
--color-white: superficie de secciones y cards; la mayor área medida del sitio (score 21.2M)
tinta encima: 20.2:1 AAA
#EAE5DF
Arena
--color-sand: la superficie cálida de apoyo; el sistema no tiene grises azulados
tinta encima: 16.1:1 AAA
#A59D92
Arena intensa
--color-sand-highlight: el acento de arena para subrayados y detalles
decorativo sobre claro; superficie con tinta encima
#797979
Gris medio
--color-grey-highlight-dark: el texto secundario real del sitio
sobre #F2F2F2: 3.9:1 · AA solo texto grande (19px+)
#A2A2A9
Gris claro
--color-grey-highlight-light: el ampersand de 300px del hero; color de forma, no de texto
2.3:1 sobre #F2F2F2: nunca texto funcional
#E4DED7
Highlight beige
--color-beige-theme-animated-text-highlight-bg: el rectángulo que crece detrás de las palabras (par oscuro: #26272A)
tinta encima: 15.2:1 AAA
El color es del proyecto (variables reales con nombre de cliente)
#A5A9FD--color-aila-purple · case AILA
#FFCA6B--color-aila-yellow · case AILA
#FFF38Blimón HeroKit · canvas WebGL del case
#101010--color-aila-almost-black · fondos de case

La tesis del sistema, medida: el acento con más área de todo el sitio (#FFF38B, score 1.44M, segundo tras el blanco) no pertenece al estudio sino a un proyecto. El :root incluso tokeniza la paleta del cliente (--color-aila-*). 14islands se mantiene neutro para que el trabajo ponga el color; el marco no compite jamás con el cuadro.

Contraste verificado

Tinta #070707 sobre: #F2F2F2 → 18:1 · #FFFFFF → 20.2:1 · #EAE5DF → 16.1:1 · #FFF38B → 17.7:1 · #FFCA6B → 13.3:1 · #A5A9FD → 9.3:1. Todo AAA: el casi negro funciona sobre cualquier superficie del sistema o de proyecto. Las trampas son los grises: #797979 solo desde 19px, y #A2A2A9 únicamente como forma gigante.

02

Typography

2 familias · 1 peso · escala 24x
Design & Tech
Work Sans + Libre Franklin Original: Aften Screen + Benton Sans -> HTML: Work Sans + Libre Franklin (Google substitutes)
Display hero · 400 / -0.05emLet's make something great
Display itálica · acentobranding, product design and development
Body · 16px / 400HeroKit is designed to be user-friendly, fast, and effortless to use.
Label · 13px / uppercaseCreative agency · Industry · More work
Un solo peso · el énfasis es la escala

Todo el sitio (display de 314px y labels de 13px por igual) usa peso 400. No hay bold: cuando 14islands quiere énfasis, cambia la escala, pasa a la itálica de Aften o hace crecer el highlight beige detrás de la palabra. El display se comporta como logotipo: 314.81px medidos con line-height 0.8 y tracking -0.05em, compuesto en escalones asimétricos. El cuerpo hace lo contrario: 13-16px, interlínea 1.4-1.5 y tracking normal, quieto y neutro.

El tracking negativo crece con el tamaño y desaparece en texto funcional: -0.05em a 314px, -0.04em a 83px, normal a 13px.

RolSize realWeightLHTracking
display hero314.81px4000.8-0.05em
display md (h4 contacto)83.33px4001.0-0.04em
body16px4001.5normal
label / nav12.96px4001.4normal · uppercase
itálica de acentohereda400heredaAftenScreenItalic real

El display escala en vw sin topar: en una pantalla 4K el hero es arquitectura. Los @font-face reales son cuatro: AftenScreen, AftenScreenItalic, BentonSans e Inter (auxiliar).

Original: Aften Screen -> HTML: Work Sans (Google substitute). Aften Screen (Monokrom, fundición noruega) es una humanista de pantalla con altura de x generosa, aperturas abiertas e itálica verdadera, usada en un único peso 400 a tamaños de póster. Work Sans gana por compartir el brief ("optimizada para pantalla"), la g de doble piso, los terminales cálidos y unas itálicas reales que cubren el papel de AftenScreenItalic. Descartadas: Instrument Sans (gesto más técnico y frío), Inter (el propio sitio la carga como auxiliar, pero a 300px es anónima) y Public Sans (deriva burocrática, rígida en display).

Original: Benton Sans -> HTML: Libre Franklin (Google substitute). Benton Sans es la revival de las gothics de Morris Fuller Benton hecha por Frere-Jones; Libre Franklin revive el mismo linaje Franklin Gothic. Es la sustitución más directa disponible: mismas proporciones en caja alta para los labels de 13px, mismo tono americano neutro. Mono: no detectada en el sitio; los bloques de código usan la pila del sistema.
03

Components

texto que actúa

El sitio casi no tiene botones: tiene texto que actúa. El control real es el label de 13px uppercase con un subrayado de 1px que entra de izquierda a derecha (curva --ease-cubic). Los botones sólidos son derivados del sistema: tinta #070707 con radio 5px, y la variante arena #EAE5DF para acciones suaves.

Highlight animado (componente real tokenizado)
We make stunning things

El rectángulo #E4DED7 hace scaleX de 0 a 1 detrás de la palabra al entrar al viewport. El texto no cambia de color ni de peso: el fondo hace el énfasis.

HeroKit
Creative techHeroKit
AILA
Product designAILA
Blobmixer
Creative techBlobmixer

Card de trabajo (componente firma): radio 5px, sin borde y sin sombra; el color del proyecto separa la card del canvas. En el sitio real la imagen vive en el canvas WebGL global y se distorsiona con la velocidad del scroll; aquí el hover escala el contenido con --ease-quint-out como eco de ese gesto.

Let's make something great together hello@14islands.com
© 2026 14islandsInstagramX / TwitterLinkedInPrivacy

Footer de contacto (componente firma): el email es un h4 de display real (83.33px medidos, line-height 1.0, tracking -0.04em) y toda su caja es clickeable. Debajo, los créditos vuelven al registro diminuto de 13px uppercase. La tensión entre las dos escalas es la composición.

04

Motion

scroll-rig de autor · 25 easings reales

El motivo por el que este sitio está en la galería: 14islands escribió @14islands/r3f-scroll-rig y su home es la demo canónica del patrón. Las clases reales del html (js-has-global-canvas lenis lenis-smooth) delatan la arquitectura: un único canvas WebGL global persigue a las imágenes del DOM para aplicarles shaders, con Lenis amortiguando el scroll debajo. Y el motion está tokenizado igual que el color: 25 curvas de easing con nombre en el :root.

Easings reales del :root del sitio
Token realCurvaUso
--ease-cubiccubic-bezier(.66, 0, .34, 1)La curva de la casa: subrayados, transiciones de interfaz
--ease-expo-outcubic-bezier(.19, 1, .22, 1)Entradas de display y reveals
--ease-quint-outcubic-bezier(.23, 1, .32, 1)Deceleraciones suaves, media
--ease-back-outcubic-bezier(.175, .885, .32, 1.275)Overshoot clásico
--ease-back-out-morecubic-bezier(.56, .91, .465, 1.65)Overshoot 1.65: el único gesto juguetón del sistema
+ 20 másin / out / in-outPenner completa: sine, quad, cubic, quart, quint, expo, circ
Demo · --ease-cubic, la curva de la casa (hover)

Simétrica y contenida: cubic-bezier(.66, 0, .34, 1). Acelera y frena con la misma elegancia; es la voz neutral de la interfaz.

Demo · --ease-back-out-more (hover)

El único rebote permitido: cubic-bezier(.56, .91, .465, 1.65), overshoot de 1.65 reservado para momentos de juego, nunca para la lectura.

Canvas global + scroll-rigLas imágenes del DOM se proyectan en un solo canvas WebGL que las persigue; al hacer scroll reciben parallax y una distorsión proporcional a la velocidad. El patrón exacto de su librería open source.
Lenis smooth scrollClases reales lenis lenis-smooth js-smooth-scrollbar-enabled: scroll amortiguado que alimenta los uniforms del shader con su velocidad.
Hero escalonado"Design", "&", "Technology" entran por pasos con translate y opacity, cada pieza con su delay, hasta componer el logo de la página.
Highlight que subrayaEl rectángulo #E4DED7 (o #26272A en secciones oscuras) crece con scaleX detrás de la palabra al entrar al viewport. Está tokenizado en el :root con nombre y todo.
Reveals por palabraLos párrafos de display aparecen palabra a palabra con máscara, siguiendo el progreso del scroll, no un timeline.
Subrayado de link1px que entra de izquierda a derecha con --ease-cubic en hover y sale hacia la derecha al soltar.

Accesibilidad: con prefers-reduced-motion, Lenis cede al scroll nativo, el canvas congela las distorsiones (las imágenes se muestran planas), los reveals aparecen completos y el highlight se pinta sin animación. Esta página aplica la misma regla a sus demos.

05

Spacing

--indent maestro · un protagonista por viewport
Tokens reales del :root
--indent: max(0.9375rem, 3.7616vw)
  15px en móvil · ~60px @1600
--menuNavigationHeight: max(5rem, 7.6968vw)
  80px en móvil · ~123px @1600
breakpoints: 600 / 900 / 1400
--vw / --vh: corregidos por JS (barras móviles)
Escala derivada (el sitio compone con --indent)
8px
16px
24px
40px
--indent @1600
nav height @1600
sección · clamp(96, 12vw, 200)
Familia de radios
0 · el texto, nunca en caja
5px · thumbs y controles
Elevación
sombras medidas en el sitio: 0
la profundidad es de superficie y de física:
#F2F2F2 → #FFFFFF → #EAE5DF → color de proyecto
+ parallax y distorsión del canvas WebGL

si algo necesita elevarse: cámbialo de superficie
o dale velocidad diferencial, nunca sombra.

Filosofía del layout: el vacío es la ornamentación. Un protagonista por viewport (titular gigante, o card de trabajo, o bloque de texto) y un label diminuto de 13px como contrapeso en la esquina. Entre el label y el display de 314px no hay elementos intermedios que llenen: la tensión entre lo diminuto y lo enorme es la composición.

06

Principles

guardrails

    Do

  • Mantén el lienzo neutro cálido: #F2F2F2 de fondo, #FFFFFF de sección, arenas #EAE5DF y #E4DED7 de apoyo.
  • Usa la tinta #070707, no negro puro: esos siete puntos de gris son la suavidad del sistema.
  • Compón el display como logotipo: peso 400, tracking -0.05em, line-height 0.8, escalones asimétricos. La escala es el énfasis.
  • Ancla cada bloque gigante con un label diminuto de 13px uppercase: la tensión de escalas es la firma.
  • Delega el color al trabajo: las cards toman el fondo del proyecto (#FFF38B, #A5A9FD, #101010); el sistema solo pone el marco.
  • Enfatiza con el highlight animado (#E4DED7 creciendo tras la palabra) o con la itálica, nunca con peso.
  • Reserva 5px como único radio para thumbnails y controles; el texto va sin caja.
  • Liga el movimiento al scroll con física: Lenis + canvas global; el shader responde a la velocidad, no a un timeline.

    Don't

  • No metas bold ni semibold: el sitio entero vive en peso 400. El énfasis es escala, itálica o highlight.
  • No uses sombras, ni suaves ni de tarjeta: la profundidad es superficie + parallax.
  • No pongas #A2A2A9 en texto funcional: es un color de forma (el ampersand de 300px), da 2.3:1.
  • No llenes el viewport: un protagonista por pantalla; si hay dos, sobra uno.
  • No uses grises fríos azulados: los neutros de apoyo son arenas cálidas.
  • No apliques el tracking negativo al texto pequeño: -0.05em es solo de display; el body va a tracking normal.
  • No conviertas el WebGL en protagonista: el shader sirve a las imágenes del DOM, no flota como demo técnica.
  • No redondees más de 5px: una card de 16px de radio pertenece a otro sistema.
07

Resources

copy & paste
:root {
  /* nombres reales del :root de 14islands.com */
  --color-almost-black: #070707;
  --color-background: #F2F2F2;
  --color-white: #FFFFFF;
  --color-sand: #EAE5DF;
  --color-sand-highlight: #A59D92;
  --color-grey-highlight-dark: #797979;
  --color-grey-highlight-light: #A2A2A9;
  --color-beige-theme-animated-text-highlight-bg: #E4DED7;
  --color-dark-theme-animated-text-highlight-bg: #26272A;

  /* paleta de proyecto tokenizada (real) */
  --color-aila-purple: #A5A9FD;
  --color-aila-yellow: #FFCA6B;
  --color-aila-grey: #1F1F1F;
  --color-aila-almost-black: #101010;
  /* limón HeroKit, medido por área en el canvas WebGL: #FFF38B */

  --font-display: "Work Sans";      /* sustituta de Aften Screen */
  --font-body: "Libre Franklin";    /* sustituta de Benton Sans */

  --radius-soft: 5px;               /* thumbs y controles; el texto sin caja */
  --shadow: none;                   /* cero sombras medidas */

  /* espaciado maestro (real) */
  --indent: max(0.9375rem, 3.7615740741vw);
  --menuNavigationHeight: max(5rem, 7.6967592593vw);
  --breakpoint-medium: 600px;
  --breakpoint-desktop: 900px;
  --breakpoint-large: 1400px;

  /* easings reales (25 tokens; los principales) */
  --ease-cubic: cubic-bezier(0.66, 0, 0.34, 1);
  --ease-expo-out: cubic-bezier(0.19, 1, 0.22, 1);
  --ease-quint-out: cubic-bezier(0.23, 1, 0.32, 1);
  --ease-back-out: cubic-bezier(0.175, 0.885, 0.32, 1.275);
  --ease-back-out-more: cubic-bezier(0.56, 0.91, 0.465, 1.65);
}
@theme {
  --color-almost-black: #070707;
  --color-background: #F2F2F2;
  --color-white: #FFFFFF;
  --color-sand: #EAE5DF;
  --color-sand-highlight: #A59D92;
  --color-grey-mid: #797979;
  --color-grey-soft: #A2A2A9;
  --color-highlight-beige: #E4DED7;
  --color-highlight-dark: #26272A;
  --color-aila-purple: #A5A9FD;
  --color-aila-yellow: #FFCA6B;
  --color-aila-grey: #1F1F1F;
  --color-aila-almost-black: #101010;
  --color-lemon-herokit: #FFF38B;

  --font-display: "Work Sans", "Helvetica Neue", sans-serif;
  --font-body: "Libre Franklin", Arial, sans-serif;

  --radius-soft: 5px;

  --spacing-indent: max(0.9375rem, 3.76vw);
  --spacing-nav: max(5rem, 7.7vw);

  --ease-cubic: cubic-bezier(0.66, 0, 0.34, 1);
  --ease-expo-out: cubic-bezier(0.19, 1, 0.22, 1);
  --ease-back-out-more: cubic-bezier(0.56, 0.91, 0.465, 1.65);

  --text-display-hero: 19.7vw;   /* 314.81px @1600, LH 0.8, -0.05em */
  --text-display-md: 5.2vw;      /* 83.33px @1600, LH 1.0, -0.04em */
  --text-body: 16px;             /* LH 1.5 */
  --text-label: 12.96px;         /* uppercase, LH 1.4 */
}
{
  "colors": {
    "almost-black": "#070707",
    "background": "#F2F2F2",
    "white": "#FFFFFF",
    "sand": "#EAE5DF",
    "sand-highlight": "#A59D92",
    "grey-mid": "#797979",
    "grey-soft": "#A2A2A9",
    "highlight-beige": "#E4DED7",
    "highlight-dark": "#26272A",
    "project": {
      "aila-purple": "#A5A9FD",
      "aila-yellow": "#FFCA6B",
      "aila-grey": "#1F1F1F",
      "aila-almost-black": "#101010",
      "herokit-lemon": "#FFF38B"
    }
  },
  "typography": {
    "display-hero": {
      "fontFamily": "Aften Screen",
      "substitute": "Work Sans",
      "fontSize": "314.81px @1600 (fluido en vw)",
      "fontWeight": 400,
      "lineHeight": "0.8",
      "letterSpacing": "-0.05em"
    },
    "display-md": {
      "fontFamily": "Aften Screen",
      "substitute": "Work Sans",
      "fontSize": "83.33px @1600",
      "fontWeight": 400,
      "lineHeight": "1.0",
      "letterSpacing": "-0.04em"
    },
    "accent-italic": {
      "fontFamily": "Aften Screen Italic",
      "substitute": "Work Sans Italic",
      "fontWeight": 400
    },
    "body": {
      "fontFamily": "Benton Sans",
      "substitute": "Libre Franklin",
      "fontSize": "16px",
      "fontWeight": 400,
      "lineHeight": "1.5",
      "letterSpacing": "normal"
    },
    "label": {
      "fontFamily": "Benton Sans",
      "substitute": "Libre Franklin",
      "fontSize": "12.96px",
      "fontWeight": 400,
      "lineHeight": "1.4",
      "letterSpacing": "normal",
      "textTransform": "uppercase"
    }
  },
  "rounded": {
    "soft": "5px",
    "text": "0px"
  },
  "shadow": {
    "system": "none"
  },
  "spacing": {
    "indent": "max(0.9375rem, 3.7615740741vw)",
    "menu-height": "max(5rem, 7.6967592593vw)",
    "breakpoints": [600, 900, 1400]
  },
  "motion": {
    "ease-cubic": "cubic-bezier(0.66, 0, 0.34, 1)",
    "ease-expo-out": "cubic-bezier(0.19, 1, 0.22, 1)",
    "ease-quint-out": "cubic-bezier(0.23, 1, 0.32, 1)",
    "ease-back-out-more": "cubic-bezier(0.56, 0.91, 0.465, 1.65)",
    "architecture": "lenis + canvas WebGL global (r3f-scroll-rig, autoría propia)",
    "html-classes": "js-has-global-canvas lenis lenis-smooth js-smooth-scrollbar-enabled"
  }
}
__DSG_EMBED__