.basicLightbox{
  position:fixed;
  display:flex;
  justify-content:center;
  align-items:center;
  top:0;
  left:0;
  width:100%;
  height:100vh;
  background:rgba(0,0,0,.8);
  opacity:.01;
  transition:opacity .4s ease;
  z-index:1000;
  will-change:opacity;
}
.basicLightbox--visible{
  opacity:1;
}
.basicLightbox__placeholder{
  max-width:100%;
  transform:scale(.9);
  transition:transform .4s ease;
  z-index:1;
  will-change:transform;
}
.basicLightbox__placeholder>iframe:first-child:last-child,
.basicLightbox__placeholder>img:first-child:last-child,
.basicLightbox__placeholder>video:first-child:last-child{
  display:block;
  position:absolute;
  top:0;
  right:0;
  bottom:0;
  left:0;
  margin:auto;
  max-width:95%;
  max-height:95%;
}
.basicLightbox__placeholder>iframe:first-child:last-child,
.basicLightbox__placeholder>video:first-child:last-child{
  pointer-events:auto;
}
.basicLightbox__placeholder>img:first-child:last-child,
.basicLightbox__placeholder>video:first-child:last-child{
  width:auto;
  height:auto;
}
.basicLightbox--iframe .basicLightbox__placeholder,
.basicLightbox--img .basicLightbox__placeholder,
.basicLightbox--video .basicLightbox__placeholder{
  width:100%;
  height:100%;
  pointer-events:none;
}
.basicLightbox--visible .basicLightbox__placeholder{
  transform:scale(1);
}


:root{
  --ink-forest:#3C4B2E;
  --ember:#C2701E;
  --ember-2:#A75C15;
  --bark:#6B4F35;
  --ink-body:#33322B;
  --void:#0A0906;

  --text-on-photo: #F4EFE3;
  --text-on-photo-dim: rgba(244,239,227,0.8);
  --hairline: rgba(244,239,227,0.16);
  --tile-bg: rgba(10,9,6,0.55);
  --tile-bg-hover: rgba(194,112,30,0.22);
  --tile-text: #F4EFE3;
  --panel-bg: rgba(244,239,227,0.84);
  --panel-blur: 7px;
}

:root[data-theme="light"]{
  --text-on-photo: #2E2B21;
  --text-on-photo-dim: rgba(46,43,33,0.72);
  --hairline: rgba(46,43,33,0.14);
  --tile-bg: rgba(255,255,255,0.55);
  --tile-bg-hover: rgba(194,112,30,0.18);
  --tile-text: #2E2B21;
  --panel-bg: rgba(255,255,255,0.82);
  --panel-blur: 5px;
  --void:#EDE7D8;
}

*{margin:0;padding:0;box-sizing:border-box;}

body{
  font-family:-apple-system,BlinkMacSystemFont,"Segoe UI",Roboto,Helvetica,Arial,sans-serif;
  color:var(--text-on-photo);
  min-height:100vh;
  background-color:var(--void);
  transition:background-color 2000ms ease, color 2000ms ease;
}

a{color:inherit;}
button{font:inherit;}

/* ---------- theme toggle : same fixed upper-right control as the main
   page, same destination-based icon logic ---------- */

.theme-toggle{
  all:unset;
  cursor:pointer;
  position:fixed;
  top:1rem; right:1rem;
  z-index:1001;
  width:2.75rem; height:2.75rem;
  border-radius:50%;
  display:flex; align-items:center; justify-content:center;
  color:var(--text-on-photo);
  background:var(--tile-bg);
  -webkit-backdrop-filter:blur(6px);
  backdrop-filter:blur(6px);
  box-shadow:0 2px 10px rgba(0,0,0,0.3);
  transition:background-color 1150ms ease, color 2000ms ease;
}
.theme-toggle:hover{ background:var(--tile-bg-hover); }
.theme-toggle svg{ width:1.3rem; height:1.3rem; }
.theme-toggle .icon-moon{ display:none; }
:root[data-theme="light"] .theme-toggle .icon-sun{ display:none; }
:root[data-theme="light"] .theme-toggle .icon-moon{ display:block; }

/* ---------- page header ---------- */

.page-header{
  max-width:78rem;
  margin:0 auto;
  padding:clamp(3.5rem,9vh,5.5rem) clamp(1.25rem,5vw,3rem) 2.5rem;
}
.page-header .site-link{
  display:inline-block;
  font-size:0.78rem;
  font-weight:700;
  letter-spacing:0.1em;
  text-transform:uppercase;
  color:var(--text-on-photo-dim);
  text-decoration:none;
  transition:color 200ms ease;
}
.page-header .site-link:hover{ color:var(--ember); }
.page-header .page-title{
  margin-top:0.75rem;
  font-size:clamp(1.9rem,5vw,2.75rem);
  font-weight:600;
  letter-spacing:-0.01em;
  text-wrap:balance;
}
.page-header .intro{
  margin-top:0.85rem;
  max-width:38rem;
  color:var(--text-on-photo-dim);
  line-height:1.65;
}

/* ---------- gallery : each verbatim <section id="sec_YYYY"> becomes its
   own grid, styled purely via the id-prefix attribute selector below ..
   zero wrapper markup added around the client's own content ---------- */

.gallery{
  max-width:78rem;
  margin:0 auto;
  padding:0 clamp(1.25rem,5vw,3rem) 1rem;
}
.gallery section[id^="sec_"]{
  display:grid;
  grid-template-columns:repeat(auto-fill,minmax(150px,1fr));
  gap:0.65rem;
  /* matches the grid's own gap exactly, so the seam between one year's
     last row and the next year's tile reads as the same uniform gap as
     everywhere else, not a bigger one .. each <section> is still its
     own separate grid (not a single continuous one across years), but
     this makes that invisible */
  margin-top:0.65rem;
}
.gallery section[id^="sec_"]:first-of-type{ margin-top:0; }
/* the year label is now a proper grid tile, same footprint as a photo,
   not a full-width divider .. it opens the SAME photo viewer at a
   dedicated title-card for that year (see the script below), so it
   reads and behaves like any other cell in the grid */
.gallery section[id^="sec_"] h3{
  aspect-ratio:1;
  margin:0;
  border-radius:10px;
  cursor:pointer;
  display:flex;
  align-items:center;
  justify-content:center;
  font-size:clamp(1.6rem,4vw,2.3rem);
  font-weight:700;
  letter-spacing:-0.01em;
  color:#F4EFE3;
  background:linear-gradient(155deg, var(--ember) 0%, var(--bark) 100%);
  box-shadow:0 2px 8px rgba(0,0,0,0.3);
  transition:transform 220ms ease, box-shadow 220ms ease;
}
.gallery section[id^="sec_"] h3:hover{
  transform:translateY(-3px) scale(1.02);
  box-shadow:0 10px 24px rgba(0,0,0,0.4);
}
.gallery section[id^="sec_"] img{
  width:100%;
  aspect-ratio:1;
  object-fit:cover;
  border-radius:10px;
  cursor:pointer;
  display:block;
  background:var(--tile-bg);
  box-shadow:0 2px 8px rgba(0,0,0,0.25);
  transition:transform 220ms ease, box-shadow 220ms ease;
}
.gallery section[id^="sec_"] img:hover{
  transform:scale(1.08);
  box-shadow:0 10px 24px rgba(0,0,0,0.4);
  position:relative;
  z-index:1;
}

/* ---------- back link : the verbatim <section class="articleMenu"><h2><a>
   is left untouched .. display:contents drops the two wrapper boxes from
   layout so the <a> alone renders as the pill button below ---------- */

.back-link-wrap{
  max-width:78rem;
  margin:0 auto;
  padding:0 clamp(1.25rem,5vw,3rem) 3rem;
}
.back-link-wrap .articleMenu,
.back-link-wrap .articleMenu h2{ display:contents; }
.back-link-wrap a{
  display:inline-flex;
  align-items:center;
  gap:0.5rem;
  padding:0.75rem 1.3rem;
  border-radius:999px;
  background:var(--tile-bg);
  color:var(--tile-text);
  text-decoration:none;
  font-weight:600;
  font-size:0.9rem;
  -webkit-backdrop-filter:blur(6px);
  backdrop-filter:blur(6px);
  transition:background-color 180ms ease, color 2000ms ease;
}
.back-link-wrap a:hover{ background:var(--tile-bg-hover); }

/* ---------- footer : verbatim contact + copyright, given the same
   frosted panel treatment as the main page's lightbox cards ---------- */

.site-footer{
  max-width:78rem;
  margin:0 auto;
  padding:0 clamp(1.25rem,5vw,3rem) clamp(3rem,8vh,5rem);
}
.site-footer .wrapper{
  background:var(--panel-bg);
  -webkit-backdrop-filter:blur(var(--panel-blur));
  backdrop-filter:blur(var(--panel-blur));
  border-top:4px solid var(--ember);
  border-radius:14px;
  padding:clamp(1.5rem,4vw,2.25rem);
  color:var(--ink-body);
  transition:background-color 2000ms ease;
}
.site-footer h3{
  font-family:Georgia,"Iowan Old Style",serif;
  font-weight:400;
  font-size:1.1rem;
  color:var(--bark);
  margin-bottom:0.9rem;
}
.site-footer ul{ list-style:none; }
.site-footer li{ margin-bottom:1rem; }
.site-footer li:last-child{ margin-bottom:0; }
.site-footer dt{
  font-weight:700;
  color:var(--ink-forest);
  font-size:0.78rem;
  letter-spacing:0.04em;
  text-transform:uppercase;
  margin-bottom:0.2em;
}
.site-footer dd{ margin-bottom:0.3em; }
.site-footer a{ color:var(--ember-2); }
.site-footer .copyRightNotice{
  margin-top:1.25rem;
  font-size:0.78rem;
  color:var(--ink-body);
  opacity:0.7;
}

/* ---------- the single-photo viewer ---------- */

.lb-photo{
  position:relative;
  max-width:92vw;
  max-height:88vh;
  display:flex;
  touch-action:none;
  transition:transform 650ms ease, opacity 650ms ease;
}
@media (prefers-reduced-motion: reduce){
  .lb-photo{ transition:opacity 650ms ease; }
}
.lb-photo img{
  max-width:92vw;
  max-height:88vh;
  width:auto;
  height:auto;
  display:block;
  border-radius:6px;
  box-shadow:0 30px 80px rgba(0,0,0,0.6);
}
.basicLightbox{ background:rgba(0,0,0,0.88); }

/* prev/next : always immediately flanking whatever's currently
   displayed .. photos have no fixed width (arbitrary aspect ratios), so
   there's no CSS formula that actually hugs the real edge the way
   .lb-year-card's own fixed width would allow .. position is instead
   driven every frame from JS (see trackFlankingNav), measuring the
   displayed card's real, live bounding box .. left/top here are just
   the initial fallback before the first measurement lands */
.lb-nav{
  all:unset;
  cursor:pointer;
  position:fixed;
  top:50%;
  left:1.25rem;
  transform:translateY(-50%);
  width:2.75rem; height:2.75rem;
  border-radius:50%;
  display:flex; align-items:center; justify-content:center;
  color:var(--bark);
  background:#F4EFE3;
  box-shadow:0 2px 10px rgba(0,0,0,0.35);
  z-index:1001;
  opacity:0.72;
  transition:opacity 200ms ease, background-color 150ms ease;
}
.lb-nav:hover{ opacity:1; background:#EAE1CC; }
.lb-nav--next{ left:auto; right:1.25rem; }
@media (max-width:760px){
  .lb-nav{ display:none; }
}
.lb-nav svg{ width:1.1rem; height:1.1rem; }

/* a second, REDUNDANT pair, always fixed at the bottom-center .. never
   moved by JS .. next to the flanking pair, this gives a predictable
   click target regardless of the current photo's size, alongside the
   pair that tracks it */
.lb-nav--fixed{
  top:auto;
  bottom:1.5rem;
  transform:none;
}
.lb-nav--fixed.lb-nav--prev{ left:calc(50% - 3.125rem); right:auto; }
.lb-nav--fixed.lb-nav--next{ left:calc(50% + 0.375rem); right:auto; }
.lb-nav[hidden]{ display:none; }
.lb-nav--hover-static{ opacity:1; transition:none; }

/* explicit close, mirroring the theme toggle's position on the other
   corner .. tapping the photo or the backdrop also close it, but this
   is the visible, discoverable way back */
.lb-close{
  all:unset;
  cursor:pointer;
  position:fixed;
  top:1rem; left:1rem;
  z-index:1001;
  width:2.75rem; height:2.75rem;
  border-radius:50%;
  display:flex; align-items:center; justify-content:center;
  color:var(--bark);
  background:#F4EFE3;
  box-shadow:0 2px 10px rgba(0,0,0,0.3);
  transition:background-color 150ms ease;
}
.lb-close:hover{ background:#EAE1CC; }
.lb-close svg{ width:1.2rem; height:1.2rem; }
.lb-close[hidden]{ display:none; }

/* the year title-card shown inside the viewer .. a bookmark between one
   year's photos and the next in the same navigable sequence .. the mini
   year strip used to live inside this wrap too, but it's now the
   persistent, page-fixed .lb-year-hbar below instead */
.lb-year-wrap{
  display:flex;
  align-items:center;
  justify-content:center;
}
.lb-year-card{
  width:min(70vw,20rem);
  height:min(70vw,20rem);
  display:flex;
  align-items:center;
  justify-content:center;
  border-radius:16px;
  background:linear-gradient(155deg, var(--ember) 0%, var(--bark) 100%);
  color:#F4EFE3;
  font-size:clamp(2.2rem,8vw,4rem);
  font-weight:700;
  letter-spacing:-0.02em;
  box-shadow:0 30px 80px rgba(0,0,0,0.6);
  transition:transform 180ms ease, box-shadow 180ms ease;
}
/* scale/glow only, no shift - same "no directional movement" preference
   already settled on for the mini year buttons */
.lb-year-card:hover{
  transform:scale(1.02);
  box-shadow:0 34px 90px rgba(0,0,0,0.68);
}

/* miniature versions of every year-panel, lined up below the displayed
   one on a single row .. clicking any of them jumps straight there, the
   current one held slightly brighter with a ring so position stays
   legible .. when they all fit, it's a plain row with no chrome ; once
   they overflow, small scroll buttons appear (see JS) and the row itself
   is drag-scrollable */
/* the nav buttons live in their own FIXED-size grid columns, outside the
   scrollable track (the middle 1fr column) entirely - not overlapping
   it, and not sharing its width the way flex siblings would .. because
   the columns are hard-coded sizes (not auto/content-based), hiding a
   button never changes any column's size, so the track's own width
   never shifts .. that's what removed the flicker, and this keeps the
   buttons visually outside the scroll area rather than overlaid on it */
.lb-year-strip-wrap{
  display:grid;
  grid-template-columns:1.9rem 1fr 1.9rem;
  align-items:center;
  gap:0.5rem;
  max-width:min(90vw,30rem);
}
/* the persistent, page-fixed instance : a constant screen position,
   never tied to whatever card is currently on display .. shown/hidden
   instantly via [hidden] - deliberately no opacity transition of its
   own, so it never fades */
.lb-year-hbar{
  position:fixed;
  left:50%;
  bottom:5rem;
  transform:translateX(-50%);
  z-index:1001;
}
.lb-year-hbar[hidden]{ display:none; }
@media (max-width:760px){
  .lb-year-hbar{ display:none; }
}
.lb-year-strip{
  grid-column:2;
  display:flex;
  flex-wrap:nowrap;
  gap:0.5rem;
  overflow-x:auto;
  scroll-behavior:smooth;
  scrollbar-width:none;
  cursor:grab;
  /* the year labels are text .. without this, a mouse-drag starting on
     one begins native text selection instead of (or fighting) the
     custom scroll-follow below */
  user-select:none;
  -webkit-user-select:none;
}
.lb-year-strip.is-dragging{ cursor:grabbing; }
.lb-year-strip::-webkit-scrollbar{ display:none; }
.lb-year-mini{
  all:unset;
  cursor:pointer;
  flex:0 0 auto;
  width:3.5rem;
  height:3.5rem;
  border-radius:8px;
  display:flex;
  align-items:center;
  justify-content:center;
  font-size:0.9rem;
  font-weight:700;
  color:#F4EFE3;
  background:linear-gradient(155deg, var(--ember) 0%, var(--bark) 100%);
  opacity:0.5;
  box-shadow:0 2px 6px rgba(0,0,0,0.3);
  transition:opacity 180ms ease, transform 180ms ease;
}
.lb-year-mini:hover{ opacity:0.85; }
.lb-year-mini--active{
  opacity:1;
  box-shadow:0 0 0 2px #F4EFE3, 0 2px 6px rgba(0,0,0,0.3);
}
.lb-year-strip-nav{
  all:unset;
  cursor:pointer;
  width:1.9rem;
  height:1.9rem;
  border-radius:50%;
  display:flex;
  align-items:center;
  justify-content:center;
  color:var(--bark);
  background:#F4EFE3;
  box-shadow:0 2px 6px rgba(0,0,0,0.35);
  opacity:0.85;
  transition:opacity 150ms ease;
}
.lb-year-strip-nav:hover{ opacity:1; }
.lb-year-strip-nav[hidden]{ display:none; }
.lb-year-strip-nav svg{ width:0.9rem; height:0.9rem; }
.lb-year-strip-nav--left{ grid-column:1; }
.lb-year-strip-nav--right{ grid-column:3; }

/* a second, PERSISTENT year picker : a vertical bar fixed to the right
   edge, centered vertically in the viewport, visible on any panel (not
   just a year-card) so jumping to a year doesn't require navigating
   back to one first .. same fits-on-one-line-or-gets-scroll-controls
   behavior as the horizontal strip, just on the other axis - and the
   same fixed-size-grid-cell reasoning for why the buttons sit outside
   the scrollable track rather than overlapping or resizing it */
.lb-year-vbar{
  position:fixed;
  right:1.25rem;
  top:50%;
  transform:translateY(-50%);
  z-index:1001;
  display:grid;
  grid-template-rows:1.9rem auto 1.9rem;
  justify-items:center;
  gap:0.5rem;
}
.lb-year-vbar[hidden]{ display:none; }
@media (max-width:760px){
  .lb-year-vbar{ display:none; }
}
.lb-year-strip-nav--up{ grid-row:1; }
.lb-year-strip-nav--down{ grid-row:3; }
.lb-year-vbar-track{
  grid-row:2;
  display:flex;
  flex-direction:column;
  gap:0.5rem;
  max-height:min(42vh,18rem);
  overflow-y:auto;
  scrollbar-width:none;
  cursor:grab;
  user-select:none;
  -webkit-user-select:none;
}
.lb-year-vbar-track.is-dragging{ cursor:grabbing; }
.lb-year-vbar-track::-webkit-scrollbar{ display:none; }
.lb-year-vbar-track .lb-year-mini{
  width:2.5rem;
  height:2.5rem;
  font-size:0.72rem;
}

/* a miniature corner icon on every PHOTO (not on a year card) that jumps
   straight back to that photo's own year title-card, same idea as the
   main page's corner menu icon */
.lb-back-icon{
  all:unset;
  cursor:pointer;
  position:absolute;
  top:0.9rem; right:0.9rem;
  z-index:2;
  display:grid;
  grid-template-columns:repeat(2, 1fr);
  gap:3px;
  width:1.6rem; height:1.6rem;
  padding:3px;
  border-radius:5px;
  background:rgba(0,0,0,0.35);
  transition:background-color 150ms ease, transform 150ms ease;
}
.lb-back-icon:hover{ background:rgba(194,112,30,0.55); transform:scale(1.1); }
.lb-back-icon span{ background:#F4EFE3; border-radius:1px; }

/* fixed page-scroll controls for the grid itself, hidden while the
   viewer is open */
.page-scroll-nav{
  position:fixed;
  right:1.25rem;
  bottom:1.25rem;
  z-index:900;
  display:flex;
  flex-direction:column;
  gap:0.6rem;
}
.page-scroll-nav[hidden]{ display:none; }
.page-scroll-nav button{
  all:unset;
  cursor:pointer;
  width:2.75rem; height:2.75rem;
  border-radius:50%;
  display:flex; align-items:center; justify-content:center;
  color:var(--bark);
  background:#F4EFE3;
  box-shadow:0 2px 10px rgba(0,0,0,0.3);
  opacity:0.8;
  transition:opacity 200ms ease, background-color 150ms ease;
}
.page-scroll-nav button:hover{ opacity:1; background:#EAE1CC; }
.page-scroll-nav svg{ width:1.1rem; height:1.1rem; }