The DFRobot team sent me a sample of the ESP32-S3 AI Camera and the following YAML configuration file for ESPHome allows integration with HomeAssistant. Due to limitations regarding the sharing of the I2C bus between the camera and the light sensor, it was not possible to implement this functionality. It seems to me that it is still a limit of ESPHome itself.
Key Configuration Notes :PSRAM Configuration is critical - must use octal
mode for ESP32-S3
- PSRAM Configuration is critical - must use
octal
mode for ESP32-S3
Camera Pins are hardware-specific - don't change unless using different module
- Camera Pins are hardware-specific - don't change unless using different module
Audio Pins support both PDM and analog microphones
- Audio Pins support both PDM and analog microphones
Number Controls provide real-time adjustment without reboot
- Number Controls provide real-time adjustment without reboot
Security: All sensitive values should be moved to secrets.yaml
- Security: All sensitive values should be moved to
secrets.yaml
This configuration provides:
Stable 25fps video streaming
- Stable 25fps video streaming
Two-way audio communication
- Two-way audio communication
Camera parameter tuning
- Camera parameter tuning
Night vision control
- Night vision control
Home Assistant integration
- Home Assistant integration
# =============================================
# DFRobot AI Camera ESP32-S3 - ESPHome Configuration
# Complete camera + audio solution for Home Assistant
# =============================================
# ----------------------------
# Core Device Configuration
# ----------------------------
esphome:
name: dfrobot_cam # Device identifier (used in API/mDNS)
friendly_name: "DFRobot AI Cam" # Human-readable name in HA
platformio_options:
build_flags: "-DBOARD_HAS_PSRAM" # Required for camera functionality
board_build.arduino.memory_type: qio_opi # Optimized memory configuration
# ----------------------------
# ESP32 Hardware Settings
# ----------------------------
esp32:
board: esp32-s3-devkitc-1 # Specific board model
framework:
type: arduino # Most stable framework for camera
version: latest # Recommended for best compatibility
flash_size: 16MB # Required for OTA updates
# ----------------------------
# PSRAM Configuration (Critical)
# ----------------------------
psram:
mode: octal # Best performance mode for S3
speed: 80MHz # Optimal speed for camera operations
# ----------------------------
# System Services
# ----------------------------
logger: # Debug logging
level: DEBUG # Change to WARN after setup
api: # Home Assistant API
encryption:
key: "************************" # Replace with your unique key
ota: # Over-The-Air Updates
password: "****************" # Secure update password
# ----------------------------
# Network Configuration
# ----------------------------
wifi:
ssid: !secret wifi_ssid # From secrets.yaml
password: !secret wifi_password # From secrets.yaml
# Fallback Access Point
ap:
ssid: "DFRobot-Cam-AP" # Visible when WiFi fails
password: "****************" # AP password (min 8 chars)
captive_portal: # Web-based config portal
# =============================================
# Camera Configuration (OV2640)
# =============================================
esp32_camera:
id: Camera # Internal reference
name: Camera # Entity name in HA
# Hardware Interface
external_clock:
pin: GPIO5 # XCLK pin
frequency: 20MHz # Critical for camera timing
i2c_pins:
sda: GPIO8 # I2C data
scl: GPIO9 # I2C clock
data_pins: [GPIO16, GPIO18, GPIO21, GPIO17, GPIO14, GPIO7, GPIO6, GPIO4] # 8-bit data bus
vsync_pin: GPIO1 # Vertical sync
href_pin: GPIO2 # Horizontal reference
pixel_clock_pin: GPIO15 # Pixel clock
# Image Parameters
max_framerate: 25 fps # Smooth video (max 60 for VGA)
idle_framerate: 0.2 fps # Power saving when idle
resolution: 640x480 # VGA resolution
jpeg_quality: 12 # 10-15 recommended (1-63 scale)
vertical_flip: True # Correct mounting orientation
contrast: 0 # Range: -2 (low) to 2 (high)
brightness: 0 # Range: -2 (dark) to 2 (bright)
saturation: 0 # Range: -2 (B&W) to 2 (vivid)
aec_mode: AUTO # Auto Exposure Control
# ----------------------------
# Video Streaming Services
# ----------------------------
esp32_camera_web_server:
- port: 8080 # Main MJPEG stream
mode: stream # /stream endpoint
- port: 8081 # Still image capture
mode: snapshot # /snapshot endpoint
# ----------------------------
# Time Synchronization
# ----------------------------
time:
- platform: homeassistant # Sync with HA server time
id: homeassistant_time # Used for timestamps
# Define UART Bus Pins
uart:
id: uart_bus
tx_pin: GPIO43
rx_pin: GPIO44
baud_rate: 9600
# =============================================
# Peripheral Controls
# =============================================
# ----------------------------
# GPIO Outputs
# ----------------------------
output:
- platform: gpio
pin: GPIO41 # Speaker gain control
id: speaker_gain
- platform: gpio
pin: GPIO40 # Audio mode selection
id: speaker_mode
- id: led_status # System status LED
platform: gpio
pin: GPIO3
- id: ir_led # Infrared night vision
platform: gpio
pin: GPIO47 # High-current capable pin
# ----------------------------
# Lighting Entities
# ----------------------------
light:
- platform: binary # Status indicator
name: "LED Status"
output: led_status
- platform: binary # IR illumination
name: "IR Night Vision"
output: ir_led
restore_mode: RESTORE_DEFAULT_OFF # Stay off after reboot
# ----------------------------
# System Controls
# ----------------------------
switch:
- platform: restart # Remote reboot capability
name: $friendly_name restart # Uses friendly_name variable
# =============================================
# Audio Subsystem (I2S)
# =============================================
# ----------------------------
# Audio Hardware Config
# ----------------------------
i2s_audio:
i2s_lrclk_pin: GPIO46 # Left/right clock
i2s_bclk_pin: GPIO45 # Bit clock
# ----------------------------
# Microphone Input
# ----------------------------
microphone:
- platform: i2s_audio
adc_type: external
i2s_din_pin: GPIO39 # Data input from mic
pdm: true # Pulse-density modulation
# ----------------------------
# Speaker Output (MAX98357)
# ----------------------------
media_player:
- platform: i2s_audio
name: "Speaker"
mode: mono # Single-channel output
i2s_dout_pin: GPIO42 # Audio data to amplifier
dac_type: external # Using external DAC
# =============================================
# Camera Adjustment Controls and Baud Rate
# =============================================
select:
- id: change_baud_rate
name: Serial Baud Rate
platform: template
options:
- "9600"
- "38400"
- "57600"
- "115200"
- "256000"
- "512000"
- "921600"
initial_option: "9600"
optimistic: true
restore_value: True
internal: false
entity_category: config
icon: mdi:swap-horizontal
set_action:
- lambda: |-
id(uart_bus).flush();
uint32_t new_baud_rate = stoi(x);
ESP_LOGD("change_baud_rate", "Changing baud rate from %i to %i",id(uart_bus).get_baud_rate(), new_baud_rate);
if (id(uart_bus).get_baud_rate() != new_baud_rate) {
id(uart_bus).set_baud_rate(new_baud_rate);
id(uart_bus).load_settings();
}
# Camera Controls
number:
- platform: template
name: "Camera Brightness"
id: camera_brightness
min_value: -2
max_value: 2
step: 0.1
initial_value: 0
restore_value: true
optimistic: true
on_value:
then:
- lambda: |-
id(Camera).set_brightness(x);
ESP_LOGD("camera", "Brightness set to: %.1f", x);
- platform: template
name: "Camera Contrast"
id: camera_contrast
min_value: -2
max_value: 2
step: 0.1
initial_value: 0
restore_value: true
optimistic: true
on_value:
then:
- lambda: |-
id(Camera).set_contrast(x);
ESP_LOGD("camera", "Contrast set to: %.1f", x);
- platform: template
name: "Camera Saturation"
id: camera_saturation
min_value: -2
max_value: 2
step: 0.1
initial_value: 0
restore_value: true
optimistic: true
on_value:
then:
- lambda: |-
id(Camera).set_saturation(x);
ESP_LOGD("camera", "Saturation set to: %.1f", x);
- platform: template
name: "Camera JPEG Quality"
id: camera_jpeg_quality
min_value: 1
max_value: 63
step: 1
initial_value: 12
restore_value: true
optimistic: true
on_value:
then:
- lambda: |-
id(Camera).set_jpeg_quality(x);
ESP_LOGD("camera", "JPEG Quality set to: %d", (int)x);
Comments