/* -- Chord Chart ------------------------------------------------
   One chord diagram: the figure (its caption, the frame of the active state) and the grid the runtime draws from
   data-shape - strings and fret wires as two gradients, the dots, the × of a muted string, a barre's dashed line, a
   capo's bold bar with the strings going on behind it. Across by default, as the player sees the fretboard (the nut
   on the fretting hand's side, the 1st string on top); upright with data-orientation="vertical". */

@layer components {
  .chord-chart {
    display: inline-grid;
    justify-items: center;
    gap: 0.25rem;
    margin: 0;
    padding: 0.375rem 0.625rem 0.5rem;
    border: 1px solid transparent;
    border-radius: var(--radius-md);
    color: var(--foreground);
    font-family: var(--font-sans);
    transition:
      background-color 120ms ease,
      border-color 120ms ease;

    & figcaption {
      font-size: 0.8125rem;
      font-weight: 700;
    }

    /* the chord sounding */
    &[data-active] {
      border-color: var(--primary);
      background-color: color-mix(in oklab, var(--primary) 10%, transparent);

      & figcaption {
        color: var(--primary);
      }

      &:not([data-colors]) .chord-chart-dot {
        background-color: var(--primary);
      }

      & .chord-chart-barre {
        border-color: var(--primary);
      }
    }
  }

  /* across (default): the nut on the fretting hand's side, the frets away from it, the strings from the 1st at the
     top; × before the nut on a muted string (nothing on an open one), a shape higher up names its first fret below */
  .chord-chart-grid {
    --chord-chart-strings: 4;
    --chord-chart-frets: 4;
    --chord-chart-tx: -50%;

    position: relative;
    inline-size: calc(var(--chord-chart-frets) * 1rem);
    block-size: calc((var(--chord-chart-strings) - 1) * 0.75rem);
    margin: 0.375rem 0.75rem 0.25rem;
    border-inline-start: 3px solid var(--foreground);
    background-image:
      linear-gradient(to right, var(--muted-foreground) 1px, transparent 1px),
      linear-gradient(to bottom, var(--muted-foreground) 1px, transparent 1px);
    background-size:
      calc((100% - 1px) / var(--chord-chart-frets)) 100%,
      100% calc((100% - 1px) / (var(--chord-chart-strings) - 1));

    /* a capo: the bold bar is the capo, the strings go on behind it to the fret wire before it */
    &[data-capo] {
      --chord-chart-behind: 1rem;

      margin-inline-start: calc(0.75rem + var(--chord-chart-behind));
      border-inline-start-width: 4px;

      &::before {
        position: absolute;
        inset-block: 0;
        inset-inline-end: calc(100% + 4px);
        inline-size: var(--chord-chart-behind);
        border-inline-start: 1px solid var(--muted-foreground);
        background-image: linear-gradient(to bottom, var(--muted-foreground) 1px, transparent 1px);
        background-size: 100% calc((100% - 1px) / (var(--chord-chart-strings) - 1));
        content: "";
      }
    }

    &[data-base] {
      margin-block-end: 1rem;
      border-inline-start-width: 1px;

      &::after {
        position: absolute;
        inset-block-start: calc(100% + 0.25rem);
        inset-inline-start: calc((100% - 1px) * 0.5 / var(--chord-chart-frets));
        color: var(--muted-foreground);
        content: attr(data-base) "fr";
        font-size: 0.625rem;
        line-height: 1;
        translate: var(--chord-chart-tx) 0;
      }
    }
  }

  .chord-chart-dot,
  .chord-chart-mark {
    position: absolute;
    inset-block-start: calc(
      (100% - 1px) * (var(--chord-chart-strings) - 1 - var(--chord-chart-i, 0)) / (var(--chord-chart-strings) - 1) +
        0.5px
    );
    translate: var(--chord-chart-tx) -50%;
  }

  .chord-chart-dot {
    inset-inline-start: calc((100% - 1px) * (var(--chord-chart-r, 0) + 0.5) / var(--chord-chart-frets));
    inline-size: 0.625rem;
    block-size: 0.625rem;
    border-radius: 50%;
    background-color: var(--chord-chart-color, var(--foreground));
  }

  .chord-chart-mark {
    inset-inline-start: calc(-0.625rem - var(--chord-chart-behind, 0rem));
    color: var(--chord-chart-color, var(--muted-foreground));
    font-size: 0.5625rem;
    line-height: 1;
  }

  /* a barre: one finger across its strings, a dashed line through them */
  .chord-chart-barre {
    position: absolute;
    inset-block-start: calc(
      (100% - 1px) * (var(--chord-chart-strings) - 1 - var(--chord-chart-j, 0)) / (var(--chord-chart-strings) - 1) +
        0.5px - 0.3125rem
    );
    inset-inline-start: calc((100% - 1px) * (var(--chord-chart-r, 0) + 0.5) / var(--chord-chart-frets));
    inline-size: 0;
    block-size: calc(
      (100% - 1px) * (var(--chord-chart-j, 0) - var(--chord-chart-i, 0)) / (var(--chord-chart-strings) - 1) + 0.625rem
    );
    border-inline-start: 3px dashed var(--foreground);
    translate: var(--chord-chart-tx) 0;
  }

  /* upright (data-orientation="vertical"), the classic chord chart: the nut on top, the strings from the
     highest-numbered on the left; × above the nut, a shape higher up names its first fret beside it */
  .chord-chart[data-orientation="vertical"] .chord-chart-grid {
    inline-size: calc((var(--chord-chart-strings) - 1) * 1rem);
    block-size: calc(var(--chord-chart-frets) * 0.875rem);
    margin: 0.75rem 0 0;
    border-inline-start: 0;
    border-block-start: 3px solid var(--foreground);
    background-size:
      calc((100% - 1px) / (var(--chord-chart-strings) - 1)) 100%,
      100% calc((100% - 1px) / var(--chord-chart-frets));

    &[data-capo] {
      margin: calc(0.75rem + var(--chord-chart-behind)) 0 0;
      border-block-start-width: 4px;

      &::before {
        inset-block: auto calc(100% + 4px);
        inset-inline: 0;
        inline-size: auto;
        block-size: var(--chord-chart-behind);
        border-inline-start: 0;
        border-block-start: 1px solid var(--muted-foreground);
        background-image: linear-gradient(to right, var(--muted-foreground) 1px, transparent 1px);
        background-size: calc((100% - 1px) / (var(--chord-chart-strings) - 1)) 100%;
      }
    }

    &[data-base] {
      border-block-start-width: 1px;

      &::after {
        inset-block-start: 0.4375rem;
        inset-inline-start: calc(100% + 0.25rem);
        translate: 0 -50%;
      }
    }

    .chord-chart-dot,
    .chord-chart-mark {
      inset-inline-start: calc((100% - 1px) * var(--chord-chart-i, 0) / (var(--chord-chart-strings) - 1) + 0.5px);
    }

    .chord-chart-dot {
      inset-block-start: calc((100% - 1px) * (var(--chord-chart-r, 0) + 0.5) / var(--chord-chart-frets));
    }

    .chord-chart-mark {
      inset-block-start: calc(-0.5rem - var(--chord-chart-behind, 0rem));
    }

    .chord-chart-barre {
      inset-block-start: calc((100% - 1px) * (var(--chord-chart-r, 0) + 0.5) / var(--chord-chart-frets));
      inset-inline-start: calc(
        (100% - 1px) * var(--chord-chart-i, 0) / (var(--chord-chart-strings) - 1) + 0.5px - 0.3125rem
      );
      inline-size: calc(
        (100% - 1px) * (var(--chord-chart-j, 0) - var(--chord-chart-i, 0)) / (var(--chord-chart-strings) - 1) + 0.625rem
      );
      block-size: 0;
      border-inline-start: 0;
      border-block-start: 3px dashed var(--foreground);
      translate: 0 -50%;
    }
  }

  /* for the right hand, mirrored: across the nut on the right, upright the strings 1st to highest from the left */
  .chord-chart[data-hand="right"] .chord-chart-grid {
    --chord-chart-tx: 50%;

    direction: rtl;
  }

  /* string colours (data-colors="strings"): string n takes chart colour n, from the 6th on they start over */
  .chord-chart[data-colors="strings"] {
    & :is([data-string="1"], [data-string="6"], [data-string="11"]) {
      --chord-chart-color: var(--chart-1);
    }
    & :is([data-string="2"], [data-string="7"], [data-string="12"]) {
      --chord-chart-color: var(--chart-2);
    }
    & :is([data-string="3"], [data-string="8"]) {
      --chord-chart-color: var(--chart-3);
    }
    & :is([data-string="4"], [data-string="9"]) {
      --chord-chart-color: var(--chart-4);
    }
    & :is([data-string="5"], [data-string="10"]) {
      --chord-chart-color: var(--chart-5);
    }

    /* a × in the string's colour mixed toward the text colour - legible in either mode */
    & .chord-chart-mark {
      color: color-mix(in oklab, var(--chord-chart-color, var(--foreground)) 55%, var(--foreground));
      font-weight: 700;
    }
  }

  @media (prefers-reduced-motion: reduce) {
    .chord-chart {
      transition: none;
    }
  }

  @media (prefers-contrast: more) {
    .chord-chart-grid {
      background-image:
        linear-gradient(to right, var(--foreground) 1px, transparent 1px),
        linear-gradient(to bottom, var(--foreground) 1px, transparent 1px);
    }
  }

  @media (forced-colors: active) {
    .chord-chart[data-active] {
      border-color: Highlight;

      & .chord-chart-dot {
        background-color: Highlight;
        forced-color-adjust: none;
      }
    }

    .chord-chart-dot {
      background-color: CanvasText;
      forced-color-adjust: none;
    }
  }
}
