/*
 * place_cards.css — rich place cards, map pin popovers and the place-detail
 * panel for the embedded widget. HANDOFF_widget_v2 Phase B.
 *
 * Loaded from widget_base.html only when WidgetConfig.enable_rich_places is on,
 * so a tenant who has not opted in downloads nothing. Every selector here is a
 * .widget-place* / .widget-pin* class that only the Phase B templates emit, so
 * nothing in this file can reach a flag-off render.
 *
 * Tokens come from widget.css (--widget-primary and friends), which loads
 * first. This file declares no new custom properties.
 *
 * MOBILE FIRST. The default rules are the 390px layout: one column, a 76px
 * square thumbnail, and a detail panel that is a bottom sheet rather than a
 * centred dialog. Wider layouts are min-width enhancements below.
 */

/* ── Card ──────────────────────────────────────────────────────────────── */

.widget-place-list {
  list-style: none;
  margin: 0;
  padding: 0;
  display: flex;
  flex-direction: column;
  gap: 10px;
}

.widget-place {
  position: relative;
  display: flex;
  align-items: stretch;
  min-width: 0;
  border: 1px solid var(--widget-border);
  border-radius: var(--widget-radius);
  background: var(--widget-bg);
  box-shadow: var(--widget-shadow);
  overflow: hidden;
}

.widget-place--has-supply {
  border-color: color-mix(
    in srgb,
    var(--widget-accent) 60%,
    var(--widget-border)
  );
}

/* The whole card is the tap target, so it is a real button: keyboard focus,
   Enter/Space and screen-reader semantics all come for free. */
.widget-place-open {
  display: flex;
  flex: 1 1 auto;
  min-width: 0;
  align-items: flex-start;
  gap: 10px;
  /* Rule 8: comfortably past the 44px minimum in both dimensions. */
  min-height: 76px;
  padding: 8px;
  border: none;
  background: transparent;
  color: inherit;
  font-family: var(--widget-font);
  text-align: left;
  cursor: pointer;
}

.widget-place-open:focus-visible {
  outline: 2px solid var(--widget-primary);
  outline-offset: -2px;
}

.widget-place-thumb {
  flex: 0 0 auto;
  width: 76px;
  height: 76px;
  border-radius: var(--widget-radius-sm);
  object-fit: cover;
  background: var(--widget-surface);
}

/* The no-photo state. Deliberately reads as a symbol on a tinted tile: a stock
   photograph here would be a picture of somewhere that is not this place. */
.widget-place-thumb--icon {
  display: flex;
  align-items: center;
  justify-content: center;
  background: color-mix(
    in srgb,
    var(--widget-primary) 10%,
    var(--widget-surface)
  );
  color: var(--widget-primary);
  font-size: 26px;
}

.widget-place-body {
  display: flex;
  flex-direction: column;
  gap: 3px;
  min-width: 0;
  max-width: 100%;
}

.widget-place-meta {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 8px;
  min-width: 0;
}

.widget-place-time {
  font-size: 12px;
  font-weight: 700;
  color: var(--widget-primary);
}

.widget-place-category,
.widget-place-day {
  display: inline-flex;
  align-items: center;
  gap: 4px;
  max-width: 100%;
  min-width: 0;
  padding: 1px 8px;
  border-radius: 20px;
  background: var(--widget-surface);
  color: var(--widget-text-muted);
  font-size: 11px;
  font-weight: 600;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.widget-place-day {
  background: color-mix(in srgb, var(--widget-primary) 14%, transparent);
  color: var(--widget-primary);
}

/* The stop number, shared by the itinerary card and the detail panel. Same
   shape and size as the consumer trip page's .itinerary-number-disc, so the
   two products draw a numbered stop the same way; the colour is the tenant's
   token rather than the per-type palette, because the widget has no pin
   colours to stay in step with. Its partner on the map is .widget-pin-disc,
   which is the same disc two pixels bigger. */
.widget-place-index {
  flex: 0 0 auto;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  min-width: 22px;
  height: 22px;
  padding: 0 5px;
  border-radius: 11px;
  background: var(--widget-primary);
  color: #fff;
  font-size: 12px;
  font-weight: 800;
  font-variant-numeric: tabular-nums;
  line-height: 1;
}

.widget-place-name {
  font-size: 15px;
  font-weight: 700;
  line-height: 1.25;
  color: var(--widget-text);
  overflow-wrap: anywhere;
}

.widget-place-blurb,
.widget-place-address {
  font-size: 12.5px;
  line-height: 1.4;
  color: var(--widget-text-muted);
  overflow-wrap: anywhere;
}

.widget-place-supply {
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  gap: 4px;
  flex: 0 0 auto;
  padding: 8px 10px 8px 0;
}

/* ── Numbered map pin ──────────────────────────────────────────────────── */

/* Rule 8: the touch target is the full 44px, the disc inside it is what you
   see. A 44px disc would swallow its neighbours on a city map, and the widget
   map has no cluster-separation pass to rescue it (the consumer map's
   clustering.js is not loaded here, and there is nothing to break: the widget
   has always drawn plain overlapping markers).

   MapLibre positions markers in screen space, so this is 30px at every zoom
   level rather than shrinking with the tiles. */
.widget-pin {
  display: flex;
  align-items: center;
  justify-content: center;
  width: 44px;
  height: 44px;
  cursor: pointer;
}

.widget-pin-disc {
  display: flex;
  align-items: center;
  justify-content: center;
  width: 30px;
  height: 30px;
  border-radius: 50%;
  /* White ring plus a shadow: the number has to stay readable over dark
     water, park green and pale street fill alike. */
  border: 2px solid #fff;
  box-shadow: 0 2px 6px rgba(0, 0, 0, 0.35);
  background: var(--widget-primary);
  color: #fff;
  font-family: var(--widget-font);
  font-size: 13px;
  font-weight: 800;
  font-variant-numeric: tabular-nums;
  line-height: 1;
}

/* ── Map pin popover ───────────────────────────────────────────────────── */

/* Height budget matters here: the map panel is ~280px tall and MapLibre clips
   a popover that does not fit. Everything below is sized so the whole popover
   lands near 175px, which fits above a pin once widget.js has panned it into
   the lower quarter. */
.widget-pin-pop {
  display: flex;
  flex-direction: column;
  gap: 5px;
  width: 200px;
  max-width: 100%;
  font-family: var(--widget-font);
}

.widget-pin-thumb {
  width: 100%;
  height: 72px;
  border-radius: var(--widget-radius-sm);
  object-fit: cover;
  background: var(--widget-surface);
}

.widget-pin-thumb--icon {
  display: flex;
  align-items: center;
  justify-content: center;
  background: color-mix(
    in srgb,
    var(--widget-primary) 10%,
    var(--widget-surface)
  );
  color: var(--widget-primary);
  font-size: 26px;
}

.widget-pin-name {
  font-size: 14px;
  line-height: 1.25;
  color: var(--widget-text);
  overflow-wrap: anywhere;
}

.widget-pin-meta {
  display: flex;
  flex-wrap: wrap;
  gap: 6px;
  min-width: 0;
}

.widget-pin-open {
  min-height: 44px;
  padding: 0 12px;
  border: none;
  border-radius: var(--widget-radius-sm);
  background: var(--widget-primary);
  color: #fff;
  font-family: var(--widget-font);
  font-size: 13px;
  font-weight: 600;
  cursor: pointer;
}

/* ── Detail panel ──────────────────────────────────────────────────────── */

.widget-place-panel {
  position: fixed;
  inset: 0;
  z-index: 40;
  display: flex;
  align-items: flex-end;
  justify-content: center;
}

.widget-place-panel-scrim {
  position: absolute;
  inset: 0;
  background: rgba(0, 0, 0, 0.45);
}

/* Bottom sheet on narrow viewports: a centred dialog on a 390px screen is a
   worse bottom sheet, and this keeps the close control near the thumb. */
.widget-place-panel-sheet {
  position: relative;
  width: 100%;
  max-width: 100%;
  max-height: 88vh;
  overflow-y: auto;
  border-radius: var(--widget-radius) var(--widget-radius) 0 0;
  background: var(--widget-bg);
  box-shadow: var(--widget-shadow-md);
}

.widget-place-panel-close {
  position: absolute;
  top: 8px;
  right: 8px;
  z-index: 1;
  width: 44px;
  height: 44px;
  min-width: 44px;
  border: none;
  border-radius: 50%;
  background: rgba(0, 0, 0, 0.55);
  color: #fff;
  font-size: 18px;
  line-height: 1;
  cursor: pointer;
}

.widget-place-panel-hero {
  display: block;
  width: 100%;
  height: 190px;
  object-fit: cover;
  background: var(--widget-surface);
}

.widget-place-panel-hero--icon {
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  gap: 8px;
  background: color-mix(
    in srgb,
    var(--widget-primary) 10%,
    var(--widget-surface)
  );
  color: var(--widget-primary);
  font-size: 40px;
}

.widget-place-panel-nophoto {
  font-size: 12px;
  font-weight: 600;
  color: var(--widget-text-muted);
}

.widget-place-panel-attr,
.widget-place-panel-sources {
  margin: 0;
  padding: 4px 14px 0;
  font-size: 11px;
  color: var(--widget-text-muted);
  overflow-wrap: anywhere;
}

.widget-place-panel-body {
  display: flex;
  flex-direction: column;
  gap: 8px;
  padding: 12px 14px 18px;
  min-width: 0;
}

.widget-place-panel-title {
  margin: 0;
  font-size: 19px;
  line-height: 1.2;
  color: var(--widget-text);
  overflow-wrap: anywhere;
}

.widget-place-panel-meta {
  display: flex;
  flex-wrap: wrap;
  gap: 8px;
  margin: 0;
  min-width: 0;
}

.widget-place-panel-address,
.widget-place-panel-blurb {
  margin: 0;
  font-size: 13.5px;
  line-height: 1.5;
  color: var(--widget-text-muted);
  overflow-wrap: anywhere;
}

.widget-place-panel-gallery {
  display: flex;
  gap: 8px;
  overflow-x: auto;
  padding-bottom: 4px;
}

.widget-place-panel-gallery img {
  flex: 0 0 auto;
  width: 120px;
  height: 90px;
  border-radius: var(--widget-radius-sm);
  object-fit: cover;
  background: var(--widget-surface);
}

.widget-place-panel-link {
  display: inline-flex;
  align-items: center;
  align-self: flex-start;
  min-height: 44px;
  padding: 0 16px;
  border-radius: var(--widget-radius-sm);
  border: 1px solid var(--widget-primary);
  color: var(--widget-primary);
  font-size: 14px;
  font-weight: 600;
  text-decoration: none;
}

.widget-supply-add-btn--wide {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 8px;
  width: 100%;
  min-height: 44px;
  border-radius: var(--widget-radius-sm);
}

.widget-place-busy {
  position: fixed;
  inset: 0;
  z-index: 39;
  display: none;
  align-items: center;
  justify-content: center;
  background: rgba(0, 0, 0, 0.2);
}

.widget-place-busy.htmx-request {
  display: flex;
}

/* ── Route connectors (Phase B2) ───────────────────────────────────────── */

/*
 * The markup and styling come from the consumer trip page
 * (trips/static/trips/css/routing.css, linked by widget/trip_detail.html).
 * Deliberately almost nothing is restated here: Zach asked for the consumer
 * connector exactly, compact pill and dashed rail included, so every override
 * that changed its SHAPE has been removed rather than tuned.
 *
 * What remains is the one thing that is genuinely different in an embed.
 */

/* Tenant colour. routing.css falls back to the consumer's teal for the
   selected mode, which is the one place a partner would notice their brand
   missing. Colour only; it does not touch size or spacing. */
.widget-place-list .route-connector__mode-btn.is-active {
  background: var(--widget-primary);
}

/* The dashed rail is absolutely positioned against the connector, so the
   connector has to be the positioning context for it to land in the right
   place inside the widget's card list. */
.widget-place-list .route-connector {
  position: relative;
}

/*
 * NOT overridden on purpose, and worth knowing before someone "fixes" it:
 *
 * Buttons stay at the consumer's 28px (26px below 768px) rather than the 44px
 * Rule 8 asks for. Zach chose the compact consumer treatment explicitly on
 * 2026-08-25. If that is ever revisited, raise it in routing.css so both
 * surfaces move together, rather than re-forking the widget.
 */
