/* Surface texture.
   Mirrors the two-part overlay the Continuum desktop app draws over every view
   (Controls/NoiseOverlay.cs): a domain-warped low-frequency field, plus a fine
   per-pixel grain on top. Here the field comes from feTurbulence rather than a
   generated bitmap, but the parameters line up with GrainSettings — a 512px base
   wavelength over four octaves, a warp strength of 100, and a light fine grain.

   The layers blend rather than paint, so they darken the paper surfaces and
   lighten the navy ones, the way the app switches sheen with its theme. They
   sit above everything and take no pointer events.

   The strengths are set for a paper-first page: enough to take the flatness off
   white, well short of anything that reads as texture on it. */

:root{
  --grain-warp:.22;   /* strength of the slow, warped field */
  --grain-fine:.14;   /* strength of the per-pixel grain */

  /* Both blend modes swing much harder against a dark backdrop than a light
     one, so paper surfaces take a second pass to read at the same weight. */
  --grain-fine-light:.22;

  /* The warped field. Two turbulences: one is the field, the other displaces
     it, which is what gives the slow bands their drift instead of an even
     mottle. */
  --grain-field:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='1560' height='980'%3E%3Cfilter id='w' x='-20%25' y='-20%25' width='140%25' height='140%25'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='0.00195' numOctaves='4' seed='902611' result='field'/%3E%3CfeTurbulence type='fractalNoise' baseFrequency='0.0013' numOctaves='2' seed='17' result='warp'/%3E%3CfeDisplacementMap in='field' in2='warp' scale='100' xChannelSelector='R' yChannelSelector='G'/%3E%3CfeColorMatrix type='matrix' values='0.33 0.33 0.33 0 0 0.33 0.33 0.33 0 0 0.33 0.33 0.33 0 0 0 0 0 0 1'/%3E%3C/filter%3E%3Crect width='100%25' height='100%25' filter='url(%23w)'/%3E%3C/svg%3E");

  /* The grain. Tiled at its own size so it stays per-pixel rather than being
     stretched into blur; stitchTiles keeps the seams invisible. */
  --grain-fine-field:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='200' height='200'%3E%3Cfilter id='g' x='0' y='0' width='100%25' height='100%25'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='0.8' numOctaves='3' seed='5' stitchTiles='stitch'/%3E%3CfeColorMatrix type='matrix' values='0.33 0.33 0.33 0 0 0.33 0.33 0.33 0 0 0.33 0.33 0.33 0 0 0 0 0 0 1'/%3E%3C/filter%3E%3Crect width='100%25' height='100%25' filter='url(%23g)'/%3E%3C/svg%3E");
}

body::before,
body::after{
  content:"";
  position:fixed;
  inset:0;
  z-index:9999;
  pointer-events:none;
}

body::before{
  background-image:var(--grain-field);
  background-size:cover;
  background-position:center;
  mix-blend-mode:soft-light;
  opacity:var(--grain-warp);
}

body::after{
  background-image:var(--grain-fine-field);
  background-size:200px 200px;
  mix-blend-mode:overlay;
  opacity:var(--grain-fine);
}

/* Second pass over the paper surfaces. `fixed` attachment keeps it registered
   with the page-wide field above, so a light band reads as more of the same
   texture rather than a patch of a different one.

   On the landing page the light surfaces are the hero and every section that
   is not a navy band; the legal and signup pages are paper throughout, and mark
   themselves with data-surface. */
section:not(.band):not(.dark):not(.darkest)::after,
.hero::after,
body[data-surface="light"]::after{
  background-image:var(--grain-fine-field),var(--grain-field);
  background-size:200px 200px,cover;
  background-attachment:fixed,fixed;
  background-position:center,center;
}

section:not(.band):not(.dark):not(.darkest),
.hero{position:relative}
section:not(.band):not(.dark):not(.darkest)::after,
.hero::after{
  content:"";
  position:absolute;
  inset:0;
  z-index:2;
  pointer-events:none;
  mix-blend-mode:overlay;
  opacity:var(--grain-fine-light);
}

body[data-surface="light"]::after{
  opacity:var(--grain-fine-light);
}

@media print{
  body::before,
  body::after,
  section:not(.band):not(.dark):not(.darkest)::after,
  .hero::after{display:none}
}
