/* ——— Icons ———
   Glyphs from Lucide (lucide.dev), ISC licensed, vendored one SVG per icon so
   that `ls app/assets/images/*.svg` is the icon index the way `ls
   app/assets/stylesheets` is the component index. Add a glyph only when a
   surface actually uses it; the file and the line below land together.

   Masked, never <img>: the span is painted with currentColor and the SVG only
   supplies the shape. That is what lets one file serve a quiet button, a
   destructive row, a straw note and dark mode without a single icon variant —
   an <img> would need one per ink. Lucide's 2px stroke on a 24px grid lands at
   ~1.3px when the icon sizes itself to 1em, which is the hairline weight the
   rest of the design is drawn in.

   Size is --icon-size, so a control can retune it the way variants retune
   everything else here. */
@layer components {
  .icon {
    display: inline-block;
    flex-shrink: 0;
    inline-size: var(--icon-size, 1em);
    block-size: var(--icon-size, 1em);
    background-color: currentColor;
    mask-image: var(--svg);
    mask-position: center;
    mask-repeat: no-repeat;
    mask-size: contain;
    pointer-events: none;
    user-select: none;
  }

  .icon--activity { --svg: url("/assets/activity-a76c6b24.svg"); }
  .icon--arrow-down { --svg: url("/assets/arrow-down-9a42fbc0.svg"); }
  .icon--arrow-left { --svg: url("/assets/arrow-left-468377e2.svg"); }
  .icon--arrow-up { --svg: url("/assets/arrow-up-d973aad3.svg"); }
  .icon--at-sign { --svg: url("/assets/at-sign-5aae1fa1.svg"); }
  .icon--bell { --svg: url("/assets/bell-f2296f62.svg"); }
  .icon--bell-off { --svg: url("/assets/bell-off-94900c5f.svg"); }
  /* The outline/solid pair rule below applies here too: bookmarking a thing is
     the one mark on a page that has an on and an off state to draw. */
  .icon--bookmark { --svg: url("/assets/bookmark-60b88ba0.svg"); }
  .icon--bookmark-filled { --svg: url("/assets/bookmark-filled-795201e0.svg"); }
  .icon--building-2 { --svg: url("/assets/building-2-a007df8a.svg"); }
  .icon--check { --svg: url("/assets/check-af489e59.svg"); }
  .icon--chevrons-down-up { --svg: url("/assets/chevrons-down-up-18dd1593.svg"); }
  .icon--chevrons-up-down { --svg: url("/assets/chevrons-up-down-4d83ec75.svg"); }
  .icon--circle-check { --svg: url("/assets/circle-check-9fe1f780.svg"); }
  .icon--circle-check-big { --svg: url("/assets/circle-check-big-497433f4.svg"); }
  .icon--circle-user { --svg: url("/assets/circle-user-8c9182f6.svg"); }
  .icon--circle-x { --svg: url("/assets/circle-x-258ebd5f.svg"); }
  .icon--clock { --svg: url("/assets/clock-5e13df23.svg"); }
  .icon--download { --svg: url("/assets/download-8f147ef2.svg"); }
  .icon--ellipsis { --svg: url("/assets/ellipsis-ed7720ee.svg"); }
  .icon--file-text { --svg: url("/assets/file-text-afd3bfe7.svg"); }
  .icon--house { --svg: url("/assets/house-342396d0.svg"); }
  /* Basecamp's own glyph for Adminland. Not building-2, which the palette
     already spends on Clients — two doors wearing one shape is worse than
     one extra file. */
  .icon--key-round { --svg: url("/assets/key-round-d3c66032.svg"); }
  .icon--life-buoy { --svg: url("/assets/life-buoy-0d4fe9d3.svg"); }
  .icon--link { --svg: url("/assets/link-dca6e5ee.svg"); }
  .icon--maximize-2 { --svg: url("/assets/maximize-2-b9a76d7c.svg"); }
  .icon--message-square { --svg: url("/assets/message-square-536d1494.svg"); }
  .icon--messages-square { --svg: url("/assets/messages-square-87334f72.svg"); }
  .icon--monitor { --svg: url("/assets/monitor-80e57ca3.svg"); }
  .icon--moon { --svg: url("/assets/moon-1126f0fd.svg"); }
  .icon--paperclip { --svg: url("/assets/paperclip-730eb538.svg"); }
  .icon--pencil { --svg: url("/assets/pencil-a6367e89.svg"); }
  .icon--plus { --svg: url("/assets/plus-77a3887e.svg"); }
  .icon--reply { --svg: url("/assets/reply-7a3459f6.svg"); }
  .icon--search { --svg: url("/assets/search-ee97fcb8.svg"); }
  .icon--share { --svg: url("/assets/share-8b9da490.svg"); }
  .icon--smile { --svg: url("/assets/smile-8072db22.svg"); }
  .icon--smile-plus { --svg: url("/assets/smile-plus-ce6ab853.svg"); }
  .icon--sliders-horizontal { --svg: url("/assets/sliders-horizontal-3cd67c92.svg"); }
  .icon--square-kanban { --svg: url("/assets/square-kanban-20aecf30.svg"); }
  .icon--type { --svg: url("/assets/type-b5593d8a.svg"); }
  /* Two shapes, not one shape and an opacity: a masked glyph is painted rather
     than drawn, so the outline and the solid are different masks. */
  .icon--star { --svg: url("/assets/star-1deeb2e3.svg"); }
  .icon--star-filled { --svg: url("/assets/star-filled-1657444d.svg"); }
  .icon--sun { --svg: url("/assets/sun-d4df8ba7.svg"); }
  .icon--trash-2 { --svg: url("/assets/trash-2-ccdef950.svg"); }
  .icon--x { --svg: url("/assets/x-8fdf8036.svg"); }

  /* ——— The card board's glyphs ———
     The board's markup began as fizzy's, so it asks for fizzy's icon NAMES.
     Fizzy draws them as <img>, which we cannot: an <img> carries its own ink,
     so it needs one file per surface and one more per theme, which is the
     whole reason this file masks instead. So the names are fizzy's and the
     shapes are Lucide's — aliases where we already vendored the same shape
     under a Lucide name. Only the names the board still speaks survive; the
     rest went with the surfaces that asked for them (2026-08-14 sweep). */
  .icon--add { --svg: url("/assets/plus-77a3887e.svg"); }
  .icon--collapse { --svg: url("/assets/chevrons-down-up-18dd1593.svg"); }
  .icon--grid { --svg: url("/assets/grid-2x2-50170731.svg"); }
}
