/*****************************************************
GALLERY GRID

Image-first tiles with the caption laid over the picture. For collections where
the pictures do the navigating and there is no reading measure to respect.

`.wide-header` lives here too: it is the heading block that breaks out of the
text column to line up with a wide gallery, and its width has to stay in step
with `.gallery-grid--wide`.

Loads:    every page
Used by:  nav/gallery-grid.html
Needs:    base.css tokens (--gallery-caption-rest, --gallery-caption-active) and
          the `full` column of the base.css `.container` grid
Not here: cards, which put the caption beside or beneath the image (cards.css);
          the picks component, which selects items editorially rather than
          listing a folder (home.css)
*****************************************************/

/* Gallery grid navigation */
.gallery-grid {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(min(100%, var(--gallery-grid-min-width)), 1fr));
  grid-auto-flow: dense;
  gap: var(--gallery-grid-gap);
  margin-bottom: var(--spacing-lg);
}

.gallery-grid-item {
  position: relative;
  min-height: 12rem;
  aspect-ratio: 1 / 1;
  overflow: hidden;
  background: var(--bg-card);
  border-radius: var(--radius-sm);
  box-shadow: var(--shadow-sm);
}

.gallery-grid-link {
  display: block;
  position: relative;
  height: 100%;
  color: var(--text-on-dark);
  border-bottom: 0;
}

.gallery-grid-link:visited,
.gallery-grid-link:hover {
  color: var(--text-on-dark);
  border-bottom: 0;
}

.gallery-grid-link img {
  position: absolute;
  inset: 0;
  width: 100%;
  height: 100%;
  object-fit: cover;
  /* Tiles are square but site screenshots are tall, so a centred crop lands in
     the middle of the body text and the site becomes unrecognisable. Anchor to
     the top instead: the header, nav, and title are what identify a site. */
  object-position: top;
  opacity: 0.82;
  filter: saturate(0.82) contrast(0.96);
  transition: transform var(--transition-normal), filter var(--transition-normal), opacity var(--transition-normal);
}

.gallery-grid-link:hover img,
.gallery-grid-link:focus-visible img {
  transform: scale(1.04);
  opacity: 1;
  filter: saturate(1.08) contrast(1.02);
}

/* Heading and intro for a wide block. Without this the heading sits on the
   narrower text column while the grid below starts further left, and the two
   read as unrelated. Matches gallery-grid--wide so their left edges agree.
   Prose inside keeps a readable measure rather than running the full width. */
.container > .wide-header {
  grid-column: full;
  width: min(100% - 2 * var(--spacing-lg), 64rem);
  margin-inline: auto;
}

.wide-header > p {
  max-width: 44rem;
}

/* A gallery is pictures, not prose, so it has no reading measure to respect.
   This variant breaks out of the text column to a wider block and centres
   itself, which is what lets the tiles be smaller and more numerous without
   the grid feeling cramped.
   👉 Pass class="gallery-grid--wide" to the include. */
.container > .gallery-grid--wide {
  grid-column: full;
  width: min(100% - 2 * var(--spacing-lg), 64rem);
  margin-inline: auto;
}

/* The element always spans the tile; how much of the image it hides is done
   with the gradient, which animates smoothly where a height change would not.
   At rest it is a band across the bottom third carrying only the title. On
   hover the scrim rises to about four fifths, leaving the top of the
   screenshot visible so the tile still reads as a website.
   Deliberately no backdrop-filter: it applies to the element's whole box, so
   a blur here would frost the entire preview no matter what the gradient
   does — which is what made the hover state feel like a full cover. */
.gallery-grid-caption {
  position: absolute;
  inset: 0;
  display: flex;
  flex-direction: column;
  justify-content: flex-end;
  padding: var(--spacing-xs) var(--spacing-sm) var(--spacing-sm);
  background: linear-gradient(
    to top,
    var(--gallery-caption-rest) 0%,
    var(--gallery-caption-rest) 30%,
    transparent 62%
  );
  text-shadow: var(--page-header-title-shadow);
  transition: background var(--transition-normal);
}

.gallery-grid-link:hover .gallery-grid-caption,
.gallery-grid-link:focus-visible .gallery-grid-caption {
  background: linear-gradient(
    to top,
    var(--gallery-caption-active) 0%,
    var(--gallery-caption-active) 78%,
    transparent 94%
  );
}

.gallery-grid-caption h3 {
  margin: 0;
  color: var(--text-on-dark);
  font-size: 0.82rem;
  font-weight: 600;
  line-height: 1.25;
}

.gallery-grid-caption p {
  max-height: 0;
  margin: 0;
  overflow: hidden;
  color: var(--text-on-dark);
  font-size: 0.8rem;
  line-height: 1.45;
  opacity: 0;
  transform: translateY(var(--spacing-xs));
  transition: max-height var(--transition-normal), margin var(--transition-normal), opacity var(--transition-normal), transform var(--transition-normal);
}

.gallery-grid-link:hover .gallery-grid-caption p,
.gallery-grid-link:focus-visible .gallery-grid-caption p {
  max-height: 14rem;
  margin-top: var(--spacing-xs);
  opacity: 1;
  transform: translateY(0);
}

/* Touch devices have no hover, so the description would never be reachable.
   Show it standing rather than leaving those readers with titles only. */
@media (hover: none) {
  .gallery-grid-caption {
      background: linear-gradient(
        to top,
        var(--gallery-caption-active) 0%,
        var(--gallery-caption-active) 78%,
        transparent 94%
      );
    
  }

  .gallery-grid-caption p {
      max-height: 14rem;
      margin-top: var(--spacing-xs);
      opacity: 1;
      transform: none;
    
  }
}

@media (min-width: 768px) {
  .gallery-grid--mosaic .gallery-grid-item:nth-child(6n + 1),
  .gallery-grid--mosaic .gallery-grid-item:nth-child(6n + 5) {
      grid-column: span 2;
      grid-row: span 2;
    
  }
}
