// @vitest-environment node
/**
 * „Gesperrt sieht gesperrt aus“ – auch ohne Farbe.
 *
 * **Der Anlass.** Die Projektregel `aria-disabled` statt `disabled` ist
 * richtig: Ein natives `disabled` nähme dem Element den Fokus, und der
 * erklärende Satz daneben würde nie vorgelesen. Der Zustand wurde aber
 * **ausschließlich über Farbtoken** gezeichnet – heller Text auf versetztem
 * Grund. Im eigenen Hochkontrast-Thema ist `--farbe-text-leise` mit
 * `--farbe-text` identisch (beides `#ffffff`) und `--farbe-grund-versetzt`
 * mit dem Grund (`#000000`): Ein gesperrter Knopf sah dort **pixelgleich**
 * aus wie ein aktiver. Unter erzwungenen Farben fallen alle beteiligten Token
 * ohnehin auf `CanvasText` und `Canvas` zusammen.
 *
 * Wer Hochkontrast braucht, drückte also auf scheinbar bereite Knöpfe, ohne
 * dass etwas geschah – genau die Verwirrung, die der Kommentar in `lernen.css`
 * zu verhindern verspricht.
 *
 * Geprüft wird hier am Stilblatt, nicht im Browser: Ob eine gestrichelte
 * Linie im echten Fenster auffällt, sagt keine Messung – das ist Sichtprüfung
 * H8. Was sich hier feststellen lässt, ist, dass der Zustand überhaupt an
 * etwas anderem hängt als an einer Farbe, die in zwei von vier Darstellungen
 * mit ihrem Gegenstück zusammenfällt.
 */

import { readFileSync } from 'node:fs';
import { join } from 'node:path';
import { fileURLToPath } from 'node:url';

import { describe, expect, it } from 'vitest';

const wurzel = fileURLToPath(new URL('..', import.meta.url));

function stil(datei: string): string {
  return readFileSync(join(wurzel, 'src', 'renderer', 'src', 'styles', datei), 'utf8');
}

const LERNEN_CSS = stil('lernen.css');
const TOKENS_CSS = stil('tokens.css');

/** Der Regelblock ab einem Selektor bis zur schließenden Klammer. */
function block(css: string, selektor: string): string {
  const anfang = css.indexOf(selektor);
  expect(anfang, `Selektor nicht gefunden: ${selektor}`).toBeGreaterThan(-1);
  const auf = css.indexOf('{', anfang);
  const zu = css.indexOf('}', auf);
  return css.slice(auf, zu);
}

describe('Der Gesperrt-Zustand hängt nicht allein an der Farbe', () => {
  it('gibt gesperrten Knöpfen ein farbunabhängiges Merkmal', () => {
    const regel = block(LERNEN_CSS, ".knopf[aria-disabled='true']");

    expect(regel).toMatch(/border-style:\s*dashed/u);
  });

  it('belegt, warum die Farbe allein nicht trägt', () => {
    /* Die Gegenprobe zur Behebung: Wären die beiden Token im
       Hochkontrast-Thema verschieden, bräuchte es das zusätzliche Merkmal
       nicht – und dieser Test dürfte gelöscht werden. Solange sie
       zusammenfallen, ist er der Beleg für den Befund. */
    const hochkontrast = block(TOKENS_CSS, ":root[data-thema='hochkontrast']");
    const werte = new Map(
      [...hochkontrast.matchAll(/--([a-z-]+):\s*(#[0-9a-f]{6})\b/gu)].map((t) => [t[1], t[2]]),
    );

    expect(werte.get('farbe-text-leise')).toBe(werte.get('farbe-text'));
    expect(werte.get('farbe-grund-versetzt')).toBe(werte.get('farbe-grund'));
  });
});

describe('Erzwungene Farben (Windows-Kontrastdesign)', () => {
  it('kennzeichnet gesperrte Knöpfe mit der Systemfarbe GrayText', () => {
    /* Die einzige Farbe, die unter erzwungenen Farben einen Zustand
       ausdrücken darf – und die einzige, die Windows-Nutzer dafür kennen.
       Sie muss ausdrücklich gesetzt werden: Die Token fallen dort alle auf
       CanvasText zusammen. */
    const bereich = LERNEN_CSS.slice(LERNEN_CSS.indexOf('@media (forced-colors: active)'));
    const regel = block(bereich, ".knopf[aria-disabled='true']");

    expect(regel).toMatch(/color:\s*GrayText/u);
    expect(regel).toMatch(/border-color:\s*GrayText/u);
  });

  it('kennzeichnet auch gesperrte Schalter', () => {
    const bereich = LERNEN_CSS.slice(LERNEN_CSS.indexOf('@media (forced-colors: active)'));
    const regel = block(bereich, ".schalter__feld[aria-disabled='true'] + .schalter__beschriftung");

    expect(regel).toMatch(/color:\s*GrayText/u);
  });
});
