# Mathe-Forscherprotokoll SDK

Kleines dependency-freies JavaScript-SDK fuer das postMessage-Protokoll zwischen mathe.digital und eingebetteten Mathe-Lern-Apps. Die IIFE-Datei wird unter `https://mathe.digital/sdk/forscher-protokoll.js` ausgeliefert.

## Quickstart: Level 1 in 10 Zeilen

```html
<script src="https://mathe.digital/sdk/forscher-protokoll.js"></script>
<script>
const mf = ForscherProtokoll.createForscherApp({
  manifest: { name: 'Meine App', version: '1.0.0' },
  getState: () => ({ state: { punkte: 3 }, beschreibung: 'Das Kind hat drei Punkte gelegt.' })
});
mf.ready();
button.onclick = () => {
  mf.action('check', 'aufgabe');
  mf.complete({ richtig: true });
};
</script>
```

Ausserhalb eines iframes oder ohne `?matheforscher=1` sind alle Sendemethoden no-ops. Sobald die Plattform `matheforscher:hello` sendet, erkennt das SDK die Einbettung und antwortet mit `ready`.

## Ohne Build-Tool

```html
<script src="https://mathe.digital/sdk/forscher-protokoll.js"></script>
<script>
const mf = ForscherProtokoll.createForscherApp({ manifest: { name: 'Zwanzigerfeld' } });
mf.ready({ zr: 20 });
</script>
```

Lokal in diesem Projekt liegt die Datei unter `/sdk/forscher-protokoll.js`, also z.B. `<script src="/sdk/forscher-protokoll.js"></script>`.

## Mit Bundler

```js
import { createForscherApp } from './forscher-protokoll.esm.js';

const mf = createForscherApp({
  manifest: { name: 'Zwanzigerfeld', supportedParams: { zr: { type: 'number', default: 20 } } },
  getState: () => ({ anzahl: 7 })
});

mf.ready({ zr: 20 });
```

## Optionen

`createForscherApp(options)` akzeptiert:

- `manifest`: optionale Selbstbeschreibung fuer `matheforscher:ready`, z.B. `name`, `description`, `kindActions`, `stateSchema`, `defaultParams`, `supportedParams`, `iconUrl`, `version`, `highlightTargets`, `performableActions`.
- `getState()`: liefert entweder direkt das State-Objekt oder `{ state, beschreibung }`.
- `onSetConfig(config)`: wird bei `matheforscher:set-config` aufgerufen. Danach sendet das SDK automatisch `matheforscher:configured` mit der aktiven Config.
- `onHighlight(targets, style)`: wird bei `matheforscher:highlight` aufgerufen. Rueckgabe optional: `{ applied, ignored }`; das SDK sendet `highlighted`.
- `onPerform(steps, mode)`: wird bei `matheforscher:perform` aufgerufen. Rueckgabe optional: `{ mode, appliedSteps, skippedSteps }`; das SDK sendet `performed`.
- `screenshot()`: liefert eine Data-URL oder `null`; bedient `matheforscher:request-screenshot` und sendet `screenshot`.

## Methoden

- `mf.ready(config?)`: sendet `matheforscher:ready` mit `payload.config`, `payload.supportedParams` und `payload.manifest`. Bei spaeterem `hello` oder `discover` sendet das SDK `ready` erneut.
- `mf.state(state?, beschreibung?)`: sendet `matheforscher:state`. Ohne Argumente wird `getState()` genutzt.
- `mf.stateDebounced(state?, beschreibung?)`: wie `state`, aber 300 ms gedrosselt.
- `mf.action(action, target?, payload?, beschreibung?)`: sendet eine bedeutsame Kind-Handlung.
- `mf.progress(teilaufgabeHinweis)`: sendet sichtbaren Zwischenfortschritt.
- `mf.complete(payload?)`: sendet einen informativen Abschluss-Hinweis.
- `mf.error(message)`: meldet einen App-internen Fehler an die Plattform.
- `mf.isEmbedded`: boolean, ob das SDK aktuell von einer Einbettung ausgeht.

## Automatische Plattform-Events

Das SDK verarbeitet eingehende Nachrichten nur, wenn `event.data.type` mit `matheforscher:` beginnt. Es beantwortet `hello` und `discover` mit `ready`, `set-config` mit `configured`, `get-state` mit `state`, `request-screenshot` mit `screenshot`, `highlight` mit `highlighted` und `perform` mit `performed`.

Alle ausgehenden Nachrichten gehen an `window.parent.postMessage(message, '*')`. Nicht serialisierbare Payloads werden per `console.warn` gemeldet, ohne die App abstuerzen zu lassen.

## `get-state` und `beschreibung` in v2

`matheforscher:get-state` ist fuer v2 vorbereitet. Traegt die eingehende Nachricht ein `id`-Feld, spiegelt die Antwort es als `replyTo` im `matheforscher:state`-Event. `beschreibung` ist ein optionales semantisches Feld in `state`- und `action`-Messages, damit KI und Lehrkraft nicht nur Daten, sondern auch deren Bedeutung bekommen.
