/* ============================================================
   STRUCTURE layer  —  Blue Dreams
   ------------------------------------------------------------
   Additive. Loads AFTER styles.css and theme-warm.css.
   Changes layout rhythm, not colour.

   TO REVERT:
     1. delete the <link> to this file in index.html
     2. restore backup/index.pre-structure.html
   styles.css is still untouched.
   ============================================================ */

/* ---- 1. break the centre ---------------------------------
   every section head was: centred pill, centred h2, centred sub.
   eight times. now the heading sits left with its supporting
   line beside it, so the eye has somewhere to travel.          */
.section > .head{
  text-align:left;
  max-width:none;
  margin-bottom:44px;
  display:grid;
  grid-template-columns:minmax(0,1.15fr) minmax(0,.85fr);
  align-items:end;
  gap:16px 48px;
  grid-template-areas:
    "tag  ."
    "h2   sub";
}
.section > .head .tag{grid-area:tag;justify-self:start;margin-bottom:4px}
.section > .head h2{grid-area:h2;max-width:16ch}
.section > .head .head-sub{grid-area:sub;margin-top:0;padding-bottom:6px;max-width:42ch}

/* the FAQ and the closing CTA stay centred on purpose — the
   contrast against the left-aligned sections is the point */
#faq > .head{
  grid-template-columns:1fr;
  grid-template-areas:"tag" "h2" "sub";
  justify-items:center;
  text-align:center;
  max-width:640px;
  margin-inline:auto;
}
#faq > .head h2{max-width:none}
#faq > .head .head-sub{max-width:46ch;text-align:center}

/* ---- 2. feature the flagship units -----------------------
   six identical cards said all six were equally ordinary, and
   one wide card + five left an orphan on the last row. so the
   FIRST and LAST both run full width (photo beside the detail)
   and the middle four sit in a tidy 2x2. mirrored, so the pair
   bookends the block instead of looking like a mistake.        */
#rooms .grid-2 > .room:first-child,
#rooms .grid-2 > .room:last-child{
  grid-column:1 / -1;
  display:grid;
  grid-template-columns:minmax(0,1.35fr) minmax(0,1fr);
  align-items:stretch;
  gap:0 26px;
  padding:14px;
}
#rooms .grid-2 > .room:first-child .room-img,
#rooms .grid-2 > .room:last-child .room-img{
  grid-row:1 / span 2;
  aspect-ratio:auto;
  height:100%;
  min-height:340px;
}
#rooms .grid-2 > .room:first-child .room-row:nth-of-type(1),
#rooms .grid-2 > .room:last-child .room-row:nth-of-type(1){
  align-self:end;margin-top:0;
}
#rooms .grid-2 > .room:first-child .room-row:nth-of-type(2),
#rooms .grid-2 > .room:last-child .room-row:nth-of-type(2){
  align-self:start;
}
#rooms .grid-2 > .room:first-child h3,
#rooms .grid-2 > .room:last-child h3{font-size:26px}
#rooms .grid-2 > .room:first-child .price,
#rooms .grid-2 > .room:last-child .price{font-size:18px}
#rooms .grid-2 > .room:first-child .shots,
#rooms .grid-2 > .room:last-child .shots{opacity:1;transform:none}

/* first: photo left, words right */
#rooms .grid-2 > .room:first-child .room-row{padding-right:8px}

/* last: mirrored — photo right, words left */
#rooms .grid-2 > .room:last-child{grid-template-columns:minmax(0,1fr) minmax(0,1.35fr)}
#rooms .grid-2 > .room:last-child .room-img{grid-column:2}
#rooms .grid-2 > .room:last-child .room-row{grid-column:1;padding-left:8px}

/* ---- 3. a full-bleed photo moment ------------------------
   everything else lives in a 1080px rounded box. this one
   breaks out edge to edge, square corners, no card.           */
.bleed{
  position:relative;
  margin:0 -14px;                 /* cancel .shell padding */
  height:min(62vh,560px);
  overflow:hidden;
  display:grid;
  place-items:center;
  text-align:center;
}
.bleed img{position:absolute;inset:0;width:100%;height:100%;object-fit:cover}
.bleed::after{
  content:'';position:absolute;inset:0;
  background:linear-gradient(180deg,rgba(20,32,26,.30),rgba(20,32,26,.46));
}
.bleed-inner{position:relative;z-index:2;color:#F1E9DA;padding:0 24px}
.bleed-inner p{
  font-size:12px;letter-spacing:.18em;text-transform:uppercase;opacity:.9;margin-bottom:12px;
}
.bleed-inner h2{
  font-family:'Fraunces','Manrope',Georgia,serif;
  font-size:clamp(26px,3.4vw,44px);color:#F1E9DA;max-width:18ch;margin:0 auto;
}

/* ---- 4. alternating photo / text rows --------------------
   the carousel shows pictures with no words. these rows are
   where the place actually gets described.                    */
.row{
  display:grid;
  grid-template-columns:repeat(2,minmax(0,1fr));
  align-items:center;
  gap:0 56px;
  max-width:var(--content);
  margin:0 auto;
  padding:0 24px 64px;
}
.row:last-of-type{padding-bottom:0}
.row-media{border-radius:var(--r-card);overflow:hidden;aspect-ratio:4/3;background:var(--chip)}
.row-media img{width:100%;height:100%;object-fit:cover}
.row-body h3{
  font-family:'Fraunces','Manrope',Georgia,serif;
  font-size:clamp(22px,2.6vw,32px);margin-bottom:14px;
}
.row-body p{color:var(--muted);font-size:15px;max-width:46ch}
.row.flip .row-media{order:2}

/* zigzag: alternation is driven by position, not a hand-set class that can drift
   out of step when a row is inserted. every even row flips its photo to the right. */
.rows .row:nth-of-type(even) .row-media{order:2}
.rows .row:nth-of-type(odd)  .row-media{order:0}

/* ---- 5. vertical rhythm ----------------------------------
   every section was padding:110px. same beat, eight times.    */
#rooms{padding-top:96px;padding-bottom:104px}
.feature{padding-top:120px;padding-bottom:120px}
#hotel{padding-top:88px;padding-bottom:88px}
#faq{padding-top:96px;padding-bottom:104px}
.carousel-section{padding-top:16px}

/* ---- 6. placeholders the owner still has to fill ---------
   deliberately obvious: this must never be mistaken for copy. */
.todo{
  border:1px dashed #B9AE99;
  border-radius:var(--r-img);
  padding:18px 20px;
  background:rgba(255,255,255,.42);
}
.todo::before{
  content:'NEEDS YOUR INPUT';
  display:block;
  font-size:10px;letter-spacing:.16em;font-weight:700;
  color:#9A8C72;margin-bottom:8px;
}
.todo p{color:var(--muted);font-size:14px;margin:0}
.todo p + p{margin-top:8px}


/* ---- responsive ------------------------------------------ */
@media (max-width:940px){
  .section > .head{
    grid-template-columns:1fr;
    grid-template-areas:"tag" "h2" "sub";
    gap:10px;
  }
  .section > .head h2{max-width:none}
  #rooms .grid-2 > .room:first-child,
  #rooms .grid-2 > .room:last-child{grid-template-columns:1fr}
  #rooms .grid-2 > .room:first-child .room-img,
  #rooms .grid-2 > .room:last-child .room-img{
    grid-row:auto;grid-column:auto;min-height:0;aspect-ratio:16/10;
  }
  #rooms .grid-2 > .room:first-child .room-row,
  #rooms .grid-2 > .room:last-child .room-row{grid-column:auto}
  #rooms .grid-2 > .room:first-child .room-row:nth-of-type(1),
  #rooms .grid-2 > .room:last-child .room-row:nth-of-type(1){margin-top:16px}
  .row{grid-template-columns:1fr;gap:22px;padding-bottom:64px}
  /* stacked: the photo always leads, so reset BOTH the class and the
     nth-of-type zigzag or even rows would put their text above the image */
  .row.flip .row-media,
  .rows .row:nth-of-type(even) .row-media,
  .rows .row:nth-of-type(odd) .row-media{order:0}
}
@media (max-width:760px){
  .bleed{margin:0 -14px;height:min(52vh,420px)}
  .row{padding-left:20px;padding-right:20px}
}

/* ---- 8. carousel is draggable ---------------------------- */
.carousel{cursor:grab;touch-action:pan-y}      /* pan-y keeps vertical page scroll working */
.carousel.is-dragging{cursor:grabbing}
.carousel img{user-select:none;-webkit-user-drag:none}

/* ---- 9. contact buttons, inside the nav pill -------------
   a second floating cluster fought the nav for the corner, so
   they live in the pill instead: one floating thing, always
   in view, no collision to manage. */
.dock{display:flex;gap:7px;align-items:center}
.dock-btn{
  width:36px;height:36px;border-radius:50%;
  display:grid;place-items:center;flex:0 0 auto;
  transition:transform .2s ease,filter .2s ease;
}
.dock-btn svg{width:18px;height:18px}
.dock-btn:hover{transform:translateY(-2px)}
.dock-btn:focus-visible{outline:2px solid var(--accent-ink);outline-offset:3px}

/* WhatsApp wears its own green, not a hover surprise */
.dock-wa{background:#25D366}
.dock-wa svg{fill:#fff}
.dock-wa:hover{filter:brightness(1.07)}

.dock-mail{background:var(--chip)}
.dock-mail svg{fill:var(--dark)}
.dock-mail:hover{background:var(--dark)}
.dock-mail:hover svg{fill:#FBF8F2}

@media (max-width:760px){
  .dock{margin-left:auto;margin-right:2px}
  .dock-btn{width:38px;height:38px}
  .dock-btn svg{width:19px;height:19px}
}

/* ---- 10. shared-space cards open galleries too ----------- */
.post[data-gallery]{cursor:pointer}
.post[data-gallery]:focus-visible{outline:2px solid var(--accent-ink);outline-offset:3px}
.post-img{position:relative}

/* Instagram keeps its own gradient, same as WhatsApp keeps its green */
.dock-ig{
  background:linear-gradient(45deg,#F9CE34 0%,#EE2A7B 45%,#6228D7 100%);
}
.dock-ig svg{fill:#fff}
.dock-ig:hover{filter:brightness(1.08)}

/* ---- 11. enquiry form ------------------------------------
   collects everything, then hands it to WhatsApp or mail. */
.enquiry{
  display:grid;
  grid-template-columns:repeat(4,minmax(0,1fr));
  gap:14px;
  max-width:760px;
  margin:30px auto 0;
  text-align:left;
}
.enquiry .field{display:flex;flex-direction:column;gap:6px}
.enquiry .field.grow{grid-column:span 2}
.enquiry .field.full{grid-column:1/-1}
.enquiry label{
  font-size:11px;letter-spacing:.1em;text-transform:uppercase;
  color:rgba(241,233,218,.72);
}
.enquiry label .opt{text-transform:none;letter-spacing:0;opacity:.65}
.enquiry input,.enquiry select,.enquiry textarea{
  background:rgba(241,233,218,.10);
  border:1px solid rgba(241,233,218,.26);
  color:#F1E9DA;border-radius:12px;padding:11px 13px;
  font-family:inherit;font-size:14px;width:100%;resize:vertical;
}
.enquiry input::placeholder,.enquiry textarea::placeholder{color:rgba(241,233,218,.45)}
.enquiry input:focus,.enquiry select:focus,.enquiry textarea:focus{
  outline:none;border-color:#F1E9DA;background:rgba(241,233,218,.16);
}
.enquiry select option{color:var(--green);background:#F1E9DA}
.enquiry-actions{grid-column:1/-1;display:flex;gap:10px;flex-wrap:wrap;margin-top:4px}
.btn-wa{background:#25D366;color:#fff;display:inline-flex;align-items:center;gap:9px}
.btn-wa svg{width:17px;height:17px;fill:#fff}
.btn-wa:hover{filter:brightness(1.07)}
.btn-outline{background:transparent;color:#F1E9DA;border:1px solid rgba(241,233,218,.4)}
.btn-outline:hover{background:rgba(241,233,218,.14)}

@media (max-width:760px){
  .enquiry{grid-template-columns:repeat(2,minmax(0,1fr));gap:12px}
  .enquiry .field.grow{grid-column:1/-1}
  .enquiry-actions .btn{flex:1 1 100%}
}

.btn-send{background:#F1E9DA;color:var(--green);font-weight:600}
.btn-send:hover{background:#FBF6EC}
.btn-send:disabled{opacity:.6;cursor:default;transform:none}
.enquiry-alt{font-size:13px;color:rgba(241,233,218,.7);align-self:center}
.enquiry-alt a{color:#F1E9DA;text-decoration:underline;text-underline-offset:3px}
.form-note a{color:#F1E9DA;text-decoration:underline}

/* the closing band is a bright beach photo and the form text is sand —
   it disappeared into it. the form now sits on its own dark panel. */
.enquiry{
  background:rgba(20,34,27,.52);
  backdrop-filter:blur(16px) saturate(1.1);
  border:1px solid rgba(241,233,218,.16);
  border-radius:var(--r-card);
  padding:26px;
}
.enquiry label{color:rgba(241,233,218,.85)}
.enquiry input,.enquiry select,.enquiry textarea{
  background:rgba(20,34,27,.34);
  border-color:rgba(241,233,218,.42);
}
.enquiry input::placeholder,.enquiry textarea::placeholder{color:rgba(241,233,218,.55)}
/* headline + sub also sat on bare photo */
.cta::after{background:linear-gradient(180deg,rgba(20,34,27,.58),rgba(20,34,27,.74))}
@media (max-width:760px){ .enquiry{padding:18px} }

/* visually hidden, still read by screen readers and search engines */
.sr-only{
  position:absolute;width:1px;height:1px;padding:0;margin:-1px;
  overflow:hidden;clip:rect(0 0 0 0);white-space:nowrap;border:0;
}

/* ---- 12. phone fixes -------------------------------------- */
@media (max-width:760px){
  /* iOS Safari zooms the whole page when a focused input is under 16px */
  .enquiry input,.enquiry select,.enquiry textarea{font-size:16px}

  /* 44px is the minimum comfortable touch target */
  .dock-btn{width:44px;height:44px}
  .dock-btn svg{width:21px;height:21px}
  .nav-toggle{width:44px;height:44px;display:grid;place-content:center;padding:0}
  .brand{min-height:44px;align-items:center}
  .nav-pill{padding:7px 7px 7px 16px;gap:10px}
  .brand img{height:28px}
  .brand span{font-size:14px}

  /* carousel dots were 7px tall - give them a real hit area
     without changing how they look */
  .dot{position:relative}
  .dot::after{content:'';position:absolute;left:50%;top:50%;
    transform:translate(-50%,-50%);width:34px;height:34px}
  .dots{gap:10px}

  .lb-nav{width:44px;height:44px}
  .lb-close{width:44px;height:44px}
}

@media (max-width:520px){
  /* two columns left the date fields at ~124px, which truncates dd/mm/yyyy */
  .enquiry{grid-template-columns:1fr}
  .enquiry .field.grow,.enquiry .field.full{grid-column:1/-1}
}

/* the unit names are long; at tablet width a quarter-column clipped them */
@media (max-width:940px){
  .enquiry{grid-template-columns:repeat(2,minmax(0,1fr))}
  .enquiry .field.grow,.enquiry .field.full{grid-column:1/-1}
}

/* MUST stay last: the 940px two-column rule above is later in the file than the
   original 520px rule, so it was winning on phones and squeezing the fields. */
@media (max-width:520px){
  .enquiry{grid-template-columns:1fr}
  .enquiry .field.grow,.enquiry .field.full{grid-column:1/-1}
}

/* ---- 13. contact icons: small to look at, big to tap ------
   they were sized 44px so thumbs could hit them, which made
   them visually heavy. now the circle is small and an
   invisible pseudo-element carries the 44px touch target. */
@media (max-width:940px){
  .dock-btn{width:32px;height:32px;position:relative}
  .dock-btn svg{width:16px;height:16px}
  .dock-btn::after{
    content:'';position:absolute;left:50%;top:50%;
    transform:translate(-50%,-50%);width:44px;height:44px;
  }
  .dock{gap:6px}
  .nav-toggle{width:40px;height:44px}
}

/* ---- 14. booking page ------------------------------------- */
.booking-intro{padding-top:150px;padding-bottom:40px}
.booking-facts{max-width:var(--content);margin:0 auto;color:var(--muted);font-size:15px;line-height:1.75}
.booking-facts p + p{margin-top:8px}
.booking-facts a{color:var(--green);text-decoration:underline;text-underline-offset:3px}
.booking-facts strong{color:var(--green)}
@media (max-width:760px){ .booking-intro{padding-top:120px} }

/* ---- 15. booking page sits on the same photo as the closing
   band, running behind the whole page instead of one strip --- */
.booking-page{
  background:url(/img/cta.jpg) center/cover no-repeat fixed;
}
.booking-page::before{
  content:'';position:fixed;inset:0;z-index:0;
  background:linear-gradient(180deg,rgba(20,34,27,.62),rgba(20,34,27,.78));
}
.booking-page .nav,
.booking-page .shell,
.booking-page .footer{position:relative;z-index:1}

/* the CTA section is now just a container - no second photo, no second scrim */
.booking-page .cta{min-height:0;background:transparent;border-radius:0}
.booking-page .cta::after{display:none}
.booking-page .cta-inner{padding-top:0}

/* intro text reads on the photo */
.booking-page .head h2,
.booking-page .booking-facts,
.booking-page .booking-facts strong{color:#F1E9DA}
.booking-page .head-sub{color:rgba(241,233,218,.8)}
.booking-page .booking-facts a{color:#F1E9DA}
.booking-page .tag{
  background:rgba(241,233,218,.14);border-color:rgba(241,233,218,.3);color:#F1E9DA;
}
.booking-page .footer{background:rgba(235,227,212,.96);border-top:0}

@media (max-width:760px){
  /* fixed backgrounds are janky on iOS - scroll it instead */
  .booking-page{background-attachment:scroll}
}

/* ---- 16. TEST: pinned hero --------------------------------
   the photo stays put at full height while the rest of the
   page scrolls up over it. */
.hero-pinned{
  /* the HERO is the sticky element - its parent (.shell) is tall, so it has
     room to stay pinned. sticking the inner stage instead gave it 0px of
     travel, because stage and hero were both exactly 100vh. */
  position:sticky;top:0;
  margin:-14px -14px 0;
  border-radius:0;
  height:100vh;height:100svh;
  min-height:0;
  display:block;
  overflow:hidden;
  background:none;
  z-index:0;
}
.hero-pinned::after{display:none}

.hero-stage{
  position:relative;
  height:100vh;height:100svh;
  display:grid;place-items:center;
  text-align:center;
  overflow:hidden;
}
.hero-stage::after{
  content:'';position:absolute;inset:0;
  background:linear-gradient(180deg,rgba(20,34,27,.34),rgba(20,34,27,.12) 42%,rgba(20,34,27,.55));
}
/* the stage is a centring grid, which shrink-wrapped and centred the
   absolutely-positioned photo instead of stretching it. force it to fill. */
.hero-pinned .hero-bg{
  position:absolute;inset:0;
  width:100%;height:100%;
  max-width:none;
  justify-self:stretch;align-self:stretch;
  object-fit:cover;
}
.hero-pinned .hero-inner{padding:0 24px;position:relative;z-index:2}

/* the page slides over the pinned photo, so it must be opaque and on top */
.after-hero{
  position:relative;z-index:2;
  background:var(--page);
  border-radius:var(--r-hero) var(--r-hero) 0 0;
  margin-top:-40px;
  box-shadow:0 -30px 60px rgba(20,34,27,.22);
}

/* hero text fades as the page climbs over it (browsers without
   scroll-timeline just keep it fully visible - no breakage) */
@media (prefers-reduced-motion:no-preference){
  .hero-stage .hero-inner{
    animation:heroFade linear both;
    animation-timeline:view();
    animation-range:exit 0% exit 70%;
  }
  @keyframes heroFade{ to{ opacity:0; transform:translateY(-30px); } }
}

@media (max-width:760px){
  .hero-pinned,.hero-stage{height:100svh}
  .after-hero{margin-top:-26px}
}

/* ---- 17. hero stage must fill its parent ------------------
   it was computing 469px inside a 636px block parent, which
   dragged the photo in with it. explicit and done. */
.hero-pinned .hero-stage{width:100%;max-width:none}

/* ---- 18. the two full-bleed bands sit BEHIND the page -----
   same trick as the booking page: a fixed background makes
   the photo feel like it is set back in the wall while the
   content slides past it. */
.bleed, .cta{
  background-repeat:no-repeat;
  background-position:center;
  background-size:cover;
  background-attachment:fixed;
}
.bleed{background-image:url(/img/bleed.jpg)}
.cta{background-image:url(/img/cta.jpg)}
.bleed > img, .cta > .cta-bg{display:none}     /* the <img> is now the CSS background */

/* ---- 19. the card photos come FORWARD --------------------
   opposite treatment to the recessed bands: lift them off
   the sand with depth, and let them respond to the cursor. */
.row-media, .post-img, .room-img{
  box-shadow:
    0 2px 4px rgba(20,34,27,.06),
    0 8px 16px rgba(20,34,27,.09),
    0 24px 48px rgba(20,34,27,.14);
  transition:transform .45s cubic-bezier(.2,.7,.3,1), box-shadow .45s ease;
  will-change:transform;
}
.row:hover .row-media,
.post:hover .post-img,
.room:hover .room-img{
  transform:translateY(-8px) scale(1.012);
  box-shadow:
    0 4px 8px rgba(20,34,27,.08),
    0 14px 28px rgba(20,34,27,.12),
    0 40px 72px rgba(20,34,27,.20);
}

/* a slow drift inside the frame as they scroll past: the photo
   is bigger than its window, so it moves against the page */
@media (prefers-reduced-motion:no-preference){
  .row-media img, .post-img img{
    animation:driftUp linear both;
    animation-timeline:view();
    animation-range:entry 0% exit 100%;
    transform-origin:center;
  }
  @keyframes driftUp{
    from{ transform:scale(1.14) translateY(2.5%); }
    to  { transform:scale(1.14) translateY(-2.5%); }
  }
}

@media (max-width:760px){
  /* fixed attachment stays ON for phones/tablets - it is only iOS Safari that
     renders it wrongly, and that is excluded further down, so Android keeps
     the recessed effect instead of everyone losing it */
  .row-media,.post-img,.room-img{
    box-shadow:0 6px 14px rgba(20,34,27,.10),0 18px 34px rgba(20,34,27,.14);
  }
}

/* ---- 20. the page cover must reach the viewport edges -----
   .after-hero lives inside .shell (14px padding), so a 14px
   strip of the PINNED hero was visible down both sides all
   the way to the footer. push the background out, pad the
   content back in so nothing moves. */
.after-hero{
  margin-left:-14px;
  margin-right:-14px;
  padding-left:14px;
  padding-right:14px;
}

/* ---- 21. recessed bands on touch devices -----------------
   iOS Safari sizes a fixed background against the whole
   document, so the photo looks blown up and jumps. It is the
   only engine that does, so exclude just it rather than every
   phone. -webkit-touch-callout only exists on iOS. */
@supports (-webkit-touch-callout: none){
  .bleed, .cta{background-attachment:scroll}
  .booking-page{background-attachment:scroll}
}
