/**
 * The quiz score shortcode: the arc, the marker riding it and the count under
 * them. The two texts are Desensitize Elements basic elements, so their type
 * comes from that stylesheet, and the arc's fill and the marker are painted
 * with the theme's gradient classes. This one only shapes them.
 *
 * The design lays the arc out in a box 360 across and half that tall, the band
 * running out to the sides of it and 44 wide, so the middle of the band is 158
 * out from the middle of the bottom edge, with a marker 64 across riding it.
 * Both ends of the band are turned whole, and are pulled in far enough that
 * those round ends stand on the bottom edge rather than hanging past it, which
 * puts them 8.0039 degrees up from it and leaves the arc 163.9922 degrees long.
 *
 * Every length here is a count of those design pixels, taken from the width the
 * gauge ends up drawn at, so the whole element scales as one picture the way an
 * image does, down to the hairline around the band: a phone and a tablet are
 * given the same arc as a desktop, only smaller, and nothing here is measured
 * twice. How wide it is drawn is a fluid size built the way the kit's own are,
 * a value for a phone, a tablet and a desktop. The caption is the exception,
 * since it is set in the site's type rather than the gauge's; those three
 * widths are the ones that hold it to the same share of the arc's opening at
 * each of them.
 *
 * The shortcode builds the band's path and the script turns the fill and the
 * marker from the same numbers, so all three are changed together.
 */

.ds-quiz-score {
    /* How wide the gauge is drawn at most is --ds-quiz-score-width, which is
       left unset here so that it can be set on the element or on anything it
       sits in; the gauge falls back to the size below and takes whatever it is
       given under that.

       The size, built the way the kit builds its own fluid sizes, phone,
       tablet and desktop. The caption inside the arc is set in the site's
       type, which comes down more steeply between a desktop and a tablet than
       the screen itself does, so a gauge held at the width the design draws it
       at would stand emptier and emptier the smaller the screen got. These
       three leave the caption the same share of the arc's opening on a phone
       and on a tablet as the design gives it on a desktop. */
    --ds-quiz-score-size: calc(clamp(216px, 294.17px - 10.178vw, 256px) + clamp(216px, 38.2px + 23.151vw, 360px) - 216px); /* 256px / 216px / 360px */

    /* One design pixel at the width the gauge ends up drawn at, which is what
       every length below is a count of. The cqi in it measures this element,
       the size container the gauge fills, so the count holds whether the gauge
       is drawn at the size above or taken in by something narrower. */
    --ds-quiz-score-px: calc( 100cqi / 360 );

    /* the marker, 64 across, and how far out it rides: the middle of the band,
       158 out from the middle of the bottom edge the arc is struck from */
    --ds-quiz-score-marker: calc( var(--ds-quiz-score-px) * 64 );
    --ds-quiz-score-orbit: calc( var(--ds-quiz-score-px) * 158 );

    /* the ring the fill is cut to: the band runs out to the sides of the box,
       180 from the middle it is struck from, and is 44 wide */
    --ds-quiz-score-outer: calc( var(--ds-quiz-score-px) * 180 );
    --ds-quiz-score-inner: calc( var(--ds-quiz-score-px) * 136 );

    /* the round end the fill starts from: half the band across, standing on
       the band's first point in the square the fill is painted on */
    --ds-quiz-score-cap-radius: calc( var(--ds-quiz-score-px) * 22 );
    --ds-quiz-score-cap-x: calc( var(--ds-quiz-score-px) * 23.5393 );
    --ds-quiz-score-cap-y: calc( var(--ds-quiz-score-px) * 158 );

    /* the border around the band and around the marker, the one the card deck
       and the accordion's bar are drawn with. The shortcode strikes the track's
       path half of it inside the band, since a stroke straddles its line where
       a border sits inside the box, and it strikes it in the design's own
       units, so the two hold to each other at every width. It is never let
       under a pixel, so the hairline still reads on the narrowest screen. */
    --ds-quiz-score-border: max( 1px, calc( var(--ds-quiz-score-px) * 1.7 ) );

    /* how far round the arc has come and where the marker stands on it, which
       the shortcode prints for the score as it was rendered and the script
       then takes over, how far the marker has grown in, and how far the round
       end has grown with it */
    --ds-quiz-score-sweep: 0deg;
    --ds-quiz-score-angle: -81.9961deg;
    --ds-quiz-score-grow: 1;
    --ds-quiz-score-cap: 1;

    /* the gauge and the caption share one cell: the caption sits inside the
       arc rather than below it, the way the design stacks them */
    display: grid;
    grid-template-areas: "gauge";
    justify-items: center;

    /* The element is the gauge's own width rather than the whole of whatever
       it is placed in, and is centred in that room, which is where the full
       width box it stands in for drew it. Being the gauge's width is what lets
       a design pixel be a share of the gauge: it is the size container the cqi
       above measures, and the gauge fills it. */
    width: min( 100%, var(--ds-quiz-score-width, var(--ds-quiz-score-size)) );
    margin-inline: auto;

    container-type: inline-size;

    /* the heading basic element takes its family from a wrapper, which the
       score is to it */
    font-family: var(--main-font);
}

/* Gauge
   -------------------------------------------------- */

.ds-quiz-score__gauge {
    grid-area: gauge;
    /* never stretched, so the ratio below is the one that sets the height */
    align-self: start;

    position: relative;
    isolation: isolate;

    width: 100%;
    aspect-ratio: 2 / 1;

    /* The band keeps to the box: its round ends stand on the bottom edge
       rather than hanging past it. The marker is wider than the band, so at
       either end of the run it does hang past, by the little it is wider.
       Nothing is cut off, since the whole point of the ends is that they are
       turned whole. */
    overflow: visible;
}

.ds-quiz-score__track {
    position: absolute;
    inset: 0;

    display: block;
    width: 100%;
    height: 100%;
}

/* The band the arc is drawn on, as one closed path rather than a stroke, so it
   carries both the site's secondary fill and the border around it, the way its
   secondary buttons do. The stroke is left out of the viewBox's scaling and
   given the border's own width, so it comes out the width the marker carries
   however wide the gauge is drawn. */
.ds-quiz-score__track__path {
    fill: var(--color-btn-secondary-bg-1, rgba( 117, 54, 74, 0.08 ));
    stroke: var(--color-btn-secondary-border-1, rgba( 117, 54, 74, 0.24 ));
    stroke-width: var(--ds-quiz-score-border);
}

/* The fill is the theme's gradient class, which paints a background rather
   than a stroke, so it is cut to shape instead: a square laid over the gauge
   with its middle on the gauge's bottom edge, cut once to how far round the
   arc has come and once to the band's ring.
   Two elements rather than one element cutting both ways, so nothing rests on
   two mask layers being composited. */
.ds-quiz-score__sweep {
    position: absolute;
    top: 0;
    left: 0;

    width: 100%;
    aspect-ratio: 1 / 1;

    /* from the band's first point, round over the top. A turn cuts straight
       across rather than round, so both of the ends it leaves are covered: the
       one the marker rides by the marker, the one it starts from by the cap */
    -webkit-mask-image: conic-gradient(
        from -81.9961deg at 50% 50%,
        #000 0deg,
        #000 var(--ds-quiz-score-sweep),
        transparent var(--ds-quiz-score-sweep),
        transparent 360deg
    );
    -webkit-mask-repeat: no-repeat;
    mask-image: conic-gradient(
        from -81.9961deg at 50% 50%,
        #000 0deg,
        #000 var(--ds-quiz-score-sweep),
        transparent var(--ds-quiz-score-sweep),
        transparent 360deg
    );
    mask-repeat: no-repeat;
}

/* A border cannot be given to a shape cut out of a background, so the arc is
   drawn twice over: once whole in the border's gradient, and once a border in
   from every edge in the fill's, the second laid over the first so the first is
   left showing as the border. The round end is drawn the same way, and both of
   its layers come first, so that where the two shapes cross, the fills cover
   the border each would otherwise draw through the other.

   Every one of the four is the same square in the same place, so the gradients
   across them line up to the pixel and the whole arc reads as one shape. */
.ds-quiz-score__edge,
.ds-quiz-score__fill,
.ds-quiz-score__cap,
.ds-quiz-score__cap__fill {
    position: absolute;
    top: 0;
    left: 0;

    width: 100%;
    aspect-ratio: 1 / 1;

    /* the gradient class paints its border through a transparent one, and these
       are cut to shape rather than bordered. Only the width is set, so the
       color the class puts on it is left where it is */
    border-width: 0;

    -webkit-mask-repeat: no-repeat;
    mask-repeat: no-repeat;
}

/* The border is the gradient the theme's .ds-bg-gd-* class paints its own
   border with, the same one the marker's border is, which the shortcode names
   by the color the arc is drawn in. */
.ds-quiz-score__edge,
.ds-quiz-score__cap {
    background: var(--ds-quiz-score-edge, var(--ds-global-border-gd-1));
}

/* The band's ring, and the ring a border in from both of its edges. Each edge
   is carried across a pixel rather than cut at one stop, which is what keeps
   the arc's sides smooth however large it is drawn. */
.ds-quiz-score__edge {
    -webkit-mask-image: radial-gradient(
        closest-side at 50% 50%,
        transparent calc( var(--ds-quiz-score-inner) - 0.5px ),
        #000 calc( var(--ds-quiz-score-inner) + 0.5px ),
        #000 calc( var(--ds-quiz-score-outer) - 0.5px ),
        transparent calc( var(--ds-quiz-score-outer) + 0.5px )
    );
    mask-image: radial-gradient(
        closest-side at 50% 50%,
        transparent calc( var(--ds-quiz-score-inner) - 0.5px ),
        #000 calc( var(--ds-quiz-score-inner) + 0.5px ),
        #000 calc( var(--ds-quiz-score-outer) - 0.5px ),
        transparent calc( var(--ds-quiz-score-outer) + 0.5px )
    );
}

.ds-quiz-score__fill {
    -webkit-mask-image: radial-gradient(
        closest-side at 50% 50%,
        transparent calc( var(--ds-quiz-score-inner) + var(--ds-quiz-score-border) - 0.5px ),
        #000 calc( var(--ds-quiz-score-inner) + var(--ds-quiz-score-border) + 0.5px ),
        #000 calc( var(--ds-quiz-score-outer) - var(--ds-quiz-score-border) - 0.5px ),
        transparent calc( var(--ds-quiz-score-outer) - var(--ds-quiz-score-border) + 0.5px )
    );
    mask-image: radial-gradient(
        closest-side at 50% 50%,
        transparent calc( var(--ds-quiz-score-inner) + var(--ds-quiz-score-border) - 0.5px ),
        #000 calc( var(--ds-quiz-score-inner) + var(--ds-quiz-score-border) + 0.5px ),
        #000 calc( var(--ds-quiz-score-outer) - var(--ds-quiz-score-border) - 0.5px ),
        transparent calc( var(--ds-quiz-score-outer) - var(--ds-quiz-score-border) + 0.5px )
    );
}

/* The round end the fill starts from. A turn cuts straight across, so the end
   the fill is left with is squared off; this puts a circle of the band's own
   width back on the band's first point and turns it whole, with the same border
   a border in from its edge.

   The circle grows in with the marker, which starts on the very same point and
   is wider, so it is not seen at all until the marker has moved off it. */
.ds-quiz-score__cap {
    -webkit-mask-image: radial-gradient(
        ellipse
        calc( var(--ds-quiz-score-cap-radius) * var(--ds-quiz-score-cap) )
        calc( var(--ds-quiz-score-cap-radius) * var(--ds-quiz-score-cap) )
        at var(--ds-quiz-score-cap-x) var(--ds-quiz-score-cap-y),
        #000 calc( 100% - 0.5px ),
        transparent 100%
    );
    mask-image: radial-gradient(
        ellipse
        calc( var(--ds-quiz-score-cap-radius) * var(--ds-quiz-score-cap) )
        calc( var(--ds-quiz-score-cap-radius) * var(--ds-quiz-score-cap) )
        at var(--ds-quiz-score-cap-x) var(--ds-quiz-score-cap-y),
        #000 calc( 100% - 0.5px ),
        transparent 100%
    );
}

/* The border is taken off the circle before it is grown rather than after, so
   that a circle still growing in is never asked for a width under zero, which
   would leave the square it is cut from uncut and paint the whole gradient.
   It costs the border its width while the circle grows, which is over by the
   time the marker has moved off it and let it be seen at all. */
.ds-quiz-score__cap__fill {
    --ds-quiz-score-cap-fill: calc( ( var(--ds-quiz-score-cap-radius) - var(--ds-quiz-score-border) ) * var(--ds-quiz-score-cap) );

    -webkit-mask-image: radial-gradient(
        ellipse var(--ds-quiz-score-cap-fill) var(--ds-quiz-score-cap-fill)
        at var(--ds-quiz-score-cap-x) var(--ds-quiz-score-cap-y),
        #000 calc( 100% - 0.5px ),
        transparent 100%
    );
    mask-image: radial-gradient(
        ellipse var(--ds-quiz-score-cap-fill) var(--ds-quiz-score-cap-fill)
        at var(--ds-quiz-score-cap-x) var(--ds-quiz-score-cap-y),
        #000 calc( 100% - 0.5px ),
        transparent 100%
    );
}

/* The marker rides the middle of the band. It is anchored at the middle of the
   gauge's bottom edge, which the arc is struck from, and swung out from there:
   turned to where it stands, pushed out to the band, then turned back, so the
   gradient on it stays upright however far round it has come.
   The fill and its border are the theme's .ds-bg-gd-* class, which paints the
   border through a transparent one, as on the card deck's progress bar. */
.ds-quiz-score__marker {
    position: absolute;
    top: 100%;
    left: 50%;
    z-index: 1;

    box-sizing: border-box;
    width: var(--ds-quiz-score-marker);
    aspect-ratio: 1 / 1;

    border-style: solid;
    border-width: var(--ds-quiz-score-border);
    border-radius: 50%;

    transform:
        translate( -50%, -50% )
        rotate( var(--ds-quiz-score-angle) )
        translateY( calc( var(--ds-quiz-score-orbit) * -1 ) )
        rotate( calc( var(--ds-quiz-score-angle) * -1 ) )
        scale( var(--ds-quiz-score-grow) );
}

/* Caption
   -------------------------------------------------- */

.ds-quiz-score__caption {
    grid-area: gauge;
    /* inside the arc, standing on the line its ends stand on */
    align-self: end;

    display: flex;
    flex-direction: column;
    align-items: center;
    /* the gap and the type are the site's own rather than the gauge's, since
       the caption is set the way the site sets a heading; the three sizes
       above are the ones set against them */
    gap: 0;

    /* the arc's opening, 272 across, rather than the whole of the gauge, so a
       longer wording turns inside the arc rather than running out past the
       ends of it */
    max-width: calc( var(--ds-quiz-score-px) * 272 );

    text-align: center;
}

/* Both numbers are set as one line, the way the design draws them. */
.ds-quiz-score__score {
    white-space: nowrap;
}

/* Running
   -------------------------------------------------- */

/* Before the script has taken the element over it is drawn for the score it
   was printed with, so a page whose script never runs still reads. Once it has,
   the parts that come in are set back, and reaching the results brings them.
   The fade is declared on the run rather than on the setting back, so being
   taken over is not itself a fade out, and so leaving the results puts the
   element back where it started in one go. */
.ds-quiz-score--ready .ds-quiz-score__track,
.ds-quiz-score--ready .ds-quiz-score__marker {
    opacity: 0;
}

.ds-quiz-score--ready .ds-quiz-score__caption {
    opacity: 0;
    transform: translateY( calc( var(--ds-quiz-score-px) * 8 ) );
}

.ds-quiz-score--playing .ds-quiz-score__track,
.ds-quiz-score--playing .ds-quiz-score__marker {
    opacity: 1;

    transition: opacity 0.42s ease-out;
}

.ds-quiz-score--playing .ds-quiz-score__caption {
    opacity: 1;
    transform: none;

    transition:
        opacity 0.56s ease-out,
        transform 0.72s cubic-bezier( 0.22, 1, 0.36, 1 );
}

/* A reader who has asked their system for less movement is shown the score as
   it ends: the script sets the gauge where it stops rather than running it,
   and nothing here fades in ahead of it. */
@media ( prefers-reduced-motion: reduce ) {
    .ds-quiz-score--playing .ds-quiz-score__track,
    .ds-quiz-score--playing .ds-quiz-score__marker,
    .ds-quiz-score--playing .ds-quiz-score__caption {
        transition: none;
    }
}
