Playlab42 le laboratoire
GuidesCréer un Epic (Parcours pédagogique)

Créer un Epic (Parcours pédagogique)#

Ce guide vous accompagne dans la création d'un Epic, une collection de slides formant un parcours pédagogique cohérent sur PlayLab42.

Qu'est-ce qu'un Epic ?#

Un Epic est l'unité de publication dans le système Parcours :

  • Collection ordonnée de slides (1 à N)
  • Possède ses propres métadonnées (titre, auteur, vignette, etc.)
  • Organisé en sections optionnelles
  • Classé dans une hiérarchie et taggé pour le filtrage

Caractéristiques :

  • 100% statique (compatible GitHub Pages)
  • Slides en HTML ou Markdown (conversion automatique)
  • Support des médias (images, vidéos, audio)
  • Progression utilisateur sauvegardée

Prérequis#

  • Connaissances de base en HTML et/ou Markdown
  • Docker installé (make serve pour tester)

Structure d'un Epic#

parcours/epics/mon-epic/
├── epic.json                # Manifest de l'epic (obligatoire)
├── thumbnail.png            # Vignette (recommandée)
├── assets/                  # Médias partagés
│   ├── images/
│   │   └── schema.png
│   └── videos/
│       └── demo.mp4
└── slides/
    ├── 01-intro/
    │   ├── slide.json       # Métadonnées de la slide
    │   └── index.html       # ou index.md (contenu)
    └── 02-concepts/
        ├── slide.json
        └── index.md

Étapes#

1. Créer le dossier de l'Epic#

mkdir -p parcours/epics/mon-epic/slides/01-intro

Convention de nommage : kebab-case pour le nom du dossier.

2. Créer le manifest epic.json#

{
  "id": "mon-epic",
  "title": "Mon Premier Epic",
  "description": "Description courte (1-3 phrases) de l'epic.",
  "hierarchy": ["playlab42"],
  "tags": ["howto", "debutant"],
  "metadata": {
    "author": "Votre Nom",
    "created": "2025-01-15",
    "duration": "15 min",
    "difficulty": "beginner",
    "language": "fr"
  },
  "icon": "📚",
  "thumbnail": "thumbnail.png",
  "content": [
    { "id": "01-intro" }
  ]
}

Champs du manifest#

ChampObligatoireDescription
id✅Identifiant unique = nom du dossier
title✅Titre affiché
description✅Description courte (1-3 phrases)
hierarchy✅Position dans la hiérarchie (["playlab42"] ou ["autres"])
tags✅Tags pour le filtrage
metadata.author✅Auteur de l'epic
metadata.created✅Date de création (ISO 8601)
metadata.updatedDate de dernière modification
metadata.durationDurée estimée ("15 min", "2h")
metadata.difficulty"beginner", "intermediate", "advanced"
metadata.languageLangue ("fr", "en")
iconEmoji pour l'icône
thumbnailChemin vers la vignette (380x180px, 19:9, < 50KB)
content✅Liste des slides et sections
drafttrue pour ne pas publier

3. Créer les slides#

Chaque slide est un dossier avec slide.json et un fichier de contenu.

Format slide.json#

{
  "id": "01-intro",
  "title": "Introduction",
  "icon": "👋"
}
ChampObligatoireDescription
id✅Identifiant = nom du dossier
title✅Titre affiché dans le menu
iconEmoji pour l'icône
descriptionDescription courte
durationDurée estimée

Contenu HTML (index.html)#

<!DOCTYPE html>
<html lang="fr">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>Introduction - PlayLab42</title>
  <link rel="stylesheet" href="../../../../../lib/theme.css">
  <link rel="stylesheet" href="../../../../_shared/slide-base.css">
  <script type="module">
    import { initTheme } from '../../../../../lib/theme.js';
    initTheme();
  </script>
</head>
<body>
  <article class="slide">
    <h1>Introduction</h1>
    <p>Bienvenue dans ce parcours !</p>

    <h2>Objectifs</h2>
    <ul>
      <li>Premier objectif</li>
      <li>Deuxième objectif</li>
    </ul>
  </article>
</body>
</html>

Contenu Markdown (index.md) - Recommandé#

# Introduction

Bienvenue dans ce parcours !

## Objectifs

- Premier objectif
- Deuxième objectif

## Code d'exemple

```javascript
function hello() {
  console.log("Hello World!");
}

Note : Les slides Markdown sont converties automatiquement en HTML lors du build.


**Avantages du Markdown :**
- Plus simple et rapide à écrire
- Coloration syntaxique automatique pour le code
- Conversion automatique lors du `build:parcours`

**Source et sorties générées :**
- `index.md` est la source ; chaque build régénère `index.html` avec le Markdown,
  le titre de `slide.json` et le template courant `parcours/_shared/slide-template.html`.
- La sortie commence exactement par `<!-- playlab42:generated-from-index.md -->`
  suivi d'un saut de ligne LF à l'écriture. La reconnaissance accepte LF ou CRLF
  (par exemple après un checkout Git), mais uniquement ce commentaire exact
  en première ligne. Ne pas modifier cette sortie ni retirer son marqueur :
  les modifications manuelles seraient perdues au prochain build.
- Un `index.html` auteur seul reste intact et ne nécessite pas le template.
- Une paire `index.md` / `index.html` sans marqueur est ambiguë : le build échoue,
  sans écraser le HTML ni remplacer `data/parcours.json`. Aucun choix de source
  ne dépend de dates, du contenu ou du champ optionnel `format`.
- Pour migrer une ancienne sortie sans marqueur, relire et sauvegarder le HTML
  hors des sources, puis supprimer **uniquement cette sortie** et reconstruire
  depuis `index.md`. Si le HTML est la source à conserver, retirer `index.md`.
- Un template absent avec du Markdown, ou un HTML marqué dont `index.md` a
  disparu, fait échouer le build. Pour adopter volontairement une sortie comme
  HTML auteur, retirer le Markdown et le marqueur après revue.

### 4. Organiser avec des sections

Pour structurer un epic avec plusieurs slides, utilisez des sections :

```json
{
  "id": "mon-epic",
  "title": "Mon Epic",
  "description": "...",
  "hierarchy": ["playlab42"],
  "tags": ["tutorial"],
  "metadata": {
    "author": "Auteur",
    "created": "2025-01-15"
  },
  "content": [
    {
      "id": "introduction",
      "title": "Introduction",
      "icon": "👋",
      "content": [
        { "id": "01-bienvenue" },
        { "id": "02-prerequis" }
      ]
    },
    {
      "id": "pratique",
      "title": "Mise en pratique",
      "icon": "🛠️",
      "content": [
        { "id": "03-exercice-1" },
        { "id": "04-exercice-2" }
      ]
    },
    { "id": "05-conclusion" }
  ]
}

5. Marquer des slides optionnelles#

{
  "content": [
    { "id": "01-intro" },
    { "id": "02-avance", "optional": true },
    { "id": "03-conclusion" }
  ]
}

Une section entière peut aussi être optionnelle :

{
  "id": "bonus",
  "title": "Pour aller plus loin",
  "icon": "🚀",
  "optional": true,
  "content": [
    { "id": "bonus-01" },
    { "id": "bonus-02" }
  ]
}

6. Ajouter des médias#

Structure recommandée#

mon-epic/
├── assets/
│   ├── images/
│   │   ├── schema.png
│   │   └── capture.jpg
│   └── videos/
│       └── demo.mp4
└── slides/
    └── 01-intro/
        └── index.html

Référencer dans HTML#

<!-- Image depuis les assets de l'epic -->
<img src="../../assets/images/schema.png" alt="Schéma explicatif">

<!-- Vidéo -->
<video controls>
  <source src="../../assets/videos/demo.mp4" type="video/mp4">
</video>

Référencer dans Markdown#

![Schéma explicatif](../../assets/images/schema.png)

<!-- Pour vidéo/audio, utiliser HTML inline -->
<video controls src="../../assets/videos/demo.mp4"></video>

Limites de taille#

ÉlémentLimite
Image< 500KB
Vidéo< 10MB
Audio< 5MB
Vignette380x180px (19:9), < 50KB
Total Epic< 50MB

7. Générer le catalogue#

make build-parcours

Le build :

  • Valide les manifests
  • Convertit les slides Markdown en HTML
  • Génère data/parcours.json

8. Tester#

make serve
# Ouvrir http://localhost:5242
# Naviguer vers l'onglet "Parcours"

Exemples#

Epic minimal (1 slide Markdown)#

parcours/epics/exemple-article/
├── epic.json
└── slides/
    └── 01-introduction/
        ├── slide.json
        └── index.md

epic.json

{
  "id": "exemple-article",
  "title": "Mon Article",
  "description": "Un article simple.",
  "hierarchy": ["autres"],
  "tags": ["article"],
  "metadata": {
    "author": "Moi",
    "created": "2025-01-15"
  },
  "content": [
    { "id": "01-introduction" }
  ]
}

slides/01-introduction/slide.json

{
  "id": "01-introduction",
  "title": "Introduction"
}

slides/01-introduction/index.md

# Introduction

Bienvenue dans mon article !

## Points clés

- Point 1
- Point 2
- Point 3

Epic complet avec sections#

Voir l'epic hello-playlab42 dans parcours/epics/hello-playlab42/ pour un exemple complet avec :

  • Vignette
  • Sections multiples
  • Slides HTML et Markdown
  • Assets

Checklist de validation#

Avant de publier votre epic, vérifiez :

  • epic.json contient tous les champs obligatoires
  • Chaque slide référencée dans content existe dans slides/
  • Chaque slide a un slide.json et un index.html ou index.md
  • Les médias référencés existent
  • La vignette fait 380x180px (19:9) et < 50KB (si sp\u00e9cifi\u00e9e)
  • make build-parcours ne génère pas d'erreurs
  • L'epic s'affiche correctement dans le viewer

Bonnes pratiques#

Contenu#

  1. Titre clair : Le titre doit indiquer le sujet du parcours
  2. Description utile : 1-3 phrases décrivant ce que l'utilisateur va apprendre
  3. Slides courtes : Une idée principale par slide
  4. Progression logique : Du simple au complexe

Structure#

  1. Préfixes numériques : 01-intro, 02-concepts, 03-pratique
  2. Sections pour 4+ slides : Organiser en groupes logiques
  3. Slides optionnelles : Pour le contenu avancé ou bonus

Médias#

  1. Optimiser les images : WebP ou PNG compressé
  2. Alt text : Toujours fournir des descriptions
  3. Vidéos courtes : < 2 minutes, ou utiliser YouTube/Vimeo

Style#

  1. Utiliser les CSS : slide-base.css pour la cohérence
  2. Variables CSS : var(--color-accent), etc.
  3. Responsive : Tester sur mobile

Markdown supporté#

FonctionnalitéSyntaxe
Titres# H1, ## H2, ### H3
Gras**texte**
Italique*texte*
Code inline`code`
Bloc de code```langage ```
Listes- item ou 1. item
Liens[texte](url)
Images![alt](chemin)
Citations> citation
TableauxGFM
Séparateurs---

La coloration syntaxique est automatique pour les blocs de code avec un langage spécifié (javascript, python, html, etc.).

Voir aussi#