diff --git a/modules/04-serie-debug.qmd b/modules/04-serie-debug.qmd index 9abfd21..40cecf6 100644 --- a/modules/04-serie-debug.qmd +++ b/modules/04-serie-debug.qmd @@ -13,6 +13,8 @@ title: "Module 4 — Communication série & débogage" L'UART (Universal Asynchronous Receiver-Transmitter) est un protocole de communication série point à point utilisant deux fils : TX (transmission) et RX (réception), sans horloge partagée — les deux extrémités doivent donc être configurées à la même vitesse (baud rate) pour interpréter correctement les bits reçus. +![Trame UART 8N1 : envoi du caractère « A » (0x41)](../schemas/svg/m04-trame-uart.svg){#fig-m04-trame-uart} + Sur l'ESP32-S3, la liaison série vers l'ordinateur (moniteur série de l'IDE) transite le plus souvent directement par le port USB natif du microcontrôleur (USB CDC), et non par un UART matériel classique relié à une puce USB-série externe — d'où l'importance de l'option « USB CDC On Boot » vue au Module 0. ## 2. Les ports série disponibles @@ -48,6 +50,8 @@ void loop() { } ``` +![Deux liaisons série simultanées : Serial vers l'ordinateur, Serial2 vers un module (TX et RX croisés)](../schemas/svg/m04-cablage-serie.svg){#fig-m04-cablage-serie} + ## 3. Bien utiliser le moniteur série ### 3.1 Fonctions d'affichage diff --git a/modules/05-i2c-spi.qmd b/modules/05-i2c-spi.qmd index fb1ff90..a58f736 100644 --- a/modules/05-i2c-spi.qmd +++ b/modules/05-i2c-spi.qmd @@ -24,6 +24,8 @@ I2C (Inter-Integrated Circuit) utilise seulement deux fils partagés par tous le Chaque périphérique possède une adresse unique (7 bits, soit 128 adresses possibles) qui permet au maître de s'adresser spécifiquement à lui sur le bus partagé. +![Bus I2C : deux fils partagés, un maître et plusieurs esclaves adressés](../schemas/svg/m05-bus-i2c.svg){#fig-m05-bus-i2c} + ### 2.2 Broches I2C par défaut sur ESP32-S3 Le framework Arduino-ESP32 définit par défaut SDA sur GPIO8 et SCL sur GPIO9 (à vérifier selon votre carte), mais ces broches peuvent être réassignées via Wire.begin(sda, scl). @@ -38,6 +40,8 @@ void setup() { ## 3. Scanner de bus I2C +![Trame I2C : écriture d'un octet vers l'adresse 0x3C (ce que teste le scanner : l'esclave répond-il par un ACK ?)](../schemas/svg/m05-trame-i2c.svg){#fig-m05-trame-i2c} + Avant de câbler un module, il est très utile de vérifier qu'il est bien détecté et de connaître son adresse exacte : ```cpp @@ -157,6 +161,8 @@ Combinez écran OLED et capteur BME280 pour afficher en temps réel la températ SPI (Serial Peripheral Interface) est plus rapide que l'I2C mais utilise davantage de fils : MOSI (données maître→esclave), MISO (esclave→maître), SCK (horloge) et une ligne CS (Chip Select) dédiée par périphérique. Il est privilégié pour les composants nécessitant un débit élevé (écrans TFT couleur, cartes SD, certains modules radio). +![Bus SPI : lignes de données et d'horloge partagées, une ligne CS par périphérique](../schemas/svg/m05-bus-spi.svg){#fig-m05-bus-spi} + | Critère | I2C | SPI | |---------------|-----------------------|--------------------------------| | Nombre de fils | 2 (partagés) | 4 (+1 CS par périphérique) | diff --git a/modules/06-interruptions-timers.qmd b/modules/06-interruptions-timers.qmd index fbd7c81..baa4b47 100644 --- a/modules/06-interruptions-timers.qmd +++ b/modules/06-interruptions-timers.qmd @@ -49,12 +49,16 @@ void loop() { Reprenez la logique de « blink sans delay » pour gérer simultanément trois comportements à des fréquences différentes : clignotement d'une LED classique toutes les 300 ms, cycle de couleur de la LED NeoPixel toutes les 1000 ms, et affichage d'un message de debug toutes les 5000 ms. +![Trois tâches périodiques indépendantes gérées avec millis(), sans jamais bloquer loop()](../schemas/svg/m06-taches-millis.svg){#fig-m06-taches-millis} + ## 4. Les interruptions matérielles ### 4.1 Principe Une interruption permet au microcontrôleur de réagir instantanément à un évènement matériel (front montant ou descendant sur une broche), en suspendant momentanément l'exécution de la boucle principale pour exécuter une fonction dédiée, appelée ISR (Interrupt Service Routine). C'est indispensable pour ne manquer aucun évènement rapide, comme une impulsion d'encodeur rotatif ou un appui bref sur un bouton. +![Déroulement d'une interruption : l'ISR lève un drapeau, loop() fait le traitement](../schemas/svg/m06-deroule-isr.svg){#fig-m06-deroule-isr} + ### 4.2 `attachInterrupt()` ```cpp @@ -93,10 +97,14 @@ Une routine d'interruption doit être aussi courte et rapide que possible : pas | CHANGE | Sur tout changement d'état | | LOW / HIGH | Tant que la broche reste dans cet état (peu utilisé) | +![Instants de déclenchement de l'ISR selon le mode choisi](../schemas/svg/m06-modes-declenchement.svg){#fig-m06-modes-declenchement} + ## 5. Exercice : compteur d'impulsions (encodeur rotatif) Un encodeur rotatif génère des impulsions sur deux broches (souvent nommées CLK et DT) permettant de détecter le sens de rotation. Câblez un encodeur rotatif et comptez le nombre de crans parcourus à l'aide d'une interruption sur la broche CLK. +![Encodeur rotatif : l'état de DT au front descendant de CLK donne le sens de rotation](../schemas/svg/m06-encodeur.svg){#fig-m06-encodeur} + ```cpp #define CLK_PIN 6 #define DT_PIN 7 diff --git a/schemas/m04_serie_debug.py b/schemas/m04_serie_debug.py new file mode 100644 index 0000000..2b4c33e --- /dev/null +++ b/schemas/m04_serie_debug.py @@ -0,0 +1,63 @@ +"""Module 4 — Communication série & débogage.""" +from outils import boite, chronogramme, fleche, toile +from style import BLEU, ENCRE, GRIS, ORANGE, VERT, Figure + + +def trame_uart(): + # 'A' = 0x41 = 0b01000001, envoyé bit de poids faible en premier + donnees = [(0x41 >> k) & 1 for k in range(8)] + bits = [1] + [0] + donnees + [1] + [1] # repos, start, D0..D7, stop, repos + points = [(i, b) for i, b in enumerate(bits)] + fig, ax, y = chronogramme([("TX", points)], 12, largeur_cm=16, hauteur_voie_cm=2.2) + ax.set_xticks([]) + ax.spines["bottom"].set_visible(False) + noms = ["repos", "start"] + [f"D{k}" for k in range(8)] + ["stop", "repos"] + couleurs = [GRIS, ORANGE] + [BLEU] * 8 + [VERT, GRIS] + for i, (n, c) in enumerate(zip(noms, couleurs)): + ax.text(i + 0.5, 1.35, n, ha="center", fontsize=8, color=c, fontweight="bold") + if 2 <= i <= 9: + ax.text(i + 0.5, -0.35, str(bits[i]), ha="center", fontsize=9, color=ENCRE) + ax.axvline(i, ymin=0.12, ymax=0.83, color="#e5e7eb", lw=0.7, zorder=0) + ax.annotate("", xy=(2, 1.85), xytext=(10, 1.85), arrowprops=dict(arrowstyle="<->", lw=0.9, color=BLEU)) + ax.text(6, 1.95, "8 bits de données : 'A' = 0x41, bit de poids faible (D0) en premier", + ha="center", va="bottom", fontsize=8, color=BLEU) + ax.annotate("", xy=(1, -0.75), xytext=(2, -0.75), arrowprops=dict(arrowstyle="<->", lw=0.9)) + ax.text(2.15, -0.75, "1 bit = 1 / 115200 s ≈ 8,7 µs", va="center", fontsize=8, color=ENCRE) + ax.text(12, -0.75, "8N1 : 8 bits, pas de parité, 1 bit de stop", ha="right", va="center", + fontsize=8, color=GRIS) + ax.set_ylim(-1.1, 2.5) + fig.tight_layout() + return fig + + +def cablage_serie(): + fig, ax = toile(16, 6.8) + pc = boite(ax, 1.8, 3.1, 3.0, 2.2, "Ordinateur\n\nMoniteur série", couleur=GRIS, taille=8.5) + esp = boite(ax, 8.0, 3.2, 4.0, 4.6, couleur=BLEU, fond="#f5f8fe") + ax.text(8.0, 5.1, "ESP32-S3", ha="center", fontsize=10, color=BLEU, fontweight="bold") + mod = boite(ax, 14.0, 3.0, 3.0, 3.8, couleur=ORANGE) + ax.text(14.0, 4.2, "Module externe\n(GPS, RFID…)", ha="center", va="center", fontsize=8.5, color=ENCRE) + # USB natif + boite(ax, 7.0, 4.2, 1.6, 0.6, "USB", couleur=GRIS, taille=8) + fleche(ax, (3.3, 4.2), (6.2, 4.2), "Serial\n(USB CDC)", double=True, couleur=VERT, taille=8) + # Broches Serial2 + for yy, nom in ((3.0, "GPIO18 (TX)"), (2.0, "GPIO17 (RX)")): + ax.text(9.9, yy, nom, ha="right", va="center", fontsize=8.5, color=ENCRE) + for yy, nom in ((3.0, "RX"), (2.0, "TX")): + ax.text(12.7, yy, nom, ha="left", va="center", fontsize=8.5, color=ENCRE) + ax.text(9.9, 1.0, "GND", ha="right", va="center", fontsize=8.5, color=ENCRE) + ax.text(12.7, 1.0, "GND", ha="left", va="center", fontsize=8.5, color=ENCRE) + fleche(ax, (10.0, 3.0), (12.5, 2.0), couleur=BLEU) + fleche(ax, (12.5, 3.0), (10.0, 2.0), couleur=ORANGE) + ax.plot([10.0, 12.5], [1.0, 1.0], color=ENCRE, lw=1.3) + ax.text(11.25, 3.35, "croisé !", ha="center", fontsize=8.5, color=ORANGE, fontweight="bold") + ax.text(11.25, 0.55, "masse commune", ha="center", fontsize=7.5, color=GRIS) + ax.text(8.0, 0.15, "Serial2.begin(9600, SERIAL_8N1, 17, 18);", ha="center", fontsize=7.5, + color=GRIS, family="monospace") + return fig + + +FIGURES = [ + Figure("m04-trame-uart", trame_uart), + Figure("m04-cablage-serie", cablage_serie), +] diff --git a/schemas/m05_i2c_spi.py b/schemas/m05_i2c_spi.py new file mode 100644 index 0000000..8c33ced --- /dev/null +++ b/schemas/m05_i2c_spi.py @@ -0,0 +1,117 @@ +"""Module 5 — Bus I2C et SPI.""" +import matplotlib.pyplot as plt + +from outils import boite, toile +from style import BLEU, CM, ENCRE, GRIS, ORANGE, VERT, Figure + + +def bus_i2c(): + fig, ax = toile(16, 6.4) + maitre = boite(ax, 1.9, 3.2, 3.0, 2.6, couleur=BLEU) + ax.text(1.9, 3.75, "ESP32-S3", ha="center", fontsize=10, color=BLEU, fontweight="bold") + ax.text(1.9, 2.95, "maître\n(génère SCL)", ha="center", va="center", fontsize=8, color=ENCRE) + y_sda, y_scl = 4.0, 2.4 + ax.plot([3.4, 15.6], [y_sda, y_sda], color=BLEU, lw=2) + ax.plot([3.4, 15.6], [y_scl, y_scl], color=ORANGE, lw=2) + ax.text(3.5, y_sda + 0.15, "SDA (GPIO8) — données", fontsize=8.5, color=BLEU, va="bottom") + ax.text(3.5, y_scl + 0.15, "SCL (GPIO9) — horloge", fontsize=8.5, color=ORANGE, va="bottom") + # Résistances de tirage + ax.plot([7.5, 9.5], [5.9, 5.9], color=ENCRE, lw=1.3) + ax.text(8.5, 6.05, "3V3", ha="center", fontsize=8, color=ENCRE) + for x, yb in ((7.8, y_sda), (9.2, y_scl)): + ax.plot([x, x], [5.9, 5.6], color=ENCRE, lw=1.3) + ax.add_patch(plt.Rectangle((x - 0.15, 4.7 if yb == y_sda else 4.2), 0.3, 0.9 if yb == y_sda else 1.4, + fill=False, ec=ENCRE, lw=1.3)) + ax.plot([x, x], [4.7 if yb == y_sda else 4.2, yb], color=ENCRE, lw=1.3) + ax.plot(x, yb, "o", color=ENCRE, ms=4) + ax.text(9.5, 5.2, "résistances de tirage\n(souvent déjà sur les modules)", fontsize=7.5, color=GRIS, va="center") + # Esclaves + for x, nom, adr in ((6.0, "Écran OLED\nSSD1306", "0x3C"), (11.5, "Capteur\nBME280", "0x76"), + (14.6, "autre\nmodule", "0x??")): + boite(ax, x, 0.85, 2.7, 1.45, f"{nom}\nadresse {adr}", couleur=VERT, taille=7.2) + for dx, yb, c in ((-0.5, y_sda, BLEU), (0.5, y_scl, ORANGE)): + ax.plot([x + dx, x + dx], [1.5, yb], color=c, lw=1.5) + ax.plot(x + dx, yb, "o", color=c, ms=4) + ax.text(1.9, 1.05, "tous sur les 2 mêmes fils :\nchacun répond\nà son adresse", ha="center", va="center", + fontsize=7.2, color=GRIS, style="italic") + return fig + + +def trame_i2c(): + # Écriture vers l'adresse 0x3C (0111100), R/W = 0, ACK, octet 0xAF, ACK + adresse = [0, 1, 1, 1, 1, 0, 0] + donnee = [1, 0, 1, 0, 1, 1, 1, 1] + bits = adresse + [0] + [0] + donnee + [0] + roles = ["adr"] * 7 + ["rw"] + ["ack"] + ["data"] * 8 + ["ack"] + fig, ax = plt.subplots(figsize=(16 * CM, 5.6 * CM)) + t0 = 1.0 + scl_x, scl_y, sda_x, sda_y = [0, t0], [1, 1], [0, 0.5], [1, 1] + sda_x += [0.5] + sda_y += [0] # START : SDA descend pendant que SCL est haut + scl_x += [t0] + scl_y += [0] + for k, b in enumerate(bits): + x = t0 + k + scl_x += [x + 0.5, x + 0.5, x + 1, x + 1] + scl_y += [0, 1, 1, 0] + sda_x += [x + 0.15, x + 0.15] + sda_y += [sda_y[-1], b] + fin = t0 + len(bits) + scl_x += [fin + 0.4, fin + 0.4, fin + 1.4] + scl_y += [0, 1, 1] + sda_x += [fin + 0.15, fin + 0.15, fin + 0.8, fin + 0.8, fin + 1.4] + sda_y += [sda_y[-1], 0, 0, 1, 1] # STOP : SDA monte pendant que SCL est haut + ax.plot(scl_x, [v + 2 for v in scl_y], color=ORANGE, lw=1.6) + ax.plot(sda_x, sda_y, color=BLEU, lw=1.6) + couleurs = {"adr": BLEU, "rw": BLEU, "ack": VERT, "data": BLEU} + for k, (b, r) in enumerate(zip(bits, roles)): + x = t0 + k + ax.axvspan(x, x + 1, ymin=0.08, ymax=0.42, color=couleurs[r], alpha=0.07 if r != "ack" else 0.2, lw=0) + ax.text(x + 0.5, -0.35, str(b), ha="center", fontsize=7.5, color=ENCRE) + groupes = [(0, 1, "START", ORANGE), (t0, t0 + 7, "adresse 0x3C (7 bits)", BLEU), (t0 + 7, t0 + 8, "R/W", BLEU), + (t0 + 8, t0 + 9, "ACK", VERT), (t0 + 9, t0 + 17, "donnée (8 bits)", BLEU), + (t0 + 17, t0 + 18, "ACK", VERT), (fin, fin + 1.4, "STOP", ORANGE)] + for a, b, txt, c in groupes: + ax.annotate("", xy=(a + 0.05, 3.45), xytext=(b - 0.05, 3.45), + arrowprops=dict(arrowstyle="|-|", color=c, lw=0.9, mutation_scale=3)) + ax.text((a + b) / 2, 3.6, txt, ha="center", va="bottom", fontsize=7.3, color=c, fontweight="bold") + ax.text(-0.3, 2.5, "SCL", ha="right", va="center", fontsize=9, fontweight="bold", color=ORANGE) + ax.text(-0.3, 0.5, "SDA", ha="right", va="center", fontsize=9, fontweight="bold", color=BLEU) + ax.text(fin + 1.4, -0.75, "ACK (en vert) : c'est l'esclave qui tire SDA à 0 pour accuser réception", + ha="right", fontsize=7.5, color=VERT) + ax.set_xlim(-0.4, fin + 1.6) + ax.set_ylim(-0.95, 4.2) + ax.axis("off") + fig.tight_layout() + return fig + + +def bus_spi(): + fig, ax = toile(16, 6.4) + boite(ax, 2.0, 3.2, 3.2, 4.4, couleur=BLEU) + ax.text(2.0, 4.55, "ESP32-S3\nmaître", ha="center", va="center", fontsize=9.5, color=BLEU, fontweight="bold") + lignes = [("SCK", 4.2, ORANGE, "horloge"), ("MOSI", 3.5, BLEU, "maître → esclave"), + ("MISO", 2.8, VERT, "esclave → maître")] + for nom, yy, c, role in lignes: + ax.plot([3.6, 15.4], [yy, yy], color=c, lw=2) + ax.text(3.75, yy + 0.08, f"{nom} — {role}", fontsize=8, color=c, va="bottom") + esclaves = [(9.0, "Écran TFT", "CS1"), (13.5, "Carte SD", "CS2")] + for i, (x, nom, cs) in enumerate(esclaves): + boite(ax, x, 0.8, 2.8, 1.1, nom, couleur=GRIS, taille=8.5) + for dx, (_, yy, c, _r) in zip((-0.9, -0.3, 0.3), lignes): + ax.plot([x + dx, x + dx], [1.35, yy], color=c, lw=1.4) + ax.plot(x + dx, yy, "o", color=c, ms=3.5) + ycs = 1.9 - i * 0.45 + ax.plot([3.6, x + 0.9, x + 0.9], [ycs, ycs, 1.35], color=ENCRE, lw=1.4, ls="--" if i else "-") + ax.text(3.75, ycs + 0.06, cs, fontsize=7.8, + color=ENCRE, va="bottom") + ax.text(15.4, 5.6, "SCK, MOSI, MISO : partagés\nCS (Chip Select) : une ligne par périphérique,\nle maître met à 0 celle de son interlocuteur", + ha="right", va="center", fontsize=7.8, color=GRIS, style="italic") + return fig + + +FIGURES = [ + Figure("m05-bus-i2c", bus_i2c), + Figure("m05-trame-i2c", trame_i2c), + Figure("m05-bus-spi", bus_spi), +] diff --git a/schemas/m06_interruptions_timers.py b/schemas/m06_interruptions_timers.py new file mode 100644 index 0000000..857e106 --- /dev/null +++ b/schemas/m06_interruptions_timers.py @@ -0,0 +1,122 @@ +"""Module 6 — Interruptions matérielles & timers.""" +import matplotlib.pyplot as plt +import numpy as np + +from outils import chronogramme +from style import BLEU, CM, ENCRE, GRIS, ORANGE, ROUGE, VERT, Figure + + +def taches_millis(): + fig, ax = plt.subplots(figsize=(16 * CM, 6.6 * CM)) + duree = 5200 + # loop() : itérations très rapides + ax.vlines(np.arange(0, duree, 40), 3.1, 3.7, color=GRIS, lw=0.6) + # LED toutes les 300 ms + t = np.arange(0, duree + 300, 300) + niveaux = np.arange(len(t)) % 2 + ax.step(t, 2.0 + niveaux * 0.6, where="post", color=BLEU, lw=1.6) + # NeoPixel toutes les 1000 ms + teintes = [ROUGE, VERT, BLEU, "#f5f5f5", ROUGE, VERT] + for k in range(6): + ax.add_patch(plt.Rectangle((k * 1000, 0.95), min(1000, duree - k * 1000), 0.6, + facecolor=teintes[k], edgecolor=GRIS, lw=0.6, alpha=0.85)) + # Debug toutes les 5000 ms + for x in (0, 5000): + ax.plot(x, 0.3, marker="v", color=ORANGE, ms=8) + ax.text(x + 60, 0.3, "Serial.print", fontsize=7, color=ORANGE, va="center") + noms = [(3.4, "loop()", GRIS), (2.3, "LED (300 ms)", BLEU), (1.25, "NeoPixel (1 s)", ENCRE), + (0.3, "debug (5 s)", ORANGE)] + for yy, n, c in noms: + ax.text(-80, yy, n, ha="right", va="center", fontsize=8.5, color=c, fontweight="bold") + ax.text(duree, 3.85, "loop() tourne en permanence : à chaque tour, on teste « l'heure est-elle venue ? »", + ha="right", fontsize=7.5, color=GRIS, style="italic") + ax.set_xlim(-50, duree) + ax.set_ylim(-0.1, 4.2) + ax.set_yticks([]) + ax.spines["left"].set_visible(False) + ax.set_xticks(range(0, 5001, 1000), [f"{s} s" for s in range(6)]) + ax.set_xlabel("millis()") + ax.grid(axis="y", visible=False) + fig.tight_layout() + return fig + + +def deroule_isr(): + fig, ax = plt.subplots(figsize=(16 * CM, 5.0 * CM)) + # Signal du bouton + ax.step([0, 3.0, 6.0, 10], [2.6, 1.9, 2.6, 2.6], where="post", color=BLEU, lw=1.6) + ax.text(-0.15, 2.25, "bouton\n(GPIO5)", ha="right", va="center", fontsize=8.5, fontweight="bold", color=BLEU) + ax.annotate("front descendant\n(FALLING)", xy=(3.0, 2.25), xytext=(1.2, 3.25), fontsize=7.5, color=BLEU, + arrowprops=dict(arrowstyle="-|>", color=BLEU, lw=0.8), ha="center") + # Exécution du processeur + y = 0.6 + ax.broken_barh([(0, 3.0), (3.35, 6.65)], (y, 0.7), facecolors=BLEU, alpha=0.25, edgecolor=BLEU) + ax.broken_barh([(3.0, 0.35)], (y, 0.7), facecolors=ROUGE, edgecolor=ROUGE) + ax.broken_barh([(5.0, 1.2)], (y, 0.7), facecolors=VERT, alpha=0.55, edgecolor=VERT) + ax.text(-0.15, y + 0.35, "processeur", ha="right", va="center", fontsize=8.5, fontweight="bold", color=ENCRE) + ax.text(1.5, y + 0.35, "loop()", ha="center", va="center", fontsize=8) + ax.text(8.1, y + 0.35, "loop()", ha="center", va="center", fontsize=8) + ax.annotate("ISR très courte :\ninterruptionDetectee = true", xy=(3.17, y), xytext=(3.4, -0.55), + fontsize=7.5, color=ROUGE, arrowprops=dict(arrowstyle="-|>", color=ROUGE, lw=0.8)) + ax.text(5.6, y + 0.35, "traitement", ha="center", va="center", fontsize=7.5) + ax.text(5.6, y + 0.95, "if (interruptionDetectee) …", ha="center", fontsize=7.2, color=VERT, + family="monospace") + ax.set_xlim(-1.6, 10) + ax.set_ylim(-0.8, 3.9) + ax.axis("off") + fig.tight_layout() + return fig + + +def modes_declenchement(): + pts = [(0, 0), (1.5, 1), (4, 0), (6, 1), (8.5, 0)] + fig, ax, y = chronogramme([("signal", pts)], 10, largeur_cm=16, hauteur_voie_cm=3.4) + ax.set_xticks([]) + ax.spines["bottom"].set_visible(False) + lignes = [("RISING", [1.5, 6], BLEU), ("FALLING", [4, 8.5], ORANGE), ("CHANGE", [1.5, 4, 6, 8.5], VERT)] + for k, (nom, xs, c) in enumerate(lignes): + yy = -0.7 - k * 0.7 + ax.text(-0.25, yy, nom, ha="right", va="center", fontsize=8.5, fontweight="bold", color=c) + ax.plot([0, 10], [yy, yy], color="#e5e7eb", lw=0.8) + for x in xs: + ax.plot(x, yy, marker="o", color=c, ms=7) + ax.plot([x, x], [yy, 0], color=c, lw=0.6, ls=":") + ax.set_ylim(-3.0, 1.5) + ax.text(10, -2.8, "● = instant où l'ISR est appelée", ha="right", fontsize=7.5, color=GRIS) + fig.tight_layout() + return fig + + +def encodeur(): + fig, axes = plt.subplots(1, 2, figsize=(16 * CM, 5.2 * CM)) + cas = [("Rotation dans un sens", 0.0, "DT = HIGH → compteur++", BLEU), + ("Rotation dans l'autre sens", 0.5, "DT = LOW → compteur--", ORANGE)] + t = np.linspace(0, 4, 2000) + for ax, (titre, dephasage, regle, c) in zip(axes, cas): + clk = ((t % 2) < 1).astype(float) + dt = (((t - 0.5 + dephasage * 2) % 2) < 1).astype(float) + ax.plot(t, clk + 1.6, color=BLEU, lw=1.6) + ax.plot(t, dt, color=GRIS, lw=1.6) + ax.text(-0.1, 2.1, "CLK", ha="right", va="center", fontsize=8.5, fontweight="bold", color=BLEU) + ax.text(-0.1, 0.5, "DT", ha="right", va="center", fontsize=8.5, fontweight="bold", color=GRIS) + for x in (1, 3): + ax.plot([x, x], [-0.25, 2.8], color=c, lw=1, ls="--") + etat = dt[np.searchsorted(t, x + 0.01)] + ax.plot(x, etat, "o", color=c, ms=6) + ax.set_title(titre, fontsize=9, loc="left") + ax.text(2, -0.75, regle, ha="center", fontsize=8.5, color=c, fontweight="bold") + ax.set_xlim(-0.6, 4) + ax.set_ylim(-1.0, 2.9) + ax.axis("off") + fig.text(0.5, 0.02, "À chaque front descendant de CLK (pointillés), l'ISR lit l'état de DT. " + "Le sens réel dépend du câblage.", ha="center", fontsize=7.5, color=GRIS, style="italic") + fig.tight_layout(rect=(0, 0.06, 1, 1)) + return fig + + +FIGURES = [ + Figure("m06-taches-millis", taches_millis), + Figure("m06-deroule-isr", deroule_isr), + Figure("m06-modes-declenchement", modes_declenchement), + Figure("m06-encodeur", encodeur), +] diff --git a/schemas/png/m04-cablage-serie.png b/schemas/png/m04-cablage-serie.png new file mode 100644 index 0000000..fabdeca Binary files /dev/null and b/schemas/png/m04-cablage-serie.png differ diff --git a/schemas/png/m04-trame-uart.png b/schemas/png/m04-trame-uart.png new file mode 100644 index 0000000..03cbcd4 Binary files /dev/null and b/schemas/png/m04-trame-uart.png differ diff --git a/schemas/png/m05-bus-i2c.png b/schemas/png/m05-bus-i2c.png new file mode 100644 index 0000000..9aa1062 Binary files /dev/null and b/schemas/png/m05-bus-i2c.png differ diff --git a/schemas/png/m05-bus-spi.png b/schemas/png/m05-bus-spi.png new file mode 100644 index 0000000..618c3d3 Binary files /dev/null and b/schemas/png/m05-bus-spi.png differ diff --git a/schemas/png/m05-trame-i2c.png b/schemas/png/m05-trame-i2c.png new file mode 100644 index 0000000..030685f Binary files /dev/null and b/schemas/png/m05-trame-i2c.png differ diff --git a/schemas/png/m06-deroule-isr.png b/schemas/png/m06-deroule-isr.png new file mode 100644 index 0000000..14c7d2b Binary files /dev/null and b/schemas/png/m06-deroule-isr.png differ diff --git a/schemas/png/m06-encodeur.png b/schemas/png/m06-encodeur.png new file mode 100644 index 0000000..eba5163 Binary files /dev/null and b/schemas/png/m06-encodeur.png differ diff --git a/schemas/png/m06-modes-declenchement.png b/schemas/png/m06-modes-declenchement.png new file mode 100644 index 0000000..4045f35 Binary files /dev/null and b/schemas/png/m06-modes-declenchement.png differ diff --git a/schemas/png/m06-taches-millis.png b/schemas/png/m06-taches-millis.png new file mode 100644 index 0000000..bd5b938 Binary files /dev/null and b/schemas/png/m06-taches-millis.png differ diff --git a/schemas/svg/m04-cablage-serie.svg b/schemas/svg/m04-cablage-serie.svg new file mode 100644 index 0000000..f8f8cdc --- /dev/null +++ b/schemas/svg/m04-cablage-serie.svg @@ -0,0 +1,1987 @@ + + + + + + + + image/svg+xml + + + Matplotlib v3.11.2, https://matplotlib.org/ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/schemas/svg/m04-trame-uart.svg b/schemas/svg/m04-trame-uart.svg new file mode 100644 index 0000000..6cc6419 --- /dev/null +++ b/schemas/svg/m04-trame-uart.svg @@ -0,0 +1,1658 @@ + + + + + + + + image/svg+xml + + + Matplotlib v3.11.2, https://matplotlib.org/ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/schemas/svg/m05-bus-i2c.svg b/schemas/svg/m05-bus-i2c.svg new file mode 100644 index 0000000..012ae8a --- /dev/null +++ b/schemas/svg/m05-bus-i2c.svg @@ -0,0 +1,2364 @@ + + + + + + + + image/svg+xml + + + Matplotlib v3.11.2, https://matplotlib.org/ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/schemas/svg/m05-bus-spi.svg b/schemas/svg/m05-bus-spi.svg new file mode 100644 index 0000000..63bdeb8 --- /dev/null +++ b/schemas/svg/m05-bus-spi.svg @@ -0,0 +1,2051 @@ + + + + + + + + image/svg+xml + + + Matplotlib v3.11.2, https://matplotlib.org/ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/schemas/svg/m05-trame-i2c.svg b/schemas/svg/m05-trame-i2c.svg new file mode 100644 index 0000000..1c92a92 --- /dev/null +++ b/schemas/svg/m05-trame-i2c.svg @@ -0,0 +1,1899 @@ + + + + + + + + image/svg+xml + + + Matplotlib v3.11.2, https://matplotlib.org/ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/schemas/svg/m06-deroule-isr.svg b/schemas/svg/m06-deroule-isr.svg new file mode 100644 index 0000000..c488791 --- /dev/null +++ b/schemas/svg/m06-deroule-isr.svg @@ -0,0 +1,1529 @@ + + + + + + + + image/svg+xml + + + Matplotlib v3.11.2, https://matplotlib.org/ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/schemas/svg/m06-encodeur.svg b/schemas/svg/m06-encodeur.svg new file mode 100644 index 0000000..871f1ee --- /dev/null +++ b/schemas/svg/m06-encodeur.svg @@ -0,0 +1,1762 @@ + + + + + + + + image/svg+xml + + + Matplotlib v3.11.2, https://matplotlib.org/ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/schemas/svg/m06-modes-declenchement.svg b/schemas/svg/m06-modes-declenchement.svg new file mode 100644 index 0000000..fe87ca3 --- /dev/null +++ b/schemas/svg/m06-modes-declenchement.svg @@ -0,0 +1,1024 @@ + + + + + + + + image/svg+xml + + + Matplotlib v3.11.2, https://matplotlib.org/ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/schemas/svg/m06-taches-millis.svg b/schemas/svg/m06-taches-millis.svg new file mode 100644 index 0000000..092ae01 --- /dev/null +++ b/schemas/svg/m06-taches-millis.svg @@ -0,0 +1,2357 @@ + + + + + + + + image/svg+xml + + + Matplotlib v3.11.2, https://matplotlib.org/ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +