/* Workflow standard, variant A. Approved 2026-08-08.
   Source of truth for how a workflow looks and behaves. Scoped to .wf-std,
   except the palette tokens and the page ground. A stage opts in with:
     <div class="stage shape-yours wf-std" data-workflow="Your Name">
   Must load AFTER the page stylesheet: it overrides earlier rules.
   See WORKFLOW-MODULE.md. */

    /* ==================================================================
       EDGE TREATMENT, variant A. Approved 2026-08-08.

       Three problems this fixes, in the order they were raised:
       1. Card faces were beige (#fbf7f0) on a white page, so nothing
          separated. Inverted: the ground is tinted, the faces are white.
       2. The Claude panel's header was a hairline on the same surface as
          its body, so it did not read as a header at all.
       3. The Slack message had no avatar, so nothing said a person or an
          app sent it.

       The move borrowed from Riveter is that colour lives on the EDGE as
       an extruded slab and the face stays neutral. Their isometric tilt
       is deliberately not copied: these cards are nodes in a flat flow
       and tilting them breaks every connector arrowhead.
       ================================================================== */

    :root{
      --bone:#f4f0ea;          /* the ground the cards sit on, now tinted */
      --paper:#ffffff;         /* the card face, now white */
      --edge-terra:#a8613f;    /* slab under a Claude surface */
      --edge-plum:#2f0d30;     /* slab under a Slack surface */
      --edge-quiet:rgba(31,41,47,.18);
      --inner:#f5f2ec;         /* inner strips, opaque now that the face is white */
      --inner-line:rgba(31,41,47,.07);
    }

    /* A later rule in the cascade sets the body background to white
       directly, so redefining --bone alone does not move the ground.
       Restate it here. The 72px grid lives on body:before and paints over
       this, so it stays.

       These two and the tokens above are the only page-wide rules in the
       standard. Everything below is scoped to .wf-std, so a card that has
       not opted in keeps exactly the look it had. */
    body{background:var(--bone)}
    .motion-field:after{background:linear-gradient(transparent,var(--bone))}

    /* --- the surface itself ------------------------------------------ */
    .wf-std .analysis,.wf-std .output,.wf-std .artifact{
      border:1px solid rgba(31,41,47,.1);
      background:#fff;
      -webkit-backdrop-filter:none;backdrop-filter:none;
      box-shadow:4px 4px 0 0 var(--edge,var(--edge-quiet)),
                 0 14px 30px -10px rgba(31,41,47,.24);
    }
    .wf-std .analysis:before,.wf-std .output:before,.wf-std .artifact:before{display:none}
    .wf-std .analysis{--edge:var(--edge-terra)}
    .wf-std .output.brief-card{--edge:var(--edge-plum)}
    /* .artifact.evidence-card carries its own box-shadow at higher specificity
       than the .artifact rule above, so the slab has to be restated here or
       the three intake slips stay flat while the big cards lift. The colour
       used to sit on a top border; the slab carries it now, one cue not two. */
    .wf-std .artifact.evidence-card{
      /* Vendor brand colours run hotter than the warm palette, so they are
         mixed toward a warm dark. The hue still says which tool it is. */
      --edge:color-mix(in srgb, rgb(var(--evidence-rgb)) 76%, #2b2018);
      border:1px solid rgba(31,41,47,.1);
      background:#fff;
      box-shadow:4px 4px 0 0 var(--edge),
                 0 12px 26px -10px rgba(31,41,47,.22);
    }
    .wf-std .artifact{background:#fff}

    /* --- the Claude panel header, now a real header ------------------- */
    .wf-std .analysis-head{
      margin:-11px -12px 0;padding:9px 12px 8px;
      border-bottom:1px solid rgba(196,121,91,.26);
      background:linear-gradient(180deg,rgba(196,121,91,.14),rgba(196,121,91,.05));
    }
    .wf-std .analysis{padding-top:11px}
    .wf-std .analysis-brand{color:#7d422a}
    .wf-std .analysis-head .run-when{color:#8a6a5c}

    /* --- inner strips need opaque fills now the face is white --------- */
    .wf-std .skill-run{margin-top:10px;border-color:var(--inner-line);background:var(--inner)}
    .wf-std .analysis-result{background:rgba(196,121,91,.08)}
    .wf-std .triage-row{background:#faf8f5;box-shadow:inset 0 0 0 1px var(--inner-line)}
    .wf-std .triage-row.vip{background:rgba(196,121,91,.11);box-shadow:inset 0 0 0 1px rgba(196,121,91,.2)}
    .wf-std .tool-content,.wf-std .artifact-body{background:#fff}
    .wf-std .tool-row{background:var(--inner)}
    .wf-std .evidence-icon{background:var(--inner);box-shadow:inset 0 0 0 1px var(--inner-line)}
    .wf-std .artifact-bar{border-bottom-color:var(--inner-line);background:var(--inner);box-shadow:none}

    /* --- a vendor mark on a filled chrome needs its own ground ---------
       Sampled from the assets: salesforce.webp is a #00a8d8 cloud and
       outreach.png is #6048ff, both on transparency. Put either on a chrome
       of its own brand colour and it disappears into it. Every mark on a
       filled chrome therefore sits on a solid white tile, which is the
       background these logos are drawn for.

       Two exceptions, both handled per workflow rather than here:
       a tinted Claude chrome sets .app back to transparent, because it is
       already a light ground; and an asset that is itself a solid coloured
       tile (hubspot.png is an opaque orange square) opts out and has its
       chrome matched to the asset instead.

       .wf-std is doubled in these selectors on purpose. The rules being
       replaced are things like `.brief-card .tool-chrome.slack-dm .app`, which
       carry four classes. A single .wf-std prefix loses to them and the tile
       silently stays translucent. Doubling ties the count, and this file loads
       after the page's own stylesheet, so it wins the tie. */
    .wf-std.wf-std .tool-chrome .app,
    .wf-std.wf-std .slack-chrome .app{
      width:20px;height:20px;
      border-radius:4px;
      background:#fff;
      box-shadow:inset 0 0 0 1px rgba(31,41,47,.12);
    }
    .wf-std.wf-std .tool-chrome .app > *,
    .wf-std.wf-std .slack-chrome .app > *{width:14px;height:14px;filter:none}

    /* One size for every intake slip mark. Inbox triage drew 20/15 and the
       others 22/17, which reads as a wobble down the page. */
    .wf-std.wf-std .evidence-icon{width:22px;height:22px}
    .wf-std.wf-std .evidence-icon > *{width:16px;height:16px}

    /* --- the Slack message, given the anatomy of a real one ----------- */
    .wf-std .brief-card .tool-chrome.slack-dm{border-bottom:0}
    .wf-std .slack-msg{display:flex;gap:9px;padding:10px 11px 11px}
    .wf-std .brief-av{
      display:grid;width:30px;height:30px;flex:none;place-items:center;
      border-radius:7px;background:var(--terra);
      box-shadow:inset 0 0 0 1px rgba(31,41,47,.12);
    }
    .wf-std .brief-av img{width:18px;height:18px;object-fit:contain;filter:brightness(0) invert(1)}
    .wf-std .brief-col{min-width:0;flex:1}
    .wf-std .brief-from{gap:5px;padding:0}
    .wf-std .brief-text{padding:3px 0 0}
    .wf-std .brief-actions{padding:7px 0 0}
    /* The action pills used to stagger in on their own chipIn animation,
       which made them the only part of the message that did not arrive with
       the card. The skill panel's rows and the reaction pills both just
       appear, so these now do too.

       Only opacity and animation are touched here. Setting a background as
       well would beat .go, .archive and .cal on specificity once scoped,
       and paint the dark primary pill white on white. */
    .wf-std .brief-actions i{
      opacity:1;
      animation:none;
      animation-delay:0s;
    }
    .wf-std .slack-reacts{padding:7px 0 0}
    .wf-std .slack-reacts i{background:#fff}
    .wf-std .slack-reacts.mine i{background:rgba(106,142,139,.13)}

    /* --- hover, switched on per card as the diagram builds -------------
       A card becomes hoverable the moment the connector leaving it starts
       to draw, so each one goes live in the order the workflow runs. The
       last card in a chain has no outgoing connector and goes live when it
       has finished arriving. The class is added by the script at the foot
       of the page and is never taken away.

       The cards already animate `transform` on the 23s loop, so a hover
       `transform` would be overridden by the running animation. `translate`
       is an independent property and composes on top of it instead. */
    @media (hover:hover){
      .artifact.hover-ready,
      .analysis.hover-ready,
      .output.hover-ready{
        transition:translate .18s cubic-bezier(.2,.7,.3,1),
                   box-shadow .18s cubic-bezier(.2,.7,.3,1),
                   border-color .18s ease;
      }
      .artifact.hover-ready:hover,
      .analysis.hover-ready:hover,
      .output.hover-ready:hover{
        z-index:9;
        translate:-3px -4px;
        border-color:rgba(31,41,47,.2);
        box-shadow:7px 8px 0 0 var(--edge,var(--edge-quiet)),
                   0 24px 46px -12px rgba(31,41,47,.3);
      }
    }
    @media (prefers-reduced-motion:reduce){
      .artifact.hover-ready:hover,
      .analysis.hover-ready:hover,
      .output.hover-ready:hover{translate:none}
    }

    /* The outline is a full-size div laid over the whole diagram. It is
       decorative, but it was hit-testing above the left column, whose cards
       sit at the default z-index while the middle and right cards sit at 4.
       That is why only the first column ignored the mouse. */
    .wf-std .system-boundary{pointer-events:none}

    /* --- the outline now closes a full circuit around the label pill ---
       It used to start at the top right corner, run right, bottom, left,
       top, and stop at the pill's left edge, so the top right stretch was
       never traced by the glow.

       Now it starts at the pill's right edge, runs the whole way round and
       finishes at the pill's left edge. The pill sits in the gap. That
       needs the top edge split in two, drawn first and last, so the order
       is top-a, right, bottom, left, top-b.

       The pill measures 3.59% to 11.64% along the outline, so the glow
       leaves at 11.9% and lands at 3.5%. Stop times are apportioned by
       segment length, which keeps the glow at a near constant speed.

       The glow departs at 55.5789%, the same instant the boundary and its
       pill start to fade in, so there is no wait between the pill landing
       and the trace beginning. It still closes at 69.0526% as before, so
       the circuit is traced more evenly rather than pausing then darting.

       The outline used to be four straight bars that met at square corners,
       with a rounded box fading in over them once they finished. That is
       what made the corners snap from sharp to round. It is one rounded
       path now, drawn by its own dash offset, so the corners are round from
       the first frame.

       Because both the stroke and the glow are driven by distance along the
       same path, they stay in step and move at a genuinely constant speed,
       with no per-segment timing to keep in sync by hand. The path is built
       by the script at the foot of the page, which needs the pixel size of
       the boundary and so re-runs on resize. */
    .wf-std .boundary-trace{position:absolute;z-index:1;inset:0;overflow:visible;pointer-events:none}
    .wf-std .boundary-trace path{
      fill:none;
      stroke:rgba(31,41,47,.22);
      stroke-width:1;
      stroke-linecap:round;
      stroke-dasharray:var(--trace-len,0);
      stroke-dashoffset:var(--trace-len,0);
      animation:traceDraw 23s linear infinite;
    }
    /* shape-funnel and wf-std sit on the same element, so this has to be a
       compound selector. As a descendant it silently matches nothing. */
    /* The travelling glow is off. Retired 2026-08-08.

       The outline drawing itself is the useful signal. The glow rode round on
       every one of the 23 second loops, which pulled the eye away from a
       diagram that had already finished assembling and that the reader was
       trying to actually read.

       Everything needed to bring it back is still here: delete the display
       rule below and the two lines under it take over again. The keyframes and
       the offset-path the script assigns are both untouched. */
    .wf-std .boundary-glow{display:none}
    .wf-std .boundary-glow{animation:glowRide 23s linear infinite}
    .wf-std .boundary-glow{top:0;left:0;offset-rotate:0deg;offset-anchor:50% 50%}

    @keyframes traceDraw{
      0%,45.913%{opacity:1;stroke-dashoffset:var(--trace-len,0)}
      57.0435%{opacity:1;stroke-dashoffset:0}
      57.7391%,100%{opacity:0;stroke-dashoffset:0}
    }
    @keyframes glowRide{
      0%,45.7652%{opacity:0;offset-distance:0%}
      45.913%{opacity:1;offset-distance:0%}
      57.0435%{opacity:1;offset-distance:100%}
      58.087%,100%{opacity:0;offset-distance:100%}
    }

    body[data-freeze] .wf-std .boundary-trace path{
      animation-delay:var(--freeze-delay,-17s)!important;
      animation-play-state:paused!important;
    }
