# GAB-144 · InteractiveMapExplorer — « Carte explorable »

**Archétype / renderer_key :** `text_cta` (cartographie) · **module :** EdTechInteractiveLearning
**Critère validé :** changer le JSON change les zones/filtres/textes sans modifier le HTML. ✅ check.py 12/12.

## Pack (structure officielle par-GAB)
```
GAB-144/
  renderer.html            ← moteur carte explorable (ne pas modifier par instance)
  instance.example.json    ← SOURCE DE VÉRITÉ (contenu réel, à plat)
  schema.contract.json     ← contrat de validation
  README-contract.md       ← ce fichier
```

## Archétype
Carte avec zones cliquables (positionnées en % dans un canvas 16/10), filtrables par catégorie. Clic sur une zone → info-panel en bas (titre + sous-titre depuis `info_subtitle_pattern`). Filtre "Tous" réinitialise la visibilité. Bouton CTA optionnel (reset).

## Champs requis (instance, à plat)
`gab_id` · `map_explorer_id` · `zones[]{id,name,cat,pop,top_pct,left_pct}` · `categories[]{key,label,emoji,color_class}`

Optionnels : `title`, `instruction`, `filter_label`, `filter_all_label`, `info_empty_text`, `info_subtitle_pattern`, `primary_cta{label,action}`, `accessibility{map_aria_label,zone_aria_hint}`, `child_safety`.

## Ce qui vient du JSON vs HTML
- **JSON** : chaque zone (nom, catégorie, population, position), les catégories/filtres, les libellés, le texte vide du panel, le pattern de sous-titre, le libellé du bouton CTA.
- **HTML** : canvas 16/10 avec forme de fond, système de filtres chip, info-panel live-region, layout, couleurs de classe par catégorie.

## Garde-fous (child_safety)
- **Aucun lien externe** : pas de href vers des sites tiers.
- **Contenu pédagogique scolaire** uniquement : géographie, biologie, histoire spatialisée (cf. use_when source).
- **BLOCKED** si `zones` absent/vide · `categories` absent/vide · `gab_id` absent.

## QA à vérifier
1. Modifier une `zone.name`/`pop` → info-panel change sans toucher au HTML (critère d'or).
2. `zones:[]` → BLOCKED propre dans le panel d'erreur.
3. `categories:[]` → BLOCKED propre.
4. Clic zone → info-panel affiche nom + sous-titre interpolé depuis `info_subtitle_pattern`.
5. Filtre "large" → seule Paris visible à pleine opacité, autres dim.
6. Bouton CTA → filtre reset à "Tous", toutes zones visibles.
7. Injection `ENGINE.init(autreInstance)` → rendu change sans recharger la page.
8. Responsive 375/768/1024 — canvas conserve aspect-ratio 16/10, aucun débordement.

## Source
`INDEX-300-interactivelearning-GAB-141-145-PLAYABLE.html` (stage `data-tpl="144"`, handlers `mxFilter` / `mxShow`, styles `.mx-*`).
Positions extraites du CSS hardcodé : `.mx-z1` top:26% left:42%, `.mx-z2` top:60% left:32%, `.mx-z3` top:65% left:58%, `.mx-z4` top:38% left:28%.
