Dans ce tutoriel, vous apprendrez à construire un système de caméra de surveillance activée par mouvement avec l’ESP32-CAM. Le système enregistre de la vidéo chaque fois qu’un mouvement est détecté et sauvegarde le flux vidéo dans un fichier sur votre ordinateur. Ce projet convient pour la surveillance, la sécurité ou l’observation de la faune.
Matériel requis
Vous trouverez ci‑dessous les composants nécessaires pour réaliser le projet. Vous aurez besoin d’un ESP32-CAM et du USB-TTL Shield ou de l’adaptateur FTDI USB-TTL pour programmer la carte.
J’ai listé deux types de capteurs de mouvement. Si vous voulez un petit format et un intervalle d’activation plus court, choisissez l’AM312. Mais si vous souhaitez n’activer la caméra que la nuit, optez pour le HC-SR501, car il peut facilement être équipé d’un capteur de lumière. Pour plus de détails, voir le Motion Activated ESP32-CAM tutoriel.

ESP32-CAM avec USB-TTL Shield

FTDI USB-TTL Adapter

Dupont Wire Set

AM312 PIR Motion Sensor

HC-SR501 PIR Motion Sensor

Câble USB
Makerguides is a participant in affiliate advertising programs designed to provide a means for sites to earn advertising fees by linking to Amazon, AliExpress, Elecrow, and other sites. As an Affiliate we may earn from qualifying purchases.
Architecture du système
Dans ce projet, nous allons implémenter un système de vidéosurveillance qui utilise l’ESP32-CAM, un capteur de mouvement et un PC pour recevoir et stocker les vidéos de surveillance.
L’ESP32-CAM exécutera un serveur de streaming vidéo qui transmet des images via Wi‑Fi si un capteur PIR connecté à l’ESP32-CAM détecte un mouvement. Les images seront reçues par une application Python s’exécutant sur un PC, qui écrit les données vidéo dans un fichier. L’image ci‑dessous illustre le montage :

Circuit de détection de mouvement
Nous commençons par monter le circuit de détection de mouvement. Cela implique de connecter le Passive Infrared Sensor (PIR) à l’ESP32-CAM. Dans cet exemple, j’utiliserai le module AM312 PIR, mais la connexion du HC-SR501 est pratiquement identique. Voir le Motion Activated ESP32-CAM tutoriel.
Connexion du capteur PIR à l’ESP32-CAM
Brancher le module AM312 PIR à l’ESP32-CAM est simple. Connectez une alimentation (batterie) de 5V (jusqu’à 12V) aux broches 5V et GND de l’ESP32-CAM comme indiqué ci‑dessous (fils rouge et bleu).

Vous pouvez fournir entre 5V et 12V pour alimenter la carte. Ne vous inquiétez pas : un régulateur de tension est connecté à la broche 5V et abaissera la tension d’entrée au niveau requis par la carte.
De la même manière, connectez le module AM312 PIR à l’alimentation (fils rouge et bleu). Il peut aussi supporter jusqu’à 12V mais faites attention à la polarité, car l’AM312 ne possède pas de protection contre l’inversion de polarité. Ensuite, connectez la sortie S ou OUT de l’AM312 à la broche GPIO13 de l’ESP32-CAM (fil vert).
Si vous utilisez le module HC-SR501 au lieu de l’AM312, connectez‑le de la même façon (GND à GND, VCC à 5V–12V).
Circuit sur breadboard
Si vous programmez l’ESP32-CAM via le USB-TTL Shield et que vous voulez tester le circuit sur une breadboard, vous pouvez alimenter l’ESP32-CAM et le capteur AM312 comme indiqué ci‑dessous :

Vous devrez laisser un petit espace entre l’ESP32-CAM et le Programming Shield puis connecter les fils aux broches exposées dans cet espace :

Les connexions sont les mêmes qu’avant. La broche GND est reliée à la broche ‘-‘, la broche 5V est reliée à la ‘+’, et GPIO13 est reliée à la broche ‘s’ de l’AM312.
Code pour tester le capteur PIR
Avant d’implémenter le code complet pour le serveur de streaming vidéo, testons le capteur PIR et le circuit. Téléversez le code suivant sur votre ESP32-CAM :
void setup() {
Serial.begin(115200);
pinMode(GPIO_NUM_13, INPUT);
}
void loop() {
bool isMotion = digitalRead(GPIO_NUM_13);
Serial.println(isMotion ? "ON" : "OFF");
delay(1000);
}
Si vous ouvrez le Serial Monitor, vous devriez voir le texte « ON » imprimé quand le capteur PIR détecte un mouvement et « OFF » sinon. Si ce n’est pas le cas, vérifiez le circuit. Vous trouverez également des conseils utiles dans le Motion Activated ESP32-CAM tutoriel.
Streaming vidéo
Dans cette section, nous implémentons le Video Streaming Server sur le module ESP32-CAM qui transmet des images vidéo si le capteur PIR détecte un mouvement. Jetez un œil au code complet ci‑dessous, puis nous en détaillerons les parties.
#include "WebServer.h"
#include "WiFi.h"
#include "esp32cam.h"
const char* WIFI_SSID = "SSID";
const char* WIFI_PASS = "PASSWORD";
const char* URL = "/video";
const auto RESOLUTION = esp32cam::Resolution::find(800, 600);
const int FRAMERATE = 10;
const byte pinPIR = GPIO_NUM_13;
const byte pinFlash = GPIO_NUM_4;
WebServer server(80);
bool isMotion() {
return digitalRead(pinPIR);
}
void handleStream() {
static char head[128];
WiFiClient client = server.client();
server.sendContent("HTTP/1.1 200 OK\r\n"
"Content-Type: multipart/x-mixed-replace; "
"boundary=frame\r\n\r\n");
while (client.connected()) {
if (isMotion()) {
analogWrite(pinFlash, 20);
auto frame = esp32cam::capture();
if (frame) {
sprintf(head,
"--frame\r\n"
"Content-Type: image/jpeg\r\n"
"Content-Length: %ul\r\n\r\n",
frame->size());
client.write(head, strlen(head));
frame->writeTo(client);
client.write("\r\n");
delay(1000 / FRAMERATE);
}
} else {
analogWrite(pinFlash, 0);
}
}
analogWrite(pinFlash, 0);
}
void initCamera() {
using namespace esp32cam;
Config cfg;
cfg.setPins(pins::AiThinker);
cfg.setResolution(RESOLUTION);
cfg.setBufferCount(2);
cfg.setJpeg(80);
Camera.begin(cfg);
}
void initWifi() {
WiFi.persistent(false);
WiFi.mode(WIFI_STA);
WiFi.begin(WIFI_SSID, WIFI_PASS);
while (WiFi.status() != WL_CONNECTED) {
delay(100);
}
Serial.printf("Stream at: http://%s%s\n",
WiFi.localIP().toString().c_str(), URL);
}
void initServer() {
server.on(URL, handleStream);
server.begin();
}
void setup() {
Serial.begin(115200);
pinMode(pinPIR, INPUT);
pinMode(pinFlash, OUTPUT);
initWifi();
initCamera();
initServer();
}
void loop() {
server.handleClient();
}
Bibliothèques
On commence par inclure les bibliothèques requises :
#include "WebServer.h" #include "WiFi.h" #include "esp32cam.h"
La WebServer.hbibliothèque est utilisée pour gérer les fonctionnalités du serveur HTTP, et la WiFi.hbibliothèque permet à l’ESP32 de se connecter à un réseau sans fil. La esp32cam bibliothèque fournit une interface simple pour configurer et utiliser le module caméra sur la carte ESP32-CAM. Vous devrez l’installer via le Library Manager :

Constantes
Ensuite, nous définissons plusieurs constantes de configuration :
const char* WIFI_SSID = "SSID"; const char* WIFI_PASS = "PASSWORD"; const char* URL = "/video"; const auto RESOLUTION = esp32cam::Resolution::find(800, 600); const int FRAMERATE = 10; const byte pinPIR = GPIO_NUM_13; const byte pinFlash = GPIO_NUM_4;
La WIFI_SSID et WIFI_PASSvariables stockent les identifiants du réseau Wi‑Fi. Vous devrez remplacer les valeurs factices SSID et PASSWORD par les identifiants de votre réseau Wi‑Fi.
La URLvariable spécifie le chemin sur le serveur que les clients utiliseront pour accéder au flux vidéo. Vous pouvez le changer, par exemple en « /video-frontdoor », mais assurez‑vous que le nom soit identique sur le serveur (ESP32-CAM) et le client (application Python).
La RESOLUTIONvariable définit la résolution de la caméra à 800 × 600 pixels. Vous pouvez bien sûr la modifier, mais la résolution doit être identique sur le serveur et le client.
Vous pouvez aussi définir le FRAMERATE, qui définit le nombre d’images par seconde que le serveur tentera d’envoyer. Comme précédemment, la fréquence d’images du serveur et du client doit correspondre.
Enfin, le pinPIR et pinFlashvariables correspondent aux broches GPIO connectées au capteur PIR et à la LED flash intégrée, respectivement.
Objets
Nous créons ensuite un serveur web qui écoute sur le port 80 :
WebServer server(80);
Fonction isMotion
La fonction isMotion() vérifie la détection de mouvement :
bool isMotion() {
return digitalRead(pinPIR);
}
Cette fonction lit le signal numérique du capteur PIR. Si le capteur sort un signal haut, un mouvement est détecté et la fonction renvoie true. N’oubliez pas que le capteur PIR a un temps d’activation qui peut être réglé pour le HC-SR501.
Fonction handleStream
La fonction handleStream() est responsable de la gestion du flux vidéo lorsqu’un client accède à l’URL /video :
On commence par déclarer un tampon nommé head qui contiendra les en-têtes HTTP pour chaque image. Ensuite, on récupère l’objet client associé à la requête HTTP en cours :
void handleStream() {
static char head[128];
WiFiClient client = server.client();
Le serveur répond au client avec un en-tête HTTP indiquant qu’il enverra une série d’images JPEG séparées par des délimiteurs marqués comme --frame. Cette technique est couramment appelée streaming MJPEG (Motion JPEG).
server.sendContent("HTTP/1.1 200 OK\r\n"
"Content-Type: multipart/x-mixed-replace; "
"boundary=frame\r\n\r\n");
Tant que le client reste connecté, la boucle continue. À l’intérieur de la boucle, on appelle la isMotion() fonction pour déterminer si un mouvement est détecté :
while (client.connected()) {
if (isMotion()) {
analogWrite(pinFlash, 20);
Si c’est le cas, nous activons la LED flash à faible luminosité via PWM en écrivant un rapport cyclique de 20 sur pinFlash. Faites attention à la luminosité du flash. Si vous mettez le flash à pleine luminosité (255) pendant une longue période, la LED risque de griller !
Nous essayons ensuite de capturer une image depuis la caméra en utilisant esp32cam::capture() :
auto frame = esp32cam::capture();
Si une image est capturée avec succès, nous préparons les en-têtes HTTP pour cette image :
if (frame) {
sprintf(head,
"--frame\r\n"
"Content-Type: image/jpeg\r\n"
"Content-Length: %ul\r\n\r\n",
frame->size());
client.write(head, strlen(head));
frame->writeTo(client);
client.write("\r\n");
delay(1000 / FRAMERATE);
}
La fonction sprintf() formate une chaîne contenant le marqueur de séparation, le type de contenu et la taille de l’image. Cet en-tête est envoyé au client via client.write(). L’image JPEG est envoyée avec frame->writeTo(client), suivie d’un retour chariot et d’un saut de ligne. Un court délai, basé sur la fréquence d’images souhaitée, est introduit pour contrôler la vitesse du streaming.
} else {
analogWrite(pinFlash, 0);
}
}
analogWrite(pinFlash, 0);
}
Si aucun mouvement n’est détecté, nous éteignons la LED flash. Après la sortie de la boucle (par exemple lorsque le client se déconnecte), nous éteignons de nouveau le flash pour nous assurer qu’il n’est pas laissé allumé.
Fonction initCamera
La fonction initCamera() initialise le matériel de l’ESP32-CAM :
void initCamera() {
using namespace esp32cam;
Config cfg;
cfg.setPins(pins::AiThinker);
cfg.setResolution(RESOLUTION);
cfg.setBufferCount(2);
cfg.setJpeg(80);
Camera.begin(cfg);
}
Dans cette fonction, un objet Config nommé cfg est créé. La méthode setPins() est appelée avec pins::AiThinker pour configurer les broches GPIO pour le modèle AI Thinker de l’ESP32-CAM. Vous pouvez utiliser le code pour d’autres cartes caméra en choisissant une configuration de broches différente. Voir le Stream Video with with XIAO-ESP32-S3-Sense et le Stream Video with ESP32-WROVER CAM, par exemple.
La résolution est définie en utilisant la valeur déclarée précédemment. Le nombre de tampons est fixé à 2 pour permettre le double buffering. La qualité de compression JPEG est réglée à 80%. Enfin, la caméra est démarrée avec Camera.begin(cfg).
Fonction initWifi
L’initialisation du Wi‑Fi a lieu dans la fonction initWifi() :
void initWifi() {
WiFi.persistent(false);
WiFi.mode(WIFI_STA);
WiFi.begin(WIFI_SSID, WIFI_PASS);
while (WiFi.status() != WL_CONNECTED) {
delay(100);
}
Serial.printf("Stream at: http://%s%s\n",
WiFi.localIP().toString().c_str(), URL);
}
La persistance du Wi‑Fi est désactivée pour éviter de stocker les identifiants en flash. L’ESP32 est configuré en mode station et commence à se connecter au réseau Wi‑Fi spécifié. La boucle attend jusqu’à l’établissement de la connexion. Une fois connecté, l’appareil affiche l’URL du flux dans le moniteur série :
Stream at: http://192.168.2.42/video
Vous devrez utiliser cette URL dans l’application cliente (application Python) qui enregistre le flux vidéo dans un fichier.
Notez que vous pouvez tester le streaming vidéo en collant cette URL dans la barre d’adresse de votre navigateur web. Mais assurez‑vous d’utiliser soit l’application cliente, soit le navigateur, et pas les deux en même temps, car un seul client peut se connecter au flux à la fois.
Fonction initServer
Le serveur HTTP est configuré dans la fonction initServer() :
void initServer() {
server.on(URL, handleStream);
server.begin();
}
Cette fonction enregistre l’endpoint /video avec la fonction handleStream() et démarre le serveur.
Fonction setup
La fonction setup() prépare l’ESP32-CAM pour l’utilisation :
void setup() {
Serial.begin(115200);
pinMode(pinPIR, INPUT);
pinMode(pinFlash, OUTPUT);
initWifi();
initCamera();
initServer();
}
La communication série est initialisée à 115200 bauds. La broche du capteur PIR est configurée en entrée et la broche de la LED flash est configurée en sortie. La connexion Wi‑Fi, la configuration de la caméra et le serveur web sont initialisés dans cet ordre.
Fonction loop
Enfin, la fonction loop() contient la logique d’exécution principale :
void loop() {
server.handleClient();
}
Cette fonction appelle en continu server.handleClient() pour traiter les requêtes HTTP entrantes des clients.
Et voilà pour le côté serveur. Dans la section suivante, nous implémentons le client qui reçoit le flux vidéo et le sauvegarde dans un fichier.
Enregistrement vidéo
Le client est implémenté sous la forme d’un script Python qui se connecte au flux MJPEG fourni par une ESP32-CAM et écrit la vidéo entrante dans un fichier local .avi. L’enregistrement est automatiquement segmenté en fichiers journaliers — un par jour calendaire. Le script peut aussi afficher facultativement le flux en direct dans une fenêtre.
Ci‑dessous se trouve le code complet. Jetez d’abord un coup d’œil, puis nous détaillerons :
import cv2
import requests
import numpy as np
import datetime
import os
# Replace with your ESP32-CAM stream URL
stream_url = 'http://192.168.2.42/video'
# match your ESP32-CAM setting
frame_width = 800
frame_height = 600
fps = 10
fourcc = cv2.VideoWriter_fourcc(*'XVID')
def get_output_filename():
date_str = datetime.datetime.now().strftime("%Y-%m-%d")
return f'recording_{date_str}.avi'
# Initialize variables
current_date = datetime.date.today()
output_file = get_output_filename()
out = cv2.VideoWriter(output_file, fourcc, fps, (frame_width, frame_height))
# Connect to MJPEG stream
print(f"Connecting to {stream_url}")
stream = requests.get(stream_url, stream=True)
if stream.status_code != 200:
print(f"Failed to connect to ESP32-CAM. Status code: {stream.status_code}")
exit()
bytes_buffer = b''
try:
for chunk in stream.iter_content(chunk_size=1024):
bytes_buffer += chunk
a = bytes_buffer.find(b'\xff\xd8') # JPEG start
b = bytes_buffer.find(b'\xff\xd9') # JPEG end
if a != -1 and b != -1 and b > a:
jpg = bytes_buffer[a:b+2]
bytes_buffer = bytes_buffer[b+2:]
# Decode the JPEG image to OpenCV format
img_array = np.frombuffer(jpg, dtype=np.uint8)
frame = cv2.imdecode(img_array, cv2.IMREAD_COLOR)
if frame is not None:
new_date = datetime.date.today()
if new_date != current_date:
out.release()
current_date = new_date
output_file = get_output_filename()
out = cv2.VideoWriter(output_file, fourcc, fps, (frame_width, frame_height))
print(f"Started new file: {output_file}")
out.write(frame)
# Optional: Show live video
cv2.imshow('ESP32-CAM Stream', frame)
if cv2.waitKey(1) & 0xFF == ord('q'):
break
except KeyboardInterrupt:
pass
finally:
out.release()
cv2.destroyAllWindows()
print(f"Video saved to {output_file}")
Bibliothèques
Le script commence par importer les bibliothèques nécessaires :
import cv2 import requests import numpy as np import datetime import os
Le module cv2 (OpenCV) est utilisé pour les opérations d’image et de vidéo. La bibliothèque requests permet d’établir la connexion au flux HTTP MJPEG de l’ESP32-CAM. La bibliothèque numpy sert à convertir les octets bruts en un tableau d’images. Le module datetime gère la date et l’heure, en particulier pour organiser les fichiers vidéo quotidiens. Enfin, os est importé pour d’éventuelles manipulations de chemins de fichiers, bien qu’il ne soit pas utilisé dans ce script particulier.
Vous devrez installer le cv2, requests et numpy bibliothèques sur votre ordinateur, de préférence dans un environnement virtuel. Voir le Object Detection with ESP32-CAM and YOLO pour un exemple plus détaillé.
Constantes
L’adresse IP de l’ESP32-CAM est définie dans la stream_url variable :
stream_url = 'http://192.168.2.42/video'
Cette URL correspond à l’endpoint défini dans le sketch Arduino (plus précisément const char* URL = "/video"). L’ESP32-CAM doit être accessible à cette adresse IP pour que le script fonctionne.
Les constantes suivantes définissent la résolution de la caméra et les paramètres d’enregistrement :
frame_width = 800 frame_height = 600 fps = 10 fourcc = cv2.VideoWriter_fourcc(*'XVID')
Les valeurs frame_width et frame_height doivent correspondre à la résolution définie sur l’ESP32-CAM (esp32cam::Resolution::find(800, 600)). La variable fps spécifie la fréquence d’images, qui doit correspondre au paramètre FRAMERATE de l’ESP32-CAM. La variable fourcc définit le codec vidéo ; ici XVID est utilisé, un codec courant pour les fichiers .avi.
Fonction get_output_filename
Ensuite, nous définissons une fonction utilitaire pour générer des noms de fichiers basés sur la date actuelle :
def get_output_filename():
date_str = datetime.datetime.now().strftime("%Y-%m-%d")
return f'recording_{date_str}.avi'
Cette fonction utilise le module datetime pour créer une chaîne au format YYYY‑MM‑DD, utilisée ensuite pour nommer le fichier de sortie, par ex. recording_2025-06-01. Cela permet que chaque enregistrement soit sauvegardé dans un fichier nommé selon la date d’enregistrement et limite la taille des fichiers. Sinon, vous pourriez vous retrouver avec un fichier vidéo massif si la caméra est activée fréquemment.
Variables
Le script initialise ensuite des variables pour gérer la segmentation quotidienne des vidéos :
current_date = datetime.date.today() output_file = get_output_filename() out = cv2.VideoWriter(output_file, fourcc, fps, (frame_width, frame_height))
La variable current_date stocke la date du jour. La variable output_file contient le nom de fichier généré par get_output_filename(). L’objet out est un OpenCV VideoWriter, qui sert à écrire les images individuelles dans le fichier .avi.
Connexion au flux
Ensuite, le script se connecte au flux vidéo de l’ESP32-CAM :
print(f"Connecting to {stream_url}")
stream = requests.get(stream_url, stream=True)
Une requête GET est envoyée à l’ESP32-CAM. Le stream=True paramètre garantit que la réponse est traitée comme une réponse en streaming, permettant de recevoir les données par morceaux.
Vérifier le statut
Immédiatement après la tentative de connexion, on vérifie le statut de la réponse :
if stream.status_code != 200:
print(f"Failed to connect to ESP32-CAM. Status code: {stream.status_code}")
exit()
Si le code HTTP n’est pas 200 (OK), le script affiche un message d’erreur et se termine. Dans ce cas, vérifiez que l’ESP32-CAM fonctionne, qu’il est connecté au Wi‑Fi et que l’URL et l’adresse IP du serveur et du client correspondent, par ex. http://192.168.2.42/video
Tampon
Le script initialise ensuite un tampon d’octets vide pour contenir les données entrantes du flux :
bytes_buffer = b''
Ce tampon sera utilisé pour accumuler les données du flux et en extraire les images JPEG individuelles.
Boucle principale
La boucle principale commence dans un try bloc :
try:
for chunk in stream.iter_content(chunk_size=1024):
bytes_buffer += chunk
Le script lit le flux par blocs de 1024 octets et ajoute chaque bloc à bytes_buffer. Cette approche traite le flux comme une suite continue d’octets.
À l’intérieur de la boucle, le script recherche les marqueurs de début et de fin d’une image JPEG :
a = bytes_buffer.find(b'\xff\xd8') # JPEG start
b = bytes_buffer.find(b'\xff\xd9') # JPEG end
Le format JPEG commence par la séquence d’octets 0xFF 0xD8 et se termine par 0xFF 0xD9. Ces marqueurs permettent au script d’isoler des images JPEG complètes à partir du flux d’octets.
Si les deux marqueurs sont trouvés et dans le bon ordre, le script extrait l’image JPEG :
if a != -1 and b != -1 and b > a:
jpg = bytes_buffer[a:b+2]
bytes_buffer = bytes_buffer[b+2:]
La tranche jpg contient l’image JPEG brute. La partie traitée est supprimée du tampon afin que le script puisse traiter l’image suivante.
Les données JPEG sont ensuite converties en une image OpenCV :
img_array = np.frombuffer(jpg, dtype=np.uint8)
frame = cv2.imdecode(img_array, cv2.IMREAD_COLOR)
Les octets bruts sont transformés en un tableau NumPy d’entiers non signés sur 8 bits. Ce tableau est décodé avec cv2.imdecode() en une trame image exploitable pour l’affichage ou l’enregistrement.
Si une trame valide est obtenue, le script vérifie si la date a changé :
if frame is not None:
new_date = datetime.date.today()
if new_date != current_date:
out.release()
current_date = new_date
output_file = get_output_filename()
out = cv2.VideoWriter(output_file, fourcc, fps, (frame_width, frame_height))
print(f"Started new file: {output_file}")
Il compare la date courante avec la date stockée précédemment. Si un nouveau jour a commencé, le fichier vidéo courant est fermé avec out.release(). Un nouveau nom de fichier est généré et un nouveau VideoWriter est initialisé pour commencer l’enregistrement dans le nouveau fichier.
La trame courante est ensuite écrite dans la vidéo de sortie :
out.write(frame)
De plus, le script affiche la vidéo dans une fenêtre d’aperçu en temps réel :
cv2.imshow('ESP32-CAM Stream', frame)
if cv2.waitKey(1) & 0xFF == ord('q'):
break
La trame est affichée avec la fonction imshow() d’OpenCV. Si l’utilisateur appuie sur la touche ‘q’, la boucle se termine et le flux est arrêté.
Gestion des exceptions
De la même façon, si le client est arrêté par une interruption clavier (par ex. Ctrl+C), le bloc finally s’assure que le fichier de sortie et la fenêtre OpenCV sont fermés :
except KeyboardInterrupt:
pass
finally:
out.release()
cv2.destroyAllWindows()
print(f"Video saved to {output_file}")
Et voilà le serveur ! Si vous lancez maintenant l’ESP32-CAM (serve) puis démarrez le client (application Python), vous disposez d’un système de surveillance qui capture la vidéo lorsqu’un mouvement est détecté et enregistre le flux dans un fichier horodaté par date pour inspection ultérieure.
Conclusions
Dans ce tutoriel, vous avez appris à construire un système de caméra de surveillance activé par mouvement avec le ESP32-CAM, un capteur de mouvement PIR, et un PC.
L’ESP32-CAM fonctionne comme un motion-activated flux vidéo MJPEG streaming server. Lorsqu’un client visite le /video URL, le serveur commence à envoyer des images vidéo. Cependant, les images ne sont capturées et envoyées que lorsqu’un mouvement est détecté par le capteur PIR. Pour plus d’informations sur la détection de mouvement, voir le Motion Activated ESP32-CAMtutoriel.
En plus de lancer le flux vidéo, la LED flash est activée pour aider à l’éclairage. Si vous avez des problèmes pour contrôler la LED flash, consultez le Control ESP32-CAM Flash LED tutoriel.
Côté client, un script Python reçoit le flux vidéo MJPEG déclenché par le mouvement depuis l’ESP32-CAM et écrit chaque image dans un .avifichier. Il crée un nouveau fichier chaque jour calendaire, ce qui facilite l’organisation et l’archivage des séquences. Le script affiche aussi optionnellement le flux en direct et peut être interrompu proprement par l’utilisateur.
Si vous souhaitez être notifié à chaque détection de mouvement, consultez notre ESP32 send Telegram Message tutoriel, qui explique comment envoyer des messages vers l’application Telegram sur votre téléphone.
Si vous voulez détecter des objets dans le flux vidéo, consultez le Object Detection with ESP32-CAM and YOLOtutoriel. Et si vous avez besoin de plus de broches GPIO pour d’autres entrées ou sorties, le More GPIO pins for ESP32-CAM peut contenir des conseils utiles.
N’hésitez pas à laisser vos questions dans la section des commentaires.
Bon bidouillage ; )

