ESP-Matter Smart Controller Tutorial: Button + Humidity + Google Home Integration (Michael Marsland, Dec 20th, 2025)
This tutorial documents how I built a custom ESP-Matter sensor on an ESP32-C3 that counts button presses, adjusts a virtual humidity sensor, and integrates with Google Home automation to control lights.
- ESP32-C3 development board
- Windows 11 (is the Operation System I am on)
Follow the official ESP-Matter instructions for building applications on ESP32 using WSL inside VSCode:
This sets up the toolchain, ESP-IDF, and required dependencies.
I started from the esp-matter/examples/sensors example. Using ChatGPT, I modified it to:
- Count the number of button presses on a single button
- Adjust a virtual humidity sensor based on the button press count
This creates a single-device multi-action Matter sensor.
To obtain a unique Matter pairing code for your device, use the ESP-Matter Manufacturing Tool:
Set the environment variable for your Matter SDK path:
export MATTER_SDK_PATH=$ESP_MATTER_PATH/connectedhomeip/connectedhomeipThen run:
esp-matter-mfg-tool -v 0xFFF2 -p 0x8001 \
--vendor-name "test vendor" \
--product-name "test product" \
--hw-ver 1 \
--hw-ver-str "hardware version" \
--pai \
-k $MATTER_SDK_PATH/credentials/test/attestation/Chip-Test-PAI-FFF2-8001-Key.pem \
-c $MATTER_SDK_PATH/credentials/test/attestation/Chip-Test-PAI-FFF2-8001-Cert.pem \
-cd $MATTER_SDK_PATH/credentials/test/certification-declaration/Chip-Test-CD-FFF2-8001.derThis generates a factory image with a unique pairing code.
Use esptool.py to flash the generated factory partition onto the ESP32-C3:
esptool.py -p /dev/ttyACM0 write_flash 0x10000 path/to/factory_partition.binReplace
/dev/ttyACM0with the correct serial port for your board.
- Open the Google Home app on your phone.
- Use the pairing code generated by the MFG tool to add the device.
- The virtual humidity sensor will now appear in Google Home as a controllable device.
Using the Google Home Automation Script Editor on your computer:
- Create a script that triggers lights based on the humidity value reported by your ESP-Matter sensor.
- Now, pressing the button changes humidity, which in turn controls your smart lights.
- Single presses set the humidity to 1, 2, 3, 4, etc...
- Presses followed by a long press (1s) set the humidity to 10, 20, 30, 40, etc... (i.e. One long press = 10%, a click and then a long press = 20%)
- Pressing the button 10 times in a row toggles the LED allowing the device to be more easily located in the dark.
- The device will reset it's humidity to 0% after one second, so it is ready to trigger the next automation.
Using the development envrionment currently (December 2025) set up on Michael's Desktop, these quick instructions can be followed to set up new devices:
-
Open this folder in VS Code
-
Plug in the device
-
Open Powershell as an administrator and run
usbipd list Look for... BUSID VID:PID DEVICE STATE 1-2 303a:1001 USB Serial Device (COM8), USB JTAG/serial debug unit Not shared usbipd bind --busid 1-2 usbipd attach --wsl --busid 1-2
-
Open a Ubuntu (WSL) terminal in VSCode (Or outside, don't matter)
-
In the WSL Terminal, run:
-
cd ~/esp-idf; source ./export.sh; cd .. cd esp-matter; source ./export.sh; cd .. export IDF_CCACHE_ENABLE=1 cd esp-matter-smart-controller/MatterSmartButton/smart-controller idf.py fullclean; idf.py set-target esp32c3; idf.py flash idf.py monitor (CTRL+] to exit the terminal) (Optional) export MATTER_SDK_PATH=$ESP_MATTER_PATH/connectedhomeip/connectedhomeip esp-matter-mfg-tool -v 0xFFF2 -p 0x8001 --vendor-name "test vendor" \ --product-name "test product" --hw-ver 1 --hw-ver-str "harware version" --pai \ -k $MATTER_SDK_PATH/credentials/test/attestation/Chip-Test-PAI-FFF2-8001-Key.pem \ -c $MATTER_SDK_PATH/credentials/test/attestation/Chip-Test-PAI-FFF2-8001-Cert.pem \ -cd $MATTER_SDK_PATH/credentials/test/certification-declaration/Chip-Test-CD-FFF2-8001.der cat out/fff2_8001/<uuid>/<uuid>-onb_codes.csv (Go to https://project-chip.github.io/connectedhomeip/qrcode.html?data=<qrcode (i.e MT:...)>) esptool.py -p /dev/ttyACM0 write_flash 0x10000 out/fff2_8001/<uuid>/<uuid>-partition.bin
-
Then you're all set to set up the device in the Google Home app and use the Matter Pairing QR code to commission the device!
- This setup allows a single physical button to perform multiple actions through virtual sensor values.
- The workflow combines ESP-Matter firmware modification, unique device pairing, and Google Home automation scripting.
Michael Marsland
This example demonstrates the integration of temperature and humidity sensors (SHTC3) and an occupancy sensor (PIR).
This application creates the temperature sensor, humidity sensor, and occupancy sensor on endpoint 1, 2, and 3 respectively.
See the docs for more information about building and flashing the firmware.
- Connecting the SHTC3, temperature and humidity sensor
| ESP32-C3 Pin | SHTC3 Pin |
|---|---|
| GND | GND |
| 3V3 | VCC |
| GPIO 4 | SDA |
| GPIO 5 | SCL |
- Connecting the PIR sensor
| ESP32-C3 Pin | PIR Pin |
|---|---|
| GND | GND |
| 3V3 | VCC |
| GPIO 7 | Output |
NOTE::
- Above mentioned wiring connection is configured by default in the example.
- Ensure that the GPIO pins used for the sensors are correctly configured through menuconfig.
- Modify the configuration parameters as needed for your specific hardware setup.
- Commission the app using Matter controller and read the attributes.
# Commission
chip-tool pairing ble-wifi 1 (SSID) (PASSPHRASE) 20202021 3840
# Start chip-tool in interactive mode
chip-tool interactive start
# Subscribe to attributes
> temperaturemeasurement subscribe measured-value 3 10 1 1
> relativehumiditymeasurement subscribe measured-value 3 10 1 2
> occupancysensing subscribe occupancy 3 10 1 3
If you encounter the following runtime error:
i2c: CONFLICT! driver_ng is not allowed to be used with this old driver
This error occurs due to a conflict between the legacy I2C driver and the newer driver model (driver_ng).
Enable the following option via idf.py menuconfig:
CONFIG_I2C_SKIP_LEGACY_CONFLICT_CHECK=y
Important: This option is only available in the latest ESP-IDF release branches:
Pull the latest code from release branches.
release/v5.2release/v5.3release/v5.4release/v5.5master- If you're using an older ESP-IDF version, you can apply this commit as a patch to add support manually.
