/* Dreamwar modern: the component set from the design system.
   Section title, Card (plain / action tile / notice / summary), ListRow,
   StatBar, Chip, Button, Field. Every modern screen is assembled from these and
   nothing else. Colors, sizes and spacing come from tokens.css.

   Density is a rule here, not taste: a phone screen is 390px wide and every
   empty band pushes the next thing the player wants below the fold. Titles
   sit 16px above their block, cards pad 12px, tiles are 64px, not 96px.

   The last part of this file is the screen layout: how one markup tree of
   blocks becomes a single column on the phone, two columns on a tablet and
   a content column with a side column on the desktop. */

/* ---- section title ---- */

.dw-section {
  margin: var(--space-4) 0 var(--space-2);
  font-family: var(--font-display);
  font-size: var(--text-section-size);
  line-height: var(--text-section-line);
  letter-spacing: var(--text-section-tracking);
  font-weight: var(--text-section-weight);
  text-transform: uppercase;
  color: var(--muted);
}

.dw-section:first-child { margin-top: 0; }

/* ---- Card ---- */

.dw-card {
  padding: var(--space-3);
  border: 1px solid var(--line);
  border-radius: var(--radius-md);
  background: var(--surface);
}

/* ---- ListRow ---- */

.dw-list {
  border: 1px solid var(--line);
  border-radius: var(--radius-md);
  background: var(--surface);
  overflow: hidden;
}

/* Two blocks in a row with no title between them still need air, or they
   read as one block that broke. The exit list at the bottom of the city
   was glued to the travel list above it. */
.dw-list + .dw-list,
.dw-card + .dw-list,
.dw-list + .dw-card,
.dw-card + .dw-card,
.dw-summary + .dw-list,
.dw-notice + .dw-card,
.dw-notice + .dw-list,
.dw-notice + .dw-notice,
.dw-card + .dw-notice,
.dw-tiles + .dw-list { margin-top: var(--space-2); }

/* A closing block - the way out of the screen - sits further off. */
.dw-list--tail { margin-top: var(--space-5); }

.dw-row {
  display: flex;
  align-items: center;
  gap: var(--space-3);
  min-height: var(--touch);
  padding: 10px var(--space-3);
  border-bottom: 1px solid var(--line-2);
  color: var(--text);
  font-size: var(--text-body-size);
  line-height: var(--text-body-line);
  text-decoration: none;
}

.dw-row:last-child { border-bottom: 0; }
.dw-row:hover { background: var(--surface-2); color: var(--accent-text); }
.dw-row > span:first-child { flex: 1 1 auto; min-width: 0; }

/* A stroke icon opens a hub row, same drawing style as the tiles. The
   name after it takes the stretch the first span otherwise takes. */
.dw-row__icon { width: 18px; height: 18px; flex: 0 0 18px; color: var(--muted); }
.dw-row__icon + span { flex: 1 1 auto; min-width: 0; }

/* Second line under the row text: time, sum, source. */
.dw-row__cap {
  display: block;
  margin-top: 2px;
  color: var(--muted);
  font-size: var(--text-caption-size);
  line-height: var(--text-caption-line);
}

.dw-row__go { flex: 0 0 auto; color: var(--dim); font-size: 18px; line-height: 1; }

/* Phone folds (owner, 27.09): rarely used rows tuck under one row that
   opens them - the settings group, the journals, the tail of the
   fighter pages. Pure CSS - a hidden checkbox and its label - because
   the engine strips scripts. From 1000px nothing folds: the fold row
   is gone and the rows stay open, the desktop has the room. */
.dw-fold__cb { position: absolute; width: 1px; height: 1px; opacity: 0; pointer-events: none; }
.dw-fold__head { display: none; }

@media (max-width: 999.98px) {
  .dw-fold__head { display: flex; cursor: pointer; -webkit-tap-highlight-color: transparent; }
  /* A fold row opens in place, a plain row goes to a page: the fold
     arrow points down, and up once open (owner, 27.09). */
  .dw-fold__mark { transform: rotate(90deg); transition: transform .15s ease; }
  .dw-fold__body { display: none; }
  .dw-fold__title { display: none; }
  .dw-fold__cb:checked + .dw-fold__head .dw-fold__mark { transform: rotate(-90deg); }
  .dw-fold__cb:checked + .dw-fold__head + .dw-fold__body { display: block; }
  /* Opened rows sit one step in: they belong to the fold row above. */
  .dw-fold__body > .dw-row { padding-left: calc(var(--space-3) + 16px); }
  /* Closed, the fold row is the last visible row of its list. */
  .dw-fold__cb:not(:checked) + .dw-fold__head { border-bottom: 0; }
  .dw-fold__cb:focus-visible + .dw-fold__head { outline: 2px solid var(--accent); outline-offset: -2px; }
}

@media (max-width: 999.98px) and (prefers-reduced-motion: reduce) {
  .dw-fold__mark { transition: none; }
}

/* Fighter page groups on the phone (06.10, owner: "on the phone the fighter page has almost no buttons... make every button
   the desktop has, in collapsible lists"): each section with buttons is a bar with its name and button count; a tap folds
   or unfolds it. Closed by default (owner 06.10), an opened group is remembered (gfold script, localStorage). Inner folds open inside a
   group. From 1000px nothing changes: the bar is gone, the section title and rows stay. */
.dw-gfold__head { display: none; }
@media (max-width: 999.98px) {
  .dw-gfold__title { display: none; }
  .dw-gfold__head { display: flex; align-items: center; gap: 8px; min-height: var(--touch); margin: 0 0 var(--space-2); padding: 10px var(--space-3); border: 1px solid var(--line); border-radius: var(--radius-md); background: var(--surface); color: var(--text); font-weight: 600; cursor: pointer; -webkit-tap-highlight-color: transparent; }
  .dw-gfold__head > span:first-child { flex: 1 1 auto; min-width: 0; }
  .dw-gfold__n { color: var(--muted); font-weight: 400; font-variant-numeric: tabular-nums; }
  .dw-gfold__head .dw-fold__mark { transform: rotate(90deg); }
  .dw-gfold__body { display: none; }
  .dw-gfold__cb:checked + .dw-gfold__head .dw-fold__mark { transform: rotate(-90deg); }
  .dw-gfold__cb:checked + .dw-gfold__head + .dw-gfold__body { display: block; }
  .dw-gfold__cb:focus-visible + .dw-gfold__head { outline: 2px solid var(--accent); outline-offset: 2px; }
  .dw-gfold__body .dw-fold__head { display: none; }
  .dw-gfold__body .dw-fold__body { display: block; }
  .dw-gfold__body .dw-fold__body > .dw-row { padding-left: var(--space-3); }
}

/* Desktop-only rows. On the phone these links live in the hubs; the
   desktop has the room to show the whole map of the game on the city
   screen (owner, 2026-09-23), so the same rows appear here from 1000px.
   The duplication with the hubs is deliberate and desktop-only. */
.dw-row.dw-desk { display: none; }

.dw-row__n {
  flex: 0 0 auto;
  min-width: 22px;
  padding: 2px 7px;
  border-radius: 10px;
  background: var(--accent-soft);
  color: var(--accent-text);
  font-size: var(--text-caption-size);
  font-weight: 600;
  text-align: center;
  font-variant-numeric: tabular-nums;
}

/* ---- Card: summary (numbers in a row, an optional note below) ---- */

.dw-summary {
  padding: var(--space-3);
  border: 1px solid var(--line);
  border-radius: var(--radius-md);
  background: var(--surface);
}

.dw-summary__row { display: flex; gap: var(--space-3); }

.dw-summary__item {
  flex: 1 1 0;
  min-width: 0;
  text-decoration: none;
  color: var(--text);
}

a.dw-summary__item:hover .dw-summary__n { color: var(--accent-text); }

.dw-summary__n {
  display: block;
  font-family: var(--font-display);
  font-size: var(--text-stat-size);
  line-height: var(--text-stat-line);
  font-variant-numeric: tabular-nums;
}

.dw-summary__cap {
  display: block;
  margin-top: 2px;
  font-size: var(--text-caption-size);
  line-height: var(--text-caption-line);
  color: var(--muted);
}

.dw-summary__note {
  margin: var(--space-3) 0 0;
  padding-top: var(--space-2);
  border-top: 1px solid var(--line-2);
  font-size: var(--text-body-sm-size);
  line-height: var(--text-body-sm-line);
}

.dw-summary__note b { font-weight: 600; }
.dw-summary__note .dw-summary__cap { display: inline; margin: 0; }

/* ---- Card: action tile ---- */

.dw-tiles {
  display: grid;
  grid-template-columns: repeat(2, minmax(0, 1fr));
  gap: var(--space-2);
  margin-bottom: var(--space-2);
}

.dw-tile {
  display: flex;
  flex-direction: column;
  justify-content: center;
  gap: 2px;
  min-height: 64px;
  padding: 10px var(--space-3);
  border: 1px solid var(--line);
  border-radius: var(--radius-md);
  background: var(--surface);
  color: var(--text);
  text-decoration: none;
}

.dw-tile:hover { border-color: var(--accent); }

.dw-tile__head { display: flex; align-items: center; gap: var(--space-2); min-width: 0; }

.dw-tile__icon { width: 18px; height: 18px; flex: 0 0 18px; color: var(--muted); }

/* The name wraps to a second line rather than being cut: on a 360px
   phone "Chaotic Battles" did not fit a half-width tile and read
   "Chaotic ...". The grid row takes the taller tile's height, so both
   tiles in the row stay level. */
.dw-tile__name {
  min-width: 0;
  font-family: var(--font-display);
  font-size: var(--text-h2-size);
  line-height: var(--text-h2-line);
}

.dw-tile__cap {
  padding-left: calc(18px + var(--space-2));
  font-size: var(--text-caption-size);
  line-height: var(--text-caption-line);
  color: var(--muted);
  font-variant-numeric: tabular-nums;
}

/* The one main action of the screen. Exactly one tile carries it. */
.dw-tile--main { border-color: var(--accent); background: var(--notice); }
.dw-tile--main .dw-tile__icon,
.dw-tile--main .dw-tile__name { color: var(--accent-text); }

/* ---- Card: notice, one per screen, the only card with a left stripe ---- */

.dw-notice {
  padding: var(--space-3);
  border: 1px solid var(--notice-line);
  border-left: 3px solid var(--accent);
  border-radius: var(--radius-md);
  background: var(--notice);
}

.dw-notice + .dw-section { margin-top: var(--space-4); }

/* A failed action: same card, danger colors. */
.dw-notice--danger {
  border-color: var(--danger-line);
  border-left-color: var(--danger);
  background: var(--danger-soft);
  color: var(--danger-text);
}

.dw-notice__title {
  margin: 0;
  font-family: var(--font-display);
  font-size: var(--text-h2-size);
  line-height: var(--text-h2-line);
  font-weight: var(--text-h2-weight);
}

.dw-notice__text {
  margin: var(--space-1) 0 0;
  font-size: var(--text-body-sm-size);
  line-height: var(--text-body-sm-line);
  color: var(--muted);
}

.dw-notice .dw-btn { margin-top: var(--space-3); }

/* Several things need attention at once: rows inside the one notice card,
   never several stripe cards stacked. Rows bleed to the card edges. */
.dw-notice__rows {
  margin: var(--space-3) calc(var(--space-3) * -1) calc(var(--space-3) * -1);
  border-top: 1px solid var(--notice-line);
}

.dw-notice__rows .dw-row { background: transparent; border-bottom-color: var(--notice-line); }
.dw-notice__rows .dw-row:last-child { border-bottom: 0; }

/* A single message: the notice card itself is the link. No title above
   it - that would be a spare line saying nothing the message does not. */
.dw-notice--link {
  display: flex;
  align-items: center;
  gap: var(--space-3);
  min-height: var(--touch);
  padding: 10px var(--space-3);
  color: var(--text);
  font-size: var(--text-body-size);
  line-height: var(--text-body-line);
  text-decoration: none;
}

.dw-notice--link > span:first-child { flex: 1 1 auto; min-width: 0; }
.dw-notice--link:hover { color: var(--accent-text); }

/* ---- Button ---- */

.dw-btn {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  min-height: var(--touch);
  padding: 0 var(--space-4);
  border: 1px solid var(--line-strong);
  border-radius: var(--radius-md);
  background: var(--surface-2);
  color: var(--text);
  font-family: var(--font-body);
  font-size: var(--text-button-size);
  font-weight: var(--text-button-weight);
  line-height: 1;
  text-decoration: none;
  cursor: pointer;
}

.dw-btn:hover { border-color: var(--accent); color: var(--accent-text); }

.dw-btn--main { border-color: var(--accent); background: var(--accent); color: var(--bg); }
.dw-btn--main:hover { color: var(--bg); border-color: var(--accent-text); background: var(--accent-text); }

.dw-btn--danger { border-color: var(--danger-line); background: var(--danger-soft); color: var(--danger-text); }
.dw-btn--danger:hover { color: var(--danger-text); }

.dw-btn--block { display: flex; width: 100%; }

/* ---- Field ----
   A label above an input. 16px text: iOS zooms the page into any field
   set smaller. Autofill keeps the theme instead of Chrome's pale fill. */

.dw-field { display: grid; gap: 6px; }

.dw-field__label {
  font-size: var(--text-caption-size);
  letter-spacing: 0.04em;
  text-transform: uppercase;
  color: var(--muted);
}

.dw-field__input {
  width: 100%;
  min-height: var(--touch);
  padding: 0 var(--space-3);
  border: 1px solid var(--line-strong);
  border-radius: var(--radius-md);
  background: var(--sunken);
  color: var(--text);
  font-family: var(--font-body);
  font-size: 16px;
  line-height: 1.2;
}

.dw-field__input:focus {
  outline: none;
  border-color: var(--accent);
  box-shadow: 0 0 0 3px var(--accent-soft);
}

.dw-field__input:-webkit-autofill {
  -webkit-text-fill-color: var(--text);
  box-shadow: 0 0 0 1000px var(--sunken) inset;
  caret-color: var(--text);
}

.dw-field__input:-webkit-autofill:focus {
  box-shadow: 0 0 0 1000px var(--sunken) inset, 0 0 0 3px var(--accent-soft);
}

/* A select dressed as the field input: same box, own chevron. */
select.dw-field__input {
  appearance: none;
  -webkit-appearance: none;
  padding-right: calc(var(--space-3) + 18px);
  background-image: linear-gradient(45deg, transparent 49%, currentColor 51%),
    linear-gradient(135deg, currentColor 49%, transparent 51%);
  background-position: calc(100% - 18px) 55%, calc(100% - 13px) 55%;
  background-size: 5px 5px;
  background-repeat: no-repeat;
}

/* A one-line note under the input: what the field is for. */
.dw-field__hint {
  font-size: var(--text-caption-size);
  line-height: var(--text-caption-line);
  letter-spacing: normal;
  text-transform: none;
  color: var(--dim);
}

/* ---- StatBar ---- */

.dw-bars { display: grid; gap: var(--space-2); }

.dw-bar__head {
  display: flex;
  justify-content: space-between;
  align-items: baseline;
  gap: var(--space-2);
  margin-bottom: var(--space-1);
}

.dw-bar__label { font-size: var(--text-caption-size); color: var(--muted); }

.dw-bar__value {
  font-family: var(--font-display);
  font-size: var(--text-stat-size);
  line-height: var(--text-stat-line);
  font-variant-numeric: tabular-nums;
}

.dw-bar__track { height: 7px; border-radius: 4px; background: var(--surface-2); overflow: hidden; }
.dw-bar__fill { display: block; height: 100%; border-radius: 4px; }
.dw-bar__fill--ok { background: var(--ok); }
.dw-bar__fill--mana { background: var(--mana); }
.dw-bar__fill--exp { background: var(--accent); }
.dw-bar__fill--danger { background: var(--danger); }

/* ---- Chip ---- */

/* A short, known set (four towns) wraps to a second line: every chip is
   visible and nothing is cut. Hiding the scrollbar was not a fix - the
   fourth town stayed clipped. Long sets (inventory folders) opt into
   sideways scrolling with --scroll, and there the bar is hidden: on
   Windows it is a 17px grey band that reads as a broken control. */
.dw-chips {
  display: flex;
  flex-wrap: wrap;
  gap: var(--space-2);
}

/* 06.10: no screen uses it any more - rows of chips wrap (owner: "buttons went off-screen into side scroll"). */
.dw-chips--scroll {
  flex-wrap: nowrap;
  overflow-x: auto;
  scrollbar-width: none;
  -ms-overflow-style: none;
}

.dw-chips--scroll::-webkit-scrollbar { display: none; }

/* A short, known set that must stay on one line - the towns. Since
   2026-09-23 the city shows two or three towns, not four (Tanderklep
   and Bairem are hidden as destinations, owner's call). Each chip starts
   at the width of its own name and the rest of the row is shared out, so
   the row is always full and no name is ever cut. Strictly equal cells
   were tried first: in the 288px desktop side column three equal cells
   left 84px each and "Tanderklep" was cut to "Tanderk..." - cut text is a
   bug, slightly unequal pills are not. */
.dw-chips--fill {
  display: flex;
  gap: 6px;
}

.dw-chips--fill .dw-chip {
  display: block;
  flex: 1 1 auto;
  min-width: 0;
  padding: 0 8px;
  line-height: 32px;
  font-size: 13px;
  text-align: center;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}

.dw-card > .dw-chips { margin-top: var(--space-3); }

.dw-chip {
  flex: 0 0 auto;
  display: inline-flex;
  align-items: center;
  height: 34px;
  padding: 0 var(--space-3);
  border: 1px solid var(--line);
  border-radius: var(--radius-pill);
  background: var(--surface);
  color: var(--text);
  font-size: 13px;
  text-decoration: none;
  white-space: nowrap;
}

.dw-chip:hover { border-color: var(--accent); color: var(--accent-text); }
.dw-chip--on { border-color: var(--accent); background: var(--surface-2); color: var(--accent-text); }

/* A count inside a chip (2026-10-13, Coliseum, owner: "buttons with a counter - where the battles are"):
   a small pill after the label, same look as .dw-row__n. A section with nothing in it gets no number and a
   muted label (--zero), so it is clear where to look without tapping; the chosen chip keeps its accent. */
.dw-chip__n {
  margin-left: 6px;
  min-width: 20px;
  padding: 1px 6px;
  border-radius: 10px;
  background: var(--accent-soft);
  color: var(--accent-text);
  font-size: 12px;
  font-weight: 600;
  line-height: 16px;
  text-align: center;
  font-variant-numeric: tabular-nums;
}
.dw-chip--zero { color: var(--muted); }
.dw-chip--zero.dw-chip--on { color: var(--accent-text); }

/* ---- screen title ---- */

.dw-title {
  margin: 0 0 var(--space-3);
  font-family: var(--font-display);
  font-size: var(--text-h1-size);
  line-height: var(--text-h1-line);
  font-weight: var(--text-h1-weight);
}

/* ---- rows inside a plain card: bleed to the edges, like notice rows ---- */

.dw-card__rows {
  margin: var(--space-3) calc(var(--space-3) * -1) 0;
  border-top: 1px solid var(--line-2);
}

.dw-card__rows:last-child { margin-bottom: calc(var(--space-3) * -1); }
/* Rows first in the card (no heading above, 05.10 clan list: "why an empty row?") - to the top edge, no line. */
.dw-card__rows:first-child { margin-top: calc(var(--space-3) * -1); border-top: 0; }
.dw-card__rows + .dw-chips { margin-top: var(--space-3); }
.dw-card__rows .dw-row:last-child { border-bottom: 0; }

/* ---- text inside a card ---- */

.dw-card__text {
  margin: 0;
  font-size: var(--text-body-sm-size);
  line-height: var(--text-body-sm-line);
  color: var(--muted);
}

/* ====================================================================
   Screen layout: one markup tree, three arrangements.

   A screen is a list of blocks (section title plus its card or list).
   The city wraps them in two groups, the content group and the side
   group, and the content group has a sub-grid for the four sections.
   On the phone the groups are display: contents - they vanish from the
   layout and every block is a flex item of the screen, put in reading
   order with `order`. On a tablet the sub-grid turns real and the four
   sections go two by two. On the desktop the groups turn real too: the
   content group on the left, the side group on the right, sticky.

   So the phone order (notice, now, battle, town, sections, exit)
   and the desktop composition (notice, battle, sections on the left;
   now, town on the right) come from the same markup. No second
   template, no hidden duplicates.
   ==================================================================== */

.dw-city,
.dw-hub {
  display: flex;
  flex-direction: column;
  gap: var(--space-4);
}

.dw-city__main,
.dw-city__side,
.dw-city__grid { display: contents; }

.dw-block { min-width: 0; }

/* Reading order on the phone. The four sections inside the sub-grid all
   take the sub-grid's number: the sub-grid is display: contents here and
   they are direct flex items, and equal numbers keep markup order. So
   the order of the sections is decided once, in the template, and holds
   on every width (CSS columns follow markup order too). */
.dw-block--notice { order: 1; }
.dw-block--now    { order: 2; }
.dw-block--battle { order: 3; }
.dw-block--town   { order: 5; }
.dw-city__grid,
.dw-city__grid > .dw-block { order: 6; }
.dw-block--exit   { order: 10; margin-top: var(--space-2); }

.dw-hub > .dw-title { margin-bottom: 0; }

/* ---- Fighter screen (user.php) ----
   The profile card carries the game's own avatar image and the marks
   the player earned; below it one markup tree splits like the city:
   a single ribbon on the phone, fighter column plus side column from
   1000px. Item names keep the game's quality colors. */

/* The head is a banner: name, level and marks run the full card
   width on top, the doll sits centered below - no squeezed name
   column, no orphan under the doll (owner, 27.09). */
.dw-profile { display: flex; flex-direction: column; gap: var(--space-3); }

/* The picture cell holds either a plain avatar image or, for admins
   and players with the full look on, the obraz.html paper doll - a
   bordered table of slot images around the avatar. Whatever it is, it
   never grows past 45% of the card, so the name never overlaps it
   (the admin's doll did on 2026-09-24). */
.dw-profile__pic { align-self: center; width: 100%; max-width: 560px; }
.dw-profile__pic img { display: block; max-width: 100%; height: auto; border-radius: var(--radius-md); }
.dw-profile__pic table { max-width: 100%; border-collapse: collapse; }
.dw-profile__pic table img { border-radius: 0; }
.dw-profile__pic td { border: 1px solid var(--line); padding: 2px; }

.dw-profile__who { min-width: 0; }
/* The player's photo left of the nick, like a Telegram profile ([DW-AVATAR], 30.09). On the own
   card the circle picks a photo (a label for the header menu's file field); without one it shows
   a camera. */
.dw-profile__photo {
  float: left;
  display: flex;
  align-items: center;
  justify-content: center;
  width: 64px;
  height: 64px;
  margin: 2px var(--space-3) var(--space-2) 0;
  overflow: hidden;
  border: 1px solid var(--line-strong);
  border-radius: var(--radius-round);
  background: var(--surface-2);
  color: var(--accent-text);
}
.dw-profile__photo img { display: block; width: 100%; height: 100%; max-width: none; object-fit: cover; }
/* A photo fills the circle without the grey ring, as in the header. */
.dw-profile__photo:has(img[src]) { border-color: transparent; }
.dw-profile__photo svg { width: 26px; height: 26px; }
label.dw-profile__photo { cursor: pointer; }
label.dw-profile__photo:hover { border-color: var(--accent); }
.dw-profile__marks { clear: both; }
/* Remove the player's photo: a POST form row at the end of the admin list. */
.dw-uadmin__form { margin: 0; }
.dw-uadmin__form > .block { display: contents; }
button.dw-row { width: 100%; border-width: 0; border-radius: 0; background: none; font-family: inherit; text-align: left; cursor: pointer; }
/* Write: a brass pill in the top right corner of the card, the nick wraps around it. */
.dw-profile__write { float: right; gap: 6px; min-height: 38px; height: 38px; margin: 0 0 var(--space-2) var(--space-3); padding: 0 16px 0 13px; font-size: var(--text-body-sm-size); }
.dw-profile__write svg { width: 16px; height: 16px; flex: 0 0 16px; }

.dw-profile__nick {
  margin: 0;
  font-family: var(--font-display);
  font-size: var(--text-h1-size);
  line-height: var(--text-h1-line);
  overflow-wrap: anywhere;
}

.dw-profile__sub { margin: 2px 0 0; color: var(--muted); font-size: var(--text-body-sm-size); }

.dw-profile__dot {
  display: inline-block;
  width: 8px;
  height: 8px;
  border-radius: var(--radius-round);
  background: var(--dim);
  vertical-align: baseline;
}

.dw-profile__dot--on { background: var(--ok-text); }

/* Marks live beside the doll, in the name column, and fill its air.
   On a narrow card the whole name column wraps below the doll
   (flex-wrap on the profile), so the nick never breaks mid-word. */
.dw-profile__marks { display: flex; flex-wrap: wrap; gap: 6px; margin-top: var(--space-2); }

.dw-mark {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  padding: 3px 8px;
  border: 1px solid var(--line);
  border-radius: 10px;
  background: var(--surface-2);
  font-size: var(--text-caption-size);
  line-height: 1.35;
  color: var(--muted);
}

.dw-mark img { max-height: 14px; width: auto; }
.dw-mark a { color: var(--accent-text); }
.dw-mark--gold { color: var(--accent-text); border-color: var(--accent); }
.dw-mark--danger { color: var(--danger-text); border-color: var(--danger-line); }

/* The doll: equipment slots around the fighter art, the old game's
   paper doll as a component. The slot columns hide on the phone - the
   card is too narrow there and the art carries the look; the doll
   lives from tablet width up (owner, 2026-09-26).

   Composition (owner, 26.09): near-square cells on all four sides of
   the art - ring/helm/ring above, body and weapon left, cape and
   shield right, boots and gloves below. The art is the big centered
   master; cells hug it. The tall 1:2 side towers are gone. */
.dw-doll { display: flex; gap: 6px; justify-content: center; }

.dw-doll__col, .dw-doll__row { display: none; }

.dw-doll__art { display: flex; align-items: center; justify-content: center; min-width: 0; }
.dw-doll__art img { display: block; max-width: 100%; max-height: 300px; width: auto; height: auto; border-radius: var(--radius-md); }

@media (min-width: 640px) {
  .dw-doll {
    display: grid;
    grid-template-columns: auto auto auto;
    grid-template-rows: auto auto auto;
    justify-content: center;
    align-items: stretch;
    gap: 6px;
  }

  .dw-doll__row { display: flex; justify-content: center; align-items: center; gap: 6px; }
  .dw-doll__row--top { grid-row: 1; grid-column: 1 / -1; }
  .dw-doll__row--bottom { grid-row: 3; grid-column: 1 / -1; }

  .dw-doll__col {
    display: flex;
    flex-direction: column;
    justify-content: space-evenly;
    gap: 6px;
  }
  .dw-doll__col--left { grid-row: 2; grid-column: 1; }
  .dw-doll__col--right { grid-row: 2; grid-column: 3; }
  .dw-doll__art { grid-row: 2; grid-column: 2; }

  /* One width for every cell; the shape follows the picture (owner,
     2026-09-26): tall game pictures (32x64, 41x82, 40x80) get a
     taller cell of the same width, the 32x32 rings a square one.
     Pictures fill by height, never their raw game size
     (docs/art-briefs/ITEM-PICTURES-FOR-DESIGN.md). */
  .dw-doll__slot {
    display: flex;
    align-items: center;
    justify-content: center;
    width: 66px;
    height: 94px;
    border-radius: 4px;
    background: var(--surface-2);
    overflow: hidden;
  }

  .dw-doll__art img { max-height: 340px; }

  /* Fill by height: max-limits only shrink and left the picture at
     its 1x game size - half a cell (art agent, 26.09). */
  .dw-doll__slot img { width: 94%; height: 94%; object-fit: contain; }

  /* Square cells: rings (32x32 pictures) and the belt, whose
     picture is horizontal - same width, square (owner, 26.09). */
  .dw-doll__slot--sq { height: 66px; }
}

/* On wide screens the art is the master: ~460px tall, two cells per
   side spread along it, the top and bottom rows frame the figure. */
@media (min-width: 1000px) {
  .dw-doll__slot { width: 96px; height: 136px; }
  .dw-doll__slot--sq { height: 96px; }
  .dw-doll__art img { max-height: 460px; }
}

/* An empty slot stays visible: a quiet contour of the item type, the
   Diablo way (owner, 27.09). Amulet, belt, badge and the third ring
   have no pictures yet, so their cells always show the contour; worn
   ones carry the quality frame computed from $info.items. */
a.dw-doll__slot { text-decoration: none; }
a.dw-doll__slot:hover { filter: brightness(1.18); }

/* Placeholder silhouettes from /i/newitems/slots/ (art agent, 27.09):
   a truly empty slot shows one dimmed; a worn item without its own
   picture (amulet, belt, badge, third ring) shows it at full
   strength inside the quality frame. */
.dw-doll__slot--empty img { opacity: .5; }

/* ---- item quality: a frame and a glow, no percent ----
   The approved mock (owner, 26.09): cell keeps the theme surface, the
   frame is 2px in the quality color, the glow scales with the class;
   valor, clan and artefact items carry a letter badge instead. Numbers
   come from tools/game/item-quality.css: the .d3 scale for doll cells,
   the smaller td scale for the 44px phone list cells. Class 0 and
   blank keep the plain strong line and no glow. */
.dw-doll__slot, .dw-slotpic { position: relative; border: 2px solid var(--line-strong); }

.dw-doll__slot.drop_1 { border-color: #818181; box-shadow: inset 0 0 6px rgba(129,129,129,.27); }
.dw-doll__slot.drop_2 { border-color: #7474e7; box-shadow: inset 0 0 8px rgba(116,116,231,.33); }
.dw-doll__slot.drop_3 { border-color: #f27979; box-shadow: inset 0 0 10px rgba(242,121,121,.40); }
.dw-doll__slot.drop_4 { border-color: #a954ff; box-shadow: inset 0 0 12px rgba(169,84,255,.47); }
.dw-doll__slot.drop_5 { border-color: #f76d3b; box-shadow: inset 0 0 16px rgba(247,109,59,.60), 0 0 5px rgba(247,109,59,.40); }
.dw-doll__slot.drop_6 { border-color: #00ff00; box-shadow: inset 0 0 20px rgba(0,255,0,.67), 0 0 7px rgba(0,255,0,.45); }
.dw-doll__slot.drop_7 { border-color: #42aaff; box-shadow: inset 0 0 24px rgba(66,170,255,.73), 0 0 11px rgba(66,170,255,.45); }
.dw-doll__slot.drop_8 { border-color: #ff00ff; box-shadow: inset 0 0 30px rgba(255,0,255,.80), 0 0 16px rgba(255,0,255,.45); }
.dw-doll__slot.valor_1, .dw-doll__slot.valor_2, .dw-doll__slot.valor_3 { border-color: #c8952e; box-shadow: inset 0 0 16px rgba(200,149,46,.55), 0 0 7px rgba(200,149,46,.40); }
.dw-doll__slot.klan { border-color: #b09c8c; box-shadow: inset 0 0 10px rgba(176,156,140,.35); }
.dw-doll__slot.art { border-color: #8866ff; box-shadow: inset 0 0 16px rgba(136,102,255,.55), 0 0 7px rgba(136,102,255,.40); }

/* The phone scale: x0.75 of the mock blur, full mock alpha; x0.55
   read as bare borders (owner, 26.09: glow missing). The outer glow
   starts at class 5 so it reads around the small cell. */
.dw-slotpic.drop_1, .dw-invpic.drop_1 { border-color: #818181; box-shadow: inset 0 0 5px rgba(129,129,129,.27); }
.dw-slotpic.drop_2, .dw-invpic.drop_2 { border-color: #7474e7; box-shadow: inset 0 0 6px rgba(116,116,231,.33); }
.dw-slotpic.drop_3, .dw-invpic.drop_3 { border-color: #f27979; box-shadow: inset 0 0 8px rgba(242,121,121,.40); }
.dw-slotpic.drop_4, .dw-invpic.drop_4 { border-color: #a954ff; box-shadow: inset 0 0 9px rgba(169,84,255,.47); }
.dw-slotpic.drop_5, .dw-invpic.drop_5 { border-color: #f76d3b; box-shadow: inset 0 0 12px rgba(247,109,59,.60), 0 0 6px rgba(247,109,59,.45); }
.dw-slotpic.drop_6, .dw-invpic.drop_6 { border-color: #00ff00; box-shadow: inset 0 0 15px rgba(0,255,0,.67), 0 0 7px rgba(0,255,0,.45); }
.dw-slotpic.drop_7, .dw-invpic.drop_7 { border-color: #42aaff; box-shadow: inset 0 0 18px rgba(66,170,255,.73), 0 0 9px rgba(66,170,255,.45); }
.dw-slotpic.drop_8, .dw-invpic.drop_8 { border-color: #ff00ff; box-shadow: inset 0 0 22px rgba(255,0,255,.80), 0 0 12px rgba(255,0,255,.45); }
.dw-slotpic.valor_1, .dw-slotpic.valor_2, .dw-slotpic.valor_3,
.dw-invpic.valor_1, .dw-invpic.valor_2, .dw-invpic.valor_3 { border-color: #c8952e; box-shadow: inset 0 0 12px rgba(200,149,46,.55), 0 0 5px rgba(200,149,46,.40); }
.dw-slotpic.klan, .dw-invpic.klan { border-color: #b09c8c; box-shadow: inset 0 0 8px rgba(176,156,140,.35); }
.dw-slotpic.art, .dw-invpic.art { border-color: #8866ff; box-shadow: inset 0 0 12px rgba(136,102,255,.55), 0 0 5px rgba(136,102,255,.40); }

/* Arena items (class 5, "(a)" in the name) keep the class frame but no
   glow: the orange glow read as the gold OD one (owner, 27.09). The old
   game told them apart by a half-tone cell background and the bold OD
   name; OD keeps its gold glow and label. */
.dw-doll__slot.arena, .dw-slotpic.arena, .dw-invpic.arena { box-shadow: none; }

.dw-doll__slot.valor_1::after, .dw-doll__slot.valor_2::after, .dw-doll__slot.valor_3::after,
.dw-doll__slot.klan::after, .dw-doll__slot.art::after,
.dw-slotpic.valor_1::after, .dw-slotpic.valor_2::after, .dw-slotpic.valor_3::after,
.dw-slotpic.klan::after, .dw-slotpic.art::after,
.dw-invpic.valor_1::after, .dw-invpic.valor_2::after, .dw-invpic.valor_3::after,
.dw-invpic.klan::after, .dw-invpic.art::after {
  position: absolute;
  top: 0;
  right: 0;
  padding: 0 2px;
  border-radius: 0 0 0 3px;
  background: rgba(18, 16, 14, .85);
  font: bold 9px/11px Verdana, Arial, sans-serif;
  pointer-events: none;
}

.dw-doll__slot.valor_1::after, .dw-doll__slot.valor_2::after, .dw-doll__slot.valor_3::after,
.dw-slotpic.valor_1::after, .dw-slotpic.valor_2::after, .dw-slotpic.valor_3::after,
.dw-invpic.valor_1::after, .dw-invpic.valor_2::after, .dw-invpic.valor_3::after { content: "\41E\414"; color: #c8952e; }
.dw-doll__slot.klan::after, .dw-slotpic.klan::after, .dw-invpic.klan::after { content: "\41A"; color: #b09c8c; }
.dw-doll__slot.art::after, .dw-slotpic.art::after, .dw-invpic.art::after { content: "\410"; color: #8866ff; }

/* The label grows with the cell: 9px is the phone list size and was lost
   on the doll and on the big item picture (owner, 27.09). */
@media (min-width: 640px) {
  .dw-doll__slot.valor_1::after, .dw-doll__slot.valor_2::after, .dw-doll__slot.valor_3::after,
  .dw-doll__slot.klan::after, .dw-doll__slot.art::after {
    top: 3px;
    right: 3px;
    padding: 1px 5px;
    border-radius: 4px;
    font-size: 12px;
    line-height: 15px;
  }
}

.dw-doll__slot.dw-itempic.valor_1::after, .dw-doll__slot.dw-itempic.valor_2::after,
.dw-doll__slot.dw-itempic.valor_3::after, .dw-doll__slot.dw-itempic.klan::after,
.dw-doll__slot.dw-itempic.art::after {
  top: 5px;
  right: 5px;
  padding: 2px 7px;
  border-radius: 5px;
  font-size: 13px;
  line-height: 17px;
}

/* The phone equipment list carries the picture before the item name;
   from tablet width the doll shows the pictures and the list goes back
   to text (owner, 2026-09-26). */
.dw-slotpic {
  flex: 0 0 auto;
  display: flex;
  align-items: center;
  justify-content: center;
  width: 64px;
  height: 92px;
  border-radius: 4px;
  background: var(--surface-2);
  overflow: hidden;
}

/* A slot with no picture yet (amulet, belt, badge, third ring): a
   quiet empty cell keeps every row's name on one vertical line. */
.dw-slotpic--none { border-color: var(--line); background: var(--surface); }

/* object-fit, not percentage height: Safari sizes a percent-tall img
   with auto width by its own rules inside a flex cell, and on the
   iPhone the pictures came out even narrower (owner, 27.09). */
.dw-slotpic img { width: 94%; height: 94%; object-fit: contain; }
.dw-slotpic--ring { height: 64px; }

/* Bigger pictures beat a big name: the item name steps down a size in
   the picture rows (owner, 27.09). */
.dw-slotpic + span { flex: 1 1 auto; min-width: 0; font-size: 14px; }

/* The generic "first span of a row stretches" rule was inflating the
   picture cell to 150px and every cell came out a different size
   (owner, 2026-09-26). The cell never stretches. */
.dw-row > span.dw-slotpic:first-child { flex: 0 0 auto; width: 64px; height: 92px; }

@media (min-width: 640px) {
  .dw-slotpic { display: none; }
}



/* Key-value rows: a label left, the value right, tabular digits. */
.dw-kv { display: grid; gap: 0; }

.dw-kv__row {
  display: flex;
  justify-content: space-between;
  align-items: baseline;
  gap: var(--space-3);
  padding: 5px 0;
  border-bottom: 1px solid var(--line-2);
  font-size: var(--text-body-sm-size);
  line-height: var(--text-body-sm-line);
}

.dw-kv__row:last-child { border-bottom: 0; }
.dw-kv__k { flex: 0 0 auto; white-space: nowrap; color: var(--muted); }
.dw-kv__v { flex: 0 1 auto; min-width: 0; text-align: right; font-variant-numeric: tabular-nums; overflow-wrap: anywhere; }
.dw-kv__v img { max-height: 14px; width: auto; vertical-align: text-bottom; }
.dw-kv--top { margin-top: var(--space-3); padding-top: var(--space-2); border-top: 1px solid var(--line-2); }
/* A long value (a browser string) goes under its label, left-aligned. */
.dw-kv__row--stack { flex-direction: column; align-items: stretch; gap: 2px; }
.dw-kv__row--stack .dw-kv__v { text-align: left; }
.dw-kv__v--code { font-family: ui-monospace, "Cascadia Mono", Consolas, "Liberation Mono", monospace; font-size: 12.5px; }
/* Hidden data (admins and moderators, 29.09): the same card with a dashed
   edge - staff-only information, not part of the player's own screen. */
.dw-card--hidden { border-style: dashed; border-color: var(--line-strong); }
/* Admin actions (29.09): punishments in the danger colour. */
.dw-uadmin .dw-row--danger > span:first-child { color: var(--danger-text); }

/* Stat rows: name, the number big, base+bonus, add-buttons. */
.dw-statrows { display: grid; gap: var(--space-2); }

.dw-statrow { display: flex; align-items: center; gap: var(--space-2); }
.dw-statrow__k { flex: 1 1 auto; color: var(--muted); font-size: var(--text-body-sm-size); }

.dw-statrow__n {
  font-family: var(--font-display);
  font-size: var(--text-stat-size);
  line-height: var(--text-stat-line);
  font-variant-numeric: tabular-nums;
}

.dw-statrow__base { color: var(--dim); font-size: var(--text-caption-size); font-variant-numeric: tabular-nums; }
.dw-statrow__add { display: flex; gap: 4px; }
.dw-statrow__add .dw-chip { min-height: 26px; padding: 0 8px; font-size: 12px; }
.dw-statrows + .dw-card__text { margin-top: var(--space-3); }


/* Item quality, clan wear and rune colors outside the compat layer:
   the fighter screen prints item names in the game's own colors. */
.dw .drop_1, .dw .drop_1 a { color: var(--drop-1); }
.dw .drop_2, .dw .drop_2 a { color: var(--drop-2); }
.dw .drop_3, .dw .drop_3 a { color: var(--drop-3); }
.dw .drop_4, .dw .drop_4 a { color: var(--drop-4); }
.dw .drop_5, .dw .drop_5 a { color: var(--drop-5); }
.dw .drop_6, .dw .drop_6 a { color: var(--drop-6); }
.dw .drop_7, .dw .drop_7 a { color: var(--drop-7); }
.dw .drop_8, .dw .drop_8 a { color: var(--drop-8); }
/* The old name colors by kind (templates/user.html, main.css): OD by
   its rank, artifact, clan artifact, class wear. The template picks
   one class in the old precedence - drop, then wear, then OD/artifact -
   because main.css let the drop and wear colors win (owner, 27.09). */
.dw .art_1, .dw .art_1 a { color: var(--valor-1); }
.dw .art_2, .dw .art_2 a { color: var(--valor-2); }
.dw .art_3, .dw .art_3 a { color: var(--valor-3); }
.dw .art_4, .dw .art_4 a { color: var(--nick-art); }
/* Role nicks everywhere, like the vip_N colours (nicks.css): the markup comes inside the nick itself (users.nick:
   <span class="admin">Ne0</span>, adm_font, md_font, vip_333). Until 03.10 only mail and forum texts coloured them -
   in the side messages ("the megaphone"), ranks and elections the admin nick stayed plain (owner 03.10). */
.dw .admin, .dw .admin a { color: var(--nick-admin); font-weight: 600; }
.dw .admin2, .dw .admin2 a { color: var(--nick-admin); }
.dw .adm_font, .dw .adm_font a { color: var(--nick-adm); }
.dw .md_font, .dw .md_font a { color: var(--nick-mod); }
.dw .vip_333, .dw .vip_333 a { color: var(--nick-vip); }
.dw .clan_art, .dw .clan_art a { color: var(--clan-art); }
.dw .wear_1, .dw .wear_1 a { color: var(--wear-1); }
.dw .wear_2, .dw .wear_2 a { color: var(--wear-2); }
.dw .wear_3, .dw .wear_3 a { color: var(--wear-3); }
.dw .runes_1 { color: var(--danger-text); }
/* Ice as text: the mana blue is a bar colour and reads too dark on
   the dark surface (item card, 27.09). */
.dw .runes_2 { color: var(--rune-ice); }
.dw .runes_3 { color: var(--ok-text); }

/* Layout: one stream of bubbles (dw-hero). The phone reads it as a
   ribbon in markup order. From 1000px a small script in user.html packs
   the bubbles Tetris-style: each goes into the shortest column, so no
   column holds a hole while another runs long (owner, 27.09). The first
   column is as wide as the doll card; the others share the rest and are
   never narrower than --dw-hero-min. Without the script the desktop
   keeps the ribbon - readable, just long. */
.dw-hero {
  --dw-hero-first: 560px;
  --dw-hero-min: 320px;
  --dw-hero-gap: 16px;
  /* Fixed places on every screen with a hero stream: a player finds a
     button where it was yesterday, on every profile (owner, 27.09). */
  --dw-hero-max: 3;
  --dw-hero-fixed: 1;
  display: flex;
  flex-direction: column;
  gap: var(--dw-hero-gap);
}

.dw-notice + .dw-hero { margin-top: var(--space-2); }

@media (min-width: 1000px) {
  .dw-hero--packed {
    display: grid;
    align-items: start;
  }

  .dw-hero__col {
    display: flex;
    flex-direction: column;
    gap: var(--dw-hero-gap);
    min-width: 0;
  }

  .dw-profile__nick { font-size: var(--text-display-size); }
}

/* ---- Clan row on the fighter's meta card ----
   What the old page set apart stays set apart (owner, 27.09): the clan
   name bold in the link colour after its kind (Legion, Order...), the
   posts bold, Recruit as a chip, the player's stage in the clan bold in
   the stage colour (main.css stage_N). */
.dw-clanrow__main { flex: 1 1 auto; min-width: 0; display: flex; flex-direction: column; gap: 4px; }
.dw-clanrow__name { color: var(--accent-text); font-weight: 600; overflow-wrap: anywhere; }
.dw-clanrow__stage { color: var(--muted); font-weight: 400; }
.dw-clanrow__roles { display: flex; flex-wrap: wrap; align-items: center; gap: 4px 10px; font-size: var(--text-body-sm-size); }
.dw-clanrow__roles b { color: var(--text); font-weight: 600; }
.dw .stage_2, .dw .stage_100 { color: var(--valor-2); }
.dw .stage_3 { color: var(--valor-1); }
.dw .stage_4 { color: var(--nick-art); }
.dw-clanrow__roles b.stage_2, .dw-clanrow__roles b.stage_100 { color: var(--valor-2); }
.dw-clanrow__roles b.stage_3 { color: var(--valor-1); }
.dw-clanrow__roles b.stage_4 { color: var(--nick-art); }

/* ---- Item card (item.php) ----
   One stream of bubbles like the fighter screen: the card with the big
   picture opens the first column, the characteristics the second, the
   rest packs Tetris-style on the desktop (dw_pack.html). The data is
   the old page's; the look is new (owner, 27.09). */
/* At most three columns: the card and its stats read down the first,
   the rest in two more - at 1800 four columns sent the eye sideways
   (owner, 27.09). */
/* Fixed places: every item shows each block in the same spot, the
   column count follows only the screen width (owner, 27.09). */
.dw-hero--item { --dw-hero-first: 440px; --dw-hero-max: 3; --dw-hero-fixed: 1; }

.dw-itemcard {
  display: grid;
  grid-template-columns: auto minmax(0, 1fr);
  gap: var(--space-3) var(--space-4);
  align-items: start;
}
.dw-itemcard > * { grid-column: 1 / -1; }
.dw-itemcard > .dw-itemcard__pic { grid-column: 1; }
.dw-itemcard > .dw-itemcard__who { grid-column: 2; align-self: center; min-width: 0; }

.dw-itemcard__name {
  margin: 0;
  font-family: var(--font-display);
  font-size: var(--text-h1-size);
  line-height: var(--text-h1-line);
  text-wrap: balance;
  overflow-wrap: anywhere;
}
.dw-itemcard__type { margin: 4px 0 0; color: var(--muted); font-size: var(--text-caption-size); }
.dw-itemcard__note { margin: 0; color: var(--muted); font-size: var(--text-caption-size); line-height: var(--text-caption-line); }
.dw-itemcard__cap { margin: var(--space-3) 0 6px; color: var(--muted); font-size: var(--text-caption-size); }
.dw-itemcard__bars { margin-bottom: var(--space-3); }
.dw-itemcard__setname { margin: 0; font-size: 16px; }
/* Set block (04.10, DW-ITEM-SETWEAR): how many parts count as in battle (the bonus needs all 4), the set body armour row
   that a worn art body armour replaces - highlighted like a worn part, the art name on a second line. */
.dw-itemcard__setworn { margin: 0; color: var(--muted); font-size: var(--text-caption-size); }
.dw-itemcard__setworn--on { color: var(--ok-text); }
.dw-itemcard__setart { display: block; margin-top: 2px; color: var(--muted); font-size: var(--text-caption-size); font-weight: 400; }
/* The description reads as text, not as a muted note (owner, 27.09). */
.dw-itemcard__opis { margin: 0; white-space: pre-line; color: var(--text); }

/* The big picture: the doll cell in the quality frame and glow, larger.
   Tall items 1:1.8, rings square - the same shapes as on the doll. */
.dw-doll__slot.dw-itempic {
  display: flex;
  align-items: center;
  justify-content: center;
  width: 104px;
  height: 188px;
  border-radius: 6px;
  background: var(--surface-2);
  overflow: hidden;
}
.dw-doll__slot.dw-itempic--sq { height: 104px; }
.dw-itempic img { width: 94%; height: 94%; object-fit: contain; }
.dw-itempic--old img { width: auto; height: auto; max-width: 90%; max-height: 90%; }

@media (min-width: 640px) {
  .dw-doll__slot.dw-itempic { width: 128px; height: 232px; }
  .dw-doll__slot.dw-itempic--sq { height: 128px; }
}

.dw-marks { display: flex; flex-wrap: wrap; gap: 6px; margin-top: var(--space-2); }
.dw-card > .dw-marks:first-child { margin-top: 0; }
a.dw-mark { color: var(--text); text-decoration: none; }
a.dw-mark:hover { border-color: var(--accent); }

/* Characteristics as rows under the card, in the same column: one
   stat per line, name left, number right, then the training bonus
   (+N), element values and "yours N" for the item worn in this slot,
   with an arrow: up - this one is better. The eye goes down, not
   sideways (owner, 27.09). */
.dw-stats .dw-kv__v { display: flex; flex-wrap: wrap; justify-content: flex-end; align-items: baseline; gap: 2px 8px; }
.dw-stat__v { color: var(--text); font-weight: 600; font-variant-numeric: tabular-nums; }
.dw-stats .dw-plus,
.dw-stats .dw-was,
.dw-stats [class^="runes_"] { font-size: var(--text-caption-size); }
.dw-plus { font-weight: 600; }
.dw-was { color: var(--muted); white-space: nowrap; }
.dw-was--up::before { content: "\25B2\00a0"; color: var(--ok-text); }
.dw-was--down::before { content: "\25BC\00a0"; color: var(--danger-text); }
.dw-stats + .dw-itemcard__note { margin-top: var(--space-3); }
.dw-ok { color: var(--ok-text); }
.dw-danger { color: var(--danger-text); }

/* Sockets: a dot per slot, filled when taken. */
.dw-pips { display: inline-flex; gap: 4px; margin-right: 6px; vertical-align: middle; }
.dw-pip { width: 10px; height: 10px; border-radius: 50%; border: 1.5px solid var(--line-strong); }
.dw-pip--on { background: var(--accent); border-color: var(--accent); }
.dw-pips--rune .dw-pip--on { background: var(--mana); border-color: var(--mana); }

.dw-copy {
  width: 12ch;
  padding: 4px 8px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  background: var(--surface-2);
  color: var(--text);
  font: inherit;
  font-variant-numeric: tabular-nums;
  text-align: right;
}
.dw-copy:focus { outline: 2px solid var(--accent); outline-offset: 1px; }

.dw-row--on { color: var(--accent-text); }
.dw-row--dim { color: var(--dim); }

/* ---- Who is online (online.php) ----
   Each row is a big link to the player's profile (51% of exits over 61
   days); paging gets big Back/Next buttons (players page as often as
   they leave). On the desktop the rows of a page read down two columns
   of half the page each (--dw-rows from the template) - down, not
   sideways. */
.dw-online__head {
  display: flex;
  align-items: baseline;
  flex-wrap: wrap;
  gap: var(--space-2) var(--space-3);
  margin-bottom: var(--space-3);
}
.dw-online__title {
  margin: 0;
  font-family: var(--font-display);
  font-size: var(--text-h1-size);
  line-height: var(--text-h1-line);
}

.dw-row > span.dw-who__marks:first-child { flex: 0 0 auto; }
.dw-who__marks { display: inline-flex; align-items: center; gap: 4px; min-width: 44px; }
.dw-who__main { flex: 1 1 auto; min-width: 0; display: flex; flex-direction: column; }
.dw-who__nick { font-weight: 600; overflow-wrap: anywhere; }
.dw-who__lvl { margin-left: 2px; color: var(--muted); font-weight: 400; font-variant-numeric: tabular-nums; }
.dw-who .dw-mark { flex: 0 0 auto; white-space: nowrap; }

@media (min-width: 1000px) {
  .dw-online__list {
    display: grid;
    grid-template-columns: repeat(2, minmax(0, 1fr));
    grid-template-rows: repeat(var(--dw-rows, 5), auto);
    grid-auto-flow: column;
    position: relative;
    overflow: hidden;
  }
  /* Row lines: each row's bottom line slips under the list edge, so the
     last row of either column draws no double line; the middle line is
     the list's own, whatever the number of rows. */
  .dw-online__list > .dw-row { margin-bottom: -1px; border-bottom: 1px solid var(--line-2); }
  .dw-online__list::after {
    content: "";
    position: absolute;
    top: 0;
    bottom: 0;
    left: 50%;
    border-left: 1px solid var(--line-2);
  }
}

/* Paging: big Back / Next, the engine's page numbers between them
   (current page in brass), and "page N of M" when there are more than
   five pages. The engine's own arrows inside the numbers are hidden -
   the buttons do that job. */
.dw-pager {
  display: flex;
  align-items: center;
  justify-content: space-between;
  flex-wrap: wrap;
  gap: var(--space-2);
  margin-top: var(--space-3);
}
.dw-pager__step {
  display: inline-flex;
  align-items: center;
  min-height: var(--touch);
  padding: 0 var(--space-4);
  border: 1px solid var(--line-strong);
  border-radius: var(--radius-md);
  background: var(--surface-2);
  color: var(--text);
  font-weight: 600;
  text-decoration: none;
}
.dw-pager__step:hover { border-color: var(--accent); color: var(--accent-text); }
.dw-pager__step--off { opacity: .35; }
.dw-pager__pages {
  display: flex;
  flex: 1 1 auto;
  flex-wrap: wrap;
  justify-content: center;
  font-size: 0;
}
.dw-pager__pages > a,
.dw-pager__pages > b,
.dw-pager__pages > button {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  min-width: 36px;
  height: 36px;
  margin: 2px;
  padding: 0 6px;
  border: 1px solid var(--line);
  border-radius: var(--radius-md);
  color: var(--text);
  font-size: var(--text-body-size);
  font-weight: 400;
  font-variant-numeric: tabular-nums;
  text-decoration: none;
}
.dw-pager__pages > b { border-color: var(--accent); color: var(--accent-text); font-weight: 600; }
.dw-pager__pages > a:hover,
.dw-pager__pages > button:hover { border-color: var(--accent); }
/* The same pager drawn by a script (inventory stock): buttons, not links. */
.dw-pager__pages > button { background: transparent; font-family: var(--font-body); cursor: pointer; }
button.dw-pager__step { font-family: var(--font-body); font-size: var(--text-body-size); cursor: pointer; }
button.dw-pager__step:disabled { opacity: .35; cursor: default; }
.dw-pager__pages > a[title="previous page"],
.dw-pager__pages > a[title="next page"] { display: none; }
.dw-pager__jump {
  display: flex;
  align-items: center;
  justify-content: center;
  flex-wrap: wrap;
  gap: var(--space-2);
  margin-top: var(--space-2);
  color: var(--muted);
}
.dw-pager__jump .dw-copy { width: 6ch; text-align: center; }
/* Compact pager (mail history, 29.09): Back, "Page N", Next - no numbers,
   one line on the phone too. */
.dw-pager__now { flex: 1 1 auto; color: var(--muted); text-align: center; font-variant-numeric: tabular-nums; }

@media (max-width: 639.98px) {
  /* Phone: Back and Next on one line, the numbers under them. */
  .dw-pager__pages { order: 3; flex-basis: 100%; }
}

/* ---- Mail (mail.php: list, history, talk, notepad, new letter) ----
   Fixed places on every mail screen (owner, 27.09): the up link on top,
   the title with its one main action on the right, the letters in the
   main column, the tools in a side column on the right from 1000px.
   On the phone: new letters from others first, then the letters, then
   the tools. */
.dw-mail__head {
  display: flex;
  align-items: center;
  flex-wrap: wrap;
  gap: var(--space-2) var(--space-3);
  margin-bottom: var(--space-3);
}
.dw-mail__title {
  margin: 0;
  font-family: var(--font-display);
  font-size: var(--text-h1-size);
  line-height: var(--text-h1-line);
  font-weight: var(--text-h1-weight);
  overflow-wrap: anywhere;
}
.dw-mail__emb { display: inline-flex; flex: 0 0 auto; }
/* The partner's photo in the one-to-one chat head (DW-AVATAR step 2, 01.10): a circle of the
   emblem's height (40 desktop, 36 phone) left of it, the clan emblem stays beside it as it was
   (owner: a badge over the photo looked bad); no ring round the photo. */
.dw-face { display: block; flex: 0 0 auto; width: 40px; height: 40px; overflow: hidden; border-radius: var(--radius-round); }
.dw-chathead .dw-face { width: 36px; height: 36px; }
.dw-face img { display: block; width: 100%; height: 100%; max-width: none; object-fit: cover; }
.dw-mail__who { color: inherit; text-decoration: none; }
.dw-mail__who:hover { color: var(--accent-text); }
.dw-mail__act { margin-left: auto; }
.dw-mark--on { color: var(--ok-text); border-color: var(--ok); }

.dw-mail {
  display: grid;
  grid-template-columns: minmax(0, 1fr);
  grid-template-areas: "unread" "main" "tools";
  gap: var(--space-4);
  align-items: start;
}
.dw-mail__unread { grid-area: unread; min-width: 0; }
.dw-mail__main { grid-area: main; min-width: 0; }
.dw-mail__tools { grid-area: tools; min-width: 0; }
.dw-mail__main > .dw-section:first-child,
.dw-mail__unread > .dw-section:first-child,
.dw-mail__tools > .dw-section:first-child { margin-top: 0; }
.dw-mail__tools .dw-section + .dw-notice { margin-bottom: var(--space-2); }

@media (min-width: 1000px) {
  .dw-mail {
    grid-template-columns: minmax(0, 1fr) minmax(300px, 360px);
    grid-template-areas: "main tools";
    gap: var(--space-3) var(--space-5);
  }
  /* New letters from others take the top of the side column; without
     them the tools start level with the letters. */
  .dw-mail--unread {
    grid-template-areas: "main unread" "main tools";
    grid-template-rows: auto 1fr;
  }
}

/* ---- Events (service_events, 02.10) ----
   The mail's places (list left, column "Events" right). A section row is a ListRow with its icon and the new count;
   in the archive the count is grey and without "+". An event is a row but not a link - the engine's text carries its
   own links (item, player, topic); the new ones get a brass dot, the time stands on the right in tabular figures. */
.dw-row__n--all { background: var(--surface-2); color: var(--muted); }
.dw-ev {
  display: flex;
  align-items: baseline;
  gap: var(--space-3);
  min-height: var(--touch);
  padding: 11px var(--space-3);
  border-bottom: 1px solid var(--line-2);
}
.dw-ev:last-child { border-bottom: 0; }
.dw-ev__text { flex: 1 1 auto; min-width: 0; margin: 0; overflow-wrap: anywhere; }
.dw-ev__text a { color: var(--accent-text); }
.dw-ev--new .dw-ev__text::before {
  content: "";
  display: inline-block;
  width: 8px;
  height: 8px;
  margin-right: 8px;
  border-radius: var(--radius-round);
  background: var(--accent);
  vertical-align: 1px;
}
.dw-ev__meta { flex: 0 0 auto; display: inline-flex; align-items: center; gap: var(--space-2); }
.dw-ev__time { color: var(--muted); font-size: var(--text-caption-size); font-variant-numeric: tabular-nums; white-space: nowrap; }
.dw-ev--new .dw-ev__time { color: var(--accent-text); }
.dw-ev__note { margin: var(--space-2) 0 0; color: var(--muted); font-size: var(--text-caption-size); }
/* Inside a section the phone shows no side column (a tail under the events; "< Events" leads back). */
@media (max-width: 999.98px) {
  .dw-events--cat .dw-mail__tools { display: none; }
}
/* ---- Side leader: Cardinal / Regent (leader.php, 02.10) ----
   One column for the sub-pages (cabinet, messages, quests, workshop, building card), the mail's places on the main
   page (leader, buildings, elections left; side links, taxes, ranks right). A row with actions on the right is
   .dw-lrow (ranks, treasury, buildings, crafts); quest texts keep the old line breaks, actions are buttons. */
.dw-leader { display: grid; gap: var(--space-3); max-width: 900px; }
.dw-leader > .dw-section { margin-bottom: 0; }
.dw-leader__now .dw-card__text { margin: 0; color: var(--muted); }
.dw-leader__who { display: flex; align-items: center; gap: var(--space-2); margin: var(--space-2) 0 var(--space-3); font-weight: 600; }
.dw-leader__who a { color: var(--text); text-decoration: none; }
.dw-leader__who a:hover { color: var(--accent-text); }
.dw-leader__sub { margin: var(--space-3) 0 var(--space-2); font-size: var(--text-body-size); font-weight: 600; }
.dw-leader__no { color: var(--dim); font-size: var(--text-body-sm-size); }
.dw-leader__empty { margin: 0; padding: 10px var(--space-3); color: var(--muted); font-size: var(--text-body-sm-size); }
.dw-leader__go { margin-top: var(--space-3); }
.dw-leader__form { display: grid; gap: var(--space-3); max-width: 520px; }
.dw-leader__form .dw-btn { justify-self: start; }
.dw-leader__form .dw-card__text { margin: 0; }
.dw-leader__acts { display: flex; flex-wrap: wrap; gap: var(--space-2); }
/* Main page of the leader - explicit rows on the desktop (design-system rule 32, owner 03.10: "make the messages
   button as tall as the neighbour bubble", "taxes level with buildings", "no ragged edges"): row 1 - the leader card
   and the side messages, stretched to one height; row 2 - buildings left, taxes and ranks right, from one line;
   the elections under them on the right (owner 02.10: "on the desktop all of it can go to the right panel").
   The entrance tiles keep their usual size over the rows. The phone keeps the old order in one column. */
/* Phone order (owner 03.10: "the side messages higher", "the side ranks higher on the phone"): leader (and the town
   battle alert), messages, taxes and ranks, buildings, elections. */
.dw-mail.dw-leader-main { grid-template-areas: "lead" "msg" "tools" "main" "vote"; }
.dw-leader__lead { grid-area: lead; display: grid; gap: var(--space-3); min-width: 0; }
.dw-leader__msg { grid-area: msg; min-width: 0; }
.dw-leader__vote { grid-area: vote; min-width: 0; }
.dw-leader__vote > .dw-section:first-child { margin-top: 0; }
@media (min-width: 1000px) {
  .dw-mail.dw-leader-main { grid-template-areas: "lead msg" "main tools" "main vote"; grid-template-rows: auto auto 1fr; }
  .dw-leader__lead,
  .dw-leader__msg { align-self: stretch; }
  .dw-leader__msg > .dw-list { height: 100%; }
  .dw-leader__msg .dw-row { height: 100%; }
}
.dw-leader__taxes { display: grid; gap: var(--space-3); }
.dw-lrow {
  display: flex;
  align-items: center;
  gap: var(--space-3);
  min-height: var(--touch);
  padding: 9px var(--space-3);
  border-bottom: 1px solid var(--line-2);
}
.dw-lrow:last-child { border-bottom: 0; }
.dw-lrow__main { flex: 1 1 auto; min-width: 0; }
.dw-lrow__name { display: flex; flex-wrap: wrap; align-items: center; gap: 6px; color: var(--text); font-weight: 600; text-decoration: none; overflow-wrap: anywhere; }
a.dw-lrow__name:hover { color: var(--accent-text); }
.dw-lrow__name a, .dw-lrow__cap a { color: inherit; text-decoration: none; }
.dw-lrow__cap { display: flex; flex-wrap: wrap; align-items: center; gap: 6px; margin-top: 2px; color: var(--muted); font-size: var(--text-caption-size); line-height: var(--text-caption-line); }
.dw-lrow__acts { display: flex; flex: 0 0 auto; flex-wrap: wrap; justify-content: flex-end; gap: var(--space-2); }
.dw-lrow > .dw-btn { flex: 0 0 auto; }
/* Side messages, "the megaphone" (leader.php?read=1, 03.10, players via the owner: "one solid page", "can't tell new
   from read - in the old one bold black was new", "the time is small"). Each message is its own card, grouped by day;
   a new one (the engine marks it read on this very showing) is bold with a brass bar and a brass time (the "new" pill
   was dropped, owner 03.10), a read one is plain and muted. The time is body size on the right; level sits under the nick, not glued to it. */
.dw-lread { gap: var(--space-2); }
/* Came from the city notice (no Cardinal up link): the wrapper's Back only on the phone, the desktop has the left
   menu (owner 03.10). Without :has the Back stays - harmless. */
@media (min-width: 1000px) {
  body:has(.dw-lread--city) #dw-back { display: none; }
}
.dw-lread__sum { margin: 0; color: var(--muted); font-size: var(--text-body-sm-size); }
.dw-lread > .dw-lread__day { margin: var(--space-3) 0 0; }
.dw-lread > .dw-lread__sum + .dw-lread__day { margin-top: 0; }
.dw-lread > .dw-lread__day:first-child { margin-top: 0; }
/* "New - N" is a heading like the days, in brass like the bar (owner 03.10: "set the new ones apart with a heading like
   Yesterday"; the "New: N" pill and the per-card "new" tag were dropped). */
/* Bold and with a brass rule to the edge: the plain brass heading read pale (owner 03.10: "now it's way too pale"). */
.dw-lread__day--new { display: flex; align-items: center; gap: 10px; color: var(--accent-text); font-size: 13px; font-weight: 700; }
.dw-lread__day--new::after { content: ""; flex: 1 1 auto; height: 2px; border-radius: 1px; background: var(--accent); }
.dw-lmsg { position: relative; padding: 12px var(--space-3) 12px calc(var(--space-3) + 2px); }
.dw-lmsg__head { display: flex; align-items: flex-start; gap: var(--space-2); }
.dw-lmsg__who { display: flex; align-items: center; gap: 8px; min-width: 0; flex: 1 1 auto; }
.dw-lmsg__who .dw-emb { margin: 0; }
.dw-lmsg__id { display: flex; flex-direction: column; min-width: 0; line-height: 1.25; }
.dw-lmsg__nick { color: var(--text); font-weight: 600; text-decoration: none; }
.dw-lmsg__lvl { color: var(--muted); font-size: var(--text-caption-size); font-variant-numeric: tabular-nums; }
.dw-lmsg__who--sys { color: var(--muted); font-size: var(--text-body-sm-size); font-weight: 600; }
.dw-lmsg__rank { max-height: 20px; width: auto; }
.dw-lmsg__meta { display: flex; flex: 0 0 auto; align-items: center; gap: var(--space-2); }
.dw-lmsg__date { color: var(--muted); font-size: var(--text-body-sm-size); font-variant-numeric: tabular-nums; }
.dw-lmsg__text { margin: 6px 0 0; color: var(--muted); line-height: 1.5; overflow-wrap: anywhere; }
.dw-lmsg__text .dw-emb { vertical-align: -5px; }
/* No brass fill for unread (owner 03.10: "no fill for now, the side bar may be enough"). */
.dw-lmsg--new { border-color: var(--line-strong); background: var(--surface-2); }
.dw-lmsg--new::before { content: ""; position: absolute; top: -1px; bottom: -1px; left: -1px; width: 4px; border-radius: var(--radius-md) 0 0 var(--radius-md); background: var(--accent); }
.dw-lmsg--new .dw-lmsg__text { color: var(--text); font-weight: 700; }
.dw-lmsg--new .dw-lmsg__date { color: var(--accent-text); font-weight: 700; }
.dw-quest { max-width: 760px; line-height: 1.55; }
.dw-quest a:not(.dw-btn) { color: var(--accent-text); }
.dw-quest .dw-btn { margin: 6px 8px 6px 0; }
.dw-quest__story { margin: 0 0 var(--space-2); color: var(--muted); font-style: italic; }
.dw-quest__say { margin: 0; }
.dw-leader--quest .dw-row__cap { display: block; }
/* Defence HQ (owner 03.10): the list view puts the officer's story right of the quest list on the desktop, its top
   level with the list (the heading stays over the list); a quest page has "All quests / Cardinal" under the text and,
   on the desktop, a "Reward" card right with the item's picture in its quality frame (script quest-prize). */
.dw-quest__nav { display: flex; flex-wrap: wrap; gap: var(--space-2); margin-top: var(--space-3); }
/* A quest opened in the list (script quest-fold, 03.10): its text and buttons under the row, take and finish in place. */
.dw-qfold { padding: var(--space-3); border-bottom: 1px solid var(--line-2); background: var(--sunken); }
.dw-list > .dw-qfold:last-child { border-bottom: 0; }
.dw-qfold__empty { margin: 0; color: var(--muted); font-size: var(--text-body-sm-size); }
.dw-leader__qmain { min-width: 0; }
.dw-quest__prizes { display: grid; gap: var(--space-2); }
.dw-quest__prize { display: flex; align-items: center; gap: var(--space-3); color: var(--text); text-decoration: none; }
.dw-quest__prize:hover .dw-quest__pname { color: var(--accent-text); }
.dw-quest__pic:empty { display: none; }
.dw-quest__pic .dw-itempic { display: flex; align-items: center; justify-content: center; width: 96px; height: 96px; border-radius: var(--radius-md); background: var(--surface-2); overflow: hidden; }
.dw-quest__pic .dw-itempic img { max-width: 88%; max-height: 88%; width: auto; height: auto; }
.dw-quest__pname { font-weight: 600; overflow-wrap: anywhere; }
@media (max-width: 999.98px) {
  .dw-quest__prizebox { display: none; }
}
@media (min-width: 1000px) {
  .dw-leader.dw-leader--quest { max-width: none; grid-template-columns: minmax(0, 1fr) minmax(280px, 360px); align-items: start; column-gap: var(--space-5); }
  .dw-leader--quest .dw-quest { max-width: none; }
  .dw-leader--qlist { grid-template-areas: "head ." "list intro"; }
  .dw-leader--qlist .dw-leader__qhead { grid-area: head; margin: 0; }
  .dw-leader--qlist .dw-leader__qlist { grid-area: list; }
  .dw-leader--qlist .dw-quest--intro { grid-area: intro; }
}
/* Rank holders: the nick in body size, not a caption (owner 03.10: "why are the nicks so small"). */
.dw-lrow__holder { display: flex; flex-wrap: wrap; align-items: center; gap: 6px; margin-top: 4px; font-size: var(--text-body-size); }
.dw-lrow__holder a { color: var(--text); text-decoration: none; }
.dw-lrow__holder a:hover { color: var(--accent-text); }
.dw-lrow__free { color: var(--muted); font-size: var(--text-body-sm-size); }
@media (min-width: 1000px) {
  .dw-leader__taxes { grid-template-columns: repeat(2, minmax(0, 1fr)); max-width: 900px; }
  .dw-leader__taxes .dw-leader__form { max-width: none; }
}
@media (max-width: 639.98px) {
  .dw-lrow:has(.dw-lrow__acts) { flex-wrap: wrap; }
  .dw-lrow__acts { justify-content: flex-start; }
}

/* ---- Workshop: the crafting table (craft.php, 02.10) ----
   The mail's places: the table left (making now, recipes, the amount form), resources right as a summary.
   A recipe is a row with two links (the result's card and "Make" with how many the player can make). */
.dw-craft__item { margin: 0 0 var(--space-3); font-family: var(--font-display); font-size: var(--text-h2-size); }
.dw-craft__act { display: flex; flex-wrap: wrap; gap: var(--space-2); margin-top: var(--space-3); }
.dw-craft__cap { margin: 0 0 var(--space-3); color: var(--muted); font-size: var(--text-body-sm-size); }
.dw-craft__level { margin-bottom: var(--space-4); }
/* Phone: resources above the recipes / making card (owner 03.10: "on the phone lift the resources over the craft list");
   the desktop keeps them in the right column. */
@media (max-width: 999.98px) {
  .dw-mail.dw-craft { grid-template-areas: "unread" "tools" "main"; }
}
/* Resources in the narrow side column: two by two, the numbers never break (03.10: "6 879 610" went on two lines). */
.dw-craft__res .dw-summary__n { white-space: nowrap; }
@media (min-width: 1000px) {
  .dw-craft__res .dw-summary__row { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); row-gap: var(--space-3); }
}
.dw-craft__done { margin: 0 0 var(--space-3); padding-bottom: var(--space-3); border-bottom: 1px solid var(--line-2); color: var(--muted); font-size: var(--text-body-sm-size); }
.dw-craft__done b { color: var(--text); }
.dw-craft__form { display: grid; gap: var(--space-3); max-width: 420px; }
.dw-craft__form .dw-craft__cap { margin: 0; }
.dw-craft__form .dw-btn--main { justify-self: start; }
.dw-rec {
  display: flex;
  align-items: center;
  gap: var(--space-3);
  min-height: var(--touch);
  padding: 9px var(--space-3);
  border-bottom: 1px solid var(--line-2);
}
.dw-rec:last-child { border-bottom: 0; }
.dw-rec__main { flex: 1 1 auto; min-width: 0; }
.dw-rec__name { display: block; color: var(--text); font-weight: 600; text-decoration: none; overflow-wrap: anywhere; }
.dw-rec__name:hover { color: var(--accent-text); }
.dw-rec__cap { display: block; margin-top: 2px; color: var(--muted); font-size: var(--text-caption-size); line-height: var(--text-caption-line); }
.dw-rec__go { flex: 0 0 auto; gap: var(--space-2); }
.dw-rec__av { min-width: 18px; padding: 0 6px; border-radius: 9px; background: var(--surface-2); color: var(--muted); font-size: var(--text-caption-size); font-variant-numeric: tabular-nums; text-align: center; }
.dw-rec__lock { flex: 0 0 auto; color: var(--dim); font-size: var(--text-caption-size); white-space: nowrap; }
.dw-rec--locked .dw-rec__name { color: var(--muted); }

/* A section opens in place (owner 02.10: "a new page for a section - can it drop down?"): the script puts the
   section page's events under the row (phone list) or into the card (desktop); "Show more" adds the next page. */
.dw-evfold { background: var(--sunken); border-bottom: 1px solid var(--line-2); }
.dw-list > .dw-evfold:last-child { border-bottom: 0; }
.dw-evfold__more {
  display: block;
  padding: 10px var(--space-3);
  border-top: 1px solid var(--line-2);
  color: var(--accent-text);
  font-size: var(--text-body-sm-size);
  text-decoration: none;
}
.dw-evfold__more[hidden] { display: none; }
.dw-evfold__more--busy,
.dw-row--busy { opacity: .6; }
.dw-evfold__empty { margin: 0; padding: 10px var(--space-3); color: var(--muted); font-size: var(--text-body-sm-size); }
.dw-row--open > .dw-row__go { transform: rotate(90deg); }
/* Defence HQ quest list (leader.php?use=16, 05.10, player idea via owner): taken - yellow, ready to hand in - green,
   "done / goal" with a bar (taken and count from DW-QUEST-LIST in leader.php, goals per quest in leader.html). */
.dw-qrow--taken { background: var(--quest-taken); box-shadow: inset 4px 0 0 var(--quest-taken-line); }
.dw-qrow--ready { background: var(--quest-ready); box-shadow: inset 4px 0 0 var(--quest-ready-line); }
.dw-qrow__st { display: block; margin-top: 3px; font-size: var(--text-caption-size); font-weight: 600; }
.dw-qrow--taken .dw-qrow__st { color: var(--quest-taken-line); }
.dw-qrow--ready .dw-qrow__st { color: var(--quest-ready-line); }
.dw-qrow__bar { display: block; max-width: 320px; height: 6px; margin-top: 5px; overflow: hidden; border-radius: var(--radius-pill); background: var(--line-2); }
.dw-qrow__bar > i { display: block; height: 100%; background: var(--quest-taken-line); }
.dw-qrow--ready .dw-qrow__bar > i { background: var(--quest-ready-line); }
/* Desktop (DW-EVENTS-DESK, owner 02.10: "why collapse into sections on the desktop, there is plenty of room"):
   the server sends the sections' events, they open as cards flowing in columns by width (420px each: two at 1280,
   three at 1920); no side column - the archive / new switch is a button in the heading. The phone keeps the list. */
.dw-evdesk,
.dw-evhead__alt { display: none; }
.dw-evsec { break-inside: avoid; margin: 0 0 var(--space-4); }
.dw-evsec > .dw-row:first-child { background: var(--surface-2); font-weight: 600; }
.dw-evsec__more {
  display: block;
  padding: 10px var(--space-3);
  color: var(--accent-text);
  font-size: var(--text-body-sm-size);
  text-decoration: none;
}
@media (min-width: 1000px) {
  .dw-mail.dw-events--desk { grid-template-columns: minmax(0, 1fr); grid-template-areas: "main"; }
  .dw-events--desk .dw-mail__tools,
  .dw-events--desk .dw-evcats { display: none; }
  /* A grid that stretches the cards over the whole width: one section - full width, two - halves, three on a wide
     screen - thirds (a player has 1.3 sections with new events on average, 02.10). Flowing columns left the right
     half empty: one card stood in the left column, three filled two of four columns at 1920 (stand 02.10). */
  .dw-events--desk .dw-evdesk {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(min(100%, 420px), 1fr));
    gap: var(--space-4);
    align-items: start;
  }
  .dw-events--desk .dw-evsec { margin: 0; }
  .dw-evhead--desk .dw-evhead__alt { display: inline-flex; margin-left: auto; }
  .dw-evhead--desk .dw-evhead__alt + .dw-mail__act { margin-left: var(--space-2); }
}

/* A row of the mail list: clan sign, nick[level], time; the unread count
   on the right. Clan signs differ in width, so the sign sits in a fixed
   box and every nick starts at the same line; no clan - an empty box. */
.dw-mailrow__pic {
  flex: 0 0 32px;
  width: 32px;
  height: 32px;
}
.dw-mailrow__main { flex: 1 1 auto; min-width: 0; display: flex; flex-direction: column; }
.dw-mailrow__nick { font-weight: 600; overflow-wrap: anywhere; }
.dw-mailrow .dw-mark { flex: 0 0 auto; white-space: nowrap; }

/* The talk, in the Telegram way (owner, 28.09: "order the other way,
   closer to TG, the message box at the bottom, on the phone and on the
   desktop"). One chat card: the letters oldest on top, newest at the
   bottom, the reply bar under the last one. Own bubbles on the right in
   the accent, the other side's on the left; time and ticks inside the
   bubble; bubbles of one side in a row sit close together. On the
   desktop the letters scroll inside the card and open at the bottom; on
   the phone the page scrolls and the reply bar sticks above the tabs. */
.dw-chat {
  border: 1px solid var(--line);
  border-radius: var(--radius-lg);
  background: var(--sunken);
  overflow: clip;
}
.dw-thread,
.dw-notes {
  display: flex;
  flex-direction: column;
  margin: 0;
  padding: var(--space-3);
  list-style: none;
}
.dw-notes { padding: 0; gap: var(--space-2); }
.dw-thread > li + li { margin-top: 10px; }
.dw-thread > .dw-msg--mine + .dw-msg--mine,
.dw-thread > .dw-msg--their + .dw-msg--their { margin-top: 3px; }

.dw-msg {
  position: relative;
  align-self: flex-start;
  max-width: min(560px, 82%);
  min-width: 0;
  padding: 6px 10px 7px;
  border: 1px solid var(--line);
  border-radius: 14px;
  border-bottom-left-radius: 4px;
  background: var(--surface);
}
.dw-msg--mine {
  align-self: flex-end;
  border-color: transparent;
  border-radius: 14px;
  border-bottom-right-radius: 4px;
  background: var(--accent-soft);
}
.dw-msg--note {
  align-self: stretch;
  max-width: none;
  padding: 10px var(--space-3);
  border-radius: var(--radius-md);
}
.dw-msg__meta {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: 2px var(--space-2);
  margin: 0 0 4px;
  color: var(--muted);
  font-size: var(--text-caption-size);
  line-height: var(--text-caption-line);
}
.dw-msg__date { font-variant-numeric: tabular-nums; }
.dw-msg__author {
  display: block;
  margin-bottom: 2px;
  color: var(--accent-text);
  font-size: var(--text-caption-size);
  font-weight: 600;
  text-decoration: none;
}
.dw-msg__meta .dw-msg__author { display: inline; margin: 0; color: var(--text); }
.dw-msg__text {
  color: var(--text);
  font-size: var(--text-body-size);
  line-height: 1.4;
  overflow-wrap: anywhere;
}
.dw-msg__text a { color: var(--accent-text); }
.dw-msg__text img { vertical-align: middle; max-width: 100%; }
.dw-msg__text .admin,
.dw-msg__text .admin a { color: var(--nick-admin); font-weight: 600; }
.dw-msg__text .admin2 { color: var(--nick-admin); }
/* Room at the end of the last line for the time, which sits in the
   bottom right corner of the bubble, as in Telegram. */
.dw-msg__pad { display: inline-block; width: 42px; height: 1px; }
.dw-msg--mine .dw-msg__pad { width: 62px; }
.dw-msg__stamp {
  position: absolute;
  right: 10px;
  bottom: 5px;
  display: inline-flex;
  align-items: center;
  gap: 3px;
  color: var(--dim);
  font-size: 11px;
  line-height: 1;
  font-variant-numeric: tabular-nums;
  white-space: nowrap;
}
.dw-msg--mine .dw-msg__stamp { color: var(--muted); }
.dw-msg__ticks { display: inline-flex; }
.dw-msg__ticks svg {
  width: 16px;
  height: 11px;
  fill: none;
  stroke: currentColor;
  stroke-width: 1.6;
  stroke-linecap: round;
  stroke-linejoin: round;
}
.dw-msg__ticks--read { color: var(--accent-text); }
/* The photo itself on top of the bubble, up to 300 wide and 380 tall -
   the 160px preview read like a stamp (owner, 28.09). */
.dw-msg__photo { display: block; margin: -2px -6px 6px; }
.dw-msg__photo img {
  display: block;
  width: auto;
  max-width: min(300px, 100%);
  max-height: 380px;
  border-radius: 10px;
}
.dw-msg__tool {
  display: inline-flex;
  align-items: center;
  min-height: 30px;
  margin-top: var(--space-2);
  padding: 0 var(--space-3);
  border: 1px solid var(--line-strong);
  border-radius: var(--radius-md);
  color: var(--text);
  font-size: var(--text-body-sm-size);
  text-decoration: none;
}
.dw-msg__tool:hover { border-color: var(--accent); color: var(--accent-text); }
.dw-msg .dw-msg__tool { margin-right: 56px; }
.dw-mail__nt { margin-bottom: var(--space-3); }
/* Live mail (DW-PUSH): while the page holds its push connection, the
   root has dw-live and Refresh is not needed; old browsers keep it. */
.dw-live .dw-mail__refresh { display: none; }

/* Day chips, the "new messages" line, "show earlier / later". */
.dw-thread > .dw-thread__day,
.dw-thread > .dw-thread__more { align-self: center; margin-top: 14px; }
.dw-thread > .dw-thread__day:first-child,
.dw-thread > .dw-thread__more:first-child { margin-top: 0; }
.dw-thread__day span {
  display: inline-block;
  padding: 3px 10px;
  border-radius: 12px;
  background: var(--surface-2);
  color: var(--muted);
  font-size: var(--text-caption-size);
  line-height: var(--text-caption-line);
}
.dw-thread > .dw-thread__new {
  align-self: stretch;
  display: flex;
  align-items: center;
  gap: var(--space-2);
  margin-top: 14px;
  color: var(--accent-text);
  font-size: var(--text-caption-size);
  font-weight: 600;
}
.dw-thread__new::before,
.dw-thread__new::after { content: ""; flex: 1 1 auto; border-top: 1px solid var(--accent); opacity: .5; }
.dw-thread__more a {
  display: inline-flex;
  align-items: center;
  min-height: 32px;
  padding: 0 var(--space-4);
  border: 1px solid var(--line-strong);
  border-radius: 16px;
  background: var(--surface);
  color: var(--text);
  font-size: var(--text-body-sm-size);
  text-decoration: none;
}
.dw-thread__more a:hover { border-color: var(--accent); color: var(--accent-text); }
.dw-thread__more--busy a { opacity: .6; pointer-events: none; }
.dw-thread__empty { align-self: center; padding: var(--space-6) 0; color: var(--muted); }

/* Back to the last letter (owner, 28.09), as in Telegram: a round button
   over the bottom right of the letters, shown by the script once the
   player is far up the history. */
.dw-chat__body { position: relative; }
.dw-chat__down {
  position: absolute;
  right: var(--space-4);
  bottom: var(--space-3);
  z-index: 2;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 44px;
  height: 44px;
  padding: 0;
  border: 1px solid var(--line-strong);
  border-radius: 50%;
  background: var(--surface);
  color: var(--muted);
  cursor: pointer;
  opacity: 0;
  pointer-events: none;
  transform: translateY(8px);
  transition: opacity .15s ease, transform .15s ease;
}
.dw-chat__down--on { opacity: 1; pointer-events: auto; transform: none; }
.dw-chat__down:hover { border-color: var(--accent); color: var(--accent-text); }
.dw-chat__down svg { width: 22px; height: 22px; }
@media (prefers-reduced-motion: reduce) {
  .dw-chat__down { transition: none; }
}

/* The reply bar: attach, the growing text box, the round send button. */
.dw-reply {
  position: relative; /* holds the emoji grid; the phone rule below makes it sticky */
  display: flex;
  align-items: flex-end;
  gap: var(--space-2);
  padding: var(--space-2) var(--space-3);
  border-top: 1px solid var(--line);
  background: var(--surface);
}
/* One line at rest: 22px line + 9px padding twice + 1px border twice =
   42px exactly, so a single line never shows a scrollbar (it did at 40px,
   owner 28.09). The script grows the box up to 200px, then it scrolls. */
.dw-reply__text {
  box-sizing: border-box;
  flex: 1 1 auto;
  min-width: 0;
  height: 42px;
  min-height: 42px;
  max-height: 200px;
  padding: 9px 14px;
  border: 1px solid var(--line-strong);
  border-radius: 21px;
  background: var(--sunken);
  color: var(--text);
  font-family: var(--font-body);
  font-size: 16px;
  line-height: 22px;
  overflow-y: hidden;
  resize: none;
}
.dw-reply__text:focus { outline: none; border-color: var(--accent); box-shadow: 0 0 0 3px var(--accent-soft); }
/* The hint in the empty box stays on one line; the box does not grow for it. */
.dw-reply__text::placeholder { white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.dw-reply__send {
  flex: 0 0 42px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 42px;
  height: 42px;
  padding: 0;
  border: 0;
  border-radius: 50%;
  background: var(--accent);
  color: var(--bg);
  cursor: pointer;
}
.dw-reply__send:hover { background: var(--accent-text); }
.dw-reply__send svg { width: 20px; height: 20px; margin-left: 2px; }
.dw-reply__attach {
  position: relative;
  flex: 0 1 auto;
  display: inline-flex;
  align-items: center;
  gap: 4px;
  max-width: 40%;
  height: 42px;
  padding: 0 4px;
  color: var(--muted);
  cursor: pointer;
}
.dw-reply__attach input {
  position: absolute;
  top: 0;
  left: 0;
  width: 100%;
  height: 100%;
  opacity: 0;
  cursor: pointer;
}
.dw-reply__attach svg { flex: 0 0 22px; width: 22px; height: 22px; }
.dw-reply__attach:hover,
.dw-reply__attach--on { color: var(--accent-text); }
.dw-reply__warn {
  margin: 0;
  padding: var(--space-2) var(--space-3);
  border-top: 1px solid var(--danger-line);
  background: var(--danger-soft);
  color: var(--danger-text);
  font-size: var(--text-body-sm-size);
  line-height: var(--text-body-sm-line);
}
.dw-reply__hint {
  overflow: hidden;
  font-size: var(--text-caption-size);
  text-overflow: ellipsis;
  white-space: nowrap;
}

@media (max-width: 999.98px) {
  /* Phone and tablet: the page scrolls; the reply bar sticks above the
     tabs while the letters are on screen, as the input does in TG. */
  /* Over the tabs, or over the on-screen keyboard when it is open (--dw-kb,
     29.09: the reply bar hid under the keyboard when the player had scrolled
     up to the letter he answers). */
  .dw-reply {
    position: sticky;
    bottom: max(calc(var(--tab-height) + env(safe-area-inset-bottom, 0px)), var(--dw-kb));
    z-index: 2;
  }
  .dw-thread > li:last-child { scroll-margin-bottom: calc(max(calc(var(--tab-height) + env(safe-area-inset-bottom, 0px)), var(--dw-kb)) + var(--dw-reply-h, 60px) + 12px); }
  /* The page scrolls here, so the button floats over the screen, just
     above the reply bar and the tabs. */
  .dw-chat__down {
    position: fixed;
    bottom: calc(max(calc(var(--tab-height) + env(safe-area-inset-bottom, 0px)), var(--dw-kb)) + var(--dw-reply-h, 60px) + var(--space-3));
  }
  .dw-reply__hint { display: none; }
  .dw-reply__attach--on .dw-reply__hint { display: inline; max-width: 96px; }
}

/* The phone chat is a window of its own, like Telegram's (owner, 30.09: "the tools
   block sits at the bottom, and since we read the newest at the bottom it always
   takes half the screen"): its own head - back, emblem, nick, online, a menu with
   the tools - and nothing else of the site: no top bar, no tabs, no unread list, no
   tools column; the reply bar sits at the very bottom. The desktop is unchanged. */
.dw-chathead { display: none; }
@media (max-width: 999.98px) {
  body:has(.dw-mail--chat) .dw-head,
  body:has(.dw-mail--chat) .dw-tabs { display: none; }
  body:has(.dw-mail--chat) .dw-main { padding-top: 0; padding-bottom: calc(var(--space-2) + env(safe-area-inset-bottom, 0px)); }
  .dw-backto--chat,
  .dw-mail__head--chat,
  .dw-mail--chat .dw-mail__tools,
  .dw-mail--chat .dw-mail__unread { display: none; }
  .dw-chathead {
    position: sticky;
    top: 0;
    z-index: 25;
    display: flex;
    align-items: center;
    gap: 10px;
    margin: 0 calc(var(--space-4) * -1) var(--space-2);
    padding: calc(6px + env(safe-area-inset-top, 0px)) var(--space-3) 6px 4px;
    background: var(--surface);
    border-bottom: 1px solid var(--line);
  }
  .dw-mail--chat .dw-reply { bottom: max(env(safe-area-inset-bottom, 0px), var(--dw-kb)); }
  .dw-mail--chat .dw-thread > li:last-child { scroll-margin-bottom: calc(max(env(safe-area-inset-bottom, 0px), var(--dw-kb)) + var(--dw-reply-h, 60px) + 12px); }
  .dw-mail--chat .dw-chat__down { bottom: calc(max(env(safe-area-inset-bottom, 0px), var(--dw-kb)) + var(--dw-reply-h, 60px) + var(--space-3)); }
  /* The chat is the window: edge to edge and at least the screen tall, a short talk sits
     at the bottom next to the reply bar (like Telegram), not under the head. */
  .dw-mail--chat .dw-chat {
    display: flex;
    flex-direction: column;
    min-height: calc(100vh - 53px - var(--space-4) - env(safe-area-inset-top, 0px) - env(safe-area-inset-bottom, 0px));
    min-height: calc(100dvh - 53px - var(--space-4) - env(safe-area-inset-top, 0px) - env(safe-area-inset-bottom, 0px));
    margin: 0 calc(var(--space-4) * -1);
    border: 0;
    border-radius: 0;
  }
  .dw-mail--chat .dw-chat__body { display: flex; flex: 1 1 auto; flex-direction: column; justify-content: flex-end; }
}
.dw-chathead__back {
  position: relative;
  display: flex;
  flex: 0 0 40px;
  align-items: center;
  justify-content: center;
  width: 40px;
  height: 40px;
  color: var(--accent-text);
}
.dw-chathead__back svg { width: 26px; height: 26px; }
.dw-chathead__dot { position: absolute; top: 7px; right: 5px; width: 9px; height: 9px; border-radius: 50%; background: var(--accent); box-shadow: 0 0 0 2px var(--surface); }
.dw-chathead__who { display: flex; flex: 1 1 auto; flex-direction: column; min-width: 0; color: var(--text); text-decoration: none; }
.dw-chathead__name { overflow: hidden; font-weight: 600; text-overflow: ellipsis; white-space: nowrap; }
/* With the partner's photo the clan emblem is small, before the nick (owner 02.10, variant B).
   The include brings its own line breaks - one space after the emblem (the game's Smarty keeps them
   too, stand page forum-room); 1px + that space = the 5px gap of the approved mock-up. */
.dw-chathead__name .dw-emb { margin-right: 1px; vertical-align: -3px; }
.dw-chathead__cap { color: var(--muted); font-size: var(--text-caption-size); line-height: var(--text-caption-line); }
.dw-chathead__cap--on { color: var(--ok-text); }
.dw-chathead__menu { position: relative; flex: 0 0 auto; margin-left: auto; }
.dw-chathead__menu > summary {
  display: flex;
  align-items: center;
  justify-content: center;
  width: 40px;
  height: 40px;
  border-radius: 50%;
  color: var(--muted);
  list-style: none;
  cursor: pointer;
}
.dw-chathead__menu > summary::-webkit-details-marker { display: none; }
.dw-chathead__menu > summary svg { width: 22px; height: 22px; }
.dw-chathead__menu[open] > summary { background: var(--surface-2); color: var(--text); }
.dw-chathead__list {
  position: absolute;
  top: calc(100% + 6px);
  right: 0;
  z-index: 30;
  width: min(290px, calc(100vw - 24px));
  box-shadow: 0 12px 32px rgba(0, 0, 0, .35);
}

@media (min-width: 1000px) {
  /* Desktop: the chat keeps a readable width next to the tools, and the
     letters scroll inside the card, the reply bar always in view. */
  .dw-mail--talk { grid-template-columns: minmax(0, 880px) minmax(300px, 360px); }
  /* The chat card fills the screen height: the letters scroll inside it
     and give way when the reply box grows, as in Telegram; few letters
     sit down by the reply box (auto top margin of the first one). */
  .dw-chat {
    display: flex;
    flex-direction: column;
    height: calc(100vh - 200px);
    min-height: 420px;
  }
  .dw-chat__body {
    flex: 1 1 auto;
    min-height: 0;
    display: flex;
    flex-direction: column;
  }
  .dw-thread {
    flex: 1 1 auto;
    min-height: 0;
    overflow-x: hidden;
    overflow-y: auto;
    overscroll-behavior: contain;
    scrollbar-width: thin;
    scrollbar-color: var(--line-strong) transparent;
  }
  .dw-chat .dw-thread > li:first-child { margin-top: auto; }
  .dw-reply,
  .dw-reply__warn { flex: 0 0 auto; }
}

/* Emoji (29.09): a smiley button by the text box and a grid of 106 common
   emoji with a 'recent' row. In the reply bar the grid floats above the
   bar; on the new-letter page it opens in the flow under the button. */
.dw-emo {
  flex: 0 0 auto;
  display: inline-flex;
  align-items: center;
  gap: 6px;
  height: 42px;
  padding: 0 4px;
  border: 0;
  border-radius: var(--radius-sm);
  background: none;
  color: var(--muted);
  font: inherit;
  cursor: pointer;
}
.dw-emo svg { flex: 0 0 24px; width: 24px; height: 24px; }
.dw-emo:hover,
.dw-emo--on { color: var(--accent-text); }
.dw-emo:focus-visible { outline: 2px solid var(--accent); outline-offset: 1px; }
.dw-emo__label { font-size: var(--text-body-sm-size); }
.dw-emo__panel {
  box-sizing: border-box;
  max-height: 300px;
  overflow-y: auto;
  overscroll-behavior: contain;
  padding: var(--space-2);
  border: 1px solid var(--line-strong);
  border-radius: var(--radius-lg);
  background: var(--surface-2);
  scrollbar-width: thin;
  scrollbar-color: var(--line-strong) transparent;
}
.dw-reply .dw-emo__panel {
  position: absolute;
  left: var(--space-2);
  right: var(--space-2);
  bottom: calc(100% + 6px);
  z-index: 5;
  box-shadow: 0 10px 30px rgba(0, 0, 0, .35);
}
.dw-emo__cap {
  margin: var(--space-2) var(--space-1) var(--space-1);
  color: var(--muted);
  font-size: var(--text-caption-size);
  letter-spacing: .04em;
  text-transform: uppercase;
}
.dw-emo__cap:first-child { margin-top: 0; }
.dw-emo__grid { display: grid; grid-template-columns: repeat(auto-fill, minmax(40px, 1fr)); }
.dw-emo__pick {
  display: flex;
  align-items: center;
  justify-content: center;
  height: 40px;
  padding: 0;
  border: 0;
  border-radius: var(--radius-sm);
  background: none;
  font-family: "Apple Color Emoji", "Segoe UI Emoji", "Noto Color Emoji", "Segoe UI Symbol", sans-serif;
  font-size: 24px;
  line-height: 1;
  cursor: pointer;
}
.dw-emo__pick:hover,
.dw-emo__pick:focus-visible { background: var(--sunken); outline: none; }
.dw-mail__emo { display: grid; justify-items: start; gap: var(--space-2); margin-top: calc(var(--space-2) * -1); }
.dw-mail__emo .dw-emo__panel { justify-self: stretch; }
@media (min-width: 1000px) {
  .dw-reply .dw-emo__panel { right: auto; width: 368px; }
}

/* Reply (29.09, DW-MAIL-REPLY): an arrow by the bubble, light so a thread is
   not a column of buttons. Desktop: it shows while the mouse is anywhere in
   the bubble's row - across the whole thread at the bubble's height, as in
   TG-inbox (.msg:hover), not only over the bubble itself (owner: "in
   TG-inbox you bring the mouse into the bubble's height and it appears").
   Touch screens: always visible. Plus the quote on top of an answer, the
   quote strip over the reply box; a jump to the original lights it up. */
.dw-msg__re {
  position: absolute;
  top: 50%;
  display: none;
  align-items: center;
  justify-content: center;
  width: 28px;
  height: 28px;
  margin-top: -14px;
  padding: 0;
  z-index: 1;
  border: 1px solid var(--line);
  border-radius: 50%;
  background: var(--surface);
  color: var(--muted);
  cursor: pointer;
}
.dw-msg--their .dw-msg__re,
.dw-msg--swiped .dw-msg__re { left: calc(100% + 6px); right: auto; }
.dw-msg--mine .dw-msg__re { right: calc(100% + 6px); }
.dw-msg--mine.dw-msg--swiped .dw-msg__re { left: calc(100% + 6px); right: auto; }
.dw-msg__re svg { width: 16px; height: 16px; }
.dw-msg__re:hover,
.dw-msg__re:focus-visible { border-color: var(--accent); color: var(--accent-text); outline: none; }
.dw-msg--swiped .dw-msg__re { display: inline-flex; }
@media (hover: hover) {
  .dw-thread > .dw-msg:hover .dw-msg__re,
  .dw-msg__re:focus-visible { display: inline-flex; }
  /* The row band: an invisible strip from the bubble to the edge of the
     thread at the bubble's height, out of the flow. Its width is exactly
     the free part of the row (container units of the thread), so the
     thread never gets wider than it looks. No container units - no band,
     the arrow then shows over the bubble only. It is ::before, painted
     under the arrow: as ::after it lay on top and took the mouse and the
     click from the arrow (owner 29.09: "the cursor does not change"). */
  .dw-thread { container-type: inline-size; }
  .dw-thread > .dw-msg::before {
    content: "";
    position: absolute;
    top: 0;
    width: calc(100cqw - 100% - 2px);
    height: 100%;
  }
  .dw-thread > .dw-msg--their::before { left: 100%; }
  .dw-thread > .dw-msg--mine::before { right: 100%; }
}
@media (hover: none) {
  .dw-msg__re { display: inline-flex; }
}
.dw-msg--flash { animation: dw-flash 1.6s ease-out; }
@keyframes dw-flash {
  0%, 35% { box-shadow: 0 0 0 3px var(--accent); }
  100% { box-shadow: 0 0 0 3px transparent; }
}
.dw-msg__quote {
  display: block;
  box-sizing: border-box;
  width: 100%;
  min-width: 0;
  margin: 2px 0 5px;
  padding: 3px 8px;
  border: 0;
  border-left: 3px solid var(--accent);
  border-radius: 4px;
  background: rgba(127, 127, 127, .12);
  color: inherit;
  font: inherit;
  text-align: left;
  cursor: pointer;
}
.dw-msg__quote-who {
  display: block;
  color: var(--accent-text);
  font-size: var(--text-caption-size);
  font-weight: 600;
  line-height: 1.35;
}
.dw-msg__quote-text {
  display: block;
  overflow: hidden;
  color: var(--muted);
  font-size: 13px;
  line-height: 1.35;
  text-overflow: ellipsis;
  white-space: nowrap;
}
.dw-msg__quote--gone { cursor: default; font-style: italic; }
.dw-reply { flex-wrap: wrap; }
/* With wrap on, the text box must not ask for its natural width, or the send
   button drops to a second line on the phone: it grows from zero instead. */
.dw-reply .dw-reply__text { flex: 1 1 0; }
.dw-reply__quote {
  flex: 0 0 100%;
  order: -1;
  display: flex;
  align-items: center;
  gap: var(--space-2);
  min-width: 0;
  padding: 0 2px 2px;
}
.dw-reply__quote > svg { flex: 0 0 20px; width: 20px; height: 20px; color: var(--accent-text); }
.dw-reply__quote-main { flex: 1 1 auto; min-width: 0; padding-left: 8px; border-left: 3px solid var(--accent); }
.dw-reply__quote-who { display: block; color: var(--accent-text); font-size: var(--text-caption-size); font-weight: 600; }
.dw-reply__quote-text { display: block; overflow: hidden; color: var(--muted); font-size: 13px; text-overflow: ellipsis; white-space: nowrap; }
.dw-reply__quote-x {
  flex: 0 0 32px;
  width: 32px;
  height: 32px;
  padding: 0;
  border: 0;
  border-radius: 50%;
  background: none;
  color: var(--muted);
  font-size: 22px;
  line-height: 1;
  cursor: pointer;
}
.dw-reply__quote-x:hover { color: var(--text); }
/* Sending (29.09): the letter stands at once with a clock until the real one comes. */
.dw-msg--pending .dw-msg__text { white-space: pre-wrap; }
.dw-msg__ticks--wait { color: var(--muted); }
.dw-msg__ticks--wait svg { width: 11px; height: 11px; }
.dw-msg__wait-note { display: block; margin-bottom: 2px; color: var(--muted); font-size: var(--text-caption-size); }

/* ---- Sets (wearkit, 29.09) ----
   The inventory grid: sets and what is worn on the left, "save what is worn"
   on the right from 1000px; on the phone the form stands between the two. */
.dw-inv.dw-kits { grid-template-areas: "main" "side" "worn"; }
.dw-kits__main { grid-area: main; min-width: 0; }
.dw-kits__side { grid-area: side; min-width: 0; }
.dw-kits__worn { grid-area: worn; min-width: 0; }
.dw-kits .dw-section:first-child { margin-top: 0; }
.dw-notice + .dw-kits { margin-top: var(--space-3); }
@media (min-width: 1000px) {
  .dw-inv.dw-kits { grid-template-areas: "main side" "worn side"; grid-template-rows: auto 1fr; }
}
/* A set row: one line on the phone too (owner 29.09) - the name with an
   ellipsis, then Wear, the contents arrow and x; the contents open under it. */
.dw-kit { padding: 10px var(--space-3); border-bottom: 1px solid var(--line-2); }
.dw-kit:last-child { border-bottom: 0; }
.dw-kit__head { display: flex; align-items: center; gap: var(--space-2); }
.dw-kit__who { flex: 1 1 auto; min-width: 0; }
.dw-kit__name { display: block; overflow: hidden; color: var(--text); font-weight: 600; text-decoration: none; text-overflow: ellipsis; white-space: nowrap; }
.dw-kit__name:hover { color: var(--accent-text); }
.dw-kit__cap { margin: 2px 0 0; color: var(--muted); font-size: var(--text-caption-size); }
.dw-kit__acts { flex: 0 0 auto; display: flex; gap: 6px; }
.dw-kit__del { justify-content: center; width: 34px; padding: 0; color: var(--muted); font-size: 18px; }
.dw-kit__del:hover { border-color: var(--danger-line); color: var(--danger-text); }
.dw-kit__more { gap: 4px; }
.dw-kit__more svg { width: 16px; height: 16px; transition: transform .15s ease; }
.dw-kit--open .dw-kit__more svg { transform: rotate(180deg); }
.dw-kit__items { margin: 8px calc(var(--space-3) * -1) -10px; padding: 0; list-style: none; border-top: 1px solid var(--line-2); background: var(--surface-2); }
.dw-kit__items .dw-kititem { padding-left: calc(var(--space-3) + 8px); }
@media (max-width: 639.98px) {
  .dw-kit__more-t { display: none; }
  .dw-kit__more { justify-content: center; width: 34px; padding: 0; }
}
@media (prefers-reduced-motion: reduce) {
  .dw-kit__more svg { transition: none; }
}
.dw-kititem {
  display: flex;
  align-items: center;
  gap: 8px;
  padding: 8px var(--space-3);
  border-bottom: 1px solid var(--line-2);
  font-size: var(--text-body-sm-size);
}
.dw-kititem:last-child { border-bottom: 0; }
.dw-kititem__name { flex: 1 1 auto; min-width: 0; color: var(--text); text-decoration: none; overflow-wrap: anywhere; }
.dw-kititem__name:hover span { text-decoration: underline; }
.dw-kititem__slot { flex: 0 0 auto; color: var(--muted); font-size: var(--text-caption-size); }
.dw-kititem--empty { color: var(--muted); }
/* What is worn: a picture in the quality frame like a worn item in the
   inventory on the desktop; on the phone no pictures, the quality dot. */
.dw-kititem__pic { flex: 0 0 52px; }
.dw-kititem--pic { gap: var(--space-3); }
.dw-kititem--pic .dw-qdot { display: none; }
.dw-kititem--pic .dw-kititem__name { font-size: var(--text-body-size); font-weight: 600; }
@media (max-width: 639.98px) {
  /* two classes: .dw-invpic (display: flex) stands lower in the file */
  .dw-kititem--pic .dw-kititem__pic { display: none; }
  .dw-kititem--pic { gap: 8px; }
  .dw-kititem--pic .dw-qdot { display: block; }
  .dw-kititem--pic .dw-kititem__name { font-size: inherit; font-weight: inherit; }
}
.dw-kits__acts { display: flex; flex-wrap: wrap; gap: var(--space-2); margin-top: var(--space-3); }
.dw-kits__fields { display: grid; gap: var(--space-3); }
.dw-kits__fields .dw-field__hint { margin: 0; }
/* A checkbox with its label - the first one in the new design. */
.dw-check { display: inline-flex; align-items: center; gap: 8px; font-size: var(--text-body-sm-size); cursor: pointer; }
.dw-check input { width: 18px; height: 18px; margin: 0; accent-color: var(--accent); }

/* A new letter: one card, the text box grows with the letter. */
.dw-mail__form { display: grid; gap: var(--space-3); }
.dw-mail__form + .dw-notice,
.dw-notice + .dw-mail__form { margin-top: var(--space-2); }
textarea.dw-field__input.dw-mail__text {
  min-height: 180px;
  padding: 10px var(--space-3);
  line-height: 1.45;
  resize: vertical;
}
.dw-field__input.dw-mail__file { padding: 6px var(--space-2); line-height: 1.4; font-size: var(--text-body-sm-size); color: var(--muted); }
.dw-mail__file::file-selector-button {
  margin-right: var(--space-3);
  min-height: 32px;
  padding: 0 var(--space-3);
  border: 1px solid var(--line-strong);
  border-radius: var(--radius-md);
  background: var(--surface-2);
  color: var(--text);
  font-family: var(--font-body);
  font-weight: 600;
  cursor: pointer;
}
.dw-mail__file::-webkit-file-upload-button {
  margin-right: var(--space-3);
  min-height: 32px;
  padding: 0 var(--space-3);
  border: 1px solid var(--line-strong);
  border-radius: var(--radius-md);
  background: var(--surface-2);
  color: var(--text);
  font-family: var(--font-body);
  font-weight: 600;
  cursor: pointer;
}
.dw-mail__send { justify-self: start; min-width: 160px; }

@media (max-width: 639.98px) {
  .dw-mail__send { justify-self: stretch; }
  .dw-msg { max-width: 86%; }
}

/* ---- Login screen ----
   The first screen a returning player sees, so it is a screen of its
   own, not the old form in the legacy layer. One narrow column at every
   width: a name, one card with the form, the way to register, a short
   list, a footer. No header and no rail: a guest has neither. */

.dw-login {
  width: 100%;
  max-width: 400px;
  margin: 0 auto;
  padding: var(--space-3) var(--space-4) calc(var(--space-6) + env(safe-area-inset-bottom, 0px));
}

.dw-login__bar { display: flex; justify-content: flex-end; min-height: 40px; }

.dw-login__brand {
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: var(--space-2);
  margin: 0 0 var(--space-5);
  text-align: center;
}

/* Logo (29.09): silver banner-shield and gold lettering on a transparent
   ground, drawn for the dark page. 1.379 : 1; phone 260px, desktop 360px. */
.dw-login__logo { display: block; margin: 0; line-height: 0; }
.dw-login__logo-img { display: block; width: 260px; max-width: 100%; height: auto; }
@media (min-width: 640px) {
  .dw-login__logo-img { width: 360px; }
}
.dw-login__logo + .dw-login__title { margin-top: var(--space-2); }

.dw-login__title {
  margin: 0;
  font-family: var(--font-display);
  font-size: var(--text-display-size);
  line-height: 1.1;
  font-weight: 700;
  letter-spacing: 0.02em;
  color: var(--text);
  text-wrap: balance;
}

.dw-login__card { padding: var(--space-4); }
.dw-login__error { margin-bottom: var(--space-3); }

.dw-login__fields { display: grid; gap: var(--space-3); }
.dw-login__fields .dw-btn { margin-top: var(--space-1); }

.dw-login__forgot {
  justify-self: center;
  padding: var(--space-1) var(--space-2);
  font-size: var(--text-caption-size);
  color: var(--muted);
}

.dw-login__forgot:hover { color: var(--accent-text); }

.dw-login__welcome { margin: 0 0 var(--space-3); text-align: center; }

.dw-login__new {
  display: grid;
  gap: var(--space-2);
  margin-top: var(--space-5);
  text-align: center;
  color: var(--muted);
}

.dw-login > .dw-login__more { margin-top: var(--space-5); }

.dw-login__foot {
  display: flex;
  flex-wrap: wrap;
  justify-content: center;
  gap: var(--space-1) var(--space-4);
  margin-top: var(--space-5);
  font-size: var(--text-caption-size);
  color: var(--muted);
}

.dw-login__foot b { color: var(--text); font-weight: 600; font-variant-numeric: tabular-nums; }
.dw-login__mail { color: var(--muted); }
.dw-login__mail:hover { color: var(--accent-text); }

/* ---- tablet, 640px and up ----
   The four sections and the hub groups go in two columns; everything
   else stays one column, the tiles stay two by two as big touch targets.

   Two CSS columns, not a two-column grid. Lists are uneven (two rows
   next to four), and a grid keeps rows aligned: the short list left a
   hole under itself before the next row began. Columns fill top to
   bottom and the browser balances their height, so a short list is
   followed by the next one straight away. Reading order stays: down the
   first column, then down the second. */

@media (min-width: 640px) {
  .dw-city__grid,
  .dw-hub {
    /* A grid of even rows, not CSS columns: bubbles on one level are
       the same size and card tops align row by row (owner, 2026-09-26;
       columns stacked blocks masonry-style with staggered tops). */
    display: grid;
    grid-template-columns: repeat(2, minmax(0, 1fr));
    gap: var(--space-4);
  }

  .dw-city__grid > .dw-block,
  .dw-hub > .dw-block {
    display: flex;
    flex-direction: column;
    min-width: 0;
  }

  /* Inside a row every card stretches to the row height. */
  .dw-city__grid > .dw-block > .dw-list,
  .dw-city__grid > .dw-block > .dw-card,
  .dw-hub > .dw-block > .dw-list,
  .dw-hub > .dw-block > .dw-card { flex: 1 1 auto; }

  .dw-hub > .dw-title { grid-column: 1 / -1; margin-bottom: 0; }

  /* A block without a title keeps the line a title would take. In two or
     three columns the neighbours start with a section title, and the
     untitled list sat a title line higher than every other card (owner,
     2026-09-24: "no alignment?"). The spacer is an empty line set in the
     section title's own type, so the height matches to the pixel. */
  .dw-hub > .dw-block--untitled::before {
    content: "\00a0";
    display: block;
    margin-bottom: var(--space-2);
    font-family: var(--font-display);
    font-size: var(--text-section-size);
    line-height: var(--text-section-line);
  }
}

/* ---- hubs on the desktop: a field of big buttons ----
   The phone ranks rows by click share because only a few fit the
   screen; the desktop shows the whole hub at once, so ranking by size
   is noise there (owner, 2026-09-24: make them all big, like the
   featured tiles on the city screen). Every link becomes a tile of the
   same size: icon, display-face name, counter. Groups keep their titles
   and data order, stacked full width, and one shared column module
   keeps tile edges aligned across groups. */

@media (min-width: 1000px) {
  .dw-hub {
    display: flex;
    flex-direction: column;
    columns: auto;
    gap: var(--space-4);
  }

  .dw-hub > .dw-block { margin-bottom: 0; }
  .dw-hub > .dw-title { margin-bottom: 0; }
  .dw-hub > .dw-block--untitled::before { content: none; }

  .dw-hub .dw-list {
    display: grid;
    grid-template-columns: repeat(auto-fill, minmax(240px, 1fr));
    gap: var(--space-3);
    border: 0;
    border-radius: 0;
    background: none;
    overflow: visible;
  }

  .dw-hub .dw-row {
    min-height: 76px;
    padding: 0 var(--space-4);
    gap: var(--space-3);
    border: 1px solid var(--line);
    border-radius: var(--radius-md);
    background: var(--surface);
  }

  .dw-hub .dw-row:hover { background: var(--surface-2); border-color: var(--accent); color: var(--text); }

  .dw-hub .dw-row__icon { width: 22px; height: 22px; flex-basis: 22px; }

  .dw-hub .dw-row__icon + span {
    font-family: var(--font-display);
    font-size: 19px;
    line-height: 1.25;
  }

  /* The chevron is list language; a button does not point at itself. */
  .dw-hub .dw-row__go { display: none; }
}

/* ---- desktop, 1000px and up ---- */

@media (min-width: 1000px) {
  .dw-login { padding-top: var(--space-6); }

  .dw-city {
    display: grid;
    grid-template-columns: minmax(0, 1fr) var(--aside);
    gap: var(--space-5);
    align-items: start;
  }

  .dw-city__main,
  .dw-city__side {
    display: flex;
    flex-direction: column;
    gap: var(--space-4);
    min-width: 0;
  }

  /* No bottom exit on the desktop: the rail has it. Admin rows, if any,
     stay in the block. */
  .dw-block--exit { margin-top: 0; }
  .dw-list--logout { display: none; }

  /* The full map of the game: rows the phone leaves to the hubs. */
  .dw-row.dw-desk { display: flex; }

  /* The reverse: rows the rail already carries on the desktop, e.g.
     Inventory on the city (owner, 27.09). A city section left with
     phone-only rows is hidden whole. */
  .dw-row.dw-mob,
  .dw-city__grid > .dw-block.dw-mob { display: none; }

  /* City sections as many columns as there are sections: without the
     hero section the desktop has three, and two columns left the third
     alone under a hole (owner, 27.09). */
  .dw-city__grid { grid-template-columns: repeat(auto-fit, minmax(200px, 1fr)); }

  /* Same rule on the city: the notice card opens the content column,
     the side column opens with a titled summary. Without the spacer the
     notice sat a title line above the summary card. */
  .dw-city__main > .dw-block--notice::before {
    content: "\00a0";
    display: block;
    margin-bottom: var(--space-2);
    font-family: var(--font-display);
    font-size: var(--text-section-size);
    line-height: var(--text-section-line);
  }

  /* Tiles are the centre of the desktop screen: taller, bigger icon and
     name, two across so each has room, four across on a wide monitor. */
  .dw-tiles { gap: var(--space-3); margin-bottom: var(--space-3); }

  .dw-tile { min-height: 88px; padding: 14px var(--space-4); gap: 4px; }
  .dw-tile:hover { background: var(--surface-2); }
  .dw-tile__icon { width: 22px; height: 22px; flex-basis: 22px; }
  .dw-tile__name { font-size: 19px; }
  .dw-tile__cap { padding-left: calc(22px + var(--space-2)); font-size: 13px; }

  /* Summary in the side column: two by two, bigger numbers. */
  .dw-city__side .dw-summary__row { flex-wrap: wrap; gap: var(--space-3) var(--space-2); }
  .dw-city__side .dw-summary__item { flex: 1 1 40%; }
  .dw-city__side .dw-summary__n { font-size: 24px; }

  .dw-city__side .dw-chips--fill .dw-chip { padding: 0 6px; font-size: 12px; }

  .dw-hub { column-gap: var(--space-5); }
}

/* A wide desktop: four tiles in one row over the two list columns, and
   the hub pages spread to three columns. 1240, not 1500: at 1280 the
   old rule kept the tiles two by two and wasted the width the owner
   asked to use (2026-09-23). */
@media (min-width: 1240px) {
  .dw-tiles { grid-template-columns: repeat(4, minmax(0, 1fr)); }

  /* The battle rows under the tiles: one card, rows in two columns with
     a rule between. A single 900px-wide row read as a stretched band. */
  .dw-block--battle .dw-list {
    columns: 2;
    column-gap: 0;
    column-rule: 1px solid var(--line-2);
  }

  .dw-block--battle .dw-row { break-inside: avoid; }
}

/* ---- Inventory (inventory.php) ----
   Fixed places (owner, 27.09): the title with the Items | Backpack switch,
   the quality chips under it; the main column holds the items; the side
   column from 1000px (under the items on the phone) holds the buttons -
   backpack sections, drop selling, nobility, kits - and under them the
   belt and the stock of elixirs and scrolls, ten to a page (owner, 28.09:
   "buttons on the right", then "put the scrolls back in the right panel,
   it is empty under the buttons"). A Belt button in the title scrolls to
   the belt at every width. One item row:
   the picture in its quality frame, the name in the item colour, worn /
   stack / rent under it, the actions as small buttons - Sell with its
   price always last, at the right edge. */
.dw-inv__head {
  display: flex;
  align-items: center;
  flex-wrap: wrap;
  gap: var(--space-2) var(--space-3);
  margin-bottom: var(--space-3);
}
.dw-inv__title {
  margin: 0;
  font-family: var(--font-display);
  font-size: var(--text-h1-size);
  line-height: var(--text-h1-line);
  font-weight: var(--text-h1-weight);
}

/* A two-way switch: where the items lie. Not chips - exactly one is on. */
.dw-seg {
  display: inline-flex;
  gap: 2px;
  padding: 3px;
  border: 1px solid var(--line);
  border-radius: var(--radius-pill);
  background: var(--sunken);
}
.dw-seg__item {
  display: inline-flex;
  align-items: center;
  height: 30px;
  padding: 0 14px;
  border-radius: 14px;
  color: var(--muted);
  font-size: var(--text-body-sm-size);
  text-decoration: none;
  white-space: nowrap;
}
.dw-seg__item:hover { color: var(--accent-text); }
.dw-seg__item--on { background: var(--surface-2); color: var(--text); box-shadow: inset 0 0 0 1px var(--line-strong); }

/* Quality chips: a dot in the quality colour, the old percent label. */
.dw-inv__q { gap: 6px; margin-bottom: var(--space-4); }
.dw-inv__q .dw-chip { gap: 6px; height: 30px; padding: 0 10px; font-variant-numeric: tabular-nums; }
.dw-qdot { flex: 0 0 8px; width: 8px; height: 8px; border-radius: 50%; background: currentColor; }

.dw-inv {
  display: grid;
  grid-template-columns: minmax(0, 1fr);
  grid-template-areas: "dop" "main" "side";
  gap: var(--space-4);
  align-items: start;
}
.dw-inv__main { grid-area: main; min-width: 0; }
.dw-inv__side { grid-area: side; min-width: 0; }
.dw-inv__dop { grid-area: dop; min-width: 0; }
.dw-inv__main > .dw-section:first-child,
.dw-inv__side > .dw-section:first-child,
.dw-inv__dop > .dw-section:first-child { margin-top: 0; }
.dw-inv__side .dw-list + .dw-section,
.dw-inv__side .dw-card + .dw-section,
.dw-inv__dop .dw-list + .dw-section { margin-top: var(--space-4); }
.dw-inv__side .dw-list + .dw-card { margin-top: var(--space-2); }
#dw-inv-dop { scroll-margin-top: var(--space-3); }

@media (min-width: 1000px) {
  .dw-inv {
    grid-template-columns: minmax(0, 1fr) minmax(300px, 360px);
    grid-template-areas: "main side" "main dop";
    grid-template-rows: auto 1fr;
    gap: var(--space-4) var(--space-5);
  }
}

.dw-invlist {
  margin: 0;
  padding: 0;
  list-style: none;
  border: 1px solid var(--line);
  border-radius: var(--radius-md);
  background: var(--surface);
  overflow: hidden;
}
/* A row without a picture (owner, 29.09: pictures only for worn items -
   the rest "blur the eye within a week and eat the room"): a quality dot,
   the name, the buttons. On the phone the buttons go under the name; from
   640px they stand in the same line on the right. */
.dw-invitem {
  display: grid;
  grid-template-columns: minmax(0, 1fr);
  grid-template-areas: "who" "acts";
  align-items: start;
  gap: 6px var(--space-3);
  padding: 8px var(--space-3);
  border-bottom: 1px solid var(--line-2);
}
.dw-invitem--worn {
  grid-template-columns: 52px minmax(0, 1fr);
  grid-template-areas: "pic who" "pic acts";
  gap: var(--space-2) var(--space-3);
  padding: 10px var(--space-3);
}
.dw-invitem__who { position: relative; }
.dw-invitem:not(.dw-invitem--worn) .dw-invitem__who { padding-left: 16px; }
/* The dot hangs left of the name: a second line of a long name and the
   caption start under the name, not under the dot. */
.dw-invitem .dw-qdot { position: absolute; left: 0; top: 7px; width: 8px; height: 8px; }
.dw-qdot--none { background: var(--line-strong); }
.dw-invitem:last-child { border-bottom: 0; }
.dw-invitem--busy { opacity: .55; pointer-events: none; }

.dw-invpic {
  grid-area: pic;
  position: relative;
  display: flex;
  align-items: center;
  justify-content: center;
  width: 52px;
  height: 72px;
  border: 2px solid var(--line-strong);
  border-radius: var(--radius-sm);
  background: var(--surface-2);
  overflow: hidden;
  text-decoration: none;
}
.dw-invpic img { width: 94%; height: 94%; object-fit: contain; }
/* An old small picture of an old item: not blown up into mush. */
.dw-invpic img.dw-invpic__old { width: auto; height: auto; max-width: 94%; max-height: 94%; }

.dw-invitem__who { grid-area: who; min-width: 0; }
.dw-invitem__name {
  color: var(--text);
  font-size: var(--text-body-size);
  line-height: var(--text-body-line);
  font-weight: 600;
  text-decoration: none;
  overflow-wrap: anywhere;
}
.dw-invitem__name:hover { text-decoration: underline; }
.dw-invitem__n { margin-left: 6px; color: var(--muted); font-size: var(--text-body-sm-size); font-variant-numeric: tabular-nums; }
.dw-invitem__cap {
  margin: 2px 0 0;
  color: var(--muted);
  font-size: var(--text-caption-size);
  line-height: var(--text-caption-line);
}
.dw-invitem__on { color: var(--ok-text); }

.dw-invitem__acts {
  grid-area: acts;
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 6px;
}
.dw-invitem__sell { margin-left: auto; font-variant-numeric: tabular-nums; }
/* "Sell" + " for N": the leading space of the price is lost inside the
   flex button, so the gap is a margin. */
.dw-invitem__price { margin-left: .3em; }
/* Phone order: wear, backpack, the rest, Sell on the right. */
.dw-invitem__wear { order: 1; }
.dw-invitem__bag { order: 2; }
.dw-invitem__more { order: 3; display: flex; flex-wrap: wrap; gap: 6px; }
.dw-invitem__sell { order: 4; }

/* Sell asks in the row itself (script inv-act): the question replaces
   the buttons until Yes or No. */
.dw-invitem__acts--ask > :not(.dw-invask) { display: none; }
.dw-invask { display: flex; flex-wrap: wrap; align-items: center; gap: 6px; margin-left: auto; }
.dw-invask__q { color: var(--accent-text); font-size: var(--text-body-sm-size); font-variant-numeric: tabular-nums; }

/* The buttons under the name. On the phone the column beside the
   picture is too narrow for Wear, To backpack and Sell for 125000: Sell
   dropped to a line of its own (owner, 28.09: "the rows break"). There
   the buttons take the full width of the card, under the picture. */
@media (max-width: 639.98px) {
  .dw-invitem .dw-btn--sm { padding: 0 10px; font-size: 13px; }
  .dw-invitem:not(.dw-invitem--worn) .dw-invitem__acts { padding-left: 16px; }
  /* One line of buttons under the name in every row (owner, 29.09): Sell
     is just "Sell" here - the price is in the question after the tap - so
     Wear, Backpack and Sell always fit. Wear and Backpack in cells of a
     fixed width (a missing button leaves its cell empty), Sell at the
     right edge, the rest between. */
  .dw-invitem__price { display: none; }
  .dw-invitem__acts { flex-wrap: nowrap; }
  .dw-invitem__wear { width: 72px; }
  .dw-invitem__bag { width: 96px; }
}
@media (min-width: 640px) {
  .dw-invitem {
    grid-template-columns: minmax(0, 1fr) auto;
    grid-template-areas: "who acts";
    align-items: center;
  }
  .dw-invitem--worn {
    grid-template-columns: 52px minmax(0, 1fr) auto;
    grid-template-areas: "pic who acts";
  }
  /* Owner, 29.09: Backpack and Wear of a fixed width at the right edge,
     Sell (its own width) grows to their left; then "no empty places in a
     row without Wear or Sell" - a missing button leaves no gap, the next
     one closes up. Backpack is always the last, at one place in every row. */
  .dw-invitem__acts { flex-wrap: nowrap; justify-content: flex-end; }
  .dw-invitem__more { order: 1; }
  .dw-invitem__sell { order: 2; margin-left: 0; }
  .dw-invitem__wear { order: 3; width: 84px; }
  .dw-invitem__bag { order: 4; width: 108px; }
}

/* Belt and stock fold (owner, 29.09): the section title is the switch;
   folded - the arrow points down (open it), open - up, as the fighter's
   folds ("they are closed - so the arrow must point down"). */
.dw-inv__fold > summary,
.dw-shop__fold > summary { display: flex; align-items: center; gap: var(--space-2); list-style: none; cursor: pointer; }
.dw-inv__fold > summary::-webkit-details-marker,
.dw-shop__fold > summary::-webkit-details-marker { display: none; }
.dw-inv__fold > summary::after,
.dw-shop__fold > summary::after {
  content: "\203A";
  margin-left: auto;
  color: var(--dim);
  font-size: 18px;
  line-height: 1;
  transform: rotate(-90deg);
  transition: transform .15s ease;
}
.dw-inv__fold:not([open]) > summary::after,
.dw-shop__fold:not([open]) > summary::after { transform: rotate(90deg); }
.dw-inv__fold > summary:hover,
.dw-shop__fold > summary:hover { color: var(--accent-text); }
.dw-inv__fold + .dw-inv__fold { margin-top: var(--space-4); }
@media (prefers-reduced-motion: reduce) {
  .dw-inv__fold > summary::after,
  .dw-shop__fold > summary::after { transition: none; }
}

/* Small buttons for rows full of actions; quiet ones for moving things. */
.dw-btn--sm { min-height: 34px; padding: 0 12px; font-size: var(--text-body-sm-size); }
.dw-btn--quiet { border-color: var(--line); background: transparent; }

/* Elixirs, scrolls and backpack sections: a name that wraps, actions on
   the right. */
.dw-dop { flex-wrap: wrap; gap: 6px var(--space-2); margin: 0; }
.dw-dop:hover { background: transparent; color: var(--text); }
.dw-dop__main { flex: 1 1 140px; min-width: 0; overflow-wrap: anywhere; }
.dw-dop__main a,
a.dw-dop__main { color: var(--text); text-decoration: none; }
.dw-dop__main a:hover,
a.dw-dop__main:hover { color: var(--accent-text); }
.dw-dop__n { margin-left: 6px; color: var(--muted); font-size: var(--text-body-sm-size); font-variant-numeric: tabular-nums; }
.dw-dop__acts { display: flex; flex-wrap: wrap; gap: 6px; margin-left: auto; }
/* A stock row: the name on its own line, the buttons under it on the
   right - the same place in every row, however long the name. */
/* Weight 0,3,0: the generic .dw-row > span:first-child (0,2,1) sets
   flex: 1 1 auto and kept short names on the button line. */
.dw-dop.dw-dop--stack > .dw-dop__main { flex-basis: 100%; }

.dw-inv__form { display: grid; gap: var(--space-3); }
.dw-inv__form .dw-notice__acts { margin-top: 0; }

/* The answer of the engine: buttons under the text of a notice. */
.dw-notice__acts { display: flex; flex-wrap: wrap; gap: var(--space-2); margin-top: var(--space-3); }
.dw-notice .dw-notice__acts .dw-btn { margin-top: 0; }
.dw-notice--ok { border-left-color: var(--ok); }

/* A short note at the bottom after a background action ("Sold +120"). */
.dw-toast {
  position: fixed;
  left: 50%;
  bottom: calc(var(--tab-height) + var(--space-4) + env(safe-area-inset-bottom, 0px));
  z-index: 60;
  max-width: calc(100% - 32px);
  padding: 10px var(--space-4);
  border: 1px solid var(--line-strong);
  border-radius: var(--radius-md);
  background: var(--surface-2);
  color: var(--text);
  font-size: var(--text-body-sm-size);
  box-shadow: 0 6px 24px rgba(0, 0, 0, .35);
  opacity: 0;
  transform: translate(-50%, 8px);
  transition: opacity .15s ease, transform .15s ease;
  pointer-events: none;
}
.dw-toast--on { opacity: 1; transform: translate(-50%, 0); }
@media (min-width: 1000px) {
  .dw-toast { bottom: var(--space-5); }
}
@media (prefers-reduced-motion: reduce) {
  .dw-toast { transition: none; }
}

/* ---- Forum (forum/index.php, post.php, edit.php; 29.09) ----
   The mail's fixed places: the up link on top, the title with its one main
   action on the right (New topic in a section, Reply in a topic). Home: the
   ways in as chips (new, mine, clan, library, rules), then the groups of
   sections - one column on the phone, two from 1000px. A section: the
   all/new switch, subsections, topics. A topic: the order switch and the
   posts; the topic tools and moderation in a side column from 1000px, under
   the posts on the phone. Counts are icons with the number (topics,
   messages, views): no "1 tem / 2 temy" grammar in a template. */
.dw-forum__head {
  display: flex;
  align-items: center;
  flex-wrap: wrap;
  gap: var(--space-2) var(--space-3);
  margin-bottom: var(--space-3);
}
.dw-forum__title {
  flex: 1 1 auto;
  min-width: 0;
  margin: 0;
  font-family: var(--font-display);
  font-size: var(--text-h1-size);
  line-height: var(--text-h1-line);
  font-weight: var(--text-h1-weight);
  overflow-wrap: anywhere;
  text-wrap: balance;
}
/* The order switch and the topic marks share one line over both columns. */
.dw-forum__bar { display: flex; flex-wrap: wrap; align-items: center; gap: var(--space-2); margin-bottom: var(--space-3); }
/* Marks in the row are as tall as the switch and the Write pill (owner: "make Pinned the size of Write"). */
.dw-forum__bar .dw-mark { height: 38px; padding: 0 14px; border-radius: var(--radius-pill); font-size: var(--text-body-sm-size); }
.dw-forum__act { flex: 0 0 auto; }
/* In the switch row the main action is a pill of the switch's height with a pen
   (owner: "Write is not organic" - a tall square button beside a pill row). */
.dw-forum__bar .dw-forum__act {
  gap: 6px;
  min-height: 38px;
  height: 38px;
  padding: 0 16px 0 13px;
  border-radius: var(--radius-pill);
  font-size: var(--text-body-sm-size);
}
.dw-forum__act svg { width: 16px; height: 16px; flex: 0 0 16px; }
.dw-forum__readall { margin-left: auto; gap: 6px; }
.dw-forum__readall svg { width: 16px; height: 16px; flex: 0 0 16px; color: var(--accent-text); }
/* An empty topic list draws no strip of border above the "no topics" notice. */
.dw-forum__topics:not(:has(.dw-topic)) { display: none; }
/* The forum paths block of the side column is a desktop thing: the phone has them
   as buttons on top of the forum home. */
@media (max-width: 999.98px) { .dw-forum__navblock { display: none; } }
/* My topics <-> My subscriptions: a quiet button on the title line, phone only; the desktop
   has the row in the side column (owner 30.09: no heap of new links on the phone). */
.dw-forum__switch { flex: 0 0 auto; }
@media (min-width: 1000px) { .dw-forum__switch { display: none; } }
/* A chip for the desktop only: the forum home has no side column of paths there, while the phone
   keeps its row of four (a fifth wraps the row). */
.dw-chip.dw-chip--desk { display: none; }
@media (min-width: 1000px) { .dw-chip.dw-chip--desk { display: inline-flex; } }
.dw-forum__more { margin-top: 0; }
/* Phone: Write / New topic is a round pen button bottom-right over the tabs, like
   Telegram's (owner, 29.09: in the row it broke onto a line of its own). The row
   keeps only the switch and the marks. */
@media (max-width: 999.98px) {
  .dw-forum__bar .dw-forum__act {
    position: fixed;
    right: 16px;
    bottom: calc(var(--tab-height) + 16px + env(safe-area-inset-bottom, 0px));
    z-index: 30;
    width: 56px;
    height: 56px;
    min-height: 56px;
    padding: 0;
    justify-content: center;
    border-radius: 50%;
    gap: 0;
    font-size: 0;
    box-shadow: 0 6px 18px rgba(0, 0, 0, .35);
  }
  .dw-forum__bar .dw-forum__act svg { width: 24px; height: 24px; flex-basis: 24px; }
  /* The switch and the marks share one line on a 360px phone: tighter pills
     (owner: "Pinned still drops to a row of its own"). */
  .dw-forum__bar { gap: 6px; }
  .dw-forum__bar .dw-seg__item { padding: 0 10px; }
  .dw-forum__bar .dw-mark { height: 32px; padding: 0 10px; font-size: var(--text-caption-size); }
}
.dw-forum__nav { margin-bottom: var(--space-4); }
.dw-forum__seg { margin-bottom: var(--space-3); }

.dw-forum {
  display: grid;
  grid-template-columns: minmax(0, 1fr);
  gap: var(--space-4);
  align-items: start;
}
.dw-forum__main,
.dw-forum__side { min-width: 0; }
.dw-forum__side > .dw-section:first-child { margin-top: 0; }
/* The forum paths block opens with its own title (margin 0 as a first child); in a topic it
   comes under the topic and moderation lists and stuck to them (owner 30.09: "forum glued to the bubble"). */
.dw-forum__side > * + .dw-forum__navblock { margin-top: var(--space-4); }

.dw-forum__groups {
  display: grid;
  grid-template-columns: minmax(0, 1fr);
  gap: var(--space-4);
  align-items: start;
}
.dw-forum__group { min-width: 0; }
.dw-forum__group > .dw-section { margin-top: 0; }

@media (min-width: 1000px) {
  .dw-forum--side {
    grid-template-columns: minmax(0, 1fr) var(--aside);
    gap: var(--space-3) var(--space-5);
  }
  /* Two columns the groups flow through, not a grid: a grid row is as tall
     as its taller group, and "News" with one section left a hole under it. */
  .dw-forum__groups { display: block; columns: 2; column-gap: var(--space-5); }
  .dw-forum__group { break-inside: avoid; margin-bottom: var(--space-4); }
}

/* Section and topic rows: the name (and the section's note) on the left,
   the counts on the right in a fixed column. */
.dw-forum__room-main,
.dw-topic__main { display: flex; flex-direction: column; gap: 2px; min-width: 0; }
.dw-forum__room-name { font-weight: 600; overflow-wrap: anywhere; }
.dw-forum__room-main .dw-row__cap { margin-top: 0; }
.dw-topic__title { overflow-wrap: anywhere; }
.dw-topic--pin .dw-topic__title { font-weight: 600; }
.dw-topic__mark { width: 14px; height: 14px; margin-right: 4px; vertical-align: -2px; color: var(--muted); }
.dw-topic__mark--pin { color: var(--accent-text); }
.dw-topic__by {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 2px 6px;
  color: var(--muted);
  font-size: var(--text-caption-size);
  line-height: var(--text-caption-line);
}
.dw-topic__nick { color: var(--text); }
.dw-topic__date { font-variant-numeric: tabular-nums; }

.dw-forum__nums {
  flex: 0 0 auto;
  display: flex;
  flex-direction: column;
  align-items: flex-end;
  gap: 2px;
  min-width: 56px;
  color: var(--muted);
  font-size: var(--text-caption-size);
  line-height: var(--text-caption-line);
  font-variant-numeric: tabular-nums;
  white-space: nowrap;
}
.dw-num { display: inline-flex; align-items: center; gap: 4px; }
.dw-num:first-child { color: var(--text); font-weight: 600; }
.dw-num::before {
  content: "";
  flex: 0 0 13px;
  width: 13px;
  height: 13px;
  background: currentColor;
  opacity: .75;
  -webkit-mask: var(--num-ic) center / contain no-repeat;
  mask: var(--num-ic) center / contain no-repeat;
}
.dw-num--topics { --num-ic: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='black' stroke-width='2.2' stroke-linecap='round'%3E%3Cpath d='M9 6h11M9 12h11M9 18h11M4 6h.5M4 12h.5M4 18h.5'/%3E%3C/svg%3E"); }
.dw-num--msgs { --num-ic: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='black' stroke-width='2.2' stroke-linejoin='round'%3E%3Cpath d='M21 11.5a8.5 8 0 0 1-12.3 7.2L3.5 20l1.3-4.2A8.5 8 0 1 1 21 11.5z'/%3E%3C/svg%3E"); }
.dw-num--views { --num-ic: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='black' stroke-width='2.2' stroke-linejoin='round'%3E%3Cpath d='M2 12s3.6-7 10-7 10 7 10 7-3.6 7-10 7S2 12 2 12z'/%3E%3Ccircle cx='12' cy='12' r='3'/%3E%3C/svg%3E"); }

/* Posts: a bubble each (owner, 29.09: "posts are not apart - make them
   bubbles"). The name and time on top, the answer and the moderator's
   delete on the right of that line; the text under it no wider than a
   readable line. Own posts in the accent, like own letters in the mail. */
.dw-posts {
  display: flex;
  flex-direction: column;
  gap: var(--space-2);
  margin: 0;
  padding: 0;
  list-style: none;
}
.dw-post {
  padding: 10px var(--space-3) var(--space-3);
  border: 1px solid var(--line);
  border-radius: 14px;
  background: var(--surface);
}
.dw-post--mine { border-color: transparent; background: var(--accent-soft); }
.dw-post:target { box-shadow: 0 0 0 2px var(--accent); }
.dw-post__head {
  display: flex;
  align-items: center;
  gap: var(--space-2);
  margin-bottom: 8px;
}
.dw-post__who {
  display: inline-flex;
  flex: 1 1 auto;
  align-items: center;
  gap: var(--space-2);
  min-width: 0;
  color: var(--text);
  font-weight: 600;
  text-decoration: none;
  overflow-wrap: anywhere;
}
a.dw-post__who:hover { color: var(--accent-text); }
/* No clan: a neutral person sign in a circle of the emblem size (06.10, owner: an empty box looked like
   "just a black square"), every nick still starts at one line. */
.dw-post__noemb { display: inline-flex; flex: 0 0 28px; align-items: center; justify-content: center; width: 28px; height: 28px;
  border: 1px solid var(--line); border-radius: 50%; background: var(--surface-2); color: var(--muted); }
.dw-post__noemb svg { width: 18px; height: 18px; }
.dw-post__id { display: flex; flex-direction: column; min-width: 0; }
.dw-post__date { color: var(--muted); font-size: var(--text-caption-size); font-weight: 400; line-height: var(--text-caption-line); font-variant-numeric: tabular-nums; }
.dw-post__acts { display: inline-flex; flex: 0 0 auto; align-items: center; gap: 6px; margin-left: auto; }
.dw-post__act {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  min-height: 30px;
  padding: 0 12px;
  border: 1px solid var(--line);
  border-radius: var(--radius-pill);
  color: var(--muted);
  font-size: var(--text-caption-size);
  text-decoration: none;
  white-space: nowrap;
}
.dw-post__act:hover { border-color: var(--accent); color: var(--accent-text); }
.dw-post__act--danger { width: 30px; padding: 0; }
.dw-post__act--danger svg { width: 16px; height: 16px; }
.dw-post__act--danger:hover { border-color: var(--danger-line); color: var(--danger-text); }
/* Moderation in place (forum-mod script): the second press confirms a deletion; a running
   request dims the button. */
.dw-post__act--danger.dw-sure { width: auto; padding: 0 10px; border-color: var(--danger-line); background: var(--danger-soft); color: var(--danger-text); }
.dw-row--danger.dw-sure { background: var(--danger-soft); }
.dw-row--danger.dw-sure > span:first-child { color: var(--danger-text); font-weight: 600; }
[data-dw-mod].dw-busy { opacity: .55; pointer-events: none; }
.dw-post__text {
  max-width: 78ch;
  color: var(--text);
  font-size: var(--text-body-size);
  line-height: 1.45;
  overflow-wrap: anywhere;
}
.dw-post__text a { color: var(--accent-text); }
.dw-post__text img { vertical-align: middle; max-width: 100%; }
.dw-post__text .admin,
.dw-post__text .admin a { color: var(--nick-admin); font-weight: 600; }
.dw-post__text .admin2 { color: var(--nick-admin); }
/* The engine stores an answer as <div class="quote">nick[level] time<br/>
   text</div> + the answer. Drawn like the mail's quote (owner, 29.09: "the
   reply box is awful"): a brass bar, the first line - who and when - in
   brass, the text muted and cut to three lines. A quote inside a quote is
   not shown: the engine sews the whole answered post, with its own quotes,
   into the answer, and the boxes piled up (a player: "reply should take
   only the last message"). One level. */
.dw-post__text .quote {
  display: -webkit-box;
  -webkit-box-orient: vertical;
  -webkit-line-clamp: 4;
  overflow: hidden;
  max-width: 60ch;
  margin: 0 0 6px;
  padding: 4px 10px;
  border-left: 4px solid var(--accent);
  border-radius: 4px;
  background: var(--accent-soft);
  color: var(--text);
  font-size: 13px;
  line-height: 1.4;
}
/* Own post is already on the brass ground: its quote is a shade darker of the same
   brass, not white (owner, 29.09: "why white"). */
.dw-post--mine .dw-post__text .quote { background: rgba(120, 80, 20, .14); }
.dw-post__text .quote::first-line { color: var(--accent-text); font-size: var(--text-caption-size); font-weight: 600; }
.dw-post__text .quote .quote { display: none; }
/* The answered post is on this page: the quote takes you there (script quote-go). */
.dw-post__text .quote.dw-quote--go { cursor: pointer; }
.dw-post__text .quote.dw-quote--go:hover { filter: brightness(.96); }
.dw-post__text .quote.dw-quote--go:focus-visible { outline: 2px solid var(--accent); outline-offset: 2px; }
@keyframes dw-post-hit { from { box-shadow: 0 0 0 3px var(--accent); } to { box-shadow: 0 0 0 3px transparent; } }
.dw-post--hit { animation: dw-post-hit 1.6s ease-out; }
@media (prefers-reduced-motion: reduce) { .dw-post--hit { animation: none; box-shadow: 0 0 0 3px var(--accent); } }
.dw-post__photo {
  display: inline-block;
  margin-top: 8px;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  overflow: hidden;
  line-height: 0;
}
.dw-post__photo img { max-width: 160px; max-height: 160px; object-fit: cover; }

/* The post being answered, over the answer box. */
.dw-post--quote {
  margin: 0 0 var(--space-3);
  padding: 8px var(--space-3);
  border: 1px solid var(--line);
  border-left: 3px solid var(--accent);
  border-radius: var(--radius-md);
  background: var(--sunken);
}
.dw-post--quote .dw-post__head { margin-bottom: 0; }
.dw-post--quote .dw-post__text { margin-top: 6px; color: var(--muted); font-size: var(--text-body-sm-size); }
/* Over the answer box the answered post's own quote shows one level deep, like in the topic:
   the engine cuts the answered text to 250 characters with its quotes, and its own words
   may not have fitted - hiding the quote left an empty box (owner, 29.09). */

/* New topic, answer, moderator forms: one card, fields in a column. */
.dw-forum__write { max-width: 720px; }
.dw-forum__form { display: grid; gap: var(--space-3); }
/* The text box: the same air as a new letter (owner: "the text is pressed to the top edge"). */
textarea.dw-field__input.dw-forum__text { min-height: 150px; padding: 10px var(--space-3); line-height: 1.45; resize: vertical; }
/* Phone, typing a post (a player on Android, 29.09: "I have to hide the keyboard to send"):
   the tab bar gives its row to the keyboard, Send sticks to the bottom of what is
   visible (Android shrinks the page for the keyboard), the box is a little lower. */
@media (max-width: 999.98px) {
  .dw-typing .dw-tabs { display: none; }
  .dw-forum__form .dw-forum__send {
    position: sticky;
    bottom: calc(var(--tab-height) + 8px + env(safe-area-inset-bottom, 0px));
    z-index: 5;
    box-shadow: 0 4px 14px rgba(0, 0, 0, .3);
  }
  /* Over the tab bar while it is shown; down to the keyboard while typing, when the bar is hidden
     (owner, 29.09: "Send covers the bottom bar"). */
  .dw-typing .dw-forum__form .dw-forum__send { bottom: calc(var(--dw-kb) + 8px); }
  textarea.dw-field__input.dw-forum__text { min-height: 120px; }
}
.dw-forum__write > .dw-notice { margin-bottom: var(--space-3); }

.dw-forum__linkrow { cursor: text; }
.dw-forum__linkrow .dw-copy { flex: 0 0 auto; width: 10ch; }

/* ---- Forum search (forum/search.php, 30.09) ----
   One line: the query and Find; hits are bubbles like posts - the topic, who and when,
   a piece of text with the match marked; the whole bubble opens the post on its page. */
.dw-forum__search { display: flex; gap: var(--space-2); align-items: center; margin-bottom: var(--space-3); }
.dw-forum__search-q { flex: 1 1 auto; min-width: 0; }
.dw-forum__search-go { flex: 0 0 auto; }
.dw-hit { padding: 0; }
.dw-hit__link { display: flex; flex-direction: column; gap: 6px; padding: 10px var(--space-3) var(--space-3); color: var(--text); text-decoration: none; }
.dw-hit__link:hover { background: var(--surface-2); border-radius: 14px; }
.dw-hit__topic { color: var(--accent-text); font-weight: 600; overflow-wrap: anywhere; }
.dw-hit__snip { max-width: 78ch; color: var(--text); line-height: 1.45; overflow-wrap: anywhere; }
.dw-hit__snip mark { padding: 0; border-radius: 2px; background: var(--accent-soft); color: inherit; font-weight: 600; }

/* ---- Block history on the fighter (user.php, 29.09) ----
   A panel on top, next to "banned / blocked": the two latest records,
   the rest under "open all" (owner: "only the last two, the rest via
   OPEN"). Records are the engine's own HTML: "<b>(date) nick></b> reason<br/>". */
.dw-bhist__list {
  margin-top: var(--space-1);
  color: var(--text);
  font-size: var(--text-body-sm-size);
  line-height: 1.5;
  overflow-wrap: anywhere;
}
.dw-notice--danger .dw-bhist__list { color: var(--danger-text); }
.dw-bhist__list b { font-weight: 600; }
.dw-bhist__more { margin-top: var(--space-2); }
.dw-bhist__more > summary {
  display: inline-flex;
  align-items: center;
  min-height: 32px;
  color: var(--accent-text);
  font-size: var(--text-body-sm-size);
  font-weight: 600;
  list-style: none;
  cursor: pointer;
}
.dw-bhist__more > summary::-webkit-details-marker { display: none; }
.dw-bhist__more > summary::after { content: "\203A"; margin-left: 6px; transform: rotate(90deg); }
.dw-bhist__more[open] > summary::after { transform: rotate(-90deg); }
.dw-bhist__hide,
.dw-bhist__more[open] .dw-bhist__show { display: none; }
.dw-bhist__more[open] .dw-bhist__hide { display: inline; }

/* ---- Status icons: the new set /i/status/new/ (29.09) ----
   Markup: templates-modern/dw_st.html. Side, class, subclass, knight, access,
   hero, arena, consultant, dealer, leader and rank, guild levels. A square box
   of the size the template asks for (--st): 20 beside a nick, 24 in the
   profile, 28 in the guild rows. Only vip_black has a dark twin. The engine's
   size rules (libs/dw_status_icons.css) match only the old paths. */
.dw-st {
  display: inline-flex;
  flex: 0 0 auto;
  align-items: center;
  justify-content: center;
  width: var(--st);
  height: var(--st);
  vertical-align: middle;
}
span.dw-st > img { display: block; width: 100%; height: 100%; max-width: none; max-height: none; object-fit: contain; }
:root[data-theme="dark"] .dw-st__l,
:root:not([data-theme="dark"]) .dw-st__d { display: none; }
.dw-kv__v .dw-st { margin-right: 4px; vertical-align: -6px; }
.dw-mark .dw-st { margin: -3px 0; }

/* ---- Clan emblem: the new set /i/klans/new/ (28.09) ----
   Markup: templates-modern/dw_emb.html. A square box of the size the
   template asks for (--emb), the drawing fitted inside, wide emblems sit
   lower. The light and the dark file are a pair and the theme shows one;
   the hidden one is lazy and is never fetched, so the theme switch swaps
   the emblem at once. Sizes (owner, 28.09: "use the size well"): the
   clan row on the fighter 48, mail headers 40, mail rows 32, Who is online 28, the clan
   mark on an item 24. */
.dw-emb {
  display: inline-flex;
  flex: 0 0 auto;
  align-items: center;
  justify-content: center;
  width: var(--emb-w);
  height: var(--emb);
  vertical-align: middle;
}
/* The generic ".dw-row > span:first-child { flex: 1 1 auto }" (0,2,1)
   outweighed the box's own flex: the emblem box grew in rows with a short
   text and shrank in rows with a long one - the Administration bird came
   out smaller than its 40 and Saint Devils stood off to the right (28.09).
   The box and the empty mail placeholder never stretch. */
.dw-row > .dw-emb:first-child { flex: 0 0 auto; }
.dw-row > .dw-mailrow__pic:first-child { flex: 0 0 32px; }
.dw-emb > img {
  display: block;
  width: 100%;
  height: 100%;
  max-width: none;
  max-height: none;
  object-fit: contain;
}
:root[data-theme="dark"] .dw-emb__l,
:root:not([data-theme="dark"]) .dw-emb__d { display: none; }
/* Fallback: no new emblem - the old _big.gif (60x60) at most 24px, never stretched (art agent 05.10). Outweighs the
   generic old-icon rule below (.dw img[src^="/i/klans/"] - 18px). */
.dw .dw-emb > img.dw-emb__old { width: auto; height: auto; max-width: min(24px, 100%); max-height: min(24px, 100%); }
/* Clan icons the engine writes into stored text by itself (a player named
   in a letter: core.php, the nick link with /i/klans/<id>.gif). The text
   is saved with the old file, and those files are three times bigger now:
   hold them to the line, beside the nick (owner's rule: 18-22px, the nick
   is not blown up). The new set is not touched. In the talk the template
   swaps them for the new set (dw-emb--mention, 29.09). */
/* New emblems in place of the old files the engine wrote into data (29.09, owner:
   "new emblems EVERYWHERE, the size is yours to choose"): in letter text 22 -
   level with the line; anywhere else 24; the old big ones 48. */
.dw-emb--old { --emb: 24px; --emb-w: 24px; margin: 0 3px 0 0; }
.dw-emb--big { --emb: 48px; --emb-w: 48px; }
.dw-emb--mention,
.dw-msg__text .dw-emb--old { --emb: 22px; --emb-w: 22px; margin: 0 3px 0 0; }
.dw img[src^="/i/klans/"]:not([src^="/i/klans/new/"]) {
  width: auto;
  height: auto;
  max-height: 18px;
  vertical-align: middle;
}

/* ---- Monster page (world/monster, 30.09) ----
   The picture stands inside its class frame, a little smaller than the frame (the drawings reach the edges);
   the frame is an SVG over it with its own ornament per class: 1 plain (rhombs), 2 strong (double frame,
   corner pieces), 3 elite (scrolls, gem), 4 boss (spikes, glow, horned crest). Class colours are the item
   quality colours, so a player reads them the same way. Phone: the picture on top, centred; desktop: the
   picture left, the text right. */
.dw-mon { display: grid; grid-template-columns: minmax(0, 1fr); gap: var(--space-4); }
.dw-mon__pic { position: relative; justify-self: center; width: 200px; height: 300px; max-width: 100%; border-radius: 8px; }
.dw-mon__img { position: absolute; left: 8%; bottom: 4%; width: 84%; height: auto; max-width: none; }
.dw-mon__frame { position: absolute; inset: 0; width: 100%; height: 100%; max-width: none; pointer-events: none; }
.dw-mon--t1 .dw-mon__pic { background: radial-gradient(ellipse at 50% 85%, rgba(139, 138, 136, .18), transparent 70%); }
.dw-mon--t2 .dw-mon__pic { background: radial-gradient(ellipse at 50% 85%, rgba(116, 116, 231, .20), transparent 70%); }
.dw-mon--t3 .dw-mon__pic { background: radial-gradient(ellipse at 50% 85%, rgba(169, 84, 255, .22), transparent 70%); }
.dw-mon--t4 .dw-mon__pic { background: radial-gradient(ellipse at 50% 85%, rgba(247, 109, 59, .26), transparent 72%); }
/* Legendary (5, main bosses of the world and events) and Structure (0: crystals, gates, outposts - not creatures,
   no coloured glow), MONSTER-TIERS-FOR-DESIGN.md, 30.09. */
.dw-mon--t5 .dw-mon__pic { background: radial-gradient(ellipse at 50% 85%, rgba(255, 0, 255, .22), transparent 72%); }
.dw-mon--t0 .dw-mon__pic { background: none; }
.dw-mon__body { min-width: 0; }
.dw-mon__head { margin-bottom: var(--space-2); }
.dw-mon__name { margin: 0; font-family: var(--font-display); font-size: var(--text-h1-size); line-height: var(--text-h1-line); overflow-wrap: anywhere; }
.dw-mon__sub { margin: 2px 0 0; color: var(--muted); font-size: var(--text-body-sm-size); }
.dw-mon__class { font-weight: 600; color: var(--muted); }
.dw-mon--t2 .dw-mon__class { color: #7474e7; }
.dw-mon--t3 .dw-mon__class { color: #a954ff; }
.dw-mon--t4 .dw-mon__class { color: #f76d3b; }
.dw-mon--t5 .dw-mon__class { color: var(--drop-8); }
.dw-mon--t0 .dw-mon__class { color: #9a8676; }
.dw-mon__opis { margin: 0 0 var(--space-2); color: var(--text); line-height: 1.45; max-width: 60ch; }
.dw-mon__skill { color: var(--text); font-weight: 600; white-space: normal; }
.dw-mon__skilltext { color: var(--muted); font-size: var(--text-body-sm-size); }
@media (min-width: 1000px) {
  .dw-mon--pic { grid-template-columns: 240px minmax(0, 560px); align-items: start; gap: var(--space-5); }
  .dw-mon__pic { width: 240px; height: 360px; }
}

/* ---- Trade: the town market (sell.php) and the players' shop (shop_new.php), 03.10 ----
   The market is tiles by section (two on the phone, as many as fit on the desktop) and the 27 private shops as
   pills. The shop: category tiles; a lot is a row like the inventory's (quality dot, name, x count or [level],
   seller under it; price and Buy on the right, under the name on the phone); filters right on the desktop. */
.dw-shop { display: grid; gap: var(--space-3); max-width: 1100px; }
.dw-shop > .dw-section { margin: var(--space-2) 0 0; }
.dw-shop > .dw-section:first-child { margin-top: 0; }
.dw-shop__town { margin: 0; color: var(--muted); font-size: var(--text-body-sm-size); }
.dw-shop__tiles { margin-bottom: 0; }
.dw-shop .dw-tile__cap { padding-left: 0; }
/* A category with no real lots: still a link, but quieter (owner 03.10: counts on the tiles). */
.dw-tile--empty { opacity: .6; }
.dw-tile--empty:hover { opacity: 1; }
.dw-shop__note { margin: 0; color: var(--muted); font-size: var(--text-body-sm-size); }
.dw-shop > .dw-section + .dw-shop__note { margin-top: calc(-1 * var(--space-2)); }
/* Private shops fold (owner 03.10: a drop-down list on the phone, then "make it a bubble, or it is unclear that it
   opens among the other bubbles"): a full-width card - name and caption like a tile, the arrow right; the shops open
   inside it. Shut on the phone, open on the desktop. */
.dw-shop__fold { padding: 0; }
.dw-shop__fold > summary { min-height: 64px; padding: 10px var(--space-3); }
.dw-shop__fold:hover { border-color: var(--accent); }
.dw-shop__fold[open] > summary { border-bottom: 1px solid var(--line-2); }
.dw-shop__foldtext { display: grid; gap: 2px; min-width: 0; }
.dw-shop__fold > summary:hover .dw-tile__name { color: var(--accent-text); }
.dw-shop__fold > .dw-shop__privs { padding: var(--space-3); }
/* Desktop: always open, a plain list - no arrow, no toggle (script shop-fold sets the class from 1000px). */
.dw-shop__fold--wide > summary { cursor: default; }
.dw-shop__fold--wide > summary::after { display: none; }
.dw-shop__fold--wide:hover { border-color: var(--line); }
.dw-shop__fold--wide > summary:hover .dw-tile__name { color: inherit; }
.dw-shop__privs { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: var(--space-2); }
.dw-shop__priv { display: block; min-width: 0; padding: 0 var(--space-3); line-height: 34px; overflow: hidden; text-overflow: ellipsis; text-align: center; }
.dw-shop__sorts { display: grid; gap: var(--space-2); margin-bottom: var(--space-3); }
.dw-shop__sorts .dw-seg { justify-self: start; }
/* Lots page: section name and sorting above the left column, "Filters" above the right one - the filter cards start
   level with the lot list on desktop (owner, 04.10). Phone: head, list, filters title, filters. */
.dw-mail.dw-shop__lots { grid-template-areas: "head" "main" "ftitle" "tools"; }
.dw-shop__lotshead { grid-area: head; min-width: 0; }
.dw-shop__lotshead > .dw-section:first-child { margin-top: 0; }
.dw-shop__lotshead .dw-shop__sorts { margin-bottom: 0; }
.dw-shop__ftitle { grid-area: ftitle; margin: 0; }
.dw-shop__lots .dw-shop__empty { border: 1px solid var(--line); border-radius: var(--radius-md); background: var(--surface); }
@media (min-width: 1000px) {
  .dw-mail.dw-shop__lots { grid-template-areas: "head ftitle" "main tools"; }
  .dw-shop__ftitle { align-self: end; }
}
.dw-shop__qual .dw-chip { gap: 6px; height: 30px; padding: 0 10px; font-variant-numeric: tabular-nums; }
.dw-lots { margin: 0; padding: 0; list-style: none; border: 1px solid var(--line); border-radius: var(--radius-md); background: var(--surface); overflow: hidden; }
.dw-lot { display: grid; grid-template-columns: minmax(0, 1fr); gap: 6px var(--space-3); padding: 9px var(--space-3); border-bottom: 1px solid var(--line-2); }
.dw-lot:last-child { border-bottom: 0; }
.dw-lot__who { position: relative; min-width: 0; padding-left: 16px; }
.dw-lot .dw-qdot { position: absolute; left: 0; top: 8px; }
.dw-lot__name { color: var(--text); font-weight: 600; text-decoration: none; overflow-wrap: anywhere; }
.dw-lot__name:hover { text-decoration: underline; }
.dw-lot__n { margin-left: 6px; color: var(--muted); font-size: var(--text-body-sm-size); font-variant-numeric: tabular-nums; }
.dw-lot__who .dw-who__lvl { margin-left: 4px; }
.dw-lot__cap { display: flex; flex-wrap: wrap; align-items: center; gap: 4px; margin: 2px 0 0; color: var(--muted); font-size: var(--text-caption-size); line-height: var(--text-caption-line); }
.dw-lot__cap a { color: var(--text); text-decoration: none; }
.dw-lot__side { max-height: 14px; width: auto; }
.dw-lot__buy { display: flex; flex-wrap: wrap; align-items: center; gap: 6px var(--space-2); padding-left: 16px; }
.dw-lot__price { margin-right: auto; font-weight: 600; font-variant-numeric: tabular-nums; white-space: nowrap; }
.dw-lot__one { display: block; color: var(--muted); font-size: var(--text-caption-size); font-weight: 400; }
.dw-shop__empty { margin: 0; padding: var(--space-3); color: var(--muted); }
.dw-shop__filter { display: grid; gap: 6px; margin-bottom: var(--space-2); }
.dw-shop__range { display: flex; align-items: center; gap: var(--space-2); }
.dw-shop__range .dw-field__input { min-width: 0; flex: 1 1 auto; }
.dw-shop__ask { display: grid; gap: var(--space-3); max-width: 640px; }
.dw-shop__q { margin: 0; line-height: 1.5; }
.dw-shop__q a { color: inherit; }
.dw-shop__acts { display: flex; flex-wrap: wrap; gap: var(--space-2); }
/* City shops (shop.php, 03.10): market buttons, the standard/modified switch, name groups with a quality dot,
   clan rows with the emblem cell kept at its own size (the row stretches its first span). */
.dw-sh__acts { margin: 0 0 var(--space-3); }
.dw-shop__note--warn { color: var(--danger-text); }
.dw-sh__seg { margin: 0 0 var(--space-3); }
.dw-sh__more { margin-top: var(--space-3); }
.dw-sh__grp .dw-qdot { flex: 0 0 8px; }
.dw-sh__gname { flex: 1 1 auto; min-width: 0; font-weight: 600; overflow-wrap: anywhere; }
.dw-sh__clan { display: flex; align-items: center; gap: var(--space-2); }
.dw-sh__clanrow > .dw-emb { flex: 0 0 auto; }
.dw-sh__clanrow > .dw-emb + span { flex: 1 1 auto; min-width: 0; }
/* Auction lot and bids (auction.php, 04.10): the lot card, the bid form, the instant-buy button under it, the bid list. */
.dw-auc__lot { display: grid; gap: var(--space-2); }
.dw-auc__name { margin: 0; font-size: var(--text-body-size); font-weight: 600; }
.dw-auc__lot .dw-lot__cap { margin: 0; }
.dw-auc__bid { display: grid; gap: var(--space-2); margin-top: var(--space-3); max-width: 640px; }
.dw-auc__form { display: grid; gap: var(--space-2); }
.dw-auc__form .dw-btn { justify-self: start; }
.dw-auc__blitz { padding-top: var(--space-3); border-top: 1px solid var(--line-2); }
.dw-auc__who { margin: 0; display: flex; flex-wrap: wrap; align-items: center; gap: 4px; }
.dw-auc__how { margin-top: var(--space-3); }
.dw-auc__rates .dw-lot__who, .dw-auc__rates .dw-lot__buy { padding-left: 0; }
/* No bids yet: the same frame as the bid list, so it does not hang in the air (owner, 04.10). */
.dw-auc__none { border: 1px solid var(--line); border-radius: var(--radius-md); background: var(--surface); }
/* Own lots and listing (komok.php, 04.10): mode tabs, the list without quality dots, the empty state in a frame. */
.dw-km__tabs { margin: 0 0 var(--space-3); }
.dw-km__list .dw-lot__who, .dw-km__list .dw-lot__buy { padding-left: 0; }
.dw-km__none { display: grid; gap: var(--space-3); padding: 0 0 var(--space-3); border: 1px solid var(--line); border-radius: var(--radius-md); background: var(--surface); }
.dw-km__none .dw-shop__acts { padding: 0 var(--space-3); }
.dw-km__none .dw-shop__acts:empty { display: none; }
.dw-km__form { max-width: 640px; }
/* Resource buyer (autobuy.php, 04.10): the list of buy orders without quality dots, the admin button under it. */
.dw-ab__lead { margin: 0 0 var(--space-3); }
.dw-ab__list .dw-lot__who, .dw-ab__list .dw-lot__buy { padding-left: 0; }
.dw-ab__adm { margin-top: var(--space-3); }
/* Skills (skill_learn.php, 04.10): rows with the 48px skill icon on the left - phone: icon, name, actions under
   the name; from 700px the actions go right as in other lot rows. Learned skills are dimmed.
   Icons (04.10, dw_skill_ico.html): new square webp from the art agent, corners rounded here; the level I-XII is a
   dark badge in the bottom right corner (the same on both themes - it sits on the painted icon); a free slot is an
   empty dashed frame of the same size. The skill card shows the icon at 96px (phone) / 128px (from 700px). */
.dw-lot.dw-sk__row { grid-template-columns: 48px minmax(0, 1fr); align-items: start; }
.dw-sk__ico { position: relative; display: block; grid-row: span 2; width: 48px; height: 48px; }
.dw-sk__pic { display: block; width: 100%; height: 100%; border-radius: 8px; }
.dw-sk__ico--free { box-sizing: border-box; border: 1px dashed var(--line-strong); border-radius: 8px; }
.dw-sk__lv { position: absolute; right: 2px; bottom: 2px; padding: 1px 4px; border-radius: 4px; background: rgba(10, 9, 8, .82); color: #f3e7cf; font-size: 10px; font-weight: 700; line-height: 1.25; letter-spacing: .03em; box-shadow: 0 0 0 1px rgba(255, 255, 255, .14); pointer-events: none; }
.dw-sk__ico--big { grid-row: auto; width: 96px; height: 96px; }
.dw-sk__ico--big .dw-sk__pic { border-radius: 12px; }
.dw-sk__ico--big .dw-sk__lv { right: 4px; bottom: 4px; padding: 2px 6px; border-radius: 6px; font-size: 13px; }
.dw-sk__row .dw-lot__who, .dw-sk__row .dw-lot__buy { padding-left: 0; }
.dw-sk__row--done .dw-lot__name { color: var(--muted); }
.dw-sk__freet { color: var(--muted); }
.dw-sk__acts .dw-btn { min-width: 36px; }
.dw-sk__more { margin: var(--space-2) 0 var(--space-3); }
.dw-sk__lead { margin: 0 0 var(--space-3); }
.dw-sk__card { display: grid; gap: var(--space-3); max-width: 640px; }
.dw-sk__opis { margin: 0; line-height: 1.5; }
@media (min-width: 700px) {
  .dw-lot.dw-sk__row { grid-template-columns: 48px minmax(0, 1fr) auto; align-items: center; }
  .dw-sk__ico { grid-row: auto; }
  .dw-sk__ico--big { width: 128px; height: 128px; }
}
/* Tattoo master (tatoo.php, 04.10): own tattoos and the shop list as lot rows with the quality dot; effects in one
   caption line "Accuracy +4% . Dodge -10%" (gains green, losses red), price and Apply / why not on the right; kinds as
   chips; delete and apply go through a question card. */
.dw-tat__lead { margin: 0 0 var(--space-2); }
.dw-tat__cap { margin: 0 0 var(--space-2); }
.dw-tat__fxl { gap: 2px 6px; }
.dw-tat__fx { white-space: nowrap; }
.dw-tat__fx + .dw-tat__fx::before { content: "\00b7"; margin-right: 6px; color: var(--muted); }
.dw-tat__fx b, .dw-tat__up { color: var(--ok-text); font-weight: 600; font-variant-numeric: tabular-nums; }
.dw-tat__fx--down b, .dw-tat__down { color: var(--danger-text); }
.dw-tat__card { display: grid; gap: var(--space-3); max-width: 640px; }
.dw-tat__card .dw-shop__q, .dw-tat__card .dw-shop__note, .dw-tat__card .dw-tat__fxl { margin: 0; }
.dw-tat__kind { display: flex; flex-wrap: wrap; align-items: center; gap: 4px 8px; margin: 0; color: var(--muted); }
.dw-tat__have { display: flex; flex-wrap: wrap; align-items: baseline; gap: 2px 16px; }
.dw-tat__have span { white-space: nowrap; }
/* Tattoo pictures (04.10, dw_tat_ico.html): square webp from the art agent, rounded here; rows - 48px on the left (the
   quality dot stays by the name), the card - 96px phone / 128px from 700px, the fighter page rows - 40px. A missing
   file hides the picture and keeps its place. */
.dw-lot.dw-tat__row { grid-template-columns: 48px minmax(0, 1fr); align-items: start; }
.dw-tat__ico { display: block; grid-row: span 2; width: 48px; height: 48px; }
.dw-tat__pic { display: block; width: 100%; height: 100%; border-radius: 8px; }
.dw-tat__ico--big { grid-row: auto; width: 96px; height: 96px; }
.dw-tat__ico--big .dw-tat__pic { border-radius: 12px; }
.dw-tat__ico--sm { width: 40px; height: 40px; }
.dw-row > span.dw-tat__ico:first-child { flex: 0 0 40px; }
.dw-tat__urow > .dw-tat__ico + span { flex: 1 1 auto; min-width: 0; }
@media (min-width: 700px) {
  .dw-lot.dw-tat__row { grid-template-columns: 48px minmax(0, 1fr) auto; align-items: center; }
  .dw-tat__ico { grid-row: auto; }
  .dw-tat__ico--big { width: 128px; height: 128px; }
  .dw-tat__ico--sm { width: 40px; height: 40px; }
}
/* Transformation master (sub.php, 04.10): one card - who you play now, the other side, what is own and shared, rules,
   the switch button; without a subclass - requirements with "you have" (green - enough, red - not), shards in pairs. */
.dw-sub__card { display: grid; gap: var(--space-3); max-width: 720px; }
.dw-sub__card .dw-shop__q, .dw-sub__card .dw-shop__note, .dw-sub__card .dw-section, .dw-sub__card .dw-shop__acts { margin: 0; }
.dw-sub__now, .dw-sub__other { margin: 0; }
.dw-sub__other { color: var(--muted); }
.dw-sub__rules { margin: 0; padding-left: 18px; color: var(--muted); line-height: 1.5; }
.dw-sub__rules li + li { margin-top: 4px; }
.dw-sub__ok, .dw-sub__no { margin-left: 6px; font-size: var(--text-caption-size); white-space: nowrap; }
.dw-sub__ok { color: var(--ok-text); }
.dw-sub__no { color: var(--danger-text); }
.dw-sub__shards { display: flex; flex-wrap: wrap; justify-content: flex-end; gap: 2px 12px; }
.dw-sub__shard { white-space: nowrap; }
.dw-sub__shard .dw-sub__ok, .dw-sub__shard .dw-sub__no { margin-left: 2px; }
/* Priest (buff.php, 04.10): nine kinds as cards (phone - one column, from 700px - two, from 1100px - three), each with
   the ordinary (credits) and the improved (valor) option - what it gives, minutes, price, Buy / why not; an active one is
   marked with "until HH:MM" and a gold border. Rows of cards are equal height (grid). */
.dw-bf__lead { margin: 0 0 var(--space-2); }
.dw-bf__grid { display: grid; gap: var(--space-3); margin-top: var(--space-3); }
@media (min-width: 700px) { .dw-bf__grid { grid-template-columns: repeat(2, minmax(0, 1fr)); } }
@media (min-width: 1100px) { .dw-bf__grid { grid-template-columns: repeat(3, minmax(0, 1fr)); } }
.dw-bf__grid > .dw-bf__card { margin: 0; }
.dw-bf__card { display: grid; grid-template-rows: auto 1fr 1fr; gap: var(--space-2); }
.dw-bf__card--on { border-color: var(--accent); }
.dw-bf__head { display: flex; flex-wrap: wrap; align-items: center; justify-content: space-between; gap: 4px 8px; }
.dw-bf__name { color: var(--text); font-weight: 600; text-decoration: none; }
.dw-bf__name:hover { text-decoration: underline; }
.dw-bf__opt { display: grid; align-content: start; gap: 6px; padding-top: var(--space-2); border-top: 1px solid var(--line-2); }
.dw-bf__what { color: var(--muted); font-size: var(--text-caption-size); line-height: 1.45; }
.dw-bf__kind { margin-right: 2px; color: var(--text); font-weight: 600; }
/* The improved (valor) option is tinted so the eye separates the two rows of each card (owner 04.10). */
.dw-bf__opt--up { padding: 8px 10px; border-top: 0; border-radius: var(--radius-sm); background: var(--accent-soft); }
.dw-bf__opt--up .dw-bf__kind { color: var(--accent-text); }
.dw-bf__buy { display: flex; align-items: center; justify-content: space-between; gap: 8px; }
.dw-bf__price { font-weight: 600; font-variant-numeric: tabular-nums; white-space: nowrap; }
.dw-bf__info { display: grid; gap: var(--space-3); max-width: 640px; }
/* Antiquities trader (points.php, 04.10): same kinds grouped in one lot row (xN, per piece, total), Hand in 1. */
.dw-pts__lead { margin: 0 0 var(--space-2); }
.dw-pts__list { margin-top: var(--space-3); }
/* Goblin exchange (forex.php, 04.10): balances and rates side by side from 900px (one row, equal height), markets as
   chips, offer rows - what you get for what, rate, who; the question card; the offer form with the balance and rate. */
.dw-fx__top { display: grid; gap: var(--space-3); margin-bottom: var(--space-3); }
@media (min-width: 900px) { .dw-fx__top { grid-template-columns: minmax(0, 1fr) minmax(0, 1.4fr); } }
.dw-fx__top > .dw-card { display: grid; align-content: start; gap: var(--space-2); margin: 0; }
.dw-fx__top .dw-section, .dw-fx__top .dw-shop__note { margin: 0; }
.dw-fx__sub .dw-kv__k, .dw-fx__sub .dw-kv__v { color: var(--muted); font-size: var(--text-caption-size); }
.dw-fx__mini { display: flex; flex-wrap: wrap; gap: 2px 14px; margin: 0 0 var(--space-3); }
.dw-fx__mini span { white-space: nowrap; }
.dw-fx__lead { margin: 0 0 var(--space-2); }
.dw-fx__more { margin-top: var(--space-3); }
.dw-fx__form, .dw-fx__ask { max-width: 640px; }
.dw-fx__ask { display: grid; gap: var(--space-3); }
.dw-fx__ask .dw-shop__q, .dw-fx__ask .dw-shop__note, .dw-fx__form .dw-section { margin: 0; }
/* Lottery (lottery.php, 04.10): jackpot/draw and prize rules side by side from 900px (equal height), the ticket form with
   36 number balls (pick 5, Random; the text field stays for no-script), tickets as rows of number chips. */
.dw-lt__top { display: grid; gap: var(--space-3); margin: var(--space-3) 0; }
@media (min-width: 900px) { .dw-lt__top { grid-template-columns: repeat(2, minmax(0, 1fr)); } }
.dw-lt__top > .dw-card { display: grid; align-content: start; gap: var(--space-2); margin: 0; }
.dw-lt__top .dw-section, .dw-lt__top .dw-shop__note, .dw-lt__last { margin: 0; }
.dw-lt__last { color: var(--muted); font-size: var(--text-caption-size); }
.dw-lt__form { display: grid; gap: var(--space-3); max-width: 640px; }
.dw-lt__form .dw-section, .dw-lt__picked { margin: 0; }
.dw-lt__picked { color: var(--muted); }
.dw-lt__grid { display: grid; grid-template-columns: repeat(6, minmax(0, 1fr)); gap: 6px; max-width: 360px; }
@media (min-width: 700px) { .dw-lt__grid { grid-template-columns: repeat(9, minmax(0, 1fr)); max-width: 480px; } }
.dw-lt__ball { aspect-ratio: 1 / 1; min-height: 36px; padding: 0; border: 1px solid var(--line-strong); border-radius: 50%; background: var(--surface); color: var(--text); font: inherit; font-weight: 600; font-variant-numeric: tabular-nums; cursor: pointer; }
.dw-lt__ball:hover { border-color: var(--accent); }
.dw-lt__ball[aria-pressed="true"] { border-color: var(--accent); background: var(--accent); color: var(--bg); }
.dw-lt__agree { display: flex; gap: 8px; align-items: flex-start; color: var(--muted); font-size: var(--text-caption-size); }
.dw-lt__nums { display: flex; flex-wrap: wrap; gap: 6px; }
.dw-lt__num { display: inline-grid; place-items: center; width: 34px; height: 34px; border-radius: 50%; background: var(--accent); color: var(--bg); font-weight: 600; font-variant-numeric: tabular-nums; }
.dw-lt__num--past { background: var(--accent-soft); color: var(--accent-text); }
.dw-lt__ask { display: grid; gap: var(--space-3); max-width: 640px; }
.dw-lt__ask .dw-shop__q, .dw-lt__ask .dw-shop__note { margin: 0; }
.dw-lt__list .dw-lot { grid-template-columns: minmax(0, 1fr); }
/* Group fights (fight_group.php, 04.10): mode chips, a bar (refresh, create, level filter); an ordinary application -
   two team columns with "vs" between them (phone - one under another), slots: a player or Take the place / why not;
   chaos and valor - one row with levels, time, count, names and Join; the create form - two team cards side by side.
   Valor top - two cards (day, week). */
.dw-fg__lead { margin: 0 0 var(--space-2); }
.dw-fg__bar { display: flex; flex-wrap: wrap; gap: 8px; margin: 0 0 var(--space-3); }
.dw-fg__list { display: grid; gap: var(--space-3); }
.dw-fg__list > .dw-fg__item { margin: 0; }
.dw-fg__tag { margin: 0 0 var(--space-2); }
.dw-fg__vs { display: grid; gap: var(--space-2); }
@media (min-width: 700px) { .dw-fg__vs { grid-template-columns: minmax(0, 1fr) auto minmax(0, 1fr); align-items: start; } }
.dw-fg__head { margin: 0 0 6px; font-weight: 600; }
.dw-fg__slots { display: grid; gap: 4px; margin: 0; padding: 0; list-style: none; }
.dw-fg__slot { display: flex; flex-wrap: wrap; align-items: center; gap: 4px; min-height: 30px; }
.dw-fg__side-ico { width: 16px; height: 16px; }
.dw-fg__slot--free { gap: 10px; margin-top: 4px; }
.dw-fg__freen { color: var(--muted); }
.dw-fg__slot--free .dw-apt__why { font-size: inherit; }
.dw-fg__mid { display: flex; align-items: center; gap: 10px; }
.dw-fg__mid::before, .dw-fg__mid::after { content: ""; flex: 1 1 auto; border-top: 1px solid var(--line-2); }
.dw-fg__vsword { color: var(--accent-text); font-size: 13px; font-weight: 700; letter-spacing: .08em; text-transform: uppercase; }
.dw-fg__time { color: var(--text); font-weight: 600; font-variant-numeric: tabular-nums; }
@media (min-width: 700px) {
  .dw-fg__mid { flex-direction: column; align-self: stretch; padding: 0 var(--space-3); }
  .dw-fg__mid::before, .dw-fg__mid::after { border-top: 0; border-left: 1px solid var(--line-2); }
}
.dw-fg__row { display: grid; gap: var(--space-2); }
@media (min-width: 700px) { .dw-fg__row { grid-template-columns: minmax(0, 1fr) auto; align-items: center; } }
.dw-fg__info .dw-fg__head, .dw-fg__info .dw-lot__cap, .dw-fg__names { margin: 0; }
.dw-fg__names { margin-top: 4px; font-size: var(--text-caption-size); }
.dw-fg__facts { display: grid; gap: 2px; margin: 4px 0 0; padding: 0; list-style: none; color: var(--muted); }
.dw-fg__facts b { color: var(--text); font-weight: 600; font-variant-numeric: tabular-nums; }
.dw-fg__facts--lead { margin: 0 0 var(--space-3); }
.dw-fg__cd { display: inline-block; min-width: 3.2em; }
.dw-btn--refresh { border-color: var(--accent); color: var(--accent-text); }
@media (min-width: 700px) { .dw-fg__facts { display: flex; flex-wrap: wrap; gap: 4px 20px; } }
.dw-fg__who { display: flex; flex-wrap: wrap; gap: 2px 14px; margin: 6px 0 0; padding: 0; list-style: none; }
.dw-fg__teams { display: grid; gap: var(--space-3); }
@media (min-width: 900px) { .dw-fg__teams { grid-template-columns: repeat(2, minmax(0, 1fr)); } }
.dw-fg__teams > .dw-fg__team { display: grid; align-content: start; gap: var(--space-2); margin: 0; }
.dw-fg__team .dw-section { margin: 0; }
.dw-fg__opts { display: grid; gap: var(--space-2); max-width: 720px; margin-top: var(--space-3); }
.dw-fg__opts .dw-shop__note { margin: 0; }
.dw-fg__chaos { max-width: 640px; margin-top: var(--space-3); }
.dw-fg__top { display: grid; gap: var(--space-3); }
@media (min-width: 900px) { .dw-fg__top { grid-template-columns: repeat(2, minmax(0, 1fr)); } }
.dw-fg__top > .dw-fg__topcard { margin: 0; }
.dw-fg__toplist { margin: 0; padding: 0; list-style: none; }
.dw-fg__toprow { display: grid; grid-template-columns: 28px minmax(0, 1fr) auto; gap: 8px; align-items: center; padding: 6px 0; border-bottom: 1px solid var(--line-2); }
.dw-fg__toprow:last-child { border-bottom: 0; }
.dw-fg__place { color: var(--muted); font-variant-numeric: tabular-nums; }
.dw-fg__pts { font-variant-numeric: tabular-nums; }
/* Coliseum (colisey.php, 04.10): list - battle cards (kind, viewers, Watch, teams with fighters and health bars);
   battle view - team health as a scoreboard, team cards (fighter: icons, nick, level, health, bar), viewers chat,
   log with a fighter picker. Hidden battles - no numbers and no bars. */
.dw-col__top { display: flex; align-items: flex-start; justify-content: space-between; gap: var(--space-2); }
.dw-col__top .dw-fg__head { margin: 0; }
.dw-col__teams { display: grid; gap: var(--space-3); }
@media (min-width: 700px) { .dw-col__teams { grid-template-columns: repeat(auto-fit, minmax(260px, 1fr)); } }
.dw-col__teams > .dw-col__team { margin: 0; }
.dw-col__tname { margin: 0 0 6px; font-weight: 600; }
.dw-col__fighters { display: grid; gap: 8px; margin: 0; padding: 0; list-style: none; }
.dw-col__f { display: grid; grid-template-columns: minmax(0, 1fr) auto; align-items: center; gap: 3px 8px; }
.dw-col__fwho { display: flex; flex-wrap: wrap; align-items: center; gap: 4px; min-width: 0; }
.dw-col__fhp { color: var(--muted); font-variant-numeric: tabular-nums; }
.dw-col__bar { grid-column: 1 / -1; height: 4px; overflow: hidden; border-radius: var(--radius-pill); background: var(--line-2); }
.dw-col__bar > i { display: block; height: 100%; background: var(--ok); }
.dw-col__f--out { opacity: .55; }
/* Score (07.10): a grid "team - vs - team", team 1 left; the numbers shrink with the screen so two fit side by side
   on a phone (owner: "health looks bad" - flex wrapped team 2 over team 1). */
.dw-col__score { display: grid; grid-template-columns: minmax(0, 1fr) auto minmax(0, 1fr); align-items: center; gap: var(--space-2) var(--space-3); margin: 0 0 var(--space-3); padding: var(--space-3); border: 1px solid var(--line); border-radius: var(--radius-md); background: var(--surface); text-align: center; }
.dw-col__side { display: grid; gap: 2px; }
.dw-col__sname { color: var(--muted); font-size: var(--text-caption-size); }
.dw-col__hp { font-size: clamp(17px, 5.4vw, 26px); line-height: 1.2; font-variant-numeric: tabular-nums; white-space: nowrap; }
.dw-col__vs { color: var(--accent-text); font-size: 12px; font-weight: 700; letter-spacing: .06em; text-transform: uppercase; }
/* Team roster (07.10): alive first, the fallen folded under "Out - N". */
.dw-col__tcnt { float: right; color: var(--muted); font-size: var(--text-caption-size); font-weight: 400; }
.dw-col__none { margin: 0 0 var(--space-2); color: var(--muted); font-size: var(--text-body-sm-size); }
.dw-col__dead { margin-top: var(--space-2); border-top: 1px solid var(--line-2); }
.dw-col__deadsum { padding: 8px 0 4px; color: var(--muted); font-size: var(--text-body-sm-size); cursor: pointer; list-style-position: inside; }
.dw-col__deadsum:hover { color: var(--accent-text); }
.dw-col__dead[open] .dw-col__deadsum { color: var(--text); }
.dw-col__chat, .dw-col__log, .dw-col__viewers { margin-top: var(--space-3); }
.dw-col__msgs, .dw-col__lines { display: grid; gap: 6px; margin: 0 0 var(--space-2); padding: 0; list-style: none; }
.dw-col__msg { overflow-wrap: anywhere; }
.dw-col__mtime { color: var(--muted); font-variant-numeric: tabular-nums; }
.dw-col__pick { display: grid; gap: var(--space-2); max-width: 520px; margin-bottom: var(--space-3); }
.dw-col__pick .dw-shop__acts { align-items: center; }
.dw-col__lines { gap: var(--space-2); }
.dw-col__line { display: grid; gap: 6px; padding: 10px 12px; border: 1px solid var(--line); border-radius: var(--radius-md); background: var(--surface-2); }
.dw-col__line .dw-col__mtime { font-size: var(--text-caption-size); }
.dw-col__ltext { display: grid; gap: 5px; color: var(--text); line-height: 1.45; overflow-wrap: anywhere; }
.dw-col__ll { display: block; }
.dw-col__ll--h { font-weight: 500; }
.dw-col__ll--m { color: var(--muted); font-size: var(--text-caption-size); }
.dw-col__grp { position: relative; display: grid; gap: 4px; padding-left: 64px; }
.dw-col__grp + .dw-col__grp { margin-top: 7px; padding-top: 7px; border-top: 1px solid var(--line); }
.dw-col__grp::before { position: absolute; top: .3em; left: 0; width: 56px; font-size: 10.5px; font-weight: 700; letter-spacing: .04em; line-height: 1.4; text-transform: uppercase; }
.dw-col__grp + .dw-col__grp::before { top: calc(7px + .3em); }
.dw-col__grp--m::before { content: "\043C\043E\0440\0430\043B\044C"; color: var(--muted); }
.dw-col__grp--f::before { content: "\044D\0444\0444\0435\043A\0442"; color: var(--mana); }
.dw-col__grp--s::before { content: "\043F\0440\0438\0451\043C"; color: var(--accent-text); }
.dw-col__grp--ch::before { content: "\0443\0434\0430\0440"; color: var(--danger-text); }
.dw-col__grp--e::before { content: "\0441\0442\0438\0445\0438\044F"; color: var(--alert); }
.dw-col__grp--x::before { content: "\043C\0438\043C\043E"; color: var(--muted); }
.dw-col__fdmg { grid-column: 1 / -1; color: var(--muted); font-size: var(--text-caption-size); }
.dw-col__fdmg b { color: var(--danger-text); font-size: 13px; font-variant-numeric: tabular-nums; }
.dw-col__dmgtot { margin: 0 0 var(--space-3); padding: 10px 12px; border-radius: var(--radius-md); background: var(--danger-soft); color: var(--text); }
.dw-col__dmgtot b { color: var(--danger-text); font-size: 20px; font-variant-numeric: tabular-nums; }
.dw-col__ltext b { color: var(--accent-text); font-weight: 600; }
.dw-col__ltext b.dw-col__dmg { color: var(--text); font-size: 1.12em; font-weight: 700; font-variant-numeric: tabular-nums; }
.dw-main .dw-col .dw-col__t1, .dw-main .dw-col .dw-col__t1 * { color: var(--team1); font-weight: 600; }
.dw-main .dw-col .dw-col__t2, .dw-main .dw-col .dw-col__t2 * { color: var(--team2); font-weight: 600; }
.dw-col__tname--1 { color: var(--team1); }
.dw-col__tname--2 { color: var(--team2); }
/* Viewers: one wrapping row, label and every viewer are items centred on one line (06.10, owner: the label sat
   below the nicks with a clan emblem). */
.dw-col__viewers { display: flex; flex-wrap: wrap; align-items: center; gap: 4px 10px; }
.dw-col__viewer { display: inline-flex; align-items: center; gap: 4px; line-height: 20px; }
.dw-col__calc { color: var(--muted); font-size: var(--text-caption-size); }
.dw-col__ltext b.dw-col__crit { color: var(--danger-text); }
.dw-col__side .dw-mark { justify-self: center; }
.dw-col__root { margin: var(--space-2) 0 0; padding-left: 18px; color: var(--muted); }
.dw-col__write { max-width: 640px; }
/* Clans (clan.php, 05.10): list - rows with place, emblem, name, leader and size, valor points; profile - header with
   a big emblem, tabs, facts and links cards, diplomacy (leader of another clan), castles, members with an online dot,
   stage and marks (two-three columns on desktop); registry - rules and a form. */
.dw-cl__clan { display: grid; grid-template-columns: 26px auto minmax(0, 1fr) auto; align-items: center; gap: 10px; }
.dw-cl__place { color: var(--muted); font-variant-numeric: tabular-nums; text-align: right; }
.dw-cl__main { display: grid; gap: 2px; min-width: 0; }
.dw-cl__name { color: var(--accent-text); font-weight: 600; overflow-wrap: anywhere; }
.dw-cl__meta { color: var(--muted); font-size: var(--text-caption-size); }
.dw-cl__lead { color: var(--text); font-weight: 600; }
.dw-cl__od { display: grid; justify-items: end; font-variant-numeric: tabular-nums; }
.dw-cl__odl { color: var(--muted); font-size: var(--text-caption-size); }
.dw-cl__head { display: flex; align-items: center; gap: var(--space-3); margin: 0 0 var(--space-3); }
.dw-cl__htext { min-width: 0; }
.dw-cl__side { display: inline-flex; align-items: center; gap: 6px; color: var(--text); font-weight: 600; }
.dw-cl__side img { width: 26px; height: 26px; }
.dw-cl__head .dw-mail__title { margin: 0; overflow-wrap: anywhere; }
.dw-cl__hmeta { display: flex; flex-wrap: wrap; align-items: center; gap: 4px; margin: 4px 0 0; color: var(--muted); }
.dw-cl__grid { display: grid; gap: var(--space-3); margin-bottom: var(--space-3); }
@media (min-width: 900px) { .dw-cl__grid { grid-template-columns: repeat(2, minmax(0, 1fr)); align-items: start; } }
.dw-cl__grid > .dw-card { margin: 0; }
.dw-cl__sub { color: var(--muted); font-size: var(--text-caption-size); }
.dw-cl__exitbar { margin-top: var(--space-5); padding-top: var(--space-3); border-top: 1px solid var(--line-2); }
.dw-cl__diplo, .dw-cl__castles, .dw-cl__members { margin-bottom: var(--space-3); }
.dw-cl__rel { margin: 0 0 var(--space-2); }
.dw-cl__relnote { margin: 0 0 var(--space-3); }
.dw-cl__castle { flex: 1 1 auto; }
.dw-cl__mhead { display: flex; flex-wrap: wrap; align-items: baseline; justify-content: space-between; gap: 6px; }
.dw-cl__mhead .dw-section { margin: 0; }
.dw-cl__count { color: var(--muted); }
.dw-cl__count b { color: var(--text); }
.dw-cl__on, .dw-cl__on b { color: var(--ok-text); }
.dw-cl__sort { margin: var(--space-2) 0; }
.dw-cl__mlist { display: grid; gap: 0 32px; margin: 0; padding: 0; list-style: none; }
@media (min-width: 900px) { .dw-cl__mlist { grid-template-columns: repeat(2, minmax(0, 1fr)); } }
.dw-cl__m { display: grid; grid-template-columns: minmax(0, 1fr) auto; align-items: center; gap: 10px; min-height: 44px; padding: 6px 0; border-bottom: 1px solid var(--line-2); }
.dw-cl__mwho { display: flex; flex-wrap: wrap; align-items: center; gap: 4px 8px; min-width: 0; }
.dw-cl__mwho a { font-weight: 500; overflow-wrap: anywhere; }
.dw-cl__mrole { display: flex; flex-wrap: wrap; justify-content: flex-end; gap: 4px; }
.dw-cl__dot { flex: 0 0 auto; width: 10px; height: 10px; border-radius: 50%; background: var(--line-strong); }
.dw-cl__m--on .dw-cl__dot { background: var(--ok); box-shadow: 0 0 0 3px var(--surface-2); }
.dw-cl__role { padding: 2px 9px; border: 1px solid var(--line); border-radius: var(--radius-pill); font-size: var(--text-caption-size); font-weight: 600; white-space: nowrap; }
.dw-cl__role--lead { border-color: var(--accent); color: var(--accent-text); }
.dw-cl__role--rec { color: var(--muted); font-weight: 500; }
.dw-cl__role--block { border-color: var(--danger-line); color: var(--danger-text); }
.dw-cl__body, .dw-cl__news { line-height: 1.55; overflow-wrap: anywhere; }
.dw-cl__news + .dw-cl__news { margin-top: var(--space-3); padding-top: var(--space-3); border-top: 1px solid var(--line-2); }
.dw-cl__list { margin: 0 0 var(--space-2); padding-left: 18px; }
.dw-cl__rules, .dw-cl__create { max-width: 640px; margin-bottom: var(--space-3); }
.dw-cl__rel2 { gap: 10px; }
.dw-cl__rel2 .dw-cl__main { flex: 1 1 auto; }
/* Clan management (admin/clan.php, 05.10): clan card (money, level, structure, leader change), level-up requirements
   with have/need marks, structure choice, members with actions, rank page, question and result for player actions,
   clan texts form. */
.dw-ca__inl { margin-left: 6px; font-size: var(--text-caption-size); }
.dw-ca__req { display: grid; gap: 6px; margin: 0 0 var(--space-2); padding: 0; list-style: none; }
.dw-ca__req li { display: grid; grid-template-columns: minmax(0, 1fr) auto; gap: 0 10px; align-items: baseline; padding: 6px 0 6px 22px; border-bottom: 1px solid var(--line-2); position: relative; }
.dw-ca__req li::before { position: absolute; left: 0; top: 6px; font-weight: 700; }
.dw-ca__req li.dw-ca__ok::before { content: "\2713"; color: var(--ok-text); }
.dw-ca__req li.dw-ca__no::before { content: "\2715"; color: var(--danger-text); }
.dw-ca__req b { font-variant-numeric: tabular-nums; }
.dw-ca__have { grid-column: 1 / -1; color: var(--muted); font-size: var(--text-caption-size); }
.dw-ca__no .dw-ca__have { color: var(--danger-text); }
.dw-ca__list { display: grid; gap: 0 32px; margin: var(--space-2) 0 0; padding: 0; list-style: none; }
@media (min-width: 1100px) { .dw-ca__list { grid-template-columns: repeat(2, minmax(0, 1fr)); } }
.dw-ca__m { display: grid; grid-template-columns: minmax(0, 1fr) auto; align-items: center; gap: 10px; min-height: 48px; padding: 6px 0; border-bottom: 1px solid var(--line-2); }
.dw-ca__acts { display: flex; flex-wrap: wrap; justify-content: flex-end; gap: 6px; }
.dw-ca__del { color: var(--danger-text); }
.dw-ca__who { display: flex; flex-wrap: wrap; align-items: center; gap: 4px 8px; margin: 0 0 var(--space-2); }
.dw-ca__ask, .dw-ca__stage, .dw-ca__change { max-width: 720px; margin-bottom: var(--space-3); }
.dw-ca__srow { gap: 10px; }
.dw-ca__srow > span:first-child { flex: 1 1 auto; }
.dw-ca__free { color: var(--muted); font-size: var(--text-caption-size); }
.dw-ca__members { margin-bottom: var(--space-3); }
.dw-ca__texts { max-width: 880px; }
.dw-ca__ta { min-height: 96px; resize: vertical; }
/* Clan missions (clan.php?missions=1, 05.10): mission cards (name, goal, note, reward), a mission - goal as a heading,
   condition and notes in body size, reward as a mark, progress number and bar, ready / take / hand in; air between blocks
   and before the buttons (owner: "move the buttons away, readable text, lots of room but all squeezed"). */
.dw-cm__list { display: grid; gap: var(--space-3); }
@media (min-width: 900px) { .dw-cm__list { grid-template-columns: repeat(2, minmax(0, 1fr)); } }
.dw-cm__list > .dw-card { margin: 0; }
.dw-cm__item { display: flex; flex-direction: column; gap: 10px; padding: var(--space-4); color: inherit; text-decoration: none; }
.dw-cm__item .dw-cm__open { margin-top: auto; }
.dw-cm__item:hover { border-color: var(--accent); }
.dw-cm__name { color: var(--accent-text); font-size: 17px; font-weight: 600; }
.dw-cm__info { display: grid; justify-items: start; gap: 8px; margin: 0; }
.dw-cm__goal { color: var(--text); line-height: 1.4; }
.dw-cm__note { color: var(--muted); font-size: var(--text-body-sm-size); line-height: 1.4; }
.dw-cm__rew { padding: 3px 12px; border: 1px solid var(--ok); border-radius: var(--radius-pill); color: var(--ok-text); font-size: var(--text-body-sm-size); font-weight: 600; }
.dw-cm__open { align-self: flex-end; color: var(--accent-text); font-size: var(--text-body-sm-size); }
.dw-cm__card { display: grid; gap: var(--space-4); max-width: 720px; padding: var(--space-4) var(--space-5); }
.dw-cm__card > p, .dw-cm__card > .dw-shop__acts { margin: 0; }
.dw-cm__card .dw-cm__info { gap: 10px; }
.dw-cm__card .dw-cm__goal { font-size: 20px; font-weight: 600; line-height: 1.35; }
.dw-cm__card .dw-cm__note { font-size: var(--text-body-size); }
.dw-cm__card .dw-shop__note { font-size: var(--text-body-size); line-height: 1.5; }
.dw-cm__prog { display: grid; gap: 8px; margin: 0; }
.dw-cm__pnum b { font-size: 28px; font-variant-numeric: tabular-nums; }
.dw-cm__pl { color: var(--muted); }
.dw-cm__bar { height: 10px; overflow: hidden; border-radius: var(--radius-pill); background: var(--line-2); }
.dw-cm__bar > i { display: block; height: 100%; background: var(--ok); }
.dw-cm__ready { color: var(--ok-text); font-size: 17px; font-weight: 600; }
/* Clan activity stats (clan.php?stats=1, 05.10): glory / reputation chips, this month and last month cards with ranked
   rows (place, nick, value, bar against the best), top three marked. */
.dw-cs__card { margin: 0; }
.dw-cs__list { display: grid; margin: var(--space-2) 0 0; padding: 0; list-style: none; }
.dw-cs__row { display: grid; grid-template-columns: 28px minmax(0, 1fr) auto; align-items: center; gap: 4px 10px; padding: 8px 0; border-bottom: 1px solid var(--line-2); }
.dw-cs__row:last-child { border-bottom: 0; }
.dw-cs__place { color: var(--muted); font-variant-numeric: tabular-nums; text-align: right; }
.dw-cs__row--top .dw-cs__place { color: var(--accent-text); font-weight: 700; }
.dw-cs__who { display: flex; flex-wrap: wrap; align-items: center; gap: 4px; min-width: 0; }
.dw-cs__who a { font-weight: 500; }
.dw-cs__val { font-variant-numeric: tabular-nums; }
.dw-cs__bar { grid-column: 2 / -1; height: 4px; overflow: hidden; border-radius: var(--radius-pill); background: var(--line-2); }
.dw-cs__bar > i { display: block; height: 100%; background: var(--accent); }
/* Clan bonuses (clan.php?rep=1 / repinfo, 05.10): reputation and glory purse (free of total, used), bonus cards (name,
   level, effect, step, used, Improve), upgrade card with have/need marks, reset with a question first. */
.dw-br__purse { display: grid; gap: var(--space-3); margin: 0 0 var(--space-3); }
@media (min-width: 700px) { .dw-br__purse { grid-template-columns: repeat(2, minmax(0, 1fr)); } }
.dw-br__res { display: grid; gap: 2px; padding: var(--space-3); border: 1px solid var(--line); border-radius: var(--radius-md); background: var(--surface); }
.dw-br__rl { color: var(--muted); font-size: var(--text-caption-size); letter-spacing: .06em; text-transform: uppercase; }
.dw-br__rv { font-size: 26px; font-variant-numeric: tabular-nums; }
.dw-br__rs { color: var(--muted); font-size: var(--text-body-sm-size); }
.dw-br__h { margin: var(--space-3) 0 var(--space-2); }
.dw-br__grid { display: grid; gap: var(--space-3); }
@media (min-width: 700px) { .dw-br__grid { grid-template-columns: repeat(2, minmax(0, 1fr)); } }
@media (min-width: 1200px) { .dw-br__grid { grid-template-columns: repeat(3, minmax(0, 1fr)); } }
.dw-br__grid > .dw-card { margin: 0; }
.dw-br__b { display: flex; flex-direction: column; gap: 8px; }
.dw-br__b .dw-shop__acts { margin-top: auto; }
.dw-br__b--on { border-color: var(--accent); }
.dw-br__bh { display: flex; align-items: baseline; justify-content: space-between; gap: 8px; }
.dw-br__bn { font-weight: 600; }
.dw-br__blv { color: var(--accent-text); font-variant-numeric: tabular-nums; }
.dw-br__eff, .dw-br__used { margin: 0; }
.dw-br__used { color: var(--muted); font-size: var(--text-body-sm-size); }
.dw-br__up { display: grid; gap: var(--space-3); max-width: 720px; }
.dw-br__up > * { margin: 0; }
.dw-br__lv { font-size: 18px; }
.dw-br__reset { margin-top: var(--space-4); }
/* Clan rating (clan.php?rating=1, 05.10): side and mode chips, ranked rows (top-3 place accent, own clan marked),
   how-it-works card; breakdown of one clan - indicator rows with value, place and points, penalty, total. */
.dw-crt > .dw-km__tabs { margin-bottom: 0; }
.dw-crt__row--top .dw-cl__place { color: var(--accent-text); font-weight: 700; }
.dw-crt__row--mine { box-shadow: inset 3px 0 0 var(--accent); }
.dw-crt__how { margin-top: var(--space-4); }
.dw-crt__how p { margin: 0 0 var(--space-2); }
.dw-crt__how p:last-child { margin-bottom: 0; }
.dw-crt__inds { display: grid; margin: var(--space-2) 0 0; padding: 0; list-style: none; }
.dw-crt__ind { display: grid; grid-template-columns: minmax(0, 1fr) auto; align-items: center; gap: 4px 12px; padding: 10px 0; border-bottom: 1px solid var(--line-2); }
.dw-crt__ind:last-child { border-bottom: 0; }
.dw-crt__il { display: grid; gap: 2px; min-width: 0; }
.dw-crt__iv { color: var(--muted); font-size: var(--text-body-sm-size); font-variant-numeric: tabular-nums; }
.dw-crt__ip { display: grid; justify-items: end; font-variant-numeric: tabular-nums; }
.dw-crt__ip > b { font-size: 18px; }
.dw-crt__ind--minus .dw-crt__ip > b { color: var(--danger-text); }
.dw-crt__ind--sum { border-top: 1px solid var(--line-strong); }
.dw-crt__ind--sum .dw-crt__ip > b { color: var(--accent-text); font-size: 22px; }
.dw-crt__card--dim .dw-crt__ind { padding: 6px 0; }
/* Clan / player clan history (clan.php?history=1, 05.10): rows - member (or clan with emblem), joined -> left and how
   long, status chip (in the clan now / left / exit not recorded). */
.dw-chh__row { display: grid; grid-template-columns: minmax(0, 1fr) auto; align-items: center; gap: 10px; }
.dw-chh__row--emb { grid-template-columns: auto minmax(0, 1fr) auto; }
.dw-chh__row--now { box-shadow: inset 3px 0 0 var(--ok); }
.dw-chh__main { display: grid; gap: 2px; min-width: 0; }
.dw-chh__who { display: flex; flex-wrap: wrap; align-items: baseline; gap: 4px; min-width: 0; }
.dw-chh__who a { font-weight: 600; }
.dw-chh__when { color: var(--muted); font-size: var(--text-body-sm-size); font-variant-numeric: tabular-nums; }
.dw-chh__st { padding: 2px 10px; border: 1px solid var(--line); border-radius: var(--radius-pill); color: var(--muted); font-size: var(--text-caption-size); white-space: nowrap; }
.dw-chh__st--now { border-color: var(--ok); color: var(--ok-text); }
.dw-chh__st--unk { border-style: dashed; }
/* Tavern (chat/index.php, 06.10): rooms - own clan and side first, who is inside under the name, how many on the right;
   a room - the chat of the mail (bubbles, reply bar sticky above the tabs on the phone, scrolling card on the desktop)
   with a side column on the desktop (Umnik question, selling an item in the Trade Hall, links); system lines (trade
   offers, Umnik) centred, private messages marked. */
.dw-tav__room { display: grid; grid-template-columns: auto minmax(0, 1fr) auto; align-items: center; gap: 10px; }
.dw-tav__room--own { background: var(--surface-2); }
.dw-tav__ico, .dw-tav__sideico { display: inline-grid; place-items: center; width: 32px; height: 32px; border-radius: var(--radius-round); background: var(--sunken); color: var(--accent-text); font-weight: 700; }
.dw-tav__sideico { background: transparent; }
.dw-tav__rmain { display: grid; gap: 2px; min-width: 0; }
.dw-tav__rname { color: var(--accent-text); font-weight: 600; overflow-wrap: anywhere; }
.dw-tav__rwho { color: var(--muted); font-size: var(--text-caption-size); overflow-wrap: anywhere; }
.dw-tav__rn { display: grid; justify-items: end; font-variant-numeric: tabular-nums; }
.dw-tav__rn > span { color: var(--muted); font-size: var(--text-caption-size); }
.dw-tav__links { margin-top: var(--space-1); }
.dw-tav-room { display: grid; gap: var(--space-3); }
.dw-tav__side { display: grid; gap: var(--space-3); align-content: start; min-width: 0; }
.dw-tav__side > .dw-card { margin: 0; }
.dw-tav__main { min-width: 0; }
@media (min-width: 1000px) {
  .dw-tav-room { grid-template-columns: minmax(0, 880px) minmax(280px, 340px); align-items: start; }
  .dw-tav-room > .dw-tav__main { grid-column: 1; grid-row: 1; }
  .dw-tav-room > .dw-tav__side { grid-column: 2; grid-row: 1; position: sticky; top: var(--space-4); }
}
.dw-tav__q { margin: 0 0 var(--space-2); font-size: 17px; line-height: 1.4; }
.dw-tav__left { color: var(--accent-text); font-variant-numeric: tabular-nums; }
.dw-tav__sellrow { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: var(--space-2); }
.dw-tav__by { display: flex; flex-wrap: wrap; align-items: baseline; gap: 6px; }
.dw-tav__by .dw-msg__author { margin-bottom: 2px; }
.dw-tav__pm, .dw-tav__re { padding: 0 6px; border: 1px solid var(--line); border-radius: var(--radius-pill); background: transparent; color: var(--muted); font: inherit; font-size: 11px; line-height: 18px; cursor: pointer; }
.dw-tav__pm:hover, .dw-tav__re:hover { border-color: var(--accent); color: var(--accent-text); }
.dw-tav__whom { display: block; margin-bottom: 2px; color: var(--accent-text); font-size: var(--text-caption-size); font-weight: 600; }
.dw-tav__priv { border-style: dashed; border-color: var(--accent); }
.dw-tav__tome { box-shadow: 0 0 0 2px var(--accent-soft); }
.dw-tav__sys, .dw-tav__act { align-self: center; max-width: min(620px, 92%); padding: 6px 12px; border-radius: var(--radius-md); background: var(--notice); color: var(--text); font-size: var(--text-body-sm-size); text-align: center; overflow-wrap: anywhere; }
.dw-tav__sys--me { border: 1px solid var(--notice-line); }
.dw-tav__sys--bot { background: var(--accent-soft); }
.dw-tav__act { background: transparent; color: var(--muted); font-style: italic; }
.dw-tav__systime { margin-left: 6px; color: var(--dim); font-size: 11px; white-space: nowrap; }
.dw-tav__sys a { color: var(--accent-text); font-weight: 600; }
.dw-tav__sys a:hover { text-decoration: underline; }
.dw-tav__padl { width: 84px; }
.dw-tav__rater { min-width: 0; font-weight: 500; overflow-wrap: anywhere; }
.dw-tav__to { display: flex; flex: 1 1 100%; align-items: center; gap: 8px; padding: 0 4px; color: var(--accent-text); font-size: var(--text-body-sm-size); }
.dw-tav__to[hidden] { display: none; }
.dw-tav__to > span { flex: 1 1 auto; min-width: 0; }
.dw-tav__tox { width: 28px; height: 28px; border: 0; border-radius: var(--radius-round); background: var(--surface-2); color: var(--text); font-size: 18px; line-height: 1; cursor: pointer; }
.dw-tav__emo { margin: calc(var(--space-2) * -1) 0 0; }
.dw-tav__rules ol { margin: var(--space-2) 0; padding-left: 22px; }
.dw-tav__rules li + li { margin-top: 6px; }
.dw-tav__smiles { display: flex; flex-wrap: wrap; gap: var(--space-2); padding: var(--space-3); }
.dw-tav__smile { display: inline-flex; align-items: center; gap: 8px; padding: 6px 10px; border: 1px solid var(--line); border-radius: var(--radius-md); color: inherit; text-decoration: none; }
a.dw-tav__smile:hover { border-color: var(--accent); }
.dw-tav__smile code { font-size: var(--text-body-sm-size); }
.dw-tav__rate { display: grid; grid-template-columns: 28px minmax(0, 1fr) auto; align-items: center; gap: 10px; }
.dw-tav__place { color: var(--muted); font-variant-numeric: tabular-nums; text-align: right; }
.dw-tav__pts { font-variant-numeric: tabular-nums; }
/* Using an item (useItem.php + magic/*, 06.10): item picture in the head (new pharmacy icons hd/xl, old gif as is),
   question card, result notices, town choice, prize list, attack target list, battles to join with teams. */
.dw-use__head { align-items: center; }
.dw-use__pic { flex: 0 0 auto; width: 72px; height: 72px; object-fit: contain; }
.dw-use__pic--old { width: auto; height: auto; max-width: 72px; max-height: 88px; }
.dw-use__prize { display: flex; align-items: center; justify-content: space-between; gap: 10px; }
.dw-use__prize > a:first-child { min-width: 0; overflow-wrap: anywhere; }
.dw-use__foe { display: grid; grid-template-columns: minmax(0, 1fr) auto auto; align-items: center; gap: 10px; }
.dw-use__fwho { min-width: 0; overflow-wrap: anywhere; }
.dw-use__ftime { color: var(--muted); font-size: var(--text-caption-size); white-space: nowrap; }
.dw-use__battle { display: grid; gap: var(--space-2); }
.dw-use__team { display: grid; gap: 6px; padding: var(--space-2) 0; border-top: 1px solid var(--line-2); }
.dw-use__team:first-of-type { border-top: 0; }
.dw-use__tname { color: var(--muted); font-size: var(--text-caption-size); font-weight: 600; letter-spacing: .04em; text-transform: uppercase; }
.dw-use__tlist { overflow-wrap: anywhere; }
.dw-use__hp { color: var(--muted); font-size: var(--text-caption-size); font-variant-numeric: tabular-nums; }
.dw-use__team .dw-btn { justify-self: start; }
.dw-use__form, .dw-use__ask, .dw-use__towns { max-width: 640px; }
/* Clan achievements (competitions.php, 05.10): opens on an achievement at once (no choice page - owner), tabs, own clan
   notice, current top-10 and last winners side by side on desktop (prize places marked), how it is counted with the prize list. */
.dw-cmp__cols { display: grid; gap: var(--space-3); }
@media (min-width: 1000px) { .dw-cmp__cols { grid-template-columns: repeat(2, minmax(0, 1fr)); align-items: start; } }
.dw-cmp__cols > .dw-card { margin: 0; }
.dw-cmp__list { display: grid; margin: var(--space-2) 0 0; padding: 0; list-style: none; }
.dw-cmp__row { display: grid; grid-template-columns: 26px auto minmax(0, 1fr) auto; align-items: center; gap: 10px; padding: 8px 0; border-bottom: 1px solid var(--line-2); }
.dw-cmp__row:last-child { border-bottom: 0; }
.dw-cmp__place { color: var(--muted); font-variant-numeric: tabular-nums; text-align: right; }
.dw-cmp__row--prize .dw-cmp__place { color: var(--accent-text); font-weight: 700; }
.dw-cmp__row--mine { box-shadow: inset 3px 0 0 var(--accent); }
.dw-cmp__main { display: grid; gap: 2px; min-width: 0; }
.dw-cmp__pz { color: var(--accent-text); }
.dw-cmp__how p { margin: 0 0 var(--space-2); }
.dw-cmp__prizes { display: grid; gap: 4px; margin: 0; padding: 0; list-style: none; }
.dw-cmp__prizes li { display: grid; grid-template-columns: 26px minmax(0, 1fr); gap: 10px; }
.dw-cmp__prizes .dw-cmp__place { color: var(--accent-text); font-weight: 700; }
/* Forum topic author under the title (05.10). */
.dw-forum__author { display: flex; flex-wrap: wrap; align-items: center; gap: 4px; margin: 4px 0 0; color: var(--muted); font-size: var(--text-body-sm-size); }
.dw-forum__authorlink { display: inline-flex; align-items: center; gap: 4px; }
/* Stone master (stones.php, 04.10): three exchange cards (phone - one column, desktop - three), stones with counts,
   a missing stone dimmed with "none", what you get, the button with how many exchanges are possible. */
.dw-stn__lead { margin: 0 0 var(--space-3); }
.dw-stn__got { margin-bottom: var(--space-3); }
.dw-stn__grid { display: grid; gap: var(--space-3); }
@media (min-width: 1000px) { .dw-stn__grid { grid-template-columns: repeat(3, minmax(0, 1fr)); } }
.dw-stn__rec { display: grid; grid-template-rows: auto auto auto auto auto 1fr auto; gap: var(--space-2); }
.dw-stn__grid > .dw-stn__rec { margin: 0; }
.dw-stn__rec--on { border-color: var(--accent); }
.dw-stn__title { margin: 0; font-size: var(--text-body-size); font-weight: 600; }
.dw-stn__need { margin: 0; padding: 0; list-style: none; border: 1px solid var(--line-2); border-radius: var(--radius-md); }
.dw-stn__st { display: flex; align-items: center; gap: var(--space-2); padding: 7px var(--space-3); border-bottom: 1px solid var(--line-2); }
.dw-stn__st:last-child { border-bottom: 0; }
.dw-stn__name { flex: 1 1 auto; min-width: 0; }
.dw-stn__have { color: var(--muted); font-size: var(--text-body-sm-size); font-variant-numeric: tabular-nums; }
.dw-stn__st--no .dw-stn__name { color: var(--muted); }
.dw-stn__st--no .dw-stn__have { color: var(--danger-text); }
.dw-stn__h { margin: 4px 0 0; color: var(--muted); font-size: var(--text-caption-size); text-transform: uppercase; letter-spacing: .04em; }
.dw-stn__odds { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 4px var(--space-3); margin: 0; padding: 0; list-style: none; font-size: var(--text-body-sm-size); }
.dw-stn__odds li { display: flex; align-items: center; gap: 6px; min-width: 0; }
.dw-stn__odds span { flex: 1 1 auto; min-width: 0; }
.dw-stn__odds b { font-weight: 600; font-variant-numeric: tabular-nums; }
.dw-stn__rare { grid-column: 1 / -1; padding-top: 4px; border-top: 1px solid var(--line-2); }
.dw-stn__rare span { font-weight: 600; }
.dw-stn__rarelist { margin: 0; color: var(--muted); font-size: var(--text-caption-size); }
/* Desktop cards are a third of the row - the odds go in one column there (two columns overlapped the long names). */
@media (min-width: 1000px) { .dw-stn__odds { grid-template-columns: minmax(0, 1fr); } }
.dw-stn__go { display: flex; flex-wrap: wrap; align-items: center; gap: var(--space-2); }
.dw-stn__can { color: var(--muted); font-size: var(--text-caption-size); }
.dw-shop__part { display: flex; flex-wrap: wrap; align-items: flex-end; gap: var(--space-2); }
.dw-shop__part .dw-field { flex: 1 1 160px; }
.dw-shop__form { display: grid; gap: var(--space-3); max-width: 640px; }
.dw-shop__pair { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: var(--space-3); }
.dw-shop__info { overflow-wrap: anywhere; }
.dw-btn__n { margin-left: 8px; padding: 1px 7px; border-radius: var(--radius-pill); background: var(--surface); color: var(--muted); font-size: var(--text-caption-size); font-variant-numeric: tabular-nums; }
@media (min-width: 700px) {
  .dw-lot { grid-template-columns: minmax(0, 1fr) auto; align-items: center; }
  .dw-lot__buy { flex-wrap: nowrap; padding-left: 0; }
  .dw-lot__price { margin-right: var(--space-2); text-align: right; }
  .dw-shop__privs { grid-template-columns: repeat(3, minmax(0, 1fr)); }
}
@media (min-width: 1000px) {
  .dw-shop__tiles { grid-template-columns: repeat(auto-fill, minmax(220px, 1fr)); }
  .dw-shop__privs { grid-template-columns: repeat(auto-fill, minmax(190px, 1fr)); }
}

/* ---- Alchemist (apteka.php, 03.10) ----
   Four cash desks of one script as tabs (credits, valor, valour marks, clan marks) with the player's balance; a row
   carries the old small picture, the description, the price and an inline quantity + Buy (or why it can't be bought). */
.dw-apt__tabs { margin-bottom: 0; }
.dw-apt__have { margin: 0; color: var(--muted); font-size: var(--text-body-sm-size); }
.dw-apt__have b { color: var(--text); font-weight: 600; font-variant-numeric: tabular-nums; }
.dw-apt__who { display: flex; align-items: flex-start; gap: var(--space-3); min-width: 0; }
/* Icons 48 in the rows, 128 on the card (art agent's brief 03.10, the owner: "can be bigger"); old gifs - contain. */
.dw-apt__pic { flex: 0 0 48px; width: 48px; height: 48px; object-fit: contain; }
.dw-apt__pic--none { display: block; border-radius: var(--radius-sm); background: var(--surface-2); }
.dw-apt__text { min-width: 0; }
.dw-apt__opis { overflow-wrap: anywhere; }
.dw-apt__item .dw-lot__buy { padding-left: calc(48px + var(--space-3)); }
.dw-apt__buy { display: flex; align-items: center; gap: 6px; margin: 0; }
.dw-apt__n { width: 52px; min-height: 34px; padding: 0 8px; text-align: center; }
.dw-apt__why { color: var(--muted); font-size: var(--text-caption-size); white-space: nowrap; }
.dw-apt__card { display: grid; grid-template-columns: minmax(0, 1fr); gap: var(--space-3); max-width: 640px; }
.dw-apt__pic--big { width: 128px; height: 128px; flex-basis: 128px; }
.dw-apt__about { display: grid; gap: var(--space-3); min-width: 0; }
.dw-apt__about .dw-apt__opis { margin: 0; line-height: 1.5; }
.dw-apt__card .dw-apt__buy { align-items: flex-end; gap: var(--space-2); }
.dw-apt__num { display: grid; gap: 6px; }
.dw-apt__num .dw-field__input { width: 90px; }
@media (min-width: 700px) {
  .dw-apt__item .dw-lot__buy { padding-left: 0; }
  .dw-apt__card { grid-template-columns: 128px minmax(0, 1fr); max-width: 720px; }
}

/* ---- Forge (forge.php, 03.10) ----
   A hub of all the forge's actions as tiles (forge.php?hub=1), then each mode: the form card left, its rules right on
   the desktop. The form's submit stays the engine's exact <input class="button" type="submit" value="OK" /> - the
   output pass injects the mode field before it - so it is styled here as the main button. */
.dw-shop__why { margin: 0; color: var(--danger-text); font-size: var(--text-body-sm-size); }
.dw-forge__form { display: grid; gap: var(--space-3); max-width: 640px; }
.dw-forge input.button {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  min-height: var(--touch);
  padding: 0 var(--space-5);
  border: 1px solid var(--accent);
  border-radius: var(--radius-md);
  background: var(--accent);
  color: var(--bg);
  font-family: var(--font-body);
  font-size: var(--text-button-size);
  font-weight: var(--text-button-weight);
  cursor: pointer;
}
.dw-forge input.button:hover { border-color: var(--accent-text); background: var(--accent-text); }
.dw-forge__rules { display: grid; gap: var(--space-2); color: var(--muted); font-size: var(--text-body-sm-size); line-height: 1.5; }
.dw-forge__rules p { margin: 0; }
.dw-forge__rules b { color: var(--text); }
.dw-forge__rules > .dw-forge__rulestitle { color: var(--text); font-weight: 600; }
.dw-forge__list { margin: 0; padding-left: 18px; }
.dw-forge__powder { display: grid; gap: 4px; }
/* Forge picker (owner 03.10: items in the list coloured like the inventory, stones too): rows instead of a drop-down
   (a phone opens a drop-down in a system sheet that drops option colours) - quality dot and coloured name like the
   inventory, level / percent / count right, a radio with the old select's field name; search over 8 rows. */
.dw-pick { display: grid; gap: 6px; min-width: 0; margin: 0; padding: 0; border: 0; }
.dw-pick > legend { padding: 0; margin-bottom: 6px; }
.dw-pick__list { border: 1px solid var(--line); border-radius: var(--radius-md); background: var(--surface); }
/* No scrolling inside the list (owner 03.10: on the phone the page scroll got caught by the item list on the way to
   the stones): 8 rows and the chosen one, the rest behind "Show all"; a search shows matches from the whole list. */
.dw-pick--js:not(.dw-pick--all):not(.dw-pick--search) .dw-pick__row--more { display: none; }
.dw-pick__all { justify-self: start; }
.dw-pick__row { display: flex; align-items: center; gap: var(--space-2); min-height: 42px; padding: 8px var(--space-3); border-bottom: 1px solid var(--line-2); cursor: pointer; }
.dw-pick__row:last-child { border-bottom: 0; }
.dw-pick__row[hidden] { display: none; }
.dw-pick__row:hover { background: var(--surface-2); }
.dw-pick__row:has(input:checked) { background: var(--accent-soft); }
.dw-pick__row input {
  flex: 0 0 auto;
  width: 18px;
  height: 18px;
  margin: 0;
  border: 2px solid var(--line-strong);
  border-radius: 50%;
  background: var(--surface);
  -webkit-appearance: none;
  appearance: none;
}
.dw-pick__row input:checked { border-color: var(--accent); background: radial-gradient(circle, var(--accent) 0 4px, var(--surface) 5px); }
.dw-pick__row input:focus-visible { outline: 2px solid var(--accent); outline-offset: 2px; }
.dw-pick__name { flex: 1 1 auto; min-width: 0; font-weight: 600; overflow-wrap: anywhere; }
.dw-pick__name--plain { font-weight: 400; color: var(--muted); }
/* Drop percent in the item's colour (owner 03.10: pale grey did not read), the level glued to the name. */
.dw-pick__pct { flex: 0 0 auto; font-size: var(--text-body-sm-size); font-weight: 600; font-variant-numeric: tabular-nums; white-space: nowrap; }
.dw-pick__meta { flex: 0 0 auto; color: var(--muted); font-size: var(--text-caption-size); font-variant-numeric: tabular-nums; white-space: nowrap; }
/* Drop filter over the enhancement stones (03.10, a player: "so you don't scroll the stones - a 5, 6, 7 drop
   filter"): the item-pick script draws the pills; the dot has the drop colour, as the list rows do. */
.dw-pick__drops { align-items: center; gap: 6px; }
.dw-pick__drops-label { color: var(--muted); font-size: var(--text-caption-size); margin-right: 2px; }
.dw-pick__drop { gap: 6px; height: 32px; padding: 0 12px; font-variant-numeric: tabular-nums; cursor: pointer; }

/* ---- Nick search (find.php, 03.10): a field with Find - on its own page and at the top of "Who is online". ---- */
.dw-find { display: flex; gap: var(--space-2); max-width: 560px; margin: 0 0 var(--space-3); }
.dw-find__input { flex: 1 1 auto; min-width: 0; }
.dw-find__list { margin-bottom: var(--space-3); }
.dw-find--page { display: grid; gap: var(--space-2); }
.dw-find__row { display: flex; gap: var(--space-2); }
.dw-find__how { display: flex; flex-wrap: wrap; gap: var(--space-2); }
.dw-find__opt { gap: 6px; cursor: pointer; }
.dw-find__opt input { margin: 0; accent-color: var(--accent); }
.dw-find__opt:has(input:checked) { border-color: var(--accent); background: var(--surface-2); color: var(--accent-text); }
.dw-find__hint { margin: 0; color: var(--muted); font-size: var(--text-caption-size); }
.dw-find__hint b { color: var(--text); font-family: monospace; }

/* Player profile (anketa.php, 07.10): photo circle in the head (no photo - person sign), action buttons, data cards in
   the clan grid (two columns from 900px, cards of one row are of one height - rule 32), guest book as forum posts with
   the owner's answer under a post, guests list, edit forms, town picker. */
.dw-ank__face { display: inline-flex; flex: 0 0 72px; align-items: center; justify-content: center; width: 72px; height: 72px; overflow: hidden; border-radius: 50%; }
.dw-ank__face img { width: 100%; height: 100%; object-fit: cover; }
.dw-ank__face--none { border: 1px solid var(--line); background: var(--surface-2); color: var(--muted); }
.dw-ank__face--none svg { width: 40px; height: 40px; }
.dw-ank__acts { margin: 0 0 var(--space-3); }
/* New guests count inside the button: its own gap (a space before an element collapses in a flex button) and a
   line box of the button text, so it sits on the text middle (07.10, owner: "close and crooked"). */
.dw-ank__gbtn { gap: 8px; }
.dw-ank__newc { padding: 2px 7px; line-height: 16px; font-weight: 600; }
.dw-ank__fotohow { margin-top: var(--space-3); }
.dw-cl__grid.dw-ank__grid { align-items: stretch; }
.dw-ank__grid .dw-kv__row--stack .dw-kv__v { text-align: left; }
.dw-ank__comm { margin-top: var(--space-3); }
.dw-ank__gb { margin-top: var(--space-4); }
.dw-ank__write { max-width: 720px; margin-bottom: var(--space-3); }
.dw-ank__area { min-height: 64px; resize: vertical; }
.dw-ank__gb .dw-post__text { overflow-wrap: anywhere; }
.dw-ank__ans { margin: 8px 0 0; padding: 6px 10px; border-left: 3px solid var(--accent); border-radius: var(--radius-md); background: var(--sunken); color: var(--muted); font-size: var(--text-body-sm-size); overflow-wrap: anywhere; }
.dw-ank__ans b { color: var(--text); font-weight: 600; }
.dw-ank__gwho { display: inline-flex; align-items: center; gap: 6px; min-width: 0; }
.dw-ank__gnoemb { flex: 0 0 20px; width: 20px; height: 20px; }
.dw-ank__gnick { overflow-wrap: anywhere; }
.dw-ank__guest--new .dw-ank__gnick { font-weight: 700; }
.dw-ank__gdate { flex: 0 0 auto; color: var(--muted); font-size: var(--text-caption-size); font-variant-numeric: tabular-nums; white-space: nowrap; }
.dw-ank__rsub { display: block; color: var(--muted); font-size: var(--text-caption-size); font-weight: 400; }
.dw-ank__form { max-width: 640px; }
.dw-ank__town { margin-top: var(--space-1); }
.dw-ank__letters .dw-chip { justify-content: center; min-width: 40px; }
/* World and community menus (menus.php, 07.10): the hub layout; a row caption keeps the body font on the desktop tiles
   (the tile title is the display font). */
.dw-hub--menus .dw-row__cap { font-family: var(--font-body); font-size: var(--text-caption-size); }

/* Classes and class skills (class.php, 07.10): own class skills as skill rows (class icon, level of the cap, what it gives
   now, raise button with the price), class and subclass rows with the status emblem, class page text with the gear
   ban, passive skills, battle skills of the class. */
.dw-row > .dw-st:first-child { flex: 0 0 auto; }
.dw-cls__head .dw-st { flex: 0 0 auto; }
.dw-cls__list { margin-bottom: var(--space-3); }
.dw-cls__crow { gap: var(--space-3); }
/* Text runs with bold numbers inside flex boxes split into items and wrapped apart ("4" alone under the head, "of 150"
   on its own line): on this screen the head meta and skill captions are plain text blocks; a class row text
   cell takes the free width (the emblem is the first child, the generic first-span rule hits it). */
.dw-cls__head .dw-cl__hmeta { display: block; }
.dw-cls .dw-sk__row .dw-lot__cap { display: block; }
.dw-cls__crow > .dw-st + span { flex: 1 1 auto; min-width: 0; }
.dw-cls__row .dw-lot__cap b { color: var(--text); font-weight: 600; }
.dw-cls__note { color: var(--muted); font-size: var(--text-caption-size); }
.dw-cls__need { color: var(--muted); font-size: var(--text-caption-size); white-space: nowrap; }
.dw-cls__about { margin-bottom: var(--space-3); }
.dw-cls__text { margin: 0 0 var(--space-3); line-height: 1.55; }
.dw-cls__ban { margin: 0 0 var(--space-2); padding: 8px 12px; border-left: 3px solid var(--danger); border-radius: var(--radius-md); background: var(--sunken); font-size: var(--text-body-sm-size); }
.dw-cls__ban--info { border-left-color: var(--accent); }
.dw-cls__ban:last-child { margin-bottom: 0; }
.dw-cls__pick { margin: var(--space-3) 0; }
.dw-cls__ico--big { width: 96px; height: 96px; }

/* Information (info.php, 07.10): the main page and the guide in the hub layout, dealers and support as rows with a clan
   emblem, a dealer page with two cards, invite text and the referral link field, old blocks inside the legacy layer. */
.dw-info__dealer { gap: var(--space-3); }
.dw-row > .dw-emb:first-child + .dw-info__dname, .dw-info__noemb + .dw-info__dname { flex: 1 1 auto; min-width: 0; }
.dw-info__noemb, .dw-row > .dw-info__noemb:first-child { flex: 0 0 28px; width: 28px; height: 28px; }
.dw-info__dname { overflow-wrap: anywhere; }
.dw-info__acts { margin: 0 0 var(--space-3); }
.dw-info__text { line-height: 1.55; overflow-wrap: anywhere; }
.dw-info__lead { margin: 0 0 var(--space-2); font-family: var(--font-display); font-size: 19px; }
.dw-info__p { margin: 0 0 var(--space-2); line-height: 1.55; }
.dw-info__p:last-child { margin-bottom: 0; }
.dw-info__ref { width: 100%; margin: 0 0 var(--space-2); font-family: ui-monospace, Consolas, monospace; font-size: 13px; }
/* Phone: the field is 16px there (the floor in base.css - the iPhone zooms into a smaller one), and a monospace
   link of 37 signs no longer fits the row: the body font and a narrower padding keep it whole at 390px. */
@media (max-width: 999.98px) {
  .dw-info__ref { padding: 0 var(--space-2); font-family: var(--font-body); }
}
.dw-info__list { margin: 0 0 var(--space-3); padding-left: 18px; line-height: 1.55; }
.dw-info__list li + li { margin-top: 4px; }
.dw-info__alert { margin-bottom: var(--space-3); }
.dw-info__legacy { margin-top: var(--space-2); }
.dw-mark--ok { color: var(--ok-text, var(--accent-text)); border-color: currentColor; }

/* Guide pages (read.php, table.php, faq.php, 07.10): a reading card (line of about 70 characters, airy leading), plain
   tables without side scroll (numbers right, tabular figures, sticky head inside the card), numbered questions. */
.dw-read__text { max-width: 760px; line-height: 1.6; overflow-wrap: anywhere; }
.dw-read__text img { max-width: 100%; height: auto; }
.dw-tbl__box { max-width: 760px; padding: 0; overflow: hidden; }
.dw-tbl { width: 100%; border-collapse: collapse; font-size: var(--text-body-sm-size); font-variant-numeric: tabular-nums; }
.dw-tbl th { position: sticky; top: 0; padding: 8px 10px; background: var(--surface-2); color: var(--muted); font-size: var(--text-caption-size); font-weight: 600; text-align: left; white-space: nowrap; }
.dw-tbl td { padding: 7px 10px; border-top: 1px solid var(--line-2); }
.dw-tbl tbody tr:nth-child(even) td { background: var(--sunken); }
.dw-tbl .dw-tbl__n { text-align: right; }
@media (max-width: 420px) { .dw-tbl th, .dw-tbl td { padding-left: 6px; padding-right: 6px; } }
.dw-tblpage .dw-chips { margin-bottom: var(--space-2); }
.dw-faq__q { gap: var(--space-3); }
.dw-row > .dw-faq__n:first-child { flex: 0 0 28px; color: var(--muted); font-variant-numeric: tabular-nums; text-align: right; }
.dw-faq__n + span { flex: 1 1 auto; min-width: 0; }

/* ---- Parcels (08.10) ----
   The mail layout and rows (list left, the "Parcels" column right on the desktop, under the content on the phone).
   A list row holds two targets - the parcel and a bin (delete asks first) - so the row is a box and the link inside
   carries the row look; a new parcel's subject is bold, as unread letters were in the old screen. */
.dw-row.dw-prow { padding: 0; gap: 0; }
.dw-row.dw-prow:hover { background: none; color: var(--text); }
.dw-prow__open { display: flex; align-items: center; gap: var(--space-3); flex: 1 1 auto; min-width: 0; min-height: var(--touch); padding: 10px var(--space-3); color: inherit; text-decoration: none; }
.dw-prow__open:hover { background: var(--surface-2); }
.dw-prow__open:hover .dw-mailrow__nick { color: var(--accent-text); }
.dw-prow__open > .dw-emb { flex: 0 0 auto; }
.dw-prow__open > .dw-mailrow__pic { flex: 0 0 32px; }
.dw-prow__nw { white-space: nowrap; }
.dw-prow__flag { color: var(--accent-text); font-weight: 600; white-space: nowrap; }
.dw-prow__theme { overflow-wrap: anywhere; color: var(--text); }
.dw-prow--new .dw-prow__theme { font-weight: 600; }
.dw-prow__del { flex: 0 0 44px; display: flex; align-items: center; justify-content: center; align-self: stretch; border-left: 1px solid var(--line-2); color: var(--muted); }
.dw-prow__del svg { width: 18px; height: 18px; }
.dw-prow__del:hover { background: var(--danger-soft); color: var(--danger-text); }
/* Parcel view: who and when on top, the text keeps the sender's line breaks; attachments are cards side by side
   on a wide screen, each with its own "Take" (the controller takes one kind per request). */
.dw-parcel { display: grid; gap: var(--space-3); }
.dw-row.dw-parcel__who { min-height: 0; padding: 0; border-bottom: 0; }
.dw-row.dw-parcel__who:hover { background: none; color: var(--text); }
.dw-parcel__nick { color: var(--text); text-decoration: none; }
.dw-parcel__nick:hover { color: var(--accent-text); }
.dw-parcel__when { flex: 0 0 auto; align-self: flex-start; color: var(--muted); font-size: var(--text-caption-size); white-space: nowrap; }
.dw-parcel__admin { margin: 0; color: var(--muted); font-size: var(--text-body-sm-size); }
.dw-parcel__text { padding-top: var(--space-3); border-top: 1px solid var(--line-2); white-space: pre-wrap; overflow-wrap: anywhere; line-height: 1.5; }
.dw-parcel__att { display: grid; gap: var(--space-3); }
@media (min-width: 700px) { .dw-parcel__att { grid-template-columns: repeat(auto-fit, minmax(180px, 1fr)); } }
/* Cards side by side start on one line: the shared card-after-card margin pushed the second one down. */
.dw-parcel__att > .dw-card { margin: 0; }
.dw-parcel__box { display: flex; flex-direction: column; gap: var(--space-2); }
.dw-parcel__boxtitle { margin: 0; color: var(--muted); font-size: var(--text-caption-size); font-weight: 600; }
.dw-parcel__things { display: grid; gap: 6px; margin: 0; padding: 0; list-style: none; overflow-wrap: anywhere; }
.dw-parcel__cnt { color: var(--muted); font-variant-numeric: tabular-nums; white-space: nowrap; }
.dw-parcel__gold { margin: 0; font-size: 20px; --dw-field-size: 20px; font-weight: 700; font-variant-numeric: tabular-nums; }
.dw-parcel__boxfoot { margin-top: auto; padding-top: var(--space-2); }
.dw-parcel__all { margin-bottom: var(--space-3); }
.dw-parcel__acts { display: flex; flex-wrap: wrap; gap: var(--space-2); margin-top: var(--space-4); }
.dw-parcel__delbtn { margin-left: auto; color: var(--danger-text); }
/* Send form: up to three items picked in one list (rows with a square mark, the forge picker's look); a picked
   stack opens its "pcs" field, three picked dim the other marks. */
.dw-parcel__row { padding: 0; gap: 0; cursor: default; }
.dw-parcel__pick { display: flex; align-items: center; gap: var(--space-2); flex: 1 1 auto; min-width: 0; min-height: 42px; padding: 8px var(--space-3); cursor: pointer; }
.dw-pick__row .dw-parcel__pick input[type=checkbox] { border-radius: var(--radius-sm); }
.dw-pick__row .dw-parcel__pick input[type=checkbox]:checked { background: var(--accent); box-shadow: inset 0 0 0 3px var(--surface); }
.dw-parcel__row--off .dw-parcel__pick { opacity: .5; cursor: not-allowed; }
.dw-parcel__qty { display: flex; align-items: center; gap: 6px; flex: 0 0 auto; padding-right: var(--space-3); color: var(--muted); font-size: var(--text-caption-size); }
.dw-parcel__qty[hidden] { display: none; }
.dw-pick__row .dw-parcel__qty .dw-field__input { width: 80px; height: 36px; padding: 0 8px; border: 1px solid var(--line-strong); border-radius: var(--radius-sm); background: var(--surface); -webkit-appearance: auto; appearance: auto; }
.dw-parcel__count { color: var(--muted); font-weight: 400; }
.dw-parcel__form textarea.dw-field__input.dw-mail__text { min-height: 110px; }
.dw-parcel__dopcnt { max-width: 220px; margin-top: var(--space-2); }
.dw-parcel__dopcnt[hidden] { display: none; }
.dw-parcel__to { display: grid; gap: var(--space-3); }
.dw-parcel__ask { display: grid; gap: var(--space-3); }
.dw-parcel__ask .dw-notice__acts { margin-top: 0; }
.dw-parcel__asktheme { margin: 0; font-weight: 600; overflow-wrap: anywhere; }
.dw-parcel__rules .dw-notice__text + .dw-notice__text { margin-top: var(--space-2); }

/* ---- Tournaments (08.10) ----
   The new tournaments only (tournaments_new2.php; the old 'classic' pages are closed since 07.10). List: cards by
   stage (registration, qualification, play-off), a level that does not fit dims the card. Tournament page: facts as a
   two-column list, the stage card with the player's state and the stage buttons, the qualification table or the
   pairs of the day. */
.dw-tour__filter { margin-bottom: var(--space-3); }
.dw-tour__cards { display: grid; grid-template-columns: repeat(auto-fill, minmax(min(100%, 260px), 1fr)); gap: var(--space-3); align-items: stretch; }
.dw-tour__cards > .dw-card { margin: 0; }
.dw-tour__card { display: flex; flex-direction: column; gap: var(--space-2); color: var(--text); text-decoration: none; }
.dw-tour__card:hover { border-color: var(--accent); }
.dw-tour__card--off { opacity: .6; }
.dw-tour__cardtop { display: flex; align-items: flex-start; justify-content: space-between; gap: var(--space-2); }
.dw-tour__cardtop .dw-mark { flex: 0 0 auto; white-space: nowrap; }
.dw-tour__name { font-weight: 700; overflow-wrap: anywhere; }
.dw-tour__facts { display: flex; flex-wrap: wrap; gap: 4px var(--space-3); color: var(--muted); font-size: var(--text-body-sm-size); }
.dw-tour__fact b { color: var(--text); font-variant-numeric: tabular-nums; }
/* Prize as its own link (owner: "prizes must stand out - not even clear they are clickable"): a cup, a caption, the
   name in the item colour, a chevron, on the accent tint. In a list card the whole card opens the tournament through the
   title link stretched over it; the prize link sits above that layer. */
.dw-tour__card { position: relative; }
.dw-tour__cardlink { color: inherit; text-decoration: none; }
.dw-tour__cardlink::after { content: ""; position: absolute; inset: 0; border-radius: inherit; }
.dw-tour__cardlink:focus-visible { outline: none; }
.dw-tour__cardlink:focus-visible::after { outline: 2px solid var(--accent); outline-offset: 2px; }
.dw-tour__prizeln { position: relative; z-index: 1; display: flex; align-items: center; gap: var(--space-2); margin-top: auto; padding: 8px var(--space-3); border: 1px solid var(--accent); border-radius: var(--radius-md); background: var(--accent-soft); color: var(--text); text-decoration: none; }
.dw-tour__prizeln:hover { border-color: var(--accent-text); background: var(--surface-2); }
.dw-tour__prizeico { flex: 0 0 24px; width: 24px; height: 24px; color: var(--accent-text); }
.dw-tour__prizetxt { flex: 1 1 auto; min-width: 0; display: flex; flex-direction: column; gap: 1px; }
.dw-tour__prizecap { color: var(--muted); font-size: var(--text-caption-size); }
.dw-tour__prizename { font-weight: 700; overflow-wrap: anywhere; }
.dw-tour__prizego { flex: 0 0 auto; color: var(--accent-text); font-size: 20px; line-height: 1; }
.dw-tour__prizebox { margin-top: var(--space-3); }
/* 1st and 2nd prize side by side when there is room, one under the other on a phone or in a narrow card. */
.dw-tour__prizes { display: grid; grid-template-columns: repeat(auto-fit, minmax(min(100%, 200px), 1fr)); gap: var(--space-2); margin-top: auto; }
.dw-tour__prizes .dw-tour__prizeln { margin-top: 0; }
.dw-tour__prizebox.dw-tour__prizes { margin-top: var(--space-3); }
.dw-tour__info { position: relative; }
.dw-tour__stage { position: absolute; top: var(--space-3); right: var(--space-3); }
.dw-tour__dl { display: grid; grid-template-columns: max-content minmax(0, 1fr); gap: 6px var(--space-3); margin: 0; padding-right: 96px; }
.dw-tour__dl dt { color: var(--muted); font-size: var(--text-body-sm-size); padding-top: 1px; }
.dw-tour__dl dd { margin: 0; overflow-wrap: anywhere; }
.dw-tour__rule { display: block; color: var(--muted); font-size: var(--text-body-sm-size); }
.dw-tour__note { color: var(--muted); font-size: var(--text-body-sm-size); }
@media (max-width: 480px) { .dw-tour__dl { grid-template-columns: 92px minmax(0, 1fr); padding-right: 0; padding-top: 30px; } }
.dw-tour__champ { margin-top: var(--space-3); }
.dw-tour__act { display: grid; gap: var(--space-2); justify-items: start; }
.dw-tour__state, .dw-tour__hint { margin: 0; }
.dw-tour__hint { color: var(--muted); font-size: var(--text-body-sm-size); line-height: 1.5; }
.dw-tour__btns { display: flex; flex-wrap: wrap; gap: var(--space-2); }
.dw-tour__more { margin-top: var(--space-3); }
.dw-tour__who { display: inline-flex; align-items: center; gap: 4px; min-width: 0; overflow-wrap: anywhere; }
/* The level never splits ("[7" / "5]" on a phone); a long nick without spaces may still break, or it would run over the score. */
.dw-tour__who .dw-who__lvl { white-space: nowrap; }
.dw-tour__who .dw-fg__side-ico { flex: 0 0 16px; }
/* Nick and level are one run of text: as separate flex items the level broke off on its own line. */
.dw-tour__wn { min-width: 0; }
.dw-tour__who a { color: inherit; text-decoration: none; font-weight: 600; }
.dw-tour__who a:hover { color: var(--accent-text); }
.dw-tour__who--none { color: var(--muted); }
/* Qualification table: place, player, points, battles (a link to the player's battles in this tournament). */
.dw-row.dw-tour__trow { display: grid; grid-template-columns: 28px minmax(0, 1fr) 52px 52px; gap: var(--space-2); min-height: 40px; padding: 6px var(--space-3); }
.dw-row.dw-tour__trow:hover { background: var(--surface-2); color: var(--text); }
.dw-tour__trow--head { color: var(--muted); font-size: var(--text-caption-size); text-transform: uppercase; letter-spacing: .04em; min-height: 32px; }
.dw-tour__trow--me { background: var(--accent-soft); }
.dw-tour__n { color: var(--muted); font-variant-numeric: tabular-nums; text-align: right; }
.dw-row > .dw-tour__n:first-child { flex: 0 0 28px; }
.dw-tour__tnum { text-align: right; font-variant-numeric: tabular-nums; color: inherit; }
a.dw-tour__tnum { color: var(--accent-text); }
/* Play-off pair: player 1, score (or the word 'vs'), player 2; the pair's battles under it; the winner bold. */
.dw-row.dw-tour__pair { display: grid; grid-template-columns: minmax(0, 1fr) auto minmax(0, 1fr); gap: 4px var(--space-2); align-items: center; padding: 8px var(--space-3); }
.dw-row.dw-tour__pair:hover { background: var(--surface-2); color: var(--text); }
.dw-tour__pair--me { background: var(--accent-soft); }
.dw-tour__pside { min-width: 0; }
.dw-tour__pside--r { justify-self: end; text-align: right; }
.dw-tour__pside--win .dw-tour__who a { font-weight: 800; }
.dw-tour__pside:not(.dw-tour__pside--win) .dw-tour__who a { font-weight: 500; }
.dw-tour__score { color: var(--muted); font-size: var(--text-caption-size); font-variant-numeric: tabular-nums; white-space: nowrap; }
.dw-tour__plog { grid-column: 1 / -1; justify-self: center; color: var(--muted); font-size: var(--text-caption-size); }
/* Whole play-off on one page (owner: "the whole play-off can be shown"): rounds from the final down, each folds
   (details; over 16 pairs folded), a chip row jumps to a round. */
.dw-tour__jump { margin-bottom: var(--space-3); }
.dw-tour__rnd { margin-bottom: var(--space-3); scroll-margin-top: 72px; }
.dw-tour__rndsum { display: flex; align-items: baseline; gap: var(--space-2); padding: 6px 0; cursor: pointer; list-style: none; }
.dw-tour__rndsum::-webkit-details-marker { display: none; }
.dw-tour__rndsum::before { content: ""; flex: 0 0 auto; width: 0; height: 0; border-style: solid; border-width: 5px 0 5px 7px; border-color: transparent transparent transparent var(--muted); transform: translateY(-1px); transition: transform .15s; }
.dw-tour__rnd[open] > .dw-tour__rndsum::before { transform: translateY(-1px) rotate(90deg); }
.dw-tour__rndname { font-family: var(--font-display); font-size: var(--text-section-size); font-weight: var(--text-section-weight); letter-spacing: var(--text-section-tracking); }
.dw-tour__rndn { color: var(--muted); font-size: var(--text-caption-size); }
.dw-tour__rndsum:hover .dw-tour__rndname { color: var(--accent-text); }
.dw-tour__days > :first-child { justify-self: start; }
.dw-tour__days { display: grid; grid-template-columns: 1fr auto 1fr; align-items: center; gap: var(--space-2); margin-bottom: var(--space-3); }
.dw-tour__days > :last-child { justify-self: end; }
.dw-tour__round { font-weight: 700; text-align: center; }
.dw-tour__winner { display: flex; align-items: center; gap: var(--space-3); font-size: 18px; }
.dw-tour__urow { gap: var(--space-2); }
.dw-tour__rules { margin-top: var(--space-3); }
.dw-tour__rules .dw-notice__text + .dw-notice__text { margin-top: var(--space-2); }

/* ---- Hero Battles (olimp.php, 08.10) ----
   Main: the state card (in the queue with the waiting time / registration open / not today), links; the side column
   holds the two point balances and the week schedule with today marked. Shop rows: name, cost, buy. History: the result
   word coloured, the opponent, the points. */
.dw-olimp__now { display: grid; gap: var(--space-2); justify-items: start; }
.dw-olimp__state { margin: 0; font-weight: 600; }
.dw-olimp__wait { color: var(--muted); font-weight: 400; font-variant-numeric: tabular-nums; }
.dw-olimp__links { margin-top: var(--space-3); }
.dw-olimp__mypts { margin-bottom: var(--space-3); }
.dw-row.dw-olimp__weekhead { min-height: 32px; padding: 6px var(--space-3); color: var(--muted); font-size: var(--text-caption-size); text-transform: uppercase; letter-spacing: .04em; }
.dw-row.dw-olimp__weekhead:hover { background: none; color: var(--muted); }
/* Main page: blocks in pairs ("now - points" one height, "links - schedule" from one line); the phone keeps the order
   now, links, points, schedule. */
.dw-olimp--main > .dw-mail__main, .dw-olimp--main > .dw-mail__tools { display: contents; }
.dw-olimp--main { grid-template-areas: "now" "links" "pts" "week"; }
.dw-olimp--main .dw-olimp__now { grid-area: now; }
.dw-olimp--main .dw-olimp__links { grid-area: links; margin-top: 0; }
.dw-olimp--main .dw-olimp__mypts { grid-area: pts; margin: 0; }
.dw-olimp--main .dw-olimp__week { grid-area: week; }
.dw-olimp--main > .dw-mail__main > *, .dw-olimp--main > .dw-mail__tools > * { margin-top: 0; margin-bottom: 0; }
@media (min-width: 1000px) {
  .dw-olimp--main { grid-template-areas: "now pts" "links week"; }
  .dw-olimp--main .dw-olimp__now, .dw-olimp--main .dw-olimp__mypts { align-self: stretch; }
}
.dw-olimp__herorow { background: var(--accent-soft); }
.dw-row.dw-olimp__mainrow { background: var(--accent-soft); font-weight: 700; color: var(--text); }
.dw-row.dw-olimp__mainrow .dw-row__icon { color: var(--accent-text); }
.dw-row.dw-olimp__mainrow .dw-row__cap { font-weight: 400; }
.dw-row.dw-olimp__mainrow:hover { background: var(--surface-2); }
/* Point figures in one low card, side by side (owner: the bubbles were tall - put the info in a line). */
.dw-olimp__pts { display: flex; flex-wrap: wrap; gap: var(--space-2) var(--space-5); padding-top: 10px; padding-bottom: 10px; }
.dw-olimp__stats { margin-bottom: var(--space-3); }
.dw-olimp__pt { display: flex; flex-direction: column; gap: 0; min-width: 0; }
.dw-olimp__pt span { color: var(--muted); font-size: var(--text-caption-size); }
.dw-olimp__pt b { font-size: 20px; line-height: 1.2; font-variant-numeric: tabular-nums; }
.dw-olimp__pt small { color: var(--muted); font-size: var(--text-caption-size); }
.dw-olimp__stat { display: flex; flex-direction: column; gap: 2px; }
.dw-olimp__stat span { color: var(--muted); font-size: var(--text-caption-size); }
.dw-olimp__stat b { font-size: 22px; font-variant-numeric: tabular-nums; }
.dw-olimp__stat small { color: var(--muted); font-size: var(--text-caption-size); }
.dw-row.dw-olimp__day { min-height: 38px; padding: 6px var(--space-3); }
.dw-row.dw-olimp__day:hover { background: none; color: var(--text); }
.dw-olimp__day--today { background: var(--accent-soft); font-weight: 600; }
.dw-row.dw-olimp__day--today:hover { background: var(--accent-soft); }
.dw-olimp__day--off { color: var(--muted); }
.dw-olimp__dayt { flex: 0 0 auto; font-variant-numeric: tabular-nums; }
.dw-olimp__side { margin-top: var(--space-3); }
.dw-olimp__info { display: grid; gap: var(--space-2); line-height: 1.5; }
.dw-olimp__info p, .dw-olimp__info ul { margin: 0; }
.dw-olimp__info ul { padding-left: 20px; display: grid; gap: 4px; }
.dw-olimp__h { font-weight: 700; margin-top: var(--space-2) !important; }
.dw-olimp__bal { display: flex; align-items: baseline; justify-content: space-between; gap: var(--space-3); margin-bottom: var(--space-3); }
.dw-olimp__bal span { color: var(--muted); }
.dw-olimp__bal b { font-size: 22px; font-variant-numeric: tabular-nums; }
.dw-olimp__item { gap: var(--space-3); }
.dw-row > .dw-olimp__iname:first-child { flex: 1 1 auto; min-width: 0; }
.dw-olimp__iname { color: var(--text); font-weight: 600; text-decoration: none; overflow-wrap: anywhere; }
.dw-olimp__iname:hover { color: var(--accent-text); }
.dw-olimp__cost { flex: 0 0 auto; color: var(--muted); font-variant-numeric: tabular-nums; white-space: nowrap; }
.dw-olimp__buy { flex: 0 0 auto; display: inline-flex; align-items: center; gap: var(--space-2); white-space: nowrap; }
.dw-olimp__off { opacity: .55; cursor: default; }
.dw-olimp__lead { margin: 0 0 var(--space-3); color: var(--muted); font-size: var(--text-body-sm-size); line-height: 1.5; }
.dw-olimp__classes { margin-bottom: var(--space-3); }
.dw-olimp__ask { display: grid; gap: var(--space-3); }
.dw-olimp__ask .dw-notice__acts { margin-top: 0; }
.dw-olimp__asktitle { margin: 0; font-weight: 700; font-size: 18px; }
/* Rating as a one-line table (owner: "the bubbles are tall on the phone and on the desktop, and wide - put the info in one
   line with a lower bubble"): place, player, points, wins of bouts in columns under a header. */
.dw-row.dw-olimp__rrow { display: grid; grid-template-columns: 28px minmax(0, 1fr) 48px 68px; gap: var(--space-2); min-height: 40px; padding: 6px var(--space-3); }
.dw-row.dw-olimp__rrow:hover { background: var(--surface-2); color: var(--text); }
.dw-olimp__rrow--head { min-height: 32px; color: var(--muted); font-size: var(--text-caption-size); text-transform: uppercase; letter-spacing: .04em; }
.dw-row.dw-olimp__rrow--head:hover { background: none; color: var(--muted); }
.dw-olimp__rwho { min-width: 0; }
.dw-olimp__rnum { text-align: right; font-variant-numeric: tabular-nums; white-space: nowrap; }
.dw-olimp__rsub { color: var(--muted); font-size: var(--text-caption-size); }
.dw-olimp__rrow--top { background: var(--accent-soft); }
.dw-row.dw-olimp__rrow--top:hover { background: var(--accent-soft); }
.dw-olimp__rrow--me { box-shadow: inset 3px 0 0 var(--accent); }
.dw-row.dw-olimp__hrow { gap: var(--space-3); }
.dw-row > .dw-olimp__hres:first-child { flex: 0 0 92px; }
.dw-olimp__hres { font-weight: 700; font-size: var(--text-body-sm-size); }
.dw-olimp__hres--win { color: var(--ok-text); }
.dw-olimp__hres--lose { color: var(--danger-text); }
.dw-olimp__hres--draw { color: var(--muted); }
/* One line: the opponent and the time side by side (wraps only when the row is too narrow). */
.dw-olimp__hmain { flex: 1 1 auto; min-width: 0; display: flex; flex-wrap: wrap; align-items: baseline; gap: 2px var(--space-3); }
.dw-olimp__hvs { min-width: 0; }
.dw-olimp__hdate { color: var(--muted); font-size: var(--text-caption-size); font-variant-numeric: tabular-nums; white-space: nowrap; }
.dw-row.dw-olimp__hrow { min-height: 40px; padding-top: 6px; padding-bottom: 6px; }
.dw-olimp__hpts { flex: 0 0 auto; font-weight: 700; font-variant-numeric: tabular-nums; }

/* ===== Battle screen (battle_group.php, block battleGroup, 08.10) =====
   Phone: score, me | foe side by side, action card, log, teams, facts, chat.
   Desktop (>= 1000px): me | action | foe in one row of equal height (combats.ru layout), below log | side column.
   Antibot traps (DW-TRAPS) are hidden by their own inline style: no display rules with !important here. */
.dw-bt { display: grid; gap: var(--space-3); max-width: 1400px; }
.dw-bt > *, .dw-bt__duel > *, .dw-bt__lower > *, .dw-bt__side > * { margin: 0; min-width: 0; }
.dw-bt .dw-card + .dw-card, .dw-bt .dw-card + .dw-notice, .dw-bt .dw-notice + .dw-card, .dw-bt .dw-notice + .dw-notice { margin-top: 0; }
.dw-bt__head { flex-wrap: nowrap; gap: 4px var(--space-3); }
.dw-bt__head .dw-mail__title { flex: 1 1 auto; min-width: 0; margin-right: auto; font-size: 21px; }
.dw-bt__head .dw-btn { flex: 0 0 auto; }
.dw-bt__turn { color: var(--muted); font-size: var(--text-body-sm-size); font-variant-numeric: tabular-nums; }
.dw-bt__mail { margin: 0; }
.dw-bt__score { margin: 0; }
.dw-bt__duel { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); grid-template-areas: "me foe" "act act" "fx fx"; gap: var(--space-2) var(--space-3); }
.dw-bt__mecol { display: contents; }
.dw-bt__fx { grid-area: fx; display: flex; flex-wrap: wrap; align-content: flex-start; gap: 4px; }
.dw-bt__fx > .dw-section { flex: 0 0 100%; margin: 0 0 2px; }
.dw-bt__fx .dw-bt__effects { display: contents; }
.dw-bt__me { grid-area: me; }
.dw-bt__foe { grid-area: foe; }
.dw-bt__act { grid-area: act; }
.dw-bt__me, .dw-bt__foe { display: grid; grid-template-columns: 36px minmax(0, 1fr); align-content: start; gap: 6px 8px; min-height: 112px; padding: 8px 10px; }
.dw-bt__duel--solo { grid-template-columns: minmax(0, 1fr); grid-template-areas: "act" "fx"; }
.dw-bt__foe { border-color: var(--danger-line); }
.dw-bt__pic { position: relative; display: flex; align-items: flex-start; justify-content: center; width: 36px; height: 54px; overflow: hidden; border-radius: var(--radius-sm); background: var(--sunken); }
.dw-bt__pic picture { display: contents; }
.dw-bt__pic img { display: block; width: 100%; height: auto; }
.dw-bt__pic img + img { display: none; }
.dw-bt__ghost { width: 64%; height: auto; margin-top: 8%; fill: var(--line-strong); }
.dw-bt__pic--mon .dw-bt__ghost { position: absolute; top: 6%; left: 18%; width: 64%; margin: 0; }
.dw-bt__pic--mon .dw-bt__img { position: relative; z-index: 1; width: 100%; height: 100%; object-fit: contain; object-position: 50% 100%; }
.dw-bt__pic--t2::after, .dw-bt__pic--t3::after, .dw-bt__pic--t4::after { content: ""; position: absolute; inset: 0; z-index: 2; border: 2px solid var(--drop-2); border-radius: inherit; pointer-events: none; }
.dw-bt__pic--t3::after { border-color: var(--drop-4); }
.dw-bt__pic--t4::after { border-color: var(--drop-5); }
/* player picture: side frame (owner 13.10: monsters are framed, players are not) - Templars blue, Dreadnoughts orange */
.dw-bt__pic--s1::after, .dw-bt__pic--s2::after { content: ""; position: absolute; inset: 0; z-index: 2; border: 2px solid #3d7be0; border-radius: inherit; pointer-events: none; }
.dw-bt__pic--s2::after { border-color: #e8780f; }
.dw-bt__tier { position: absolute; bottom: 6px; left: 50%; z-index: 3; display: none; padding: 1px 8px; border-radius: var(--radius-pill); background: var(--surface); color: var(--muted); font-size: 10px; font-weight: 700; letter-spacing: .05em; text-transform: uppercase; transform: translateX(-50%); }
.dw-bt__pic--t2 .dw-bt__tier { color: var(--drop-2); }
.dw-bt__pic--t3 .dw-bt__tier { color: var(--drop-4); }
.dw-bt__pic--t4 .dw-bt__tier { color: var(--drop-5); }
.dw-bt__who { display: grid; gap: 4px; min-width: 0; align-content: start; }
/* name and level are one run of text: the level follows the last word ("... warrior / of death [50]"), long names wrap
   by words, a single long word breaks; nothing is cut off (owner 10.10) */
.dw-bt__name { display: block; margin: 0; min-width: 0; line-height: 1.25; overflow-wrap: anywhere; }
.dw-bt__name b { font-weight: 600; }
.dw-bt__name .dw-who__lvl { margin-left: 4px; white-space: nowrap; }
@media (max-width: 420px) { .dw-bt__name { font-size: 13px; } }
.dw-bt__name a { color: inherit; }
.dw-bt__tag { display: block; color: var(--muted); font-size: 10.5px; font-weight: 700; letter-spacing: .06em; text-transform: uppercase; }
.dw-bt__tag--foe { color: var(--danger-text); }
.dw-bt__bars { display: grid; gap: 3px; }
.dw-bt__barrow { display: flex; align-items: baseline; justify-content: space-between; gap: 4px; margin: 0; color: var(--muted); font-size: 11.5px; font-variant-numeric: tabular-nums; white-space: nowrap; }
.dw-bt__barrow b { color: var(--text); font-weight: 600; }
.dw-bt__blab { font-size: 10.5px; font-weight: 700; letter-spacing: .05em; }
.dw-bt__bar { display: block; height: 6px; overflow: hidden; border-radius: var(--radius-pill); background: var(--line-2); }
.dw-bt__bar > i { display: block; height: 100%; border-radius: inherit; background: var(--ok); }
.dw-bt__bar--mid > i { background: var(--accent); }
.dw-bt__bar--low > i { background: var(--alert); }
.dw-bt__bar--mp > i { background: var(--mana); }
.dw-bt__effects { grid-column: 1 / -1; display: flex; flex-wrap: wrap; gap: 4px; margin: 0; padding: 0; list-style: none; }
.dw-bt__ef, .dw-bt__efx { display: inline-flex; align-items: baseline; gap: 4px; margin: 0; padding: 2px 8px; border: 1px solid var(--quest-ready-line); border-radius: var(--radius-pill); background: var(--quest-ready); font-size: 12px; line-height: 1.35; }
.dw-bt__efx { grid-column: 1 / -1; justify-self: start; }
.dw-bt__ef--bad { border-color: var(--danger-line); background: var(--danger-soft); }
.dw-bt__ef small, .dw-bt__efx small { color: var(--muted); font-size: 11px; }
.dw-bt__foe > .dw-bt__state, .dw-bt__foe > .dw-shop__note { grid-column: 1 / -1; }
.dw-bt__foe > .dw-bt__state { font-size: 16px; }
.dw-bt__dmg { grid-column: 1 / -1; display: flex; align-items: baseline; justify-content: space-between; gap: 6px; margin: 0; color: var(--muted); font-size: 12px; white-space: nowrap; }
.dw-bt__dmg b { color: var(--danger-text); font-size: 13px; font-variant-numeric: tabular-nums; }
.dw-bt__tagready { color: var(--accent-text); }
.dw-bt__ready { display: none; grid-column: 1 / -1; margin: 0; padding: 3px 8px; border-radius: var(--radius-sm); background: var(--accent-soft); color: var(--accent-text); font-size: 12px; font-weight: 600; line-height: 1.3; }
.dw-bt__log .dw-col__line:first-child { border-color: var(--accent); box-shadow: inset 3px 0 0 var(--accent); }
.dw-bt__queue { grid-column: 1 / -1; justify-self: stretch; min-width: 0; max-width: 100%; margin: 0; overflow: hidden; color: var(--muted); font-size: 12px; text-overflow: ellipsis; white-space: nowrap; }
.dw-bt__me > *, .dw-bt__foe > * { max-width: 100%; }
.dw-bt__queue span { font-weight: 600; }
/* action card */
.dw-bt__act { display: grid; align-content: start; gap: var(--space-3); }
.dw-bt--turn .dw-bt__act { border-color: var(--accent); box-shadow: 0 0 0 1px var(--accent-soft); }
.dw-bt__form, .dw-bt__form > .block { display: block; margin: 0; padding: 0; border: 0; background: none; }
.dw-bt__formin { display: grid; gap: var(--space-4); }
.dw-bt__warn { margin: 0; }
.dw-bt__state { margin: 0; font-family: var(--font-display); font-size: 20px; line-height: 1.2; }
.dw-bt__state b { font-family: var(--font-body); font-variant-numeric: tabular-nums; }
.dw-bt__chg { display: flex; flex-wrap: wrap; align-items: center; gap: 6px var(--space-3); margin: 0; }
.dw-bt__pick { max-width: 420px; }
.dw-bt__zonesets { display: grid; gap: var(--space-4); }
.dw-bt__zones { display: grid; grid-template-columns: 56px minmax(0, 1fr); align-items: center; gap: var(--space-2) var(--space-3); }
.dw-bt__zlab { grid-column: 1 / -1; display: flex; align-items: baseline; flex-wrap: nowrap; gap: 2px 8px; margin: 0; color: var(--muted); font-family: var(--text-section-family); font-size: var(--text-section-size); letter-spacing: var(--text-section-tracking); text-transform: uppercase; }
.dw-bt__zlab b { min-width: 0; max-width: 100%; overflow: hidden; color: var(--text); font-family: var(--font-body); font-size: var(--text-body-sm-size); font-weight: 600; letter-spacing: 0; text-overflow: ellipsis; text-transform: none; white-space: nowrap; }
.dw-bt__fwrap { position: relative; width: 56px; }
.dw-bt__fig { display: block; width: 56px; height: 112px; }
.dw-bt__body { fill: var(--surface-2); stroke: var(--line-strong); stroke-width: 1.4; stroke-linejoin: round; }
.dw-bt__zn { fill: transparent; transition: fill .12s; }
.dw-bt__zsep { fill: none; stroke: var(--line-strong); stroke-width: .8; stroke-dasharray: 2 2; }
.dw-bt__hit { position: absolute; left: 0; right: 0; cursor: pointer; }
.dw-bt__hit--1 { top: 0; height: 17.97%; }
.dw-bt__hit--2 { top: 17.97%; height: 21.09%; }
.dw-bt__hit--3 { top: 39.06%; height: 21.09%; }
.dw-bt__hit--4 { top: 60.16%; height: 39.84%; }
.dw-bt__opts { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 6px; min-width: 0; }
.dw-bt__opt, .dw-bt__sk { position: relative; display: block; min-width: 0; }
.dw-bt__opt input, .dw-bt__sk input { position: absolute; top: 0; left: 0; width: 1px; height: 1px; margin: 0; opacity: 0; pointer-events: none; }
.dw-bt__opt span { display: flex; align-items: center; justify-content: center; min-height: 44px; padding: 4px 8px; border: 1px solid var(--line-strong); border-radius: var(--radius-md); background: var(--surface); color: var(--text); font-size: var(--text-body-sm-size); font-weight: 500; line-height: 1.2; text-align: center; cursor: pointer; transition: background .12s, border-color .12s, color .12s; -webkit-user-select: none; user-select: none; }
.dw-bt__opt span:hover, .dw-bt__sk:not(.dw-bt__sk--off) > span:hover { border-color: var(--accent); }
.dw-bt__opt input:focus-visible + span, .dw-bt__sk input:focus-visible + span { outline: 2px solid var(--accent); outline-offset: 2px; }
.dw-bt__zones--at .dw-bt__opt input:checked + span { border-color: var(--alert); background: var(--alert); color: var(--alert-on); }
.dw-bt__zones--df .dw-bt__opt input:checked + span { border-color: var(--team1); background: var(--team1); color: var(--bg); }
.dw-bt__zones--at:has(input[value="1"]:checked) .dw-bt__zn--1,
.dw-bt__zones--at:has(input[value="2"]:checked) .dw-bt__zn--2,
.dw-bt__zones--at:has(input[value="3"]:checked) .dw-bt__zn--3,
.dw-bt__zones--at:has(input[value="4"]:checked) .dw-bt__zn--4 { fill: var(--alert); }
.dw-bt__zones--df:has(input[value="1"]:checked) .dw-bt__zn--1,
.dw-bt__zones--df:has(input[value="1"]:checked) .dw-bt__zn--2,
.dw-bt__zones--df:has(input[value="2"]:checked) .dw-bt__zn--2,
.dw-bt__zones--df:has(input[value="2"]:checked) .dw-bt__zn--3,
.dw-bt__zones--df:has(input[value="3"]:checked) .dw-bt__zn--3,
.dw-bt__zones--df:has(input[value="3"]:checked) .dw-bt__zn--4,
.dw-bt__zones--df:has(input[value="4"]:checked) .dw-bt__zn--1,
.dw-bt__zones--df:has(input[value="4"]:checked) .dw-bt__zn--4 { fill: var(--team1); }
.dw-bt__skills, .dw-bt__scroll { display: grid; gap: var(--space-2); }
.dw-bt__skills > .dw-shop__note, .dw-bt__scroll > .dw-shop__note { font-size: var(--text-caption-size); }
.dw-bt__sklist, .dw-bt__belt { display: grid; grid-template-columns: repeat(auto-fill, minmax(165px, 1fr)); gap: 6px; }
.dw-bt__sk, .dw-bt__sc { position: relative; display: grid; min-width: 0; }
.dw-bt__sc input { position: absolute; top: 0; left: 0; width: 1px; height: 1px; margin: 0; opacity: 0; pointer-events: none; }
.dw-bt__sk > span, .dw-bt__sc > span { display: flex; align-items: center; gap: 8px; min-height: 48px; padding: 5px 10px 5px 6px; border: 1px solid var(--line-strong); border-radius: var(--radius-md); background: var(--surface); cursor: pointer; transition: background .12s, border-color .12s; -webkit-user-select: none; user-select: none; }
.dw-bt__skt { display: grid; gap: 1px; min-width: 0; }
.dw-bt__skt b { font-size: 13.5px; font-weight: 600; line-height: 1.2; overflow-wrap: break-word; -webkit-hyphens: auto; hyphens: auto; }
.dw-bt__skt small { color: var(--muted); font-size: 11.5px; line-height: 1.2; font-variant-numeric: tabular-nums; }
.dw-bt__sk .dw-sk__ico { flex: 0 0 36px; width: 36px; height: 36px; }
.dw-bt__sk .dw-sk__pic { border-radius: 6px; }
.dw-bt__sk .dw-sk__lv { right: -3px; bottom: -3px; padding: 0 3px; font-size: 9px; line-height: 13px; }
.dw-bt__scimg { flex: 0 0 32px; width: 32px; height: 32px; object-fit: contain; }
.dw-bt__sc > span { padding-left: 10px; cursor: pointer; border: 1px solid var(--line-strong); border-radius: var(--radius-md); background: var(--surface); }
.dw-bt__sc > span:hover { border-color: var(--accent); }
.dw-bt__sc input:checked + span { border-color: var(--accent); background: var(--accent-soft); box-shadow: inset 0 0 0 1px var(--accent); }
.dw-bt__sc input:focus-visible + span { outline: 2px solid var(--accent); outline-offset: 2px; }
.dw-bt__form--scroll .dw-bt__sklist { opacity: .5; }
.dw-bt__mpnote { color: var(--accent-text); }
.dw-bt__sk input:checked + span { border-color: var(--accent); background: var(--accent-soft); box-shadow: inset 0 0 0 1px var(--accent); }
.dw-bt__sk input:checked + span .dw-bt__skt b::before { content: "\2713\00a0"; color: var(--accent-text); }
.dw-bt__sk--on > span { border-color: var(--accent); background: var(--accent-soft); cursor: default; }
.dw-bt__sk--on small { color: var(--accent-text); }
.dw-bt__sk--off > span { border-style: dashed; cursor: default; }
.dw-bt__sk--off .dw-sk__ico, .dw-bt__sk--off b { opacity: .55; }
/* folds (09.10, a player: "to pick a skill on the phone I have to scroll", "the belt scrolls were hidden in the old
   version"): ready skills stay in sight; charged / cooldown / no-MP ones fold under "other skills" (open on a
   computer by the script), the belt folds under "belt" (open state remembered; open when a scroll is picked).
   Controls in a closed fold are still sent with the form; the belt default is "no scroll". */
.dw-bt__skoff, .dw-bt__beltbox { display: grid; gap: var(--space-2); }
.dw-bt__skoffsum, .dw-bt__beltsum { display: flex; align-items: center; gap: 4px 8px; min-height: 36px; color: var(--muted); font-size: var(--text-body-sm-size); font-weight: 600; list-style: none; cursor: pointer; -webkit-user-select: none; user-select: none; }
.dw-bt__skoffsum::-webkit-details-marker, .dw-bt__beltsum::-webkit-details-marker { display: none; }
.dw-bt__skoffsum::after, .dw-bt__beltsum::after { content: "\203A"; margin-left: auto; color: var(--dim); font-size: 18px; line-height: 1; transform: rotate(90deg); transition: transform .15s ease; }
.dw-bt__skoff[open] > .dw-bt__skoffsum::after, .dw-bt__beltbox[open] > .dw-bt__beltsum::after { transform: rotate(-90deg); }
.dw-bt__skoffsum:hover, .dw-bt__beltsum:hover { color: var(--accent-text); }
.dw-bt__beltsum { color: var(--text); font-family: var(--text-section-family); font-size: var(--text-section-size); font-weight: 400; letter-spacing: var(--text-section-tracking); text-transform: uppercase; }
.dw-bt__beltsum small { color: var(--muted); font-family: var(--font-body); font-size: var(--text-caption-size); letter-spacing: 0; text-transform: none; }
.dw-bt__beltbox:has(input[name="tid"]:checked:not([value="0"])) > .dw-bt__beltsum { color: var(--accent-text); }
@media (prefers-reduced-motion: reduce) { .dw-bt__skoffsum::after, .dw-bt__beltsum::after { transition: none; } }
@media (max-width: 999px) {
  /* owner 13.10: the team health board goes below the action card, so zones and skills fit one phone screen */
  .dw-bt > * { order: 2; }
  .dw-bt > .dw-bt__mail, .dw-bt > .dw-bt__boss { order: 0; }
  .dw-bt > .dw-bt__duel { order: 1; }
  .dw-bt__me > .dw-bt__pic, .dw-bt__foe > .dw-bt__pic { align-self: center; }
  .dw-bt__formin { gap: var(--space-3); }
  .dw-bt__zonesets { gap: var(--space-3); }
  .dw-bt__zones { grid-template-columns: minmax(0, 1fr); gap: 6px; }
  .dw-bt__fwrap { display: none; }
  .dw-bt__zones--at .dw-bt__opts { grid-template-columns: repeat(4, minmax(0, 1fr)); }
  .dw-bt__opts { gap: 5px; }
  .dw-bt__opt span { min-height: 40px; padding: 4px; font-size: 13px; }
  .dw-bt__mphint { display: none; }
  .dw-bt__sklist, .dw-bt__belt { grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 5px; }
  .dw-bt__sk > span, .dw-bt__sc > span { gap: 6px; min-height: 44px; padding: 4px 6px 4px 4px; }
  .dw-bt__sc > span { padding-left: 8px; }
  .dw-bt__sk .dw-sk__ico { flex: 0 0 30px; width: 30px; height: 30px; }
  .dw-bt__scimg { flex: 0 0 28px; width: 28px; height: 28px; }
  .dw-bt__skt b { font-size: 13px; }
  .dw-bt__skt small { font-size: 11px; }
  .dw-bt__hitbtn { min-height: 48px; }
}
.dw-bt__go { position: sticky; bottom: calc(var(--tab-height) + env(safe-area-inset-bottom, 0px) + 8px); z-index: 2; display: grid; margin: 0 -4px; padding: 6px 4px 0; border-radius: var(--radius-md); background: var(--surface); }
.dw-bt__zonesets--off .dw-bt__opt span { cursor: default; opacity: .6; }
.dw-bt__zonesets--off .dw-bt__opt span:hover { border-color: var(--line-strong); }
.dw-bt__zonesets--off .dw-bt__zn { opacity: .6; }
.dw-bt__state--wait { font-size: 17px; }
.dw-bt__chgbtn { flex: 0 0 auto; margin-left: auto; padding: 3px 10px; border: 1px solid var(--line-strong); border-radius: var(--radius-pill); color: var(--text); font-family: var(--font-body); font-size: 12px; font-weight: 600; letter-spacing: 0; text-transform: none; white-space: nowrap; }
.dw-bt__chgbtn:hover { border-color: var(--accent); color: var(--accent-text); }
.dw-bt__hitbtn { width: 100%; min-height: 52px; font-size: 18px; letter-spacing: .02em; }
.dw-bt__hitbtn[disabled] { opacity: .7; cursor: progress; }
.dw-bt__key { display: none; }
@media (min-width: 1000px) and (hover: hover) {
  .dw-bt__key { display: inline-block; margin-left: 8px; padding: 0 5px; border: 1px solid currentColor; border-radius: 4px; font-size: 11px; font-weight: 600; line-height: 16px; opacity: .55; }
  .dw-bt__hitbtn .dw-bt__key { font-size: 12px; line-height: 18px; }
}
.dw-bt__radio { display: flex; align-items: center; gap: 8px; min-height: 36px; }
fieldset.dw-bt__who { display: grid; gap: 2px; margin: 0; padding: 0; border: 0; }
/* lower part: log, teams, facts, chat */
.dw-bt__lower { display: grid; gap: var(--space-3); }
.dw-bt__side { display: grid; align-content: start; gap: var(--space-3); }
.dw-bt__log .dw-col__lines { margin: 0; }
.dw-bt__team + .dw-bt__team { margin-top: var(--space-3); padding-top: var(--space-3); border-top: 1px solid var(--line-2); }
.dw-bt__fighters { display: grid; gap: 8px; margin: 0; padding: 0; list-style: none; }
.dw-bt__f { display: grid; grid-template-columns: minmax(0, 1fr) auto; align-items: start; gap: 3px 8px; }
.dw-bt__fhp { padding-top: 1px; }
.dw-bt__fwho { display: flex; flex-wrap: wrap; align-items: center; gap: 4px; min-width: 0; }
.dw-bt__fnick { overflow-wrap: anywhere; }
.dw-bt__fhp { color: var(--text); font-size: 13px; font-variant-numeric: tabular-nums; white-space: nowrap; }
.dw-bt__fhp small { color: var(--muted); font-size: 11px; }
.dw-bt__f .dw-bt__bar { grid-column: 1 / -1; height: 4px; }
.dw-bt__f--out { opacity: .55; }
.dw-bt__f--out .dw-bt__fhp { color: var(--muted); }
.dw-bt__f--me .dw-bt__fnick { color: var(--accent-text); font-weight: 600; }
.dw-bt__f--foe { margin: 0 -6px; padding: 4px 6px; border-radius: var(--radius-sm); background: var(--danger-soft); }
.dw-mark--foe { border-color: var(--danger-line); color: var(--danger-text); }
.dw-bt__kv { display: grid; gap: 5px; margin: 0; }
.dw-bt__kv > div { display: flex; align-items: baseline; justify-content: space-between; gap: var(--space-3); }
.dw-bt__kv dt { color: var(--muted); font-size: var(--text-body-sm-size); }
.dw-bt__kv dd { margin: 0; font-weight: 600; font-variant-numeric: tabular-nums; text-align: right; white-space: nowrap; }
.dw-bt__facts .dw-shop__acts { margin-top: var(--space-3); }
/* world boss */
.dw-bt__boss { display: grid; grid-template-columns: repeat(3, minmax(0, 1fr)); gap: var(--space-2); text-align: center; }
.dw-bt__bossrow { display: grid; gap: 2px; margin: 0; }
.dw-bt__bossrow span { color: var(--muted); font-size: 12px; }
.dw-bt__bossrow b { font-size: 20px; font-variant-numeric: tabular-nums; }
.dw-bt__bossnote { grid-column: 1 / -1; margin: 0; color: var(--muted); font-size: 12px; }
/* battle over */
.dw-bt__result { display: grid; justify-items: center; gap: var(--space-3); padding: var(--space-5) var(--space-4); text-align: center; }
.dw-bt__rtitle { margin: 0; font-family: var(--font-display); font-size: 36px; line-height: 1.1; }
.dw-bt__result--win { border-color: var(--accent); background: linear-gradient(180deg, var(--accent-soft), var(--surface) 75%); }
.dw-bt__result--win .dw-bt__rtitle { color: var(--accent-text); }
.dw-bt__result--lose { border-color: var(--danger-line); }
.dw-bt__result--lose .dw-bt__rtitle { color: var(--danger-text); }
.dw-bt__rnote { margin: 0; color: var(--muted); }
.dw-bt__gain { display: flex; flex-wrap: wrap; justify-content: center; gap: var(--space-2); margin: 0; }
.dw-bt__gain > div { min-width: 120px; padding: 8px 14px; border: 1px solid var(--line); border-radius: var(--radius-md); background: var(--surface-2); }
.dw-bt__gain dt { color: var(--muted); font-size: 12px; }
.dw-bt__gain dd { margin: 0; font-size: 22px; font-weight: 700; font-variant-numeric: tabular-nums; }
.dw-bt__minus { color: var(--danger-text); }
.dw-bt__result .dw-shop__acts { justify-content: center; }
.dw-bt__mlist { display: grid; gap: var(--space-2); margin: 0; padding: 0; list-style: none; }
.dw-bt__mrow { display: grid; grid-template-columns: minmax(0, 1fr) auto; gap: 3px 8px; align-items: baseline; }
.dw-bt__mname { font-weight: 600; overflow-wrap: anywhere; }
.dw-bt__mstep { color: var(--muted); font-size: var(--text-body-sm-size); text-align: right; }
.dw-bt__mstep b { color: var(--accent-text); }
.dw-bt__mbar { grid-column: 1 / -1; display: block; height: 4px; overflow: hidden; border-radius: var(--radius-pill); background: var(--line-2); }
.dw-bt__mbar > i { display: block; height: 100%; background: var(--accent); }
@media (min-width: 1000px) {
  .dw-bt__head .dw-mail__title { font-size: var(--text-h1-size); }
  .dw-bt__duel { grid-template-columns: minmax(190px, 240px) minmax(0, 1fr) minmax(190px, 240px); grid-template-areas: "me act foe"; gap: var(--space-3); }
  .dw-bt__mecol { grid-area: me; display: flex; flex-direction: column; gap: var(--space-3); min-width: 0; }
  .dw-bt__mecol > * { margin: 0; }
  .dw-bt__mecol > .dw-bt__me { flex: 1 1 auto; }
  .dw-bt__fx { justify-content: center; }
  .dw-bt__name b { white-space: normal; overflow-wrap: anywhere; }
  .dw-bt__me, .dw-bt__foe { grid-template-columns: minmax(0, 1fr); justify-items: center; gap: var(--space-2); min-height: 0; padding: var(--space-3); text-align: center; }
  .dw-bt__pic { width: 150px; height: 225px; border-radius: var(--radius-md); }
  .dw-bt__barrow { font-size: 12px; }
  .dw-bt__pic--mon { background: radial-gradient(ellipse at 50% 40%, var(--surface-2), var(--sunken)); }
  .dw-bt__tier { display: block; }
  .dw-bt__ready { display: block; }
  .dw-bt__tagready { display: none; }
  .dw-bt__who { width: 100%; }
  .dw-bt__name { justify-content: center; }
  .dw-bt__queue { display: -webkit-box; white-space: normal; -webkit-box-orient: vertical; -webkit-line-clamp: 3; line-clamp: 3; }
  .dw-bt__effects { justify-content: center; }
  .dw-bt__efx { justify-self: center; }
  .dw-bt__act { padding: var(--space-4); }
  .dw-bt__zonesets { grid-template-columns: repeat(2, minmax(0, 1fr)); gap: var(--space-4) var(--space-5); }
  .dw-bt__zones--df { order: -1; }
  .dw-bt__zones--df { grid-template-columns: 56px minmax(0, 250px); justify-content: start; }
  .dw-bt__zones--at { grid-template-columns: minmax(0, 250px) 56px; justify-content: end; }
  .dw-bt__duel--solo { grid-template-columns: minmax(0, 1fr); grid-template-areas: "act"; }
  .dw-bt__zones--at .dw-bt__fwrap { order: 2; }
  .dw-bt__zones--at .dw-bt__zlab { justify-content: flex-end; }
  .dw-bt__opts { grid-template-columns: minmax(0, 1fr); gap: 5px; }
  .dw-bt__opt span { min-height: 38px; }
  .dw-bt__dmg { justify-content: center; gap: 8px; }
  .dw-bt__lower { grid-template-columns: minmax(0, 1fr) minmax(300px, 380px); align-items: start; }
  .dw-bt__go { bottom: 12px; }
}

/* ===== Castle and tower (world/castle.php, world/tower.php, world/build.php, 12.10) =====
   Owner: "castle and tower". The castle page is many states on one controller (list, card, castle on the
   player's cell, management, clan warehouse, dungeon); the tower page is a list, a card and a teleport. Built
   from the common parts (cards, rows, tiles, kv, notices); this block only lays out the castle picture next to
   the facts, the list rows (side, colored name, level, clan) and the side-bonus grid. */
.dw-ct { display: grid; gap: var(--space-3); }
.dw-ct > * { margin: 0; }
.dw-ct__hero { display: grid; grid-template-columns: 112px minmax(0, 1fr); align-items: start; gap: var(--space-3); }
.dw-ct__hero:has(.dw-ct__pic[hidden]) { grid-template-columns: minmax(0, 1fr); }
.dw-ct__pic { display: block; width: 112px; height: auto; aspect-ratio: 170 / 140; border: 1px solid var(--line); border-radius: var(--radius-md); background: var(--surface-2); object-fit: cover; }
.dw-ct__info { grid-column: 1 / -1; margin: 0; color: var(--muted); font-size: var(--text-body-sm-size); overflow-wrap: anywhere; }
.dw-ct__row, .dw-ct__urow, .dw-ct__brow, .dw-ct__wrow { align-items: center; gap: 8px; }
.dw-ct__row--live { box-shadow: inset 3px 0 0 var(--accent); }
.dw-ct__main { display: grid; flex: 1 1 auto; gap: 2px; min-width: 0; }
.dw-ct__name { display: flex; flex-wrap: wrap; align-items: center; gap: 2px 6px; min-width: 0; font-weight: 600; overflow-wrap: anywhere; }
.dw-ct__meta { display: flex; flex-wrap: wrap; align-items: center; gap: 2px 6px; color: var(--muted); font-size: var(--text-caption-size); font-variant-numeric: tabular-nums; }
.dw-ct__name img, .dw-ct__meta img { vertical-align: middle; }
.dw-ct__side { flex: 0 0 16px; width: 16px; height: 16px; }
.dw-ct__hk { min-width: 64px; color: var(--muted); font-size: var(--text-caption-size); font-weight: 400; }
.dw-ct__hrow .dw-ct__main { gap: 4px; }
.dw-ct__item { margin: 0; font-weight: 600; overflow-wrap: anywhere; }
.dw-ct__ok { color: var(--ok-text); }
.dw-ct__no { color: var(--dim); }
.dw-ct__sh { margin: 0 0 var(--space-2); color: var(--muted); font-family: var(--text-section-family); font-size: var(--text-section-size); letter-spacing: var(--text-section-tracking); text-transform: uppercase; }
.dw-ct__today .dw-kv__k, .dw-ct__today .dw-kv__v { color: var(--accent-text); font-weight: 600; }
.dw-ct__bgrid { display: grid; grid-template-columns: 76px repeat(2, minmax(0, 1fr)); align-items: stretch; max-width: 560px; margin-top: var(--space-2); font-size: var(--text-body-sm-size); }
/* a small table: a level column, then the two sides side by side; rows divided by lines (owner 12.10: "crooked" - it was
   stretched over the whole desktop width) */
.dw-ct__bgrid > span { display: flex; align-items: center; min-width: 0; padding: 7px 10px 7px 0; border-top: 1px solid var(--line-2); }
.dw-ct__bgrid > .dw-ct__bh { gap: 4px; padding-top: 0; border-top: 0; color: var(--muted); font-size: var(--text-caption-size); }
.dw-ct__bv > span { min-width: 0; overflow-wrap: anywhere; }
.dw-ct__blv { color: var(--muted); white-space: nowrap; font-variant-numeric: tabular-nums; }
.dw-ct__tax { margin-top: var(--space-3); }
.dw-ct__lvh { margin: var(--space-3) 0 var(--space-1); color: var(--muted); font-size: var(--text-caption-size); font-weight: 600; font-variant-numeric: tabular-nums; }
.dw-ct > .dw-section + .dw-ct__lvh { margin-top: 0; }
/* the palaces fold looks like a button row (owner 12.10: not clear the list opens) */
.dw-ct__foldsum { display: flex; align-items: center; justify-content: space-between; gap: var(--space-2); min-height: var(--touch); padding: 10px var(--space-3); border: 1px solid var(--line); border-radius: var(--radius-md); background: var(--surface); color: var(--text); list-style: none; cursor: pointer; -webkit-user-select: none; user-select: none; }
.dw-ct__foldsum::-webkit-details-marker { display: none; }
.dw-ct__foldsum:hover { border-color: var(--accent); }
.dw-ct__foldgo { display: inline-flex; align-items: center; gap: 6px; color: var(--accent-text); font-size: var(--text-body-sm-size); font-weight: 600; }
.dw-ct__foldgo::after { content: "\203A"; font-size: 18px; line-height: 1; transform: rotate(90deg); transition: transform .15s ease; }
.dw-ct__fold[open] .dw-ct__foldgo::after { transform: rotate(-90deg); }
.dw-ct__fhide, .dw-ct__fold[open] .dw-ct__fshow { display: none; }
.dw-ct__fold[open] .dw-ct__fhide { display: inline; }
.dw-ct__fold[open] > .dw-ct__foldsum { margin-bottom: var(--space-2); }
.dw-ct .dw-card > * + *, .dw-ct .dw-notice > * + * { margin-top: var(--space-2); }
@media (min-width: 1000px) {
  .dw-ct__hero { grid-template-columns: 170px minmax(0, 1fr); }
  .dw-ct__pic { width: 170px; }
}

/* ==== Lands (world/world.php, block world/newWorld), 13.10 ====
   The move cross sits right under the cell header and never moves: steps come every 0.5 s (L3), so everything that
   changes (refusals, flee result, arena, dungeon time) is placed below it. Neighbour tint = location_types.color (--c). */
.dw-ld__head { display: flex; align-items: center; gap: var(--space-3); min-height: 52px; margin: 0 0 var(--space-3); }
.dw-ld__sw { flex: 0 0 12px; width: 12px; height: 40px; border-radius: var(--radius-sm); background: var(--ld-c); box-shadow: inset 0 0 0 1px rgba(0, 0, 0, .18); }
.dw-ld__ht { min-width: 0; }
.dw-ld__title { margin: 0; font-family: var(--text-h1-family); font-size: var(--text-h1-size); font-weight: var(--text-h1-weight); line-height: 1.2; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.dw-ld__meta { margin: 2px 0 0; color: var(--muted); font-size: var(--text-caption-size); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.dw-ld__grid { display: grid; gap: var(--space-3); }
.dw-ld__left, .dw-ld__right { display: grid; gap: var(--space-3); align-content: start; min-width: 0; }
.dw-ld__pad { display: grid; grid-template-columns: repeat(3, minmax(0, 1fr)); grid-template-rows: repeat(3, 82px); grid-template-areas: ". n ." "w c e" ". s ."; gap: 6px; max-width: 440px; }
.dw-ld__d { position: relative; display: flex; flex-direction: column; justify-content: center; gap: 2px; min-width: 0; padding: 6px 10px 6px 14px; border: 1px solid var(--line); border-radius: var(--radius-md); background: var(--surface); background: color-mix(in srgb, var(--ld-c) 16%, var(--surface)); color: var(--text); text-decoration: none; overflow: hidden; -webkit-tap-highlight-color: transparent; }
.dw-ld__d::before { content: ""; position: absolute; left: 0; top: 0; bottom: 0; width: 5px; background: var(--ld-c); }
.dw-ld__d--north { grid-area: n; }
.dw-ld__d--south { grid-area: s; }
.dw-ld__d--west { grid-area: w; }
.dw-ld__d--east { grid-area: e; }
.dw-ld__d--c { grid-area: c; }
a.dw-ld__d:hover { border-color: var(--accent); }
a.dw-ld__d:active { transform: translateY(1px); }
.dw-ld__dk { display: flex; align-items: center; gap: 6px; color: var(--muted); font-size: 11px; font-weight: 600; letter-spacing: .04em; text-transform: uppercase; }
.dw-ld__dn { display: -webkit-box; -webkit-box-orient: vertical; -webkit-line-clamp: 2; overflow: hidden; font-size: var(--text-body-sm-size); font-weight: 600; line-height: 1.2; overflow-wrap: anywhere; }
.dw-ld__dt { color: var(--muted); font-size: 11px; line-height: 1.2; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.dw-ld__d kbd { display: none; min-width: 16px; padding: 0 4px; border: 1px solid var(--line-strong); border-radius: 4px; color: var(--muted); font: 600 10px/14px var(--font-body); text-align: center; }
.dw-ld__d--wall { background-image: repeating-linear-gradient(135deg, transparent 0 7px, rgba(0, 0, 0, .10) 7px 8px); }
.dw-ld__d--wall .dw-ld__dn { color: var(--muted); font-weight: 500; }
.dw-ld__d--off { opacity: .55; }
.dw-ld__d--none { border-style: dashed; background: transparent; }
.dw-ld__d--none::before { display: none; }
.dw-ld__go { align-items: center; text-align: center; border-color: var(--danger); background: var(--danger); color: #fff; box-shadow: 0 2px 0 rgba(0, 0, 0, .18); }
.dw-ld__go::before { display: none; }
.dw-ld__go:hover { border-color: var(--danger); filter: brightness(1.08); }
.dw-ld__go .dw-ld__dt { color: rgba(255, 255, 255, .85); }
.dw-ld__gon { font-family: var(--text-h2-family); font-size: 20px; font-weight: 700; line-height: 1.1; }
.dw-ld__here { border-color: var(--line-strong); border-style: dashed; }
.dw-ld__pad--lock .dw-ld__d--off::after { content: ""; position: absolute; right: 8px; top: 8px; width: 8px; height: 8px; border-radius: 50%; background: var(--danger); }
.dw-ld__why { margin: 0; color: var(--danger-text); font-size: var(--text-caption-size); }
.dw-ld__acts { display: flex; flex-wrap: wrap; gap: var(--space-2); }
.dw-ld__acts:empty { display: none; }
.dw-ld__st { padding-top: 8px; padding-bottom: 8px; }
.dw-ld__map { display: flex; flex-wrap: wrap; align-items: center; gap: var(--space-2) var(--space-3); }
.dw-ld__mapimg { display: block; width: 210px; height: 210px; border: 1px solid var(--line); border-radius: var(--radius-sm); image-rendering: pixelated; image-rendering: crisp-edges; }
.dw-ld__g7 { display: grid; grid-template-columns: repeat(7, 40px); grid-auto-rows: 40px; gap: 2px; padding: 4px; border: 1px solid var(--line); border-radius: var(--radius-md); background: var(--sunken); }
.dw-ld__g { position: relative; display: block; border-radius: 3px; background: var(--ld-c); box-shadow: inset 0 0 0 1px rgba(0, 0, 0, .18); }
.dw-ld__g--none { background: transparent; box-shadow: none; }
.dw-ld__g--wall { background-image: repeating-linear-gradient(135deg, transparent 0 5px, rgba(0, 0, 0, .28) 5px 6px); }
.dw-ld__g--me { box-shadow: inset 0 0 0 3px #ff0000, inset 0 0 0 5px #fff; }
.dw-ld__g--go { box-shadow: inset 0 0 0 2px #fff, 0 0 0 2px var(--accent); }
.dw-ld__g--go:hover { box-shadow: inset 0 0 0 2px #fff, 0 0 0 3px var(--accent); }
.dw-ld__gp { position: absolute; bottom: 4px; width: 10px; height: 10px; border: 1px solid rgba(0, 0, 0, .55); border-radius: 50%; }
.dw-ld__gp--own { left: 4px; background: #e4f00f; }
.dw-ld__gp--foe { right: 4px; background: #12ede2; }
.dw-ld__mk--go { background: transparent; border: 2px solid var(--accent); }
.dw-ld__maptg { font-size: var(--text-body-sm-size); }
.dw-ld__maplg { display: flex; flex-wrap: wrap; align-items: center; gap: 4px 6px; margin: 0; color: var(--muted); font-size: var(--text-caption-size); }
.dw-ld__mk { display: inline-block; width: 10px; height: 10px; margin-left: 4px; border: 1px solid rgba(0, 0, 0, .3); }
.dw-ld__mk--me { background: #ff0000; }
.dw-ld__mk--own { background: #e4f00f; }
.dw-ld__mk--foe { background: #12ede2; }
.dw-ld__box > * + * { margin-top: var(--space-2); }
.dw-ld__h { display: flex; align-items: baseline; gap: var(--space-2); margin: 0; font-family: var(--text-h2-family); font-size: var(--text-h2-size); font-weight: var(--text-h2-weight); line-height: 1.25; }
.dw-ld__h3 { margin: var(--space-3) 0 0; color: var(--muted); font-size: var(--text-caption-size); font-weight: 600; letter-spacing: .04em; text-transform: uppercase; }
.dw-ld__n { color: var(--muted); font-size: var(--text-body-sm-size); font-weight: 500; font-variant-numeric: tabular-nums; }
.dw-ld__mons { display: grid; gap: 4px; }
.dw-ld__mon { display: grid; grid-template-columns: 44px minmax(0, 1fr) auto; align-items: center; gap: var(--space-3); padding: 4px 6px; border-radius: var(--radius-md); color: var(--text); text-decoration: none; }
.dw-ld__mon:hover { background: var(--surface-2); }
.dw-ld__mpic { position: relative; display: block; width: 44px; height: 54px; border-radius: var(--radius-sm); background: var(--sunken); overflow: hidden; }
.dw-ld__mpic img { display: block; width: 44px; height: 66px; object-fit: cover; object-position: top; }
.dw-ld__mpic--t2::after, .dw-ld__mpic--t3::after, .dw-ld__mpic--t4::after { content: ""; position: absolute; inset: 0; border: 2px solid var(--drop-2); border-radius: inherit; }
.dw-ld__mpic--t3::after { border-color: var(--drop-4); }
.dw-ld__mpic--t4::after { border-color: var(--drop-5); }
.dw-ld__mid { display: grid; gap: 2px; min-width: 0; }
.dw-ld__mname { font-weight: 600; overflow-wrap: anywhere; }
.dw-ld__mname .dw-who__lvl { margin-left: 4px; white-space: nowrap; }
.dw-ld__mmeta { display: flex; flex-wrap: wrap; align-items: center; gap: 4px 8px; }
.dw-ld__mmeta:empty { display: none; }
.dw-ld__lv { color: var(--muted); font-size: var(--text-caption-size); }
.dw-ld__lv--up { color: var(--danger-text); font-weight: 600; }
.dw-ld__mc { color: var(--muted); font-size: var(--text-body-sm-size); font-weight: 600; font-variant-numeric: tabular-nums; white-space: nowrap; }
.dw-ld__obj { padding-top: var(--space-2); }
.dw-ld__orow { display: grid; grid-template-columns: auto minmax(0, 1fr) auto; align-items: center; gap: var(--space-3); color: var(--text); text-decoration: none; }
.dw-ld__opic { display: block; width: 68px; height: 56px; border-radius: var(--radius-sm); object-fit: cover; }
.dw-ld__oico { display: grid; place-items: center; width: 44px; height: 44px; border-radius: var(--radius-sm); background: var(--sunken); color: var(--muted); }
.dw-ld__oico svg { width: 26px; height: 26px; }
.dw-ld__ot { display: grid; gap: 2px; min-width: 0; }
.dw-ld__ok { color: var(--muted); font-size: var(--text-caption-size); }
.dw-ld__otxt { margin: 0; font-size: var(--text-body-sm-size); }
.dw-ld__tiles { grid-template-columns: repeat(auto-fill, minmax(min(100%, 200px), 1fr)); margin-bottom: 0; }
.dw-ld__tiles .dw-tile { min-height: 0; }
.dw-ld__tiles .dw-tile__name { font-family: var(--font-body); font-size: var(--text-body-size); font-weight: 600; }
.dw-ld__users { display: flex; flex-wrap: wrap; gap: 6px 16px; }
.dw-ld__who { display: inline-flex; align-items: center; gap: 6px; min-width: 0; }
.dw-ld__who a { display: inline-flex; align-items: center; gap: 6px; }
.dw-ld__x { display: inline-grid; place-items: center; width: 26px; height: 26px; border-radius: 50%; color: var(--danger-text); font-weight: 700; text-decoration: none; }
.dw-ld__x:hover { background: var(--danger-soft); }
.dw-ld__pick { display: grid; gap: var(--space-2); }
.dw-ld__pu { display: flex; align-items: center; gap: var(--space-2); min-height: var(--touch); }
.dw-ld__pu input { width: 20px; height: 20px; flex: 0 0 20px; accent-color: var(--danger); }
.dw-ld__bt { display: flex; flex-wrap: wrap; align-items: center; justify-content: space-between; gap: var(--space-2); padding-top: var(--space-2); border-top: 1px solid var(--line); }
.dw-ld__btn { display: grid; gap: 2px; font-weight: 600; }
.dw-ld__btk { color: var(--muted); font-size: var(--text-caption-size); font-weight: 400; }
.dw-ld__bta { display: flex; flex-wrap: wrap; gap: 6px; }
.dw-ld__msgs { display: grid; gap: 4px; }
.dw-ld__msg { margin: 0; font-size: var(--text-body-sm-size); overflow-wrap: anywhere; }
.dw-ld__mt { color: var(--muted); font-variant-numeric: tabular-nums; }
.dw-ld__calm { margin: 0; color: var(--muted); }
.dw-ld__foot { display: flex; flex-wrap: wrap; gap: var(--space-2); margin-top: var(--space-2); }
.dw-ld__code > * + * { margin-top: var(--space-2); }
.dw-ld__ch { margin: 0; font-weight: 600; }
.dw-ld__code form { display: block; line-height: 1.5; }
.dw-ld__code form br { display: none; }
.dw-ld__code form img { display: inline-block; margin: 4px 0; }
.dw-ld__code img { vertical-align: middle; border-radius: var(--radius-sm); }
.dw-ld__code input[name="code"] { display: block; margin: var(--space-2) 0 var(--space-3); box-sizing: border-box; width: 180px; max-width: 100%; min-height: var(--touch); padding: 6px 10px; border: 1px solid var(--line-strong); border-radius: var(--radius-md); background: var(--surface); color: var(--text); font-size: 20px; --dw-field-size: 20px; letter-spacing: .08em; }
.dw-ld__code input.button { display: block; min-height: var(--touch); padding: 0 var(--space-4); border: 0; border-radius: var(--radius-md); background: var(--danger); color: #fff; font: var(--text-button-weight) var(--text-button-size) var(--text-button-family); cursor: pointer; }
.dw-ld__write { display: grid; gap: var(--space-3); }
@media (min-width: 1000px) {
  .dw-ld__grid { grid-template-columns: 400px minmax(0, 1fr); align-items: start; gap: var(--space-4); }
  .dw-ld__pad { grid-template-rows: repeat(3, 92px); }
  .dw-ld__d kbd { display: inline-block; }
  .dw-ld__g7 { grid-template-columns: repeat(7, 48px); grid-auto-rows: 48px; }
}
@media (max-width: 380px) {
  .dw-ld__pad { grid-template-rows: repeat(3, 76px); gap: 4px; }
  .dw-ld__d { padding-left: 11px; padding-right: 6px; }
  .dw-ld__gon { font-size: 18px; }
  .dw-ld__g7 { grid-template-columns: repeat(7, 36px); grid-auto-rows: 36px; }
}
/* ==== /Lands ==== */

/* ==== Lairs (world/dungeon.php, block world/dungeon), 13.10 ==== */
.dw-dn__sec { display: grid; gap: var(--space-2); }
.dw-dn__sec > .dw-section { margin: 0; }
.dw-dn__list { display: grid; align-items: stretch; gap: var(--space-2); }
.dw-dn__row { display: flex; flex-wrap: wrap; align-items: center; justify-content: space-between; gap: var(--space-2) var(--space-3); }
.dw-dn__info { display: grid; gap: 2px; min-width: 0; }
.dw-dn__name { font-weight: 600; }
.dw-dn__meta { color: var(--muted); font-size: var(--text-caption-size); font-variant-numeric: tabular-nums; white-space: nowrap; }
.dw-dn__acts { display: flex; flex-wrap: wrap; gap: var(--space-2); }
.dw-dn__other { display: grid; padding-top: 4px; padding-bottom: 4px; }
.dw-dn__orow { display: flex; justify-content: space-between; gap: var(--space-3); padding: 8px 0; border-top: 1px solid var(--line); color: var(--muted); }
.dw-dn__orow:first-child { border-top: 0; }
@media (min-width: 1000px) {
  .dw-dn__list { grid-template-columns: repeat(2, minmax(0, 1fr)); }
}
/* ==== /Lairs ==== */

/* ==== Box (box.php, block box), 13.10 ==== */
.dw-box { max-width: 640px; }
.dw-box__prize > * + * { margin-top: var(--space-2); }
.dw-box__lead { margin: 0; color: var(--muted); }
.dw-box__row { display: grid; grid-template-columns: 64px minmax(0, 1fr) auto; align-items: center; gap: var(--space-3); }
.dw-box__pic { display: grid; place-items: center; width: 64px; height: 64px; border-radius: var(--radius-md); background: var(--sunken); color: var(--accent-text); }
.dw-box__pic svg { width: 36px; height: 36px; }
.dw-box__pic .dw-use__pic { width: 56px; height: 56px; }
.dw-box__name { font-size: 18px; font-weight: 600; overflow-wrap: anywhere; }
.dw-box__cnt { font-size: 20px; font-weight: 700; font-variant-numeric: tabular-nums; }
/* ==== /Box ==== */

/* ==== Small pages (news, shame board, lair cooldowns, epic battles, nobility), 13.10 ==== */
.dw-sm { max-width: 820px; }
.dw-sm__list { display: grid; gap: var(--space-2); }
.dw-sm__item { display: grid; gap: 4px; color: var(--text); text-decoration: none; }
.dw-sm__item:hover { border-color: var(--accent); }
.dw-sm__date { margin: 0; color: var(--muted); font-size: var(--text-caption-size); font-variant-numeric: tabular-nums; }
.dw-sm__lead { overflow-wrap: anywhere; }
.dw-sm__more { color: var(--accent-text); font-size: var(--text-body-sm-size); font-weight: 600; }
.dw-sm__news > * + * { margin-top: var(--space-2); }
.dw-sm__text { margin: 0; line-height: 1.55; overflow-wrap: anywhere; }
.dw-sm__ban > * + * { margin-top: 4px; }
.dw-sm__banwho { margin: 0; font-weight: 600; }
.dw-sm__meta { margin: 0; color: var(--muted); font-size: var(--text-caption-size); }
.dw-sm__rows { display: grid; padding-top: 4px; padding-bottom: 4px; }
.dw-sm__row { display: flex; flex-wrap: wrap; align-items: center; justify-content: space-between; gap: 6px var(--space-3); padding: 9px 0; border-top: 1px solid var(--line); overflow-wrap: anywhere; }
.dw-sm__row:first-child { border-top: 0; }
.dw-sm__left { color: var(--muted); font-size: var(--text-body-sm-size); font-variant-numeric: tabular-nums; white-space: nowrap; }
.dw-sm__ra { display: flex; flex-wrap: wrap; gap: 6px; }
.dw-sm__epic { display: flex; flex-wrap: wrap; align-items: center; justify-content: space-between; gap: var(--space-2) var(--space-3); }
.dw-sm__einfo { display: grid; gap: 2px; }
.dw-sm__tiles { margin-bottom: 0; grid-template-columns: repeat(auto-fill, minmax(min(100%, 220px), 1fr)); }
.dw-sm__tiles .dw-tile { min-height: 0; }
.dw-sm__tiles .dw-tile__name { font-family: var(--font-body); font-size: var(--text-body-size); font-weight: 600; }
.dw-sm__grade > * + * { margin-top: var(--space-2); }
.dw-sm__h { margin: 0; font-family: var(--text-h2-family); font-size: var(--text-h2-size); font-weight: var(--text-h2-weight); }
/* ==== /Small pages ==== */

/* ==== Live battles (main page tiles, battle hub rows), 13.10 ====
   A battle kind is lit only while it is really open: registration window or open requests (player request 13.10).
   No permanent highlight (owner 30.09: a lit tile reads as "something is on there now"). */
.dw-tile--live { border-color: var(--accent); background: var(--notice); }
.dw-tile--live .dw-tile__name { color: var(--accent-text); }
.dw-tile--live .dw-tile__cap { color: var(--accent-text); font-weight: 600; }
.dw-tile--live .dw-tile__cap::before, .dw-row--live .dw-row__cap::before { content: ""; display: inline-block; width: 7px; height: 7px; margin-right: 6px; border-radius: 50%; background: var(--accent); vertical-align: 1px; }
.dw-row--live { background: var(--notice); box-shadow: inset 3px 0 0 var(--accent); }
.dw-row--live .dw-row__cap { color: var(--accent-text); font-weight: 600; }
/* ==== /Live battles ==== */

/* ==== Medium pages (ratings, resource, battle log, obelisk, duels), 13.10 ==== */
/* Ratings (rating.php): one-line table rows like the Heroes rating - place, player (+ valor rank), value (+ place shift). */
.dw-rt__kinds { margin-bottom: var(--space-2); }
.dw-row.dw-rt__row { display: grid; grid-template-columns: 48px minmax(0, 1fr) auto; align-items: center; gap: var(--space-2); min-height: 40px; padding: 6px var(--space-3); }
.dw-row.dw-rt__row:hover { background: var(--surface-2); color: var(--text); }
.dw-rt__row--head { min-height: 32px; color: var(--muted); font-size: var(--text-caption-size); text-transform: uppercase; letter-spacing: .04em; }
.dw-row.dw-rt__row--head:hover { background: none; color: var(--muted); }
.dw-rt__n { color: var(--muted); font-variant-numeric: tabular-nums; text-align: right; }
.dw-rt__row--top { background: var(--accent-soft); }
.dw-rt__row--top .dw-rt__n { color: var(--accent-text); font-weight: 700; }
.dw-rt__row--me { box-shadow: inset 3px 0 0 var(--accent); }
.dw-rt__who { display: grid; gap: 2px; min-width: 0; }
.dw-rt__sub { color: var(--muted); font-size: var(--text-caption-size); }
.dw-rt__num { display: grid; justify-items: end; gap: 2px; font-variant-numeric: tabular-nums; white-space: nowrap; }
.dw-rt__d { color: var(--muted); font-size: var(--text-caption-size); }
.dw-rt__d--up { color: var(--ok-text); }
.dw-rt__d--down { color: var(--danger-text); }
.dw-rt__d--new { color: var(--accent-text); }
.dw-rt__place { margin: var(--space-2) 0; }
.dw-rt__prize { display: grid; gap: var(--space-1); margin: var(--space-2) 0; }
.dw-rt__prize p { margin: 0; }
.dw-rt__prize > p > a { color: var(--accent-text); }
/* Resource gathering (world/resource.php): facts card, one-minute progress, code form kept 1:1 with the old one. */
.dw-rs__res { margin: 0 0 var(--space-2); font-size: var(--text-h2-size); }
.dw-rs__facts { display: grid; gap: 6px; margin: 0; padding: 0; list-style: none; }
.dw-rs__facts li { display: flex; justify-content: space-between; gap: var(--space-3); padding: 4px 0; border-top: 1px solid var(--line); }
.dw-rs__facts li:first-child { border-top: 0; }
.dw-rs__facts span { color: var(--muted); }
.dw-rs__run > * + * { margin-top: var(--space-2); }
.dw-rs__now { margin: 0; }
.dw-rs__bar { height: 10px; border-radius: var(--radius-pill); background: var(--sunken); overflow: hidden; }
.dw-rs__bar i { display: block; height: 100%; border-radius: inherit; background: var(--accent); transition: width .9s linear; }
.dw-rs__left { margin: 0; color: var(--muted); font-variant-numeric: tabular-nums; }
.dw-rs__left--done { color: var(--accent-text); font-weight: 600; }
.dw-rs__code form { display: block; line-height: 1.5; }
.dw-rs__code form br { display: none; }
.dw-rs__code img { display: inline-block; margin: 4px 0; vertical-align: middle; border-radius: var(--radius-sm); }
.dw-rs__code input[name="code"] { display: block; margin: var(--space-2) 0 var(--space-3); box-sizing: border-box; width: 180px; max-width: 100%; min-height: var(--touch); padding: 6px 10px; border: 1px solid var(--line-strong); border-radius: var(--radius-md); background: var(--surface); color: var(--text); font-size: 20px; --dw-field-size: 20px; letter-spacing: .08em; }
.dw-rs__code input.button { display: block; min-height: var(--touch); padding: 0 var(--space-4); border: 0; border-radius: var(--radius-md); background: var(--accent); color: var(--bg); font: var(--text-button-weight) var(--text-button-size) var(--text-button-family); cursor: pointer; }
.dw-rs__code .dw-shop__note { margin: var(--space-3) 0 0; }
/* Battle history (logBattle.php): one card per battle - result for the viewed player, kind and date, teams with HP. */
.dw-bl__list { display: grid; gap: var(--space-3); margin-top: var(--space-3); }
.dw-bl__b { display: grid; gap: var(--space-2); }
.dw-bl__head { display: flex; flex-wrap: wrap; align-items: baseline; justify-content: space-between; gap: 4px var(--space-3); }
.dw-bl__res { font-weight: 700; }
.dw-bl__b--win .dw-bl__res { color: var(--ok-text); }
.dw-bl__b--lose .dw-bl__res { color: var(--danger-text); }
.dw-bl__b--draw .dw-bl__res, .dw-bl__b--stop .dw-bl__res { color: var(--muted); }
.dw-bl__b--win { box-shadow: inset 3px 0 0 var(--ok); }
.dw-bl__b--lose { box-shadow: inset 3px 0 0 var(--danger); }
.dw-bl__meta { color: var(--muted); font-size: var(--text-caption-size); }
.dw-bl__team { padding: 6px 10px; border-radius: var(--radius-md); background: var(--surface-2); border-left: 3px solid var(--line-strong); }
.dw-bl__team--1 { border-left-color: var(--team1); }
.dw-bl__team--2 { border-left-color: var(--team2); }
.dw-bl__tn { margin: 0 0 4px; color: var(--muted); font-size: var(--text-caption-size); text-transform: uppercase; letter-spacing: .04em; }
.dw-bl__team--won .dw-bl__tn { color: var(--text); font-weight: 600; }
.dw-bl__fs { display: grid; gap: 2px; margin: 0; padding: 0; list-style: none; }
.dw-bl__f { display: flex; align-items: center; justify-content: space-between; gap: var(--space-2); min-height: 28px; }
.dw-bl__who { display: inline-flex; align-items: center; gap: 6px; min-width: 0; overflow-wrap: anywhere; }
.dw-bl__f--me .dw-bl__who > a { font-weight: 700; }
.dw-bl__f--dead .dw-bl__who > a { opacity: .6; }
.dw-bl__hp { color: var(--muted); font-size: var(--text-caption-size); font-variant-numeric: tabular-nums; white-space: nowrap; }
.dw-bl__f--dead .dw-bl__hp { color: var(--danger-text); }
.dw-bl > .dw-shop__note { margin-top: var(--space-3); }
/* Obelisks (world/obelisk.php): list rows - name, effect, cell; owner clan on the right; single obelisk - facts and siege. */
.dw-row.dw-ob__row { display: grid; grid-template-columns: minmax(0, 1fr) auto; align-items: center; gap: var(--space-3); }
.dw-ob__main { display: grid; gap: 2px; min-width: 0; }
.dw-ob__name { font-weight: 600; color: var(--accent-text); }
.dw-ob__fx { font-size: var(--text-body-sm-size); }
.dw-ob__meta { color: var(--muted); font-size: var(--text-caption-size); }
.dw-ob__live { color: var(--danger-text); font-weight: 600; }
.dw-ob__own { display: inline-flex; align-items: center; justify-content: flex-end; gap: 6px; min-width: 0; text-align: right; }
.dw-ob__kn { overflow-wrap: anywhere; font-size: var(--text-body-sm-size); }
.dw-ob__free { color: var(--muted); font-size: var(--text-caption-size); }
.dw-ob__big { margin: 0 0 var(--space-2); font-size: var(--text-h2-size); font-weight: 600; }
.dw-ob__war { box-shadow: inset 3px 0 0 var(--danger); }
.dw-ob__wt { margin: 0 0 var(--space-2); font-weight: 700; color: var(--danger-text); }
.dw-ob__how p { margin: var(--space-2) 0 0; }
@media (max-width: 520px) {
  .dw-row.dw-ob__row { grid-template-columns: minmax(0, 1fr); gap: 6px; }
  .dw-ob__own { justify-content: flex-start; text-align: left; }
}
/* Duels (fight.php): request rows - time, who, tags; own request card with actions. */
.dw-row.dw-du__row { display: flex; flex-wrap: wrap; align-items: center; gap: 4px var(--space-2); }
.dw-row > span.dw-du__t:first-child { flex: 0 0 44px; color: var(--muted); font-variant-numeric: tabular-nums; }
.dw-du__who { display: inline-flex; flex: 1 1 140px; align-items: center; gap: 6px; min-width: 0; overflow-wrap: anywhere; }
.dw-du__tags { display: inline-flex; flex-wrap: wrap; align-items: center; justify-content: flex-end; gap: 4px; margin-left: auto; }
.dw-du__tag { padding: 1px 8px; border: 1px solid var(--line-strong); border-radius: var(--radius-pill); color: var(--muted); font-size: var(--text-caption-size); white-space: nowrap; }
.dw-du__tag--fist { border-color: var(--notice-line); }
.dw-du__tag--wait { border-color: var(--accent); color: var(--accent-text); }
.dw-du__row--busy { opacity: .75; }
.dw-du__me > * + * { margin-top: var(--space-2); }
.dw-du__st { margin: 0; font-weight: 700; }
.dw-du__vs { display: flex; flex-wrap: wrap; align-items: center; gap: 6px; margin: 0; }
.dw-du__me .dw-shop__acts { margin-top: var(--space-3); }
/* ==== /Medium pages ==== */

/* ==== Tail pages (small pages, estate, blogs, photos, friends, communities, adventure groups, grail, classes, tutorial, paid requests), 13.10 ==== */
/* Small tail pages: radio, my quests, warnings, votes, game help, contacts, phone notifications, settings. */
.dw-sm .dw-card > p { margin: 0; }
.dw-sm .dw-card > p + p, .dw-sm .dw-card > p + .dw-shop__acts, .dw-sm .dw-card > .dw-section + p { margin-top: var(--space-2); }
.dw-row.dw-sm__quest { cursor: default; }
.dw-row.dw-sm__quest:hover { background: none; color: var(--text); }
.dw-sm__vhint { margin: 0; color: var(--muted); font-size: var(--text-body-sm-size); }
.dw-row.dw-sm__vote { display: grid; grid-template-columns: minmax(0, 1fr) auto; align-items: center; gap: var(--space-3); }
.dw-sm__vt { display: grid; gap: 6px; min-width: 0; overflow-wrap: anywhere; }
.dw-sm__vbar { display: block; height: 6px; border-radius: var(--radius-pill); background: var(--sunken); overflow: hidden; }
.dw-sm__vbar i { display: block; height: 100%; border-radius: inherit; background: var(--accent); }
.dw-sm__vn { display: grid; justify-items: end; font-variant-numeric: tabular-nums; }
.dw-sm__sides { display: grid; gap: var(--space-3); margin-top: var(--space-3); grid-template-columns: repeat(auto-fit, minmax(min(100%, 240px), 1fr)); }
.dw-sm__side { display: grid; grid-template-columns: 72px minmax(0, 1fr); align-items: start; gap: var(--space-3); }
.dw-sm__side img { width: 72px; height: auto; border-radius: var(--radius-md); }
.dw-sm__side p { margin: 0; }
.dw-row.dw-sm__ct { display: flex; flex-wrap: wrap; align-items: center; justify-content: space-between; gap: 6px var(--space-2); }
.dw-row.dw-sm__ct:hover { background: none; color: var(--text); }
.dw-row > span.dw-sm__ctwho:first-child { display: inline-flex; flex: 1 1 160px; flex-wrap: wrap; align-items: center; gap: 6px; min-width: 0; overflow-wrap: anywhere; }
.dw-sm__on { padding: 0 8px; border: 1px solid var(--ok); border-radius: var(--radius-pill); color: var(--ok-text); font-size: var(--text-caption-size); }
.dw-sm__ctacts { display: inline-flex; gap: 6px; margin-left: auto; }
.dw-sm__push { display: grid; gap: var(--space-3); }
.dw-sm__push .dw-check { align-items: flex-start; font-size: var(--text-body-size); }
.dw-sm__push .dw-check input { flex: 0 0 auto; margin-top: 2px; }
.dw-sm__sub { margin-left: 26px; }
.dw-sm__pushc > * + * { margin-top: var(--space-2); }
.dw-set__form { display: grid; gap: var(--space-3); }
.dw-set__card > * + * { margin-top: var(--space-2); }
.dw-set__card > p { margin-bottom: 0; }
.dw-set__grid { display: grid; gap: var(--space-3); grid-template-columns: repeat(auto-fill, minmax(min(100%, 150px), 1fr)); align-items: start; }
.dw-set__grid .dw-field { grid-template-rows: minmax(2.4em, auto) auto; align-content: start; }
.dw-set__grid .dw-field__label { align-self: end; }
/* ==== world (13.10, big run): adventure groups (dw-ag), graal (dw-grl), subclasses (dw-sc2), tutorial (dw-edu).
   Templates: adventureGroup.html + dw_ag_card.html, world/graal.html, second_class.html + dw_sc2_*.html, edu.html.
   Only own classes and tokens.css variables; everything else on these screens is built from ready blocks. ==== */

/* ---- Adventure groups (adventure_group.php) ----
   A group is a card: goal, facts line, members as rows (never bubbles), free seats with one button.
   Phone - one column; desktop - two equal columns, cards of a row keep one height (grid stretch). */
.dw-ag__bar { display: flex; flex-wrap: wrap; align-items: center; gap: var(--space-2); }
.dw-ag__list { display: grid; gap: var(--space-3); }
.dw-ag__item { display: grid; align-content: start; gap: var(--space-2); min-width: 0; }
/* Cards of one list start on one line: no extra top margin of the "card after card" rule inside the grid. */
.dw-ag__list > .dw-ag__item { margin: 0; }
.dw-ag__item--mine { border-color: var(--accent); box-shadow: inset 3px 0 0 var(--accent); }
.dw-ag__top { display: flex; flex-wrap: wrap; align-items: baseline; justify-content: space-between; gap: var(--space-1) var(--space-3); }
.dw-ag__goal { flex: 1 1 60%; min-width: 0; margin: 0; font-family: var(--font-display); font-size: var(--text-h2-size); line-height: var(--text-h2-line); overflow-wrap: anywhere; }
.dw-ag__goal--none { color: var(--muted); }
.dw-ag__tags { display: inline-flex; flex-wrap: wrap; gap: var(--space-1); }
.dw-ag__meta { margin: 0; color: var(--muted); font-size: var(--text-body-sm-size); }
.dw-ag__meta b { color: var(--text); font-weight: 600; font-variant-numeric: tabular-nums; }
.dw-ag__who { display: grid; margin: 0; padding: 0; list-style: none; border-top: 1px solid var(--line-2); }
.dw-ag__m { display: flex; flex-wrap: wrap; align-items: center; gap: var(--space-1) var(--space-2); min-height: 40px; padding: 3px 0; border-bottom: 1px solid var(--line-2); }
.dw-ag__m--wait { color: var(--muted); }
.dw-ag__mn { display: inline-flex; align-items: center; gap: 6px; min-width: 0; margin-right: auto; overflow-wrap: anywhere; vertical-align: middle; }
/* No clan - an empty cell of the emblem size, so the nicks of a group stand on one line. */
.dw-ag__noemb { flex: 0 0 20px; width: 20px; height: 20px; }
.dw-ag__mn a { color: var(--text); font-weight: 600; text-decoration: none; }
.dw-ag__mn a:hover { color: var(--accent-text); }
.dw-ag__free { display: flex; flex-wrap: wrap; align-items: center; justify-content: space-between; gap: var(--space-2); min-height: var(--touch); }
.dw-ag__freen { color: var(--muted); }
.dw-ag__why { color: var(--muted); font-size: var(--text-caption-size); }
.dw-ag__acts { margin-top: var(--space-1); }
/* "Disband" asks first: a details block, no script. The summary is a quiet text link, the answer is a danger button. */
.dw-ag__sure > summary { display: inline-flex; align-items: center; min-height: var(--touch); color: var(--danger-text); font-size: var(--text-body-sm-size); list-style: none; cursor: pointer; }
.dw-ag__sure > summary::-webkit-details-marker { display: none; }
.dw-ag__sure > summary:hover { text-decoration: underline; }
.dw-ag__surebox { display: flex; flex-wrap: wrap; align-items: center; gap: var(--space-2) var(--space-3); padding: var(--space-3); border: 1px solid var(--danger-line); border-radius: var(--radius-md); background: var(--danger-soft); color: var(--danger-text); }
.dw-ag__surebox p { flex: 1 1 200px; margin: 0; font-size: var(--text-body-sm-size); }
/* An invitation: the notice card, the leader's name stays in the text line. */
.dw-ag__inv .dw-ag__mn { display: inline-flex; margin-right: 0; }
.dw-ag__form { max-width: 640px; }
@media (min-width: 900px) {
  .dw-ag__list { grid-template-columns: repeat(2, minmax(0, 1fr)); }
}

/* ---- Graal (world/graal.php) ----
   The list row is a link: name with the side icon, what it gives, owner line. The card is built from dw-kv. */
.dw-grl__main { display: grid; gap: 2px; min-width: 0; }
.dw-grl__name { display: inline-flex; align-items: center; gap: 6px; min-width: 0; font-weight: 600; overflow-wrap: anywhere; }
.dw-grl__name img { flex: 0 0 auto; width: 16px; height: 16px; }
.dw-grl__fx { font-size: var(--text-body-sm-size); }
.dw-grl__meta { display: flex; flex-wrap: wrap; align-items: center; gap: var(--space-1) 6px; color: var(--muted); font-size: var(--text-caption-size); }
.dw-grl__big { margin: 0 0 var(--space-2); font-size: var(--text-h2-size); font-weight: 600; overflow-wrap: anywhere; }
p.dw-grl__how { margin-top: var(--space-3); }
.dw-grl__act { display: grid; gap: var(--space-2); border-color: var(--accent); }
.dw-grl__act h2 { margin: 0; }
.dw-grl__cool b { color: var(--text); font-variant-numeric: tabular-nums; white-space: nowrap; }

/* ---- Subclasses (second_class.php) ----
   The screen reuses the class screen blocks (dw-cl__head, dw-cls__*); own - the two skills of a subclass
   and the reference grid of all classes. */
.dw-sc2__cat { display: grid; gap: var(--space-3); }
/* Class cards of the reference grid start on one line and end on one line (no margins of the ready card rules). */
.dw-sc2__cat > .dw-sc2__grp { margin: 0; }
.dw-sc2__skills { display: grid; margin: 0; padding: 0; list-style: none; }
.dw-sc2__skill { display: grid; gap: 2px; padding: var(--space-2) 0; border-bottom: 1px solid var(--line-2); }
.dw-sc2__skill:first-child { padding-top: 0; }
.dw-sc2__skill:last-child { padding-bottom: 0; border-bottom: 0; }
.dw-sc2__sn { font-weight: 600; }
.dw-sc2__fx { font-size: var(--text-body-sm-size); line-height: var(--text-body-sm-line); }
.dw-sc2__meta { color: var(--muted); font-size: var(--text-caption-size); }
a.dw-sc2__link { color: var(--accent-text); text-decoration: underline; }
@media (min-width: 900px) {
  .dw-sc2__cat { grid-template-columns: repeat(2, minmax(0, 1fr)); }
}

/* ---- Tutorial (edu.php) ----
   One screen - one thing to do: the mentor's words, the task card with the reward and one wide main button.
   A narrow reading column on the desktop; the step bar has six segments (steps 3-8 of the course). */
.dw-edu { max-width: 720px; }
.dw-edu__prog { display: flex; align-items: center; gap: var(--space-3); }
.dw-edu__pn { flex: 0 0 auto; color: var(--muted); font-size: var(--text-caption-size); letter-spacing: 0.04em; text-transform: uppercase; font-variant-numeric: tabular-nums; }
.dw-edu__bar { flex: 1 1 auto; display: grid; grid-template-columns: repeat(6, minmax(0, 1fr)); gap: var(--space-1); }
.dw-edu__seg { display: block; height: 6px; border-radius: var(--radius-sm); background: var(--line); }
.dw-edu__seg--done { background: var(--accent); }
.dw-edu__seg--now { background: var(--accent-soft); box-shadow: inset 0 0 0 1px var(--accent); }
.dw-edu__talk { display: grid; gap: var(--space-2); }
.dw-edu__who, .dw-edu__tk { margin: 0; color: var(--muted); font-size: var(--text-caption-size); letter-spacing: 0.04em; text-transform: uppercase; }
.dw-edu__say { margin: 0; line-height: 1.55; }
.dw-edu__task { display: grid; gap: var(--space-2); border-color: var(--accent); }
.dw-edu__tk { color: var(--accent-text); }
.dw-edu__what { margin: 0; font-family: var(--font-display); font-size: var(--text-h1-size); line-height: var(--text-h1-line); overflow-wrap: anywhere; }
.dw-edu__rew { margin: 0; color: var(--muted); font-size: var(--text-body-sm-size); }
.dw-edu__rew b { color: var(--accent-text); font-weight: 600; }
.dw-edu__go { min-height: 52px; }
a.dw-edu__link { color: var(--accent-text); text-decoration: underline; }
.dw-edu__done .dw-edu__rew { margin-top: var(--space-2); }
.dw-edu__stop { margin: var(--space-2) 0 0; font-size: var(--text-body-sm-size); }
.dw-edu__stop a { color: var(--muted); }
.dw-edu__stop a:hover { color: var(--danger-text); }
/* Estate (empire.php, 13.10): one screen, many views - own estate, buildings, warehouse, market, barracks, army, marches,
   building queue, paid services, estate sale and purchase, the list of all estates. Templates: templates-modern/empire.html
   and dw_emp_*.html. Built from the shared parts (dw-card, dw-row, dw-kv, dw-notice, dw-btn, dw-field); the rules below are
   only what those parts do not give: a row with a text column and an action column that wraps on the phone, the resource
   strip, the price line, the army line, small number inputs inside a row. Colours - tokens only. */

/* One column, not too wide on the desktop: rows carry a button at the right edge. */
.dw-emp.dw-emp { max-width: 860px; }

/* ---- texts inside cards ---- */
.dw-emp__title { margin: 0 0 var(--space-2); font-family: var(--font-display); font-size: var(--text-h2-size); line-height: var(--text-h2-line); overflow-wrap: anywhere; }
.dw-emp__text { margin: 0; line-height: 1.5; overflow-wrap: anywhere; }
.dw-emp__q { margin: 0; font-size: var(--text-h2-size); line-height: 1.3; overflow-wrap: anywhere; }
.dw-emp__q a { color: var(--accent-text); }
.dw-emp__cr { margin: 0; }
.dw-emp__lnk { color: var(--accent-text); }
.dw-emp__on { color: var(--accent-text); font-weight: 600; }
.dw-emp__list { display: grid; gap: 4px; margin: 0; padding: 0 0 0 20px; line-height: 1.45; }

/* Blocks stacked inside one card: summary, question, form. */
.dw-emp__sum > * + *,
.dw-emp__card > * + *,
.dw-emp__ask > * + * { margin-top: var(--space-3); }
/* In a form whose middle is a list of rows: the buttons and the note under the rows. */
.dw-emp .dw-emp__gap { margin-top: var(--space-3); }

/* ---- resources in the backpack: four cells in a row, also at 390px ---- */
.dw-emp__res { display: grid; grid-template-columns: repeat(4, minmax(0, 1fr)); gap: 6px; margin: 0; padding: 0; list-style: none; }
.dw-emp__res li { display: grid; gap: 2px; min-width: 0; padding: 6px 8px; border: 1px solid var(--line-2); border-radius: var(--radius-sm); background: var(--sunken); }
.dw-emp__res span { color: var(--muted); font-size: var(--text-caption-size); line-height: var(--text-caption-line); }
.dw-emp__res b { overflow: hidden; font-size: var(--text-body-sm-size); font-weight: 600; font-variant-numeric: tabular-nums; white-space: nowrap; text-overflow: ellipsis; }
@media (max-width: 359.98px) {
  .dw-emp__res { grid-template-columns: repeat(2, minmax(0, 1fr)); }
}

/* ---- a row: text column, then actions; actions drop under the text when they do not fit ---- */
.dw-emp .dw-emp__row { display: flex; flex-wrap: wrap; align-items: center; gap: var(--space-2) var(--space-3); }
.dw-emp .dw-emp__row:hover { background: none; color: var(--text); }
.dw-emp .dw-emp__row > .dw-emp__main { display: grid; flex: 1 1 180px; gap: 3px; min-width: 0; }
.dw-emp .dw-emp__row > .dw-emp__side { display: inline-flex; flex: 0 1 auto; flex-wrap: wrap; align-items: center; justify-content: flex-end; gap: 6px var(--space-2); margin-left: auto; }
.dw-emp__name { font-weight: 600; overflow-wrap: anywhere; }
a.dw-emp__name { color: var(--accent-text); text-decoration: none; }
a.dw-emp__name:hover { text-decoration: underline; }
.dw-emp__meta { color: var(--muted); font-size: var(--text-caption-size); line-height: var(--text-caption-line); overflow-wrap: anywhere; }
.dw-emp__meta a { color: inherit; text-decoration: underline; }
.dw-emp__price { font-variant-numeric: tabular-nums; white-space: nowrap; }
.dw-emp__cnt { flex: 0 0 auto; font-variant-numeric: tabular-nums; }

/* A state mark at the right edge of a row. */
.dw-emp__tag { display: inline-block; padding: 1px 8px; border: 1px solid var(--line-strong); border-radius: var(--radius-pill); color: var(--muted); font-size: var(--text-caption-size); line-height: 1.5; text-decoration: none; white-space: nowrap; }
.dw-emp__tag--go { border-color: var(--accent); color: var(--accent-text); }
.dw-emp__tag--no { border-color: var(--danger-line); color: var(--danger-text); }

/* ---- price line: credits and four resources; what the player lacks is red ---- */
.dw-emp__cost { display: inline-flex; flex-wrap: wrap; gap: 2px var(--space-2); }
.dw-emp__c { white-space: nowrap; }
.dw-emp__c b { font-weight: 600; font-variant-numeric: tabular-nums; }
.dw-emp__c--no { color: var(--danger-text); }

/* ---- army line: unit name and count ---- */
.dw-emp__squad { display: flex; flex-wrap: wrap; gap: 2px var(--space-3); font-size: var(--text-body-sm-size); line-height: var(--text-body-sm-line); }
.dw-emp__unit { white-space: nowrap; }
.dw-emp__unit a { color: inherit; }
.dw-emp__unit b { margin-left: 4px; font-variant-numeric: tabular-nums; }

/* Owner in a line: side sign, clan emblem, nick. */
.dw-emp__who { display: inline-flex; flex-wrap: wrap; align-items: center; gap: 4px 6px; min-width: 0; font-size: var(--text-body-sm-size); overflow-wrap: anywhere; }

/* ---- small number input inside a row (hire, gather an army) ---- */
.dw-emp .dw-emp__num { flex: 0 0 84px; width: 84px; padding: 0 var(--space-2); text-align: right; }
.dw-emp__inline { display: inline-flex; flex: 0 0 auto; align-items: center; gap: var(--space-2); margin: 0 0 0 auto; }
.dw-emp .dw-emp__pick { display: flex; align-items: center; gap: var(--space-3); cursor: pointer; }
.dw-emp .dw-emp__pick > .dw-emp__main { display: grid; flex: 1 1 auto; gap: 3px; min-width: 0; }

/* ---- the list of all estates: place, estate, points ---- */
.dw-emp .dw-emp__erow { display: grid; grid-template-columns: 28px minmax(0, 1fr) auto; align-items: center; gap: var(--space-2); }
.dw-emp .dw-emp__erow > .dw-emp__main { display: grid; gap: 3px; min-width: 0; }
.dw-emp__erow--mine { box-shadow: inset 3px 0 0 var(--accent); }
.dw-emp__place { color: var(--muted); font-variant-numeric: tabular-nums; text-align: right; }
.dw-emp__pts { display: grid; justify-items: end; text-align: right; white-space: nowrap; font-variant-numeric: tabular-nums; }
.dw-emp__pts span { color: var(--muted); font-size: var(--text-caption-size); }

/* ---- armies marching on the estate, inside the danger notice ---- */
.dw-emp__foes { display: grid; gap: 6px; margin: var(--space-2) 0 0; padding: 0; list-style: none; }
.dw-emp__foes li { display: flex; flex-wrap: wrap; align-items: center; gap: 4px 6px; }
.dw-emp__foes a { color: inherit; font-weight: 600; }
.dw-emp__eta { margin-left: auto; font-size: var(--text-body-sm-size); font-variant-numeric: tabular-nums; white-space: nowrap; }

/* ---- battle report: ready markup from the cron ---- */
.dw-emp__log { line-height: 1.5; overflow-wrap: anywhere; }
.dw-emp__log img { max-height: 16px; width: auto; vertical-align: text-bottom; }
.dw-emp__log a { color: var(--accent-text); }

/* The way out at the bottom sits a step lower. */
.dw-emp__foot { margin-top: var(--space-2); }
/* ---- Social screens (13.10): blogs (dw-blg), photo albums (dw-ft), friends (dw-frd), communities (dw-cmm) ----
   service_blog.html, service_foto.html, service_friends.html, service_communities.html and their parts
   (dw_blg_who.html, dw_blg_post.html, dw_blg_cpager.html, dw_ft_row.html, dw_cmm_topic.html, dw_cmm_write.html).
   The screens are built from ready parts (dw-shop, dw-card, dw-list / dw-row, dw-topic, dw-posts / dw-post, dw-chips,
   dw-notice, dw-field, dw-pager); here is only what those parts do not give. Selectors carry two own classes where
   they must win over a ready single-class rule whatever the order of the files. */

/* -- Screen head: the title with a by-line (author, date, album, marks) under it -- */
.dw-blg__headtext,
.dw-ft__headtext,
.dw-cmm__headtext { display: grid; flex: 1 1 auto; gap: 6px; min-width: 0; }
.dw-blg__by,
.dw-ft__by {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 4px 8px;
  margin: 0;
  color: var(--muted);
  font-size: var(--text-body-sm-size);
  line-height: var(--text-body-sm-line);
}
.dw-blg__dot,
.dw-ft__dot { color: var(--dim); }
.dw-ft__alb { color: var(--accent-text); }
.dw-ft__marks,
.dw-cmm__marks { display: flex; flex-wrap: wrap; gap: 6px; margin: 0; }
.dw-ft__marks svg { width: 12px; height: 12px; }

/* A player in one line (dw_blg_who.html): the nick with no link inside a row that is a link itself. */
.dw-blg__wn b { color: var(--text); font-weight: 600; }
/* The side sign before a nick in a post head (dw_blg_post.html). */
.dw-blg__side-ico { margin-right: 4px; vertical-align: -3px; }

/* -- Blogs: the feed -- */
.dw-blg__cols {
  display: grid;
  grid-template-columns: minmax(0, 1fr);
  gap: var(--space-4);
  align-items: start;
}
.dw-blg__main,
.dw-blg__side { min-width: 0; }
@media (min-width: 1000px) {
  /* The feed left, the two "best" lists in the side column; their titles sit inside the cards,
     so both columns start on one line. */
  .dw-blg__cols { grid-template-columns: minmax(0, 1fr) var(--aside); gap: var(--space-3) var(--space-5); }
}
/* A like count beside the forum counts (comments, views): a heart drawn in the template. */
.dw-blg__likes { display: inline-flex; align-items: center; gap: 4px; }
.dw-blg__likes svg { flex: 0 0 13px; width: 13px; height: 13px; opacity: .75; }
.dw-blg__rowname { display: block; overflow-wrap: anywhere; }
.dw-blg .dw-blg__rowcap { display: flex; flex-wrap: wrap; align-items: center; gap: 2px 8px; }

/* -- Blogs: one record -- */
.dw-blg__post { display: grid; gap: var(--space-3); min-width: 0; }
/* The author's own markup may be wider than the card: it scrolls inside, the page does not. */
.dw-blg__text { min-width: 0; overflow-x: auto; }
.dw-blg__att { display: grid; gap: var(--space-2); justify-items: start; }
.dw-blg__attpic { display: inline-flex; align-items: center; gap: var(--space-3); color: var(--text); text-decoration: none; }
.dw-blg__attpic:hover { color: var(--accent-text); }
.dw-blg__attpic img { max-width: 120px; max-height: 120px; border: 1px solid var(--line); border-radius: var(--radius-sm); }
.dw-blg__attcap { margin: 0; color: var(--muted); font-size: var(--text-body-sm-size); }
.dw-blg__attcap a { color: var(--accent-text); }
.dw-blg__stat,
.dw-ft__stat {
  display: flex;
  flex-wrap: wrap;
  gap: 4px var(--space-4);
  margin: 0;
  padding-top: var(--space-2);
  border-top: 1px solid var(--line-2);
  color: var(--muted);
  font-size: var(--text-caption-size);
  line-height: var(--text-caption-line);
}
.dw-blg__stat b,
.dw-ft__stat b { color: var(--text); font-weight: 600; }
.dw-blg__acts { align-items: center; }
/* "You like it" and "main photo of the profile": marks as tall as the buttons beside them. */
.dw-blg .dw-blg__liked,
.dw-ft .dw-ft__main {
  min-height: var(--touch);
  padding: 0 var(--space-3);
  border-radius: var(--radius-md);
  font-size: var(--text-body-sm-size);
}
.dw-blg__liked svg { width: 14px; height: 14px; }
.dw-blg__likebtn { gap: 6px; }
.dw-blg__likebtn svg { width: 18px; height: 18px; }
/* The record code for the chat: the row is a label, the field keeps its width. */
.dw-blg__link { cursor: text; }
.dw-blg__link .dw-blg__code { flex: 0 0 auto; width: 10ch; }

/* -- Forms: text boxes and comment forms -- */
.dw-blg .dw-blg__area,
.dw-cmm .dw-cmm__area { min-height: 180px; padding: 10px var(--space-3); line-height: 1.45; resize: vertical; }
.dw-blg .dw-blg__area--sm,
.dw-cmm .dw-cmm__area { min-height: 76px; }
.dw-blg .dw-blg__write,
.dw-cmm .dw-cmm__write { max-width: 720px; }
/* The photo page is one narrow column: its forms take the column width. */
.dw-ft .dw-ft__vote,
.dw-ft .dw-ft__write { max-width: none; }

/* -- Deleting with one link (the controllers ask nothing): the link hides under a fold, the first
   tap opens the warning and the red button, the second deletes. No script, no new parameters. -- */
.dw-blg__del > summary,
.dw-ft__del > summary,
.dw-frd__del > summary,
.dw-cmm__del > summary,
.dw-blg__cdel > summary { list-style: none; cursor: pointer; }
.dw-blg__del > summary::-webkit-details-marker,
.dw-ft__del > summary::-webkit-details-marker,
.dw-frd__del > summary::-webkit-details-marker,
.dw-cmm__del > summary::-webkit-details-marker,
.dw-blg__cdel > summary::-webkit-details-marker { display: none; }
.dw-blg__del[open] > summary,
.dw-ft__del[open] > summary,
.dw-frd__del[open] > summary,
.dw-cmm__del[open] > summary,
.dw-blg__cdel[open] > summary { border-color: var(--danger-line); color: var(--danger-text); }
.dw-blg__delbox,
.dw-ft__delbox { max-width: 640px; margin-top: var(--space-2); }
/* In a post head (comment, feed record): the fold keeps to the right, the red button opens under it. */
.dw-blg__cdel { flex: 0 0 auto; align-self: flex-start; margin-left: auto; text-align: right; }
.dw-blg__cdel > a { display: flex; margin-top: 6px; }
/* In a list row (friend, community member): the note and the red button open under the summary. */
.dw-frd__delbox,
.dw-cmm__delbox { display: flex; flex-wrap: wrap; align-items: center; gap: var(--space-2); margin-top: var(--space-2); }
.dw-frd__delnote,
.dw-cmm__delnote { color: var(--muted); font-size: var(--text-caption-size); line-height: var(--text-caption-line); }

/* -- Photo albums: rows with a thumbnail -- */
.dw-ft__row {
  display: flex;
  align-items: center;
  gap: var(--space-3);
  min-height: var(--touch);
  padding: 10px var(--space-3);
  border-bottom: 1px solid var(--line-2);
  color: var(--text);
  text-decoration: none;
}
.dw-ft__row:last-child { border-bottom: 0; }
.dw-ft__row:hover { background: var(--surface-2); color: var(--accent-text); }
.dw-ft__thumb {
  display: flex;
  flex: 0 0 72px;
  align-items: center;
  justify-content: center;
  width: 72px;
  height: 72px;
  overflow: hidden;
  border: 1px solid var(--line);
  border-radius: var(--radius-md);
  background: var(--sunken);
  color: var(--dim);
}
.dw-ft__thumb img { max-width: 100%; max-height: 100%; }
.dw-ft__thumb svg { width: 28px; height: 28px; }
.dw-ft__rmain { display: flex; flex: 1 1 auto; flex-direction: column; gap: 2px; min-width: 0; }
.dw-ft__rname { font-weight: 600; overflow-wrap: anywhere; }
.dw-ft__rcap {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 2px 8px;
  color: var(--muted);
  font-size: var(--text-caption-size);
  line-height: var(--text-caption-line);
  overflow-wrap: anywhere;
}
.dw-ft__count { white-space: nowrap; font-size: var(--text-body-sm-size); }

/* -- Photo albums: one photo -- */
.dw-ft.dw-ft--one { max-width: 760px; }
.dw-ft__fig { display: grid; gap: var(--space-3); justify-items: center; margin: 0; }
.dw-ft__pic { display: block; max-width: 100%; }
.dw-ft__pic img { display: block; max-width: 100%; height: auto; border-radius: var(--radius-sm); }
.dw-ft__stat { justify-self: stretch; }
.dw-ft__orig { color: var(--accent-text); }
/* The engine's links to the neighbour photos, drawn as the pager numbers. */
.dw-ft .dw-ft__nav { justify-content: center; margin-top: 0; }
.dw-ft__manage { display: grid; gap: var(--space-3); }

/* -- Friends and community members: a row with the player left and small actions right;
   on the phone the actions wrap under the name -- */
.dw-frd__row,
.dw-cmm__urow {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  justify-content: space-between;
  gap: var(--space-2) var(--space-3);
  min-height: var(--touch);
  padding: 10px var(--space-3);
  border-bottom: 1px solid var(--line-2);
}
.dw-frd__row:last-child,
.dw-cmm__urow:last-child { border-bottom: 0; }
.dw-frd__who,
.dw-cmm__uwho { display: inline-flex; flex-wrap: wrap; align-items: center; gap: 4px 8px; min-width: 0; }
.dw-frd__off { color: var(--dim); font-size: var(--text-caption-size); }
.dw-frd__acts,
.dw-cmm__uacts { display: flex; flex-wrap: wrap; align-items: flex-start; gap: var(--space-2); }

/* -- Communities -- */
.dw-cmm__opis { margin: 0 0 var(--space-3); overflow-wrap: anywhere; }
.dw-cmm__name { display: block; font-weight: 600; overflow-wrap: anywhere; }
.dw-cmm .dw-cmm__cap { display: flex; flex-wrap: wrap; align-items: center; gap: 2px 10px; }
.dw-cmm__owner { display: inline-flex; flex-wrap: wrap; align-items: center; gap: 4px; }
/* ---- Requests and paid services (family dw-rq, 13.10.2026) ----
   Eight screens of one family: premium subscription (reqVipStatus.php), race / sex / class reset (reqChangeRace.php),
   stone shop (buystone.php), platinum transfer (send_gold_gold.php), credits transfer (sendMoney.php), artifact order
   (reqArt.php), artifact showcase (arts.php), stat points (addStat.php). The screens are built from dw-shop, dw-card,
   dw-notice, dw-lots, dw-kv and dw-field; only what those do not give is here. Selectors use the dw-rq classes only. */

/* The "you have" line: the link to buy more. */
.dw-rq__have a { color: var(--accent-text); text-decoration: none; }
.dw-rq__have a:hover { text-decoration: underline; }

/* Subscription cards: one column on the phone, pairs of one height on the desktop. */
.dw-rq__plans { display: grid; gap: var(--space-3); }
.dw-rq__plan { display: flex; flex-direction: column; gap: var(--space-2); }
/* The grid gap spaces the cards; the common "card after card" margin would push the right card of a pair down. */
.dw-rq .dw-rq__plans .dw-rq__plan { margin-top: 0; }
.dw-rq__h { margin: 0; font-family: var(--font-display); font-size: var(--text-h2-size); line-height: var(--text-h2-line); font-weight: var(--text-h2-weight); }
.dw-rq__lead { margin: 0; font-size: var(--text-body-sm-size); line-height: var(--text-body-sm-line); }
.dw-rq__list { margin: 0; padding-left: 18px; color: var(--muted); font-size: var(--text-body-sm-size); line-height: 1.5; }
.dw-rq__list li + li { margin-top: 2px; }

/* Terms with prices: the list keeps to the card bottom, so the buy rows of a pair of cards stand on one line. */
.dw-rq__offers { margin: auto 0 0; padding: 0; list-style: none; border-top: 1px solid var(--line-2); }
.dw-rq__offer { display: flex; flex-wrap: wrap; align-items: center; gap: 6px var(--space-2); min-height: var(--touch); padding: 5px 0; border-bottom: 1px solid var(--line-2); }
.dw-rq__offer:last-child { border-bottom: 0; }
.dw-rq__term { flex: 1 1 auto; min-width: 0; }
.dw-rq__price { font-weight: 600; font-variant-numeric: tabular-nums; white-space: nowrap; }

/* "Not enough N" next to a price, and the warning before a button that cannot be undone. */
.dw-rq__lack { margin: 0; color: var(--danger-text); font-size: var(--text-caption-size); line-height: var(--text-caption-line); }
.dw-rq__warn { margin: 0; color: var(--danger-text); font-size: var(--text-body-sm-size); line-height: var(--text-body-sm-line); }

/* Chosen operations with their prices (the question and the result of reqChangeRace.php). */
.dw-rq__lines { margin: 0; padding: 0; list-style: none; }
.dw-rq__line { display: flex; flex-wrap: wrap; align-items: baseline; justify-content: space-between; gap: 2px var(--space-3); padding: 7px 0; border-bottom: 1px solid var(--line-2); font-size: var(--text-body-sm-size); line-height: var(--text-body-sm-line); }
.dw-rq__line:last-child { border-bottom: 0; }
.dw-rq__line b { font-weight: 600; font-variant-numeric: tabular-nums; white-space: nowrap; }
.dw-rq__line .dw-rq__lack { flex: 1 0 100%; }
.dw-rq__line--off > span:first-child,
.dw-rq__line--off > b { color: var(--dim); }

/* Checkbox rows: the name, under it the price and what the operation changes. A row without a checkbox - not enough money. */
.dw-rq__opts { display: grid; border-top: 1px solid var(--line-2); }
.dw-rq__opts .dw-rq__opt { display: flex; align-items: flex-start; gap: var(--space-2); min-height: var(--touch); padding: 10px 0; border-bottom: 1px solid var(--line-2); font-size: var(--text-body-size); line-height: var(--text-body-line); }
.dw-rq__opts .dw-rq__opt:last-child { border-bottom: 0; }
.dw-rq__opt input { flex: 0 0 auto; margin-top: 2px; }
.dw-rq__opts .dw-rq__opt--off { padding-left: calc(18px + var(--space-2)); color: var(--dim); }
.dw-rq__optt { min-width: 0; }
.dw-rq__optc { display: block; margin-top: 2px; color: var(--muted); font-size: var(--text-caption-size); line-height: var(--text-caption-line); }
.dw-rq__opt--off .dw-rq__optc { color: var(--danger-text); }

/* Stone shop: the pack buttons of a booster go under its name on every width. */
.dw-rq__lots .dw-rq__lot--packs { grid-template-columns: minmax(0, 1fr); }
.dw-rq__lots .dw-rq__packs { flex-wrap: wrap; padding-left: 16px; }
.dw-rq__pack--off { display: inline-flex; align-items: center; min-height: 34px; padding: 0 12px; border: 1px dashed var(--line); border-radius: var(--radius-md); color: var(--dim); font-size: var(--text-caption-size); }

/* The receiver line of a transfer. */
.dw-rq__to { margin: 0; overflow-wrap: anywhere; }
.dw-rq__to a { color: var(--accent-text); text-decoration: none; }

/* Three short fields in a row: requirement points taken off a clan artifact. */
.dw-rq__three { display: grid; grid-template-columns: repeat(3, minmax(0, 1fr)); gap: var(--space-2); align-items: end; }

/* Artifact order: the form and the parameters of the new artifact - one under the other on the phone, a pair of one
   height on the desktop. The grid gap spaces them, so the common "card after card" margin is taken off. */
.dw-rq__order { display: grid; gap: var(--space-3); }
.dw-rq .dw-rq__order .dw-rq__side { margin-top: 0; align-content: start; }

@media (min-width: 1000px) {
  .dw-rq__plans { grid-template-columns: repeat(2, minmax(0, 1fr)); }
  .dw-rq__order { grid-template-columns: minmax(0, 640px) minmax(0, 440px); }
}
/* ---- Game pages, second tail batch (13.10.2026): menagerie and hall of reflections (dw-fb), waiting for the enemy
   after an attack scroll (dw-wm), paid item strengthening (dw-ac), avatars (dw-avs), file exchange (dw-fc).
   Templates: fightBeast.html, fightShadow.html, waitEnemyMagic.html, autocraft.html, avatars.html, service_fc.html and
   dw_fc_row.html. The screens are built from ready parts (dw-shop, dw-card, dw-notice, dw-field, dw-kv, dw-list / dw-row,
   dw-posts, dw-pager, the waiting card dw-du__me of the arena, the thumbnail rows dw-ft__row of the photo albums); here
   is only what those parts do not give. Colours - tokens only. Selectors carry two classes where they must win over a
   ready single-class rule whatever the order of the files.
   The avatars screen uses dw-avs, not dw-av: dw-av is the player's photo button in the page header (base.css). ---- */

/* -- Menagerie and hall of reflections: one reading column; the monster picker is a two-column grid
      (who, how many) that keeps on one line at 390px -- */
.dw-shop.dw-fb { max-width: 640px; }
.dw-fb__intro { display: grid; gap: var(--space-3); }
.dw-fb__say { margin: 0; line-height: 1.5; overflow-wrap: anywhere; }
.dw-fb__rows { display: grid; gap: var(--space-2); }
.dw-fb__pick { display: grid; grid-template-columns: minmax(0, 1fr) 84px; align-items: center; gap: var(--space-2); }
.dw-fb__cap { color: var(--muted); font-size: var(--text-caption-size); letter-spacing: 0.04em; text-transform: uppercase; }

/* -- Waiting for the enemy: the seconds left as one big number with a caption beside it -- */
.dw-shop.dw-wm { max-width: 640px; }
.dw-wm__k { color: var(--muted); }
.dw-wm__who { color: var(--text); font-weight: 600; text-decoration: none; }
.dw-wm__who:hover { color: var(--accent-text); }
.dw-wm__left { display: flex; align-items: center; gap: var(--space-3); margin-bottom: 0; padding: var(--space-3) 0; border-top: 1px solid var(--line-2); border-bottom: 1px solid var(--line-2); }
.dw-wm__n { color: var(--accent-text); font-family: var(--font-display); font-size: var(--text-display-size); line-height: 1; font-variant-numeric: tabular-nums; }
.dw-wm__cap { color: var(--muted); font-size: var(--text-caption-size); line-height: var(--text-caption-line); }

/* -- Paid strengthening: one column; the "now / will be / price" table between two lines -- */
.dw-shop.dw-ac { max-width: 640px; }
.dw-ac__kv { border-top: 1px solid var(--line-2); border-bottom: 1px solid var(--line-2); }
.dw-ac__how { display: grid; gap: var(--space-2); }
.dw-ac__how .dw-section { margin: 0; }

/* -- Avatars: the row is not a link itself (a name may carry its own link), so no row hover;
      one picture - centred, never wider than the card -- */
.dw-shop.dw-avs { max-width: 640px; }
.dw-ft__row.dw-avs__row:hover { background: none; color: var(--text); }
.dw-avs__thumb { color: var(--dim); text-decoration: none; }
.dw-avs__row a:not(.dw-btn):not(.dw-avs__thumb) { color: var(--accent-text); }
.dw-avs__fig { display: grid; justify-items: center; gap: var(--space-2); margin: 0; }
.dw-avs__pic { display: block; max-width: 100%; height: auto; border-radius: var(--radius-sm); }
.dw-avs__name { color: var(--muted); font-size: var(--text-body-sm-size); line-height: var(--text-body-sm-line); text-align: center; overflow-wrap: anywhere; }
.dw-avs__name a { color: var(--accent-text); }

/* -- File exchange: the file page is one narrow column, its forms take the column width;
      a description in a list row is cut to two lines -- */
.dw-fc.dw-fc--one { max-width: 760px; }
.dw-fc--one .dw-fc__form { max-width: none; }
.dw-fc__path a { text-decoration: none; }
.dw-fc__path a:hover { text-decoration: underline; }
.dw-fc__file { display: grid; gap: var(--space-3); min-width: 0; }
.dw-fc__pic { display: block; justify-self: center; max-width: 100%; max-height: 320px; width: auto; height: auto; border-radius: var(--radius-sm); }
.dw-fc__audio { display: block; width: 100%; }
.dw-fc__text { margin: 0; line-height: 1.5; overflow-wrap: anywhere; }
/* The owner's form hides under a fold (details, no script): the summary is a button, the form opens under it. */
.dw-fc__fold > summary { list-style: none; cursor: pointer; }
.dw-fc__fold > summary::-webkit-details-marker { display: none; }
.dw-fc__fold[open] > summary { border-color: var(--accent); color: var(--accent-text); }
.dw-fc__foldbox { margin-top: var(--space-2); }
.dw-fc .dw-fc__area { min-height: 96px; padding: 10px var(--space-3); line-height: 1.45; resize: vertical; }
.dw-fc__desc { display: -webkit-box; overflow: hidden; color: var(--muted); font-size: var(--text-body-sm-size); line-height: var(--text-body-sm-line); overflow-wrap: anywhere; -webkit-box-orient: vertical; -webkit-line-clamp: 2; }
.dw-fc__type { letter-spacing: 0.04em; text-transform: uppercase; }
/* ---- Requests and paid services, second batch (family dw-rq, new classes dw-rq2, 13.10.2026) ----
   Twelve screens: rigold transfer (send_gold.php), unique tattoos and amulets (reqTatoo.php), tattoo change
   (reqChangeTatoo.php), payment claim (outgoing.php), ancient scrolls (buyscrolls.php), artifact sell-back (sellArt.php),
   credit system (reqCredit.php), divine stone change (reqChangeGs.php), credits for rigolds (reqMoney.php), nick change
   (reqChangeNick.php), sex / race / birthplace (backups.php), stat redistribution (changeStats.php).
   The screens are built from the dw-rq classes of the first batch and from dw-shop, dw-card, dw-notice, dw-lots, dw-kv,
   dw-field; only what those do not give is here. */

/* A price row with a caption under the name (what an amulet gives, the bonus of an exchange tier): the name takes the
   free width and wraps inside it, the price always stays on the right of the same row. */
.dw-rq .dw-rq2__offer { flex-wrap: nowrap; }
.dw-rq2__offer .dw-rq__term { flex: 1 1 0; overflow-wrap: anywhere; }
.dw-rq2__what { display: block; color: var(--muted); font-size: var(--text-caption-size); line-height: var(--text-caption-line); }

/* A choice row with a short name (divine stones): the name and the button stay on one line on the phone too. */
.dw-rq .dw-rq2__row { grid-template-columns: minmax(0, 1fr) auto; align-items: center; }
.dw-rq .dw-rq2__row .dw-lot__buy { padding-left: 0; }

/* A sentence with a player's text inside (a nick of 60 signs, an artifact name without spaces): the long word breaks
   instead of pushing the page wider than the phone. */
.dw-rq2__wrap { overflow-wrap: anywhere; }

/* The consent checkbox with a long caption: the caption wraps, the box stays at its first line. */
.dw-rq .dw-rq2__agree { display: flex; align-items: flex-start; }
.dw-rq2__agree input { flex: 0 0 auto; margin-top: 1px; }
/* ==== info2 (second tail batch, 13.10): clan sites rating, geography, game statistics, exchange charts,
   password and e-mail pages. Prefix dw-i2; everything else is built from ready classes (dw-sm, dw-rt, dw-kv, dw-row). ==== */

/* Clan sites rating (count_r.php): a narrow place column (tens of clans, not thousands of players), the clan line -
   side icon, emblem, name - and the site address under it. */
.dw-row.dw-i2__srow { grid-template-columns: 30px minmax(0, 1fr) auto; align-items: start; }
.dw-row.dw-i2__srow.dw-rt__row--head { align-items: center; }
.dw-i2__clan { display: flex; align-items: flex-start; gap: 6px; min-width: 0; }
.dw-i2__clan > img { flex: 0 0 auto; margin-top: 3px; }
.dw-i2__clan > .dw-emb { flex: 0 0 auto; margin-top: 1px; }
.dw-i2__clan a { min-width: 0; color: inherit; font-weight: 600; text-decoration: none; overflow-wrap: anywhere; }
.dw-i2__clan a:hover { color: var(--accent-text); }
.dw-i2__site { overflow-wrap: anywhere; }
.dw-i2__site a { color: var(--accent-text); }

/* Geography (geo_stat.php): a player row - emblem, nick, level; a place row - name, count on the right. */
.dw-i2__pl { display: flex; align-items: center; gap: 6px; min-width: 0; }
.dw-i2__pl > .dw-emb, .dw-i2__pl > .dw-who__lvl { flex: 0 0 auto; white-space: nowrap; }
.dw-i2__nick { min-width: 0; font-weight: 600; overflow-wrap: anywhere; }
.dw-i2__geo { overflow-wrap: anywhere; }

/* Statistics (stat.php) and the chart menu (graph.php): cards side by side on a wide screen, one column on the phone.
   The grid gap spaces the cards, so the common "card after card" top margin is taken off (it pushed the second card down). */
.dw-i2__grid { display: grid; gap: var(--space-3); grid-template-columns: repeat(auto-fill, minmax(min(100%, 240px), 1fr)); }
.dw-i2__grid--wide { grid-template-columns: repeat(auto-fill, minmax(min(100%, 300px), 1fr)); }
.dw-i2__grid > .dw-card { margin: 0; min-width: 0; }
.dw-i2__num { white-space: nowrap; font-variant-numeric: tabular-nums; }
.dw-i2__town { margin: 0 0 var(--space-2); font-family: var(--text-h2-family); font-size: var(--text-h2-size); line-height: var(--text-h2-line); font-weight: var(--text-h2-weight); overflow-wrap: anywhere; }
/* Players by level: "level - count" cells, two columns on the phone. */
.dw-i2__lv { display: grid; gap: 0 var(--space-4); grid-template-columns: repeat(auto-fill, minmax(120px, 1fr)); }
.dw-i2__lvc { display: flex; justify-content: space-between; align-items: baseline; gap: var(--space-2); padding: 5px 0; border-bottom: 1px solid var(--line-2); font-size: var(--text-body-sm-size); line-height: var(--text-body-sm-line); }

/* Exchange chart: the picture drawn by the server is 400x200 - never wider than the card. */
.dw-i2__chart { display: block; width: 100%; max-width: 400px; height: auto; margin: 0 0 var(--space-2); border: 1px solid var(--line); border-radius: var(--radius-sm); }

/* Saving the e-mail: the one-time warning above the field. */
.dw-i2__warn { margin: 0; color: var(--danger-text); font-size: var(--text-body-sm-size); line-height: var(--text-body-sm-line); }
/* ==== /info2 ==== */
/* ==== /Tail pages ==== */
