/*
 * Login, signup, password reset and the account page: the four least-designed screens in the app,
 * unified as one centred column. Mobile first: below 48rem the "card" is full-bleed, because a
 * boxed card with its own margins on a 360px screen just steals width from the tap targets it is
 * supposed to protect. Above 48rem it becomes an actual card, floating on stone the way the rest of
 * pretor.ar does.
 */

.auth-page {
  display: flex;
  flex-direction: column;
  gap: 1.75rem;
  max-inline-size: 26rem;
  margin-inline: auto;
}

.auth-card {
  display: flex;
  flex-direction: column;
  gap: 1.5rem;
}

@media (width >= 48rem) {
  .auth-card {
    background: var(--color-surface);
    border: 1px solid var(--color-border);
    border-radius: var(--radius);
    box-shadow: 0 1px 2px color-mix(in srgb, var(--ink) 6%, transparent),
                0 8px 24px color-mix(in srgb, var(--ink) 8%, transparent);
    padding: 2.5rem;
  }
}

.auth-form {
  display: flex;
  flex-direction: column;
  gap: 1.25rem;
}

.auth-field {
  display: flex;
  flex-direction: column;
  gap: .4rem;
}

.auth-field label {
  font-size: var(--step--1);
  font-weight: 600;
  color: var(--color-text-subtle);
}

/* Every field is at least a thumb's width tall, on the phone this layout is designed for first. */
.auth-field .input {
  min-block-size: 44px;
  padding: .7rem .9rem;
  font-size: var(--step-0);
}

/* Carried on every page while the address is unproven, so it has to read as persistent standing
   state rather than as a flash that just arrived and will go away on its own. */
.confirmation-banner {
  --alert-border-color: var(--gold-soft);

  display: flex;
  flex-wrap: wrap;
  align-items: center;
  justify-content: space-between;
  gap: var(--size-2);
  margin-block-end: var(--size-4);
}

.confirmation-banner p {
  margin: 0;
}

/* The sentence under the heading, on the four screens that open with one. It had no rule at all
   until PRE-148 put a fourth caller on it, so it kept the browser's 1em paragraph margin, and .auth-card
   is a flex column: a flex item's margin does not collapse, so it added itself to the 1.5rem gap and
   those ledes sat further from their heading than anything else in the card. Margin only, on purpose.
   Size and colour are what .auth-hint and .auth-legal use to say "this is small print", and a lede
   is the opposite: it is the sentence the reader is meant to read first. */
.auth-lede {
  margin: 0;
}

/* The password rule, stated before it is broken rather than only in the error that follows. */
.auth-hint {
  margin: 0;
  font-size: var(--step--1);
  color: var(--color-text-subtle);
}

.auth-submit {
  min-block-size: 44px;
  inline-size: 100%;
}

.auth-links {
  text-align: center;
  font-size: var(--step--1);
}

/* Lo que se acepta al apretar el botón, dicho junto al botón. Chico y en
   gris: informa, no compite con la acción. */
.auth-legal {
  margin: 0;
  font-size: var(--step--1);
  color: var(--color-text-subtle);
  text-align: center;
}

.auth-errors ul {
  margin: 0;
  padding-inline-start: 1.1rem;
}

/* Account: same column, a card per state rather than one form. */

.account-status {
  display: flex;
  flex-direction: column;
  gap: 1.25rem;
}

/*
 * The casilla card is an anchor landing (#casilla): every connect, disconnect and OAuth return
 * redirects here. Without a scroll margin the fragment aligns the card's border with the viewport
 * top and the sticky bar (53px, see .app-bar::before's comment) covers the heading, so the lawyer
 * lands on a card whose title is hidden. The extra half rem keeps a breath of the page above it.
 */
#casilla {
  scroll-margin-top: calc(53px + 0.5rem);
}

/*
 * The card carries tabindex="-1" so the fragment landing moves FOCUS and not only the viewport
 * (accounts/_mailbox.html.erb says why). -1 keeps it out of the tab order, so the landing is the
 * only thing that can ever focus it, which is what the rest of this rule turns on.
 *
 * Chrome matches :focus-visible on that programmatic focus anyway, so the base rule painted a 2px
 * ring around the whole card after every connect, disconnect, password submit and OAuth return,
 * for a mouse user who never touched a key. Suppressed rather than kept, and this is not the
 * WCAG 2.4.7 trade it looks like: that criterion is about the keyboard focus INDICATOR, and this
 * element cannot be reached by keyboard. The card is what just scrolled into view carrying the
 * answer, and a ring around it adds nothing except an error-looking border on a card whose own
 * border already states its status.
 *
 * BOTH properties, because the base rule sets three. Naming only `outline` left the second half of
 * the ring on: border-radius: 3px snapped the card's corners square for as long as it held focus,
 * and outlineStyle alone could not see it. The same token .card uses, so the two cannot drift.
 */
#casilla:focus-visible {
  outline: none;
  border-radius: var(--rounded-xl);
}

.account-telegram {
  display: flex;
  align-items: center;
  gap: .5rem;
  margin: 0;
}

.account-status-icon {
  --icon-color: var(--color-positive);
  --icon-size: 1.15rem;
}

.account-action {
  min-block-size: 44px;
}

/* Cargar créditos: the presets and the custom amount, side by side and weighted the same. The
   block gets its own padding so the row of amounts is not flush against the heading above it. */
.account-credit-purchase {
  display: flex;
  flex-direction: column;
  gap: 1.25rem;
  padding-block: 1.25rem;
}

.account-credit-presets {
  display: flex;
  flex-wrap: wrap;
  gap: .6rem;
}

/* Smaller than .account-action, but the 44px touch target stays: this is a money button on a
   phone, and shrinking the thing you tap to spend money is the wrong economy. The size comes off
   the inline padding and the type scale instead. */
.account-amount {
  min-block-size: 44px;
  padding-inline: .9rem;
  font-size: var(--step--1);
}

/* One row per open session. Wraps rather than scrolls: at 360px the device, the address and the
   button do not fit on a line, and a row you have to scroll to reach the end of is a row whose
   Cerrar button nobody finds. */
.account-sessions {
  display: flex;
  flex-direction: column;
  gap: .75rem;
  margin: 0;
  padding: 0;
  list-style: none;
}

.account-session {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: .5rem 1rem;
  padding-block: .75rem;
  border-block-start: 1px solid var(--color-border);
}

.account-session:first-child {
  border-block-start: 0;
}

.account-session__what {
  flex: 1 1 12rem;
}

.account-session__what p {
  margin: 0;
}

.account-session__device {
  font-weight: 600;
}

.account-session__where,
.account-session__when {
  font-size: var(--step--1);
  color: var(--color-text-subtle);
}

.account-session__end {
  min-block-size: 44px;
}

/* Almacenamiento: the two ways out of a full quota. Same column-and-gap treatment as the credit
   purchase block above, because they are the same kind of thing (a short explanation and one
   control) and a firm arrives at both from the same refusal. */
.account-storage-purchase,
.account-storage-files {
  display: flex;
  flex-direction: column;
  gap: 1.25rem;
  padding-block: 1.25rem;
}

.account-storage-purchase p,
.account-storage-files p {
  margin: 0;
}

/* One row per stored file, the shape .account-session already uses: at 360px the name, the size
   and the Borrar button do not fit on a line, so the row wraps rather than scrolls. A row you have
   to scroll to reach the end of is a row whose button nobody finds. */
.storage-files {
  display: grid;
  grid-template-columns: minmax(0, 1fr) auto auto;
  margin: 0;
  padding: 0;
  list-style: none;
}

.storage-file {
  display: grid;
  grid-column: 1 / -1;
  grid-template-columns: subgrid;
  align-items: center;
  column-gap: 1rem;
  padding-block: .75rem;
  border-block-start: 1px solid var(--color-border);
}

.storage-file:first-child {
  border-block-start: 0;
}

/* Takes the room, so the size and the button hold the end of the row. A filename comes off a
   scanner and can be one unbroken 80-character string, which would otherwise push them off. */
.storage-file__details {
  display: flex;
  flex-direction: column;
  gap: .25rem;
  min-inline-size: 0;
  overflow-wrap: anywhere;
}

.storage-file__size {
  text-align: end;
  white-space: nowrap;
}

.storage-file__size,
.storage-file__case {
  font-size: var(--step--1);
  color: var(--color-text-subtle);
}

.storage-file__delete,
.storage-files__delete-all {
  min-block-size: 44px;
}

.storage-files__order {
  display: flex;
  flex-wrap: wrap;
  gap: .5rem 1.25rem;
  font-size: var(--step--1);
}

.storage-files__order a[aria-current="true"] {
  color: inherit;
  text-decoration: none;
  font-weight: 600;
}

.voice-surface {
  display: flex;
  flex-direction: column;
  gap: .5rem;
  min-inline-size: 0;
  margin: 0;
  padding: 0;
  border: 0;
}

.voice-surface__title {
  padding: 0;
  font-weight: 600;
}

.voice-options {
  display: flex;
  flex-direction: column;
  margin: 0;
  padding: 0;
  list-style: none;
}

.voice-option {
  display: grid;
  grid-template-columns: minmax(0, 1fr) auto;
  align-items: center;
  gap: .75rem 1rem;
  padding-block: 1rem;
  border-block-start: 1px solid var(--color-border);
}

.voice-option__text p,
.voice-option__actual {
  margin: 0;
}

.voice-option__nombre {
  font-weight: 600;
}

.voice-option__descripcion,
.voice-option__actual {
  font-size: var(--step--1);
  color: var(--color-text-subtle);
}

.voice-option__pick {
  min-block-size: 44px;
}

.voice-option__sample {
  grid-column: 1 / -1;
  inline-size: 100%;
}

.voice-custom {
  display: flex;
  flex-direction: column;
  gap: .5rem;
  padding-block-start: 1.25rem;
  border-block-start: 1px solid var(--color-border);
}

.voice-custom h3,
.voice-custom p {
  margin: 0;
}

/* The channel hop, which is the hero of the unlinked state since 2026-08-25: a button that opens
   the chat with the code already in it, and beside it a QR for the reader who is on a computer
   while Telegram is on their phone. Before this the card offered only the command below, and a
   lawyer who did not know which bot to paste it into went looking and found somebody else's.

   Row on a wide screen, stacked on a narrow one, where the QR is the less useful half: somebody
   reading this on the phone can simply tap. */
.account-channel {
  display: flex;
  flex-wrap: wrap;
  gap: 1.25rem;
  align-items: center;
  margin-block: 1rem;
}

.account-qr,
.guide__qr {
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: .5rem;
  max-inline-size: 100%;
}

/* The QR carries its own quiet zone, so it needs a light plate to scan against in either theme:
   a dark-mode inversion is a code a phone camera will not read. */
.account-qr svg,
.guide__qr svg {
  background: #fff;
  padding: .5rem;
  border-radius: .25rem;
  max-inline-size: 100%;
  block-size: auto;
}

.guide__qr {
  margin-block: 1.25rem;
}

/* The /vincular command, now the FALLBACK under that pair rather than the hero: still large,
   monospace and one tap from the clipboard, so it survives the trip into Telegram without a
   retyped character for whoever chooses to carry it by hand. */
.account-code {
  padding: 1rem 1.1rem;
  min-block-size: 44px;
}

.account-code textarea {
  resize: none;
  border: 0;
  background: transparent;
  padding: 0;
  outline: 0;
  font-size: var(--step-1);
  letter-spacing: .04em;
  text-align: center;
  white-space: nowrap;
  overflow-x: auto;
}

.account-code__copy {
  min-inline-size: 44px;
  min-block-size: 44px;
}

.account-expiry {
  font-size: var(--step--1);
  color: var(--color-text-subtle);
}

.account-signout {
  align-self: flex-start;
  min-block-size: 44px;
}

/* The bank transfer alternative to Checkout Pro: cheaper, but manual, so it sits below the card
   buttons rather than beside them. */
.account-transfer {
  display: flex;
  flex-direction: column;
  gap: 1rem;
  padding-block-start: 1.25rem;
  border-block-start: 1px solid var(--color-border);
}

.account-transfer h3 {
  margin: 0;
}

.account-transfer-field {
  display: flex;
  flex-direction: column;
  gap: .35rem;
}

.account-transfer-label {
  font-size: var(--step--1);
  font-weight: 600;
  color: var(--color-text-subtle);
}

.account-transfer-value {
  padding: .5rem .75rem;
}

.account-transfer-copy {
  min-inline-size: 44px;
  min-block-size: 44px;
}

/* The three sections of "Tu cuenta". Links, not a JavaScript tablist: aria-current is the state,
   and it is what the styling hangs off, so the open tab is said once and read by both the eye and
   the screen reader. Same pattern the expediente views use. */
.account-tabs {
  display: flex;
  flex-wrap: wrap;
  gap: .25rem;
  margin-block: 1.5rem;
  border-block-end: 1px solid var(--color-border);
}

.account-tabs__tab {
  padding: .6rem 1rem;
  min-block-size: 44px;
  display: inline-flex;
  align-items: center;
  color: var(--color-text-subtle);
  text-decoration: none;
  border-block-end: 2px solid transparent;
  /* Pulled down onto the container's rule so the open tab's underline replaces it rather than
     sitting above it. */
  margin-block-end: -1px;
}

.account-tabs__tab[aria-current="page"] {
  color: var(--color-text);
  border-block-end-color: var(--color-accent);
}
