/* Step 4 is the real CRM screen from its first appearance through the final
   push. It remains one node inside the journey for the entire sequence. */

.journey-finish{
  --channel-scale:1;
  position:absolute;
  z-index:9;
  left:50%;
  top:50%;
  width:900px;
  max-width:88%;
  aspect-ratio:16/9;
  overflow:hidden;
  border-radius:16px;
  background:var(--mist);
  box-shadow:0 34px 76px -52px rgb(25 23 28 / .58);
  opacity:1;
  transform:translate3d(-50%,-50%,0);
  transform-origin:center;
  pointer-events:none;
}

/* Step 4 reuses the finished CRM interface rendered by the walkthrough below.
   This copy stays static and combines the full desktop app with the supplied
   real iPhone frame instead of relying on the old desktop screenshot. */
.journey-finish:has(.journey-crm-static){
  width:min(1120px,94%);
  max-width:none;
  overflow:visible;
  background:transparent;
  box-shadow:none;
}

/* The chip placeholder is retired. Standing two channel icons in for the
   inbox meant the card entered as an empty grey panel and only became the
   product at the full-screen reveal, so the tile advertised something other
   than where it was taking you. The real CRM is already mounted by the time
   the tile enters (desktop showed it from entry all along), so the card now
   previews its own destination at every width. */

.journey-crm-static{
  position:absolute;
  inset:0;
  border-radius:inherit;
  container-type:inline-size;
}

.journey-crm-static>.channels-shot{
  width:100%;
  height:100%;
  object-fit:cover;
  border-radius:inherit;
}

.journey-crm-static.is-ready>.crm-ui{
  width:100%;
  height:100%;
  --crm-board-h:calc(100% - 38px);
}

.journey-finish .journey-crm-static.is-ready>.crm-phone{
  display:block;
  left:-10%;
  right:auto;
  bottom:-5%;
  width:24%;
  height:auto;
  opacity:1;
  transform:none;
}

.journey-crm-static .crm-phone__bubble{
  opacity:1;
  transform:none;
}

/* The pushed-away card has one job left: sign the finished system. Keep the
   full CRM and real iPhone in Step 4, then reduce the payoff thumbnail to the
   product mark instead of leaving a cropped fragment of the app behind. */
.journey-finish>.journey-crm-brand{
  display:none;
  position:absolute;
  z-index:20;
  inset:0;
  align-items:center;
  justify-content:center;
  gap:clamp(8px,4cqw,14px);
  margin:0;
  padding:12px;
  border-radius:inherit;
  background:var(--white);
  box-shadow:0 18px 42px -28px rgb(25 23 28 / .48);
  container-type:inline-size;
  opacity:0;
  pointer-events:none;
}

.journey-crm-brand .crm-ui__brand-mark,
.journey-crm-brand .crm-ui__brand-mark img{
  width:clamp(28px,16cqw,48px);
  height:clamp(28px,16cqw,48px);
  border-radius:clamp(7px,4cqw,12px);
}

.journey-crm-brand .crm-ui__brand-name{
  color:var(--ink);
  font-size:clamp(15px,8.5cqw,25px);
  font-weight:750;
  letter-spacing:-.03em;
}

.journey-finish.is-brand-card>.journey-crm-brand{
  display:flex;
  opacity:var(--keep-brand-reveal,1);
}

/* The phone belongs in the full static composition, not inside the tiny card
   after the journey has pushed that entire scene into its payoff position. */
.journey-finish.is-keep-card .journey-crm-static>.crm-phone{
  display:none;
}

/* The former standalone CRM chapter now resolves inside Step 4 itself. Its
   final instruction sits beside the same live inbox/phone composition, then
   clears as the Guru begins the existing push into the commission payoff. */
.journey-crm-step-copy{
  position:absolute;
  z-index:10;
  left:4%;
  top:50%;
  width:min(31%,390px);
  color:var(--ink);
  opacity:0;
  transform:translate3d(0,calc(-50% + 18px),0);
  transition:opacity .22s ease,transform .32s cubic-bezier(.22,.61,.36,1);
  pointer-events:none;
}

.journey-crm-step-copy em{
  color:var(--navy-2);
  font-size:13px;
  font-style:normal;
  font-weight:800;
  letter-spacing:.12em;
  text-transform:uppercase;
}

.journey-crm-step-copy h2{
  max-width:10ch;
  margin:18px 0 0;
  font-size:clamp(2.35rem,3.8vw,4.15rem);
  line-height:.98;
  letter-spacing:-.045em;
}

.journey-crm-step-copy p{
  max-width:34ch;
  margin:20px 0 0;
  color:var(--muted);
  font-size:clamp(15px,1.25vw,18px);
  line-height:1.5;
}

.journey-crm-card-face small{
  display:block;
  margin-bottom:8px;
  font-size:11px;
  font-weight:800;
  letter-spacing:.1em;
  text-transform:uppercase;
}

/* The final tile's label sits over the CRM preview while it is still one of
   the four cards. The preview itself is z-index 9, so this face must be above
   it; the expanded desktop composition has its own full Step 04 copy. */
.journey-crm-card-face{z-index:11}

.journey-crm-card-face strong{
  display:block;
  max-width:12ch;
}

@media(min-width:1000px){
  .journey-step--bookings.is-crm-expanded .journey-crm-card-face{
    opacity:0;
  }

  .journey-step--bookings.is-crm-expanded .journey-crm-step-copy{
    opacity:1;
    transform:translate3d(0,-50%,0);
  }

  .journey-step--bookings.is-crm-expanded .journey-finish:has(.journey-crm-static){
    left:67%;
    width:min(900px,62%);
  }

  .journey-step--bookings.is-crm-copy-clear .journey-crm-step-copy{
    opacity:0;
    transform:translate3d(0,calc(-50% - 12px),0);
  }
}

@media(max-width:999px){
  .journey-crm-step-copy{display:none}
  .journey-step--bookings.is-push-active .journey-crm-card-face{opacity:0}
}

.channels-screen{
  width:900px;
  height:506.25px;
  display:grid;
  grid-template-columns:170px 1fr;
  gap:10px;
  padding:10px;
  background:var(--mist);
  color:var(--ink);
  font-family:var(--sans);
  transform:scale(var(--channel-scale,1));
  transform-origin:top left;
}

.channels-rail,
.channels-main{
  min-width:0;
  overflow:hidden;
  border-radius:14px;
  background:var(--white);
}

.channels-rail{
  display:flex;
  flex-direction:column;
  padding:18px 12px;
}

.channels-brand{display:flex;align-items:center;gap:8px;color:var(--ink)}
.channels-brand img{width:26px;height:26px;flex:none}
.channels-brand strong{font-size:13px;letter-spacing:-.02em}

.channels-rail>p{
  margin:7px 6px 18px;
  color:var(--muted);
  font-size:9px;
  font-weight:750;
  letter-spacing:.05em;
  text-transform:uppercase;
}

.channels-nav{display:grid;gap:3px}
.channels-nav span{
  min-height:32px;
  display:flex;
  align-items:center;
  gap:8px;
  padding:0 9px;
  border-radius:8px;
  font-size:10px;
  font-weight:650;
}

.channels-nav span::before{
  content:"";
  width:12px;
  height:12px;
  flex:none;
  border:1.4px solid currentColor;
  border-radius:3px;
}

.channels-nav .is-active{background:#f1ebff;color:var(--navy)}

.channels-user{
  min-height:42px;
  display:flex;
  align-items:center;
  gap:9px;
  margin-top:auto;
  padding:0 9px;
  border-radius:9px;
  background:var(--mist);
  font-size:10px;
  font-weight:700;
}

.channels-user b{
  width:22px;
  height:22px;
  display:grid;
  place-items:center;
  flex:none;
  border-radius:50%;
  background:var(--teal);
  color:var(--white);
  font-size:7px;
}

.channels-main{padding:0 25px 22px}
.channels-topbar{height:62px;display:flex;align-items:center;justify-content:space-between;gap:12px}
.channels-topbar h3{margin:0;font-size:20px;letter-spacing:-.03em}

.channels-topbar>span,
.channels-row em{
  border-radius:999px;
  background:#eaf8f0;
  color:#16784b;
  font-style:normal;
  font-weight:800;
}

.channels-topbar>span{padding:6px 9px;font-size:9px}
.channels-content h4{margin:0;font-size:24px;line-height:1;letter-spacing:-.03em}
.channels-content>p{margin:6px 0 20px;color:var(--muted);font-size:11px}
.channels-list{overflow:hidden;border:1px solid var(--line);border-radius:12px}

.channels-row{
  min-height:67px;
  display:grid;
  grid-template-columns:auto minmax(0,1fr) auto;
  align-items:center;
  gap:12px;
  padding:12px 14px;
}

.channels-row+.channels-row{border-top:1px solid var(--line)}
.channels-provider{width:34px;height:34px;display:grid;place-items:center;flex:none;border-radius:50%;background:#f1ebff;font-style:normal}
.channels-provider svg{width:19px;height:19px}
.channels-row>span{min-width:0}
.channels-row b,.channels-row small{display:block}
.channels-row b{font-size:11px}
.channels-row small{margin-top:2px;color:var(--muted);font-size:9px;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.channels-row em{padding:5px 8px;font-size:8px}

@media(max-width:999px){
  .journey-finish{
    --channel-scale:1;
    top:50%;
    width:900px;
    max-width:88%;
    border-radius:12px;
    box-shadow:none;
  }

  /* No chip-to-CRM crossfade here any more. `.is-crm-expanded` is not a
     reveal switch, it is the full-stage layout state (it also moves the
     desktop panel, releases the clip-path, opens the step copy and compacts
     the WhatsApp dock), so gating the visual on it withheld the inbox for the
     whole approach. The CRM now renders from the tile's first frame at every
     width and `.is-crm-expanded` stays at fill>.82 where the rest of the
     journey depends on it. */
}

@media(prefers-reduced-motion:reduce){
  .journey-finish{opacity:1;transform:translate3d(-50%,-50%,0)}
}

/* ---------------------------------------------------------------
   Phone (<=768px) only. Desktop and tablet keep the 16/9 card and the
   JS-driven --channel-scale exactly as they were.

   On a phone the card is only ~319px wide, so scaling the 900px desktop
   screen into it landed the interface at scale .35 - 11px labels rendered
   at under 4px, i.e. an unreadable grey smear. Two changes fix it at the
   source rather than by nudging the scale:
     1. the card goes portrait (3/4), which buys real vertical room;
     2. the screen stops being a scaled 900px design and becomes a fluid
        layout sized in container units, so every label is legible at
        whatever width the push leaves the card.
   container-type:size is safe here because aspect-ratio gives the card a
   definite height.
   --------------------------------------------------------------- */
@media(max-width:768px){
  .journey-finish{
    aspect-ratio:3/4;
    container-type:size;
  }

  .channels-screen{
    width:100%;
    height:100%;
    display:flex;
    flex-direction:column;
    gap:0;
    padding:3.4cqw;
    transform:none;
  }

  /* The rail is chrome, not content. On a 319px card it ate a third of the
     width to show six nav labels nobody can read; the channel list is the
     point of this screen. */
  .channels-rail{display:none}

  .channels-main{padding:0 4.4cqw 4.4cqw;flex:1;min-height:0}
  .channels-topbar{height:auto;padding:4.6cqw 0 3.4cqw}
  .channels-topbar h3{font-size:6.2cqw}
  .channels-topbar>span{padding:1.6cqw 2.6cqw;font-size:3.2cqw}

  .channels-content h4{font-size:6.4cqw;line-height:1.05}
  .channels-content>p{margin:2.2cqw 0 4.4cqw;font-size:3.6cqw;line-height:1.35}

  .channels-list{border-radius:3.4cqw}
  .channels-row{
    min-height:0;
    gap:3.4cqw;
    padding:3.6cqw 3.8cqw;
  }
  .channels-provider{width:9.6cqw;height:9.6cqw}
  .channels-provider svg{width:5.4cqw;height:5.4cqw}
  .channels-row b{font-size:4cqw}
  .channels-row small{margin-top:.6cqw;font-size:3.2cqw}
  .channels-row em{padding:1.4cqw 2.4cqw;font-size:2.9cqw}
}

/* ---------------------------------------------------------------
   Phone (<=768px), keep beat only: two clear bands.

   The keep beat is the only place the Step 4 card, the purple Guru and the
   "Your direct channel" payoff are on screen together. On a phone the card
   used to be PINNED here at 120px in the top-left corner for the whole beat,
   with the Guru teleported to a fixed offset beside it - which meant the
   push had nothing to push, the card read as a postage stamp, and for the
   stretch before the words arrive the screen was two small objects and about
   70% empty panel.

   The card is no longer pinned. js/booking-keep.js drives it on the phone the
   same way it drives it on desktop, only mirrored: it lands top-LEFT instead
   of top-right (the site's own fixed menu button owns the top-right corner)
   and the Guru is flipped to push it that way. That gives:

     band 1, top          the card at 58% of the stage width, real size,
                          with the Guru walking it in from its right edge
     band 2, from 41%     the label, the payoff lines and the CRM link

   Nothing in this file positions the card any more; the geometry lives with
   the motion that owns it.
   --------------------------------------------------------------- */
@media(max-width:768px){
  /* Belongs to the card wherever the push has left it. The shot is a
     2000x1157 desktop capture and the keep card is portrait, so the only
     honest reading is the conversation column on its own - which is what the
     app itself shows on a phone. cover scales to the frame height and the
     horizontal window is parked on the guest list rather than centred across
     the whole desktop. */
  .system-journey[data-keep-active] .journey-finish.is-keep-card{
    border:1px solid rgb(25 23 28 / .08);
    background:var(--white);
    box-shadow:0 18px 40px -26px rgb(25 23 28 / .5);
    container-type:normal;
  }

  .system-journey[data-keep-active] .journey-finish.is-keep-card .channels-shot{
    object-fit:cover;
    object-position:22% 0;
    transform:none;
  }

  .system-journey[data-keep-active] .keep-push-guru{width:104px}

  /* Band 2. Was 54% - re-measured against the actual landed card (168px wide,
     top 98, height width*9/16 ~= 94.5px once brandReveal completes, so the
     card's floor sits at ~192px of an 844 stage, ~23%). 54% was clearing a
     card roughly double that height, and left a tall blank gap above the
     "0% commission / 100% yours" text - Reuben's round-2 report. 32% keeps a
     real gutter under the landed card and the Guru's feet while pulling the
     text block up out of that dead space. */
  /* justify-content:center on .keep-payoff (booking-keep.css) re-centres this
     tall inset box's content vertically, which was silently eating the gutter
     the 32% top inset just bought back - the text rendered ~115px lower than
     the inset alone implied. flex-start makes the inset the actual text
     position instead of a box the text floats inside. */
  .system-journey[data-keep-active] .keep-payoff{inset:32% 20px 5%;justify-content:flex-start}
}

/* ---------------------------------------------------------------
   Phone (<=768px): Step 4 IS a phone.

   The card used to be a 3/4 box showing crm-real.webp - a 2000x1157 desktop
   capture - with object-fit:cover and the window parked at 22%. What that
   actually rendered was a vertical slice of a desktop app: the left third of
   a conversation list, the right pane sheared off mid-word, and no frame
   anywhere to say what you were looking at. It read as a broken image, and
   the Guru pushing it read as pushing nothing.

   So on a phone the card stops being a crop of a desktop screen and becomes a
   phone, using the same replica the /crm section renders in portrait. The
   .crm-spot--phone rules in css/crm-ui.css already do the whole conversion
   (sidebar to header strip, list owns the screen, chrome to status bar); all
   that is needed here is to size the device to the card the push is driving.

   --crm-phone-w is written by js/booking-keep.js on every frame, so the device
   is always exactly the width the push has left the card at, and the 1:2 the
   replica derives from it is the card's own aspect ratio. One number, no
   scale transform, nothing to drift.
   --------------------------------------------------------------- */
.journey-finish-phone{display:none}

@media(max-width:768px){
  .journey-finish{
    /* 1:2, the device's ratio, replacing the 3/4 the cropped shot needed. */
    aspect-ratio:1/2;
    container-type:normal;
    overflow:visible;
    background:none;
    box-shadow:none;
  }

  .journey-finish .channels-shot{display:none}

  .journey-finish .journey-crm-static{display:none}

  .journey-finish .journey-finish-phone{
    display:block;
    width:100%;
    height:100%;
    /* The wrapper carries .crm-spot--phone so the replica's portrait rules
       apply, but that class also DECLARES --crm-phone-w (min(300px,70vw,30svh))
       in css/crm-spotlight.css for the /crm section's own stage. Declared on
       the element itself it beats the live value js/booking-keep.js writes on
       the card above it, and the device rendered at 253px inside a 168px card.
       Explicitly taking the parent's value hands the number back to the push. */
    --crm-phone-w:inherit;
  }

  /* The replica sizes itself off --crm-phone-w. Inside the keep card that
     number is the card, so the device fills it exactly rather than being
     scaled into it. */
  /* Three classes, because css/crm-ui.css loads after this file and its
     `.crm-spot--phone .crm-ui` width/height would otherwise win on order. */
  .journey-finish .journey-finish-phone .crm-ui{
    width:100%;
    height:100%;
    border-width:calc(var(--crm-phone-w,180px) * .035);
    border-radius:calc(var(--crm-phone-w,180px) * .13);
  }

  /* Type that has to survive the push down to ~150px of device width. Same
     approach css/crm-spotlight.css takes for the /crm section: every size is
     a clamp off the one width, so nothing collapses into a grey smear at the
     small end or bloats at the large one. */
  .journey-finish .journey-finish-phone .crm-ui__url{font-size:clamp(6px,calc(var(--crm-phone-w,180px) * .042),10px)}
  .journey-finish .journey-finish-phone .crm-ui__brand-name{font-size:clamp(7px,calc(var(--crm-phone-w,180px) * .05),12px)}
  .journey-finish .journey-finish-phone .crm-ui__convos-head h3{font-size:clamp(8px,calc(var(--crm-phone-w,180px) * .058),14px)}
  .journey-finish .journey-finish-phone .crm-ui__convos-count{font-size:clamp(6px,calc(var(--crm-phone-w,180px) * .04),9.5px)}
  .journey-finish .journey-finish-phone .crm-ui__row-name{font-size:clamp(7px,calc(var(--crm-phone-w,180px) * .05),12px)}
  .journey-finish .journey-finish-phone .crm-ui__row-time{font-size:clamp(6px,calc(var(--crm-phone-w,180px) * .038),9px)}
  .journey-finish .journey-finish-phone .crm-ui__row-summary{font-size:clamp(6px,calc(var(--crm-phone-w,180px) * .04),10px)}
  .journey-finish .journey-finish-phone .crm-ui__row-channel,
  .journey-finish .journey-finish-phone .crm-ui__pip{font-size:clamp(5.5px,calc(var(--crm-phone-w,180px) * .034),8.5px)}

  /* Structure, not just type. The replica's own portrait mode is drawn for a
     ~300px device; the push lands this one at ~168px, and at that width the
     desktop-derived boxes (34px channel marks, 10px gutters, four 30px channel
     tiles) added up to more than the panel and the fourth tile plus every
     unread pill were being sliced off by the panel's overflow. Measured: the
     channel bar wanted 145px inside 137, the rows 129 inside 127. Everything
     that contributes to those two sums is now a fraction of the one width, so
     the device stays whole at whatever size the push leaves it. */
  .journey-finish .journey-finish-phone .crm-ui__board{padding:calc(var(--crm-phone-w,180px) * .03);gap:calc(var(--crm-phone-w,180px) * .03)}
  .journey-finish .journey-finish-phone .crm-ui__side{padding:calc(var(--crm-phone-w,180px) * .04) calc(var(--crm-phone-w,180px) * .05)}
  .journey-finish .journey-finish-phone .crm-ui__brand img{width:calc(var(--crm-phone-w,180px) * .13);height:calc(var(--crm-phone-w,180px) * .13)}

  .journey-finish .journey-finish-phone .crm-ui__convos-head{padding:calc(var(--crm-phone-w,180px) * .045) calc(var(--crm-phone-w,180px) * .05) calc(var(--crm-phone-w,180px) * .025)}
  .journey-finish .journey-finish-phone .crm-ui__channel-bar{
    gap:calc(var(--crm-phone-w,180px) * .022);
    padding:calc(var(--crm-phone-w,180px) * .028) calc(var(--crm-phone-w,180px) * .04);
  }
  .journey-finish .journey-finish-phone .crm-ui__tile{
    width:calc(var(--crm-phone-w,180px) * .145);
    height:calc(var(--crm-phone-w,180px) * .145);
    border-radius:calc(var(--crm-phone-w,180px) * .04);
  }
  .journey-finish .journey-finish-phone .crm-ui__tile svg{width:62%;height:62%}
  .journey-finish .journey-finish-phone .crm-ui__tile-badge{
    min-width:calc(var(--crm-phone-w,180px) * .065);
    height:calc(var(--crm-phone-w,180px) * .065);
    font-size:calc(var(--crm-phone-w,180px) * .042);
  }

  .journey-finish .journey-finish-phone .crm-ui__row{
    gap:calc(var(--crm-phone-w,180px) * .04);
    padding:calc(var(--crm-phone-w,180px) * .045) calc(var(--crm-phone-w,180px) * .05);
  }
  .journey-finish .journey-finish-phone .crm-ui__row-mark{
    width:calc(var(--crm-phone-w,180px) * .13);
    height:calc(var(--crm-phone-w,180px) * .13);
  }
  .journey-finish .journey-finish-phone .crm-ui__row-mark svg{width:60%;height:60%}
  /* The unread count is the one thing in the row that can be dropped: the
     "3 new" in the panel header already carries it, and holding a pill on the
     right of the foot row is what pushed the channel name - which is the whole
     claim of this screen - onto a second line. */
  .journey-finish .journey-finish-phone .crm-ui__pip{display:none}
}

/* The <=768px keep-beat block above styles the card as a white surface with a
   border and shadow. The device carries its own bezel and shadow now, so the
   card underneath it has to stop drawing a second one. */
@media(max-width:768px){
  .system-journey[data-keep-active] .journey-finish.is-keep-card{
    border:0;
    background:none;
    box-shadow:none;
  }
}

/* ===============================================================
   Live CRM walkthrough inside Step 4

   The homepage owns the scroll. These rules borrow the /crm pinned visual
   layout while cancelling its own 420vh track and nested sticky geometry.
   The complete p=1 composition remains the same panel booking-keep pushes.
   =============================================================== */
.journey-finish:has(.crm-spot--embedded){
  inset:0;
  width:100%;
  height:100%;
  max-width:none;
  aspect-ratio:auto;
  overflow:visible;
  transform:none;
}

.journey-step--bookings.is-crm-expanded .journey-finish:has(.crm-spot--embedded){
  inset:0;
  left:0;
  top:0;
  width:100%;
  height:100%;
}

/* The generic journey keeps a 60px crop reserve at full mobile fill for its
   website scenes. The CRM has its own internal gutters, so that reserve cuts
   off the active step heading. Once Step 4 owns the stage, release the crop. */
.journey-step--bookings.is-crm-expanded{
  clip-path:inset(0 round 16px)!important;
}

.journey-crm-static.is-ready{display:block}
.journey-crm-static.is-ready + .journey-finish-phone{display:none!important}

.journey-finish .crm-spot--embedded{
  width:100%;
  height:100%;
  padding:0;
  overflow:visible;
  background:transparent;
}

.journey-finish .crm-spot--embedded.crm-spot--pinned .crm-spot__track,
.journey-finish .crm-spot--embedded.crm-spot--phone .crm-spot__track{
  height:100%;
}

.journey-finish .crm-spot--embedded.crm-spot--pinned .crm-spot__sticky,
.journey-finish .crm-spot--embedded.crm-spot--phone .crm-spot__sticky{
  position:relative;
  top:auto;
  width:100%;
  height:100%;
  padding:0;
  overflow:visible;
}

.journey-finish .crm-spot--embedded .crm-spot__grid{
  width:100%;
  height:100%;
  max-width:none;
  padding:clamp(34px,4.5vw,64px);
  box-sizing:border-box;
}

.journey-finish .crm-spot--embedded .crm-spot__stage{
  height:min(560px,72vh);
}

.journey-finish .crm-spot--embedded .crm-section__action{display:none}

.journey-finish.is-brand-card .crm-spot--embedded{
  opacity:calc(1 - var(--keep-brand-reveal,1));
}

/* At CRM progress 1 the flying badge is already parked directly over the
   real app brand mark. Once the outer panel starts shrinking, that old
   stage-relative transform would drift away from the resized app and look
   like a second Guru floating in the middle of the frame. The real mark is
   underneath it, so hand over to that mark for the complete push. */
.journey-finish.is-keep-card .crm-spot--embedded [data-crm-badge]{display:none}

.journey-step--bookings .journey-finish.is-keep-card:has(.crm-spot--embedded){
  right:auto;
  bottom:auto;
  height:auto;
  aspect-ratio:16/9;
  overflow:hidden;
}

/* Compact the finished CRM as one object. Resizing its live grid caused the
   two-column desktop scene to reflow while the Guru was moving it, so the
   visitor saw a tall phone crop rather than the screen physically shrinking.
   The outer card still supplies the clipping and rounded corner; its single
   child keeps the measured full-stage dimensions and scales with the same
   scalar as the push. */
.journey-finish.is-keep-card>.journey-crm-static{
  width:var(--keep-source-w);
  height:var(--keep-source-h);
  transform:scale(var(--keep-scale));
  transform-origin:top left;
}

/* In the four-card overview, Step 4 previews the problem rather than the
   solution: the notification pile owns the image area and the long CRM copy
   waits until the card opens to full stage. */
.journey-step--bookings:not(.is-crm-expanded) .crm-spot--embedded .crm-spot__grid{
  grid-template-columns:minmax(0,1fr);
}

.journey-step--bookings:not(.is-crm-expanded) .crm-spot--embedded .crm-spot__copy{
  display:none;
}

.journey-step--bookings:not(.is-crm-expanded) .crm-spot--embedded .crm-spot__stage{
  width:100%;
}

.journey-step--bookings:not(.is-crm-expanded) .crm-spot--embedded .crm-spot__notes,
.journey-step--bookings:not(.is-crm-expanded) .crm-spot--embedded .crm-spot__marks{
  transform:scale(1.65);
  transform-origin:center;
}

@media(max-width:1023px){
  .journey-finish .crm-spot--embedded .crm-spot__grid{
    padding:18px 16px 22px;
  }

  .journey-finish .crm-spot--embedded .crm-spot__stage{
    height:auto;
  }

  /* The 1.65 blow-up above is measured for the wide 16/9 row card. The
     portrait card is 327x724 at 390px, where the same scale throws the pile
     to 488x765 and hangs it ~135px past the card's own top edge - the tile
     would enter as a spill instead of a preview. Natural scale is exactly the
     stage box, so the pile sits inside the card it belongs to. */
  .journey-step--bookings:not(.is-crm-expanded) .crm-spot--embedded .crm-spot__notes,
  .journey-step--bookings:not(.is-crm-expanded) .crm-spot--embedded .crm-spot__marks{
    transform:none;
  }
}

@media(max-width:768px){
  .journey-finish .journey-crm-static.is-ready{display:block}

  .journey-step--bookings .journey-finish.is-keep-card:has(.crm-spot--embedded){
    aspect-ratio:1/2;
  }

}
