USB C WiFi BLE Sensor Node

Created 4 project docs

Design Notes — USB-C WiFi BLE Environmental Node

View Document

Input: USB-C receptacle J1, 5 V sink-only, USB 2.0 D+/D- routed to ESP32-C3 native USB Serial/JTAG. USB-C configuration: R1/R2 = 5.1 kΩ Rd f...

Firmware Starter — ESP32-C3-WROOM-02-N4

View Document

MCU/module: ESP32-C3-WROOM-02-N4 Framework: Arduino on PlatformIO

Board Bring-Up Plan — USB-C WiFi BLE Environmental Node

View Document

Equipment: current-limited 5 V USB supply or USB power meter, multimeter, oscilloscope, USB-C cable, ESD-safe workstation, PlatformIO firmwa...

Technical Construction File — USB-C WiFi BLE Environmental Node

View Document

Draft, schematic-stage. FCC Part 15 intentional radiator integration using pre-certified module conditions.
Implemented the schematic for the USB-C powered Wi‑Fi/BLE temperature/humidity node and created the supporting project files:
Open items:
  • PCB layout has not been started yet; airwires are expected until placement/routing.
  • Generic passives/testpoints still need production MPN assignment before manufacturing export.
  • Layout must enforce ESP32 antenna keepout and keep the SHT40 away from heat sources.
Suggested next steps:
  1. Set board size/stackup and antenna/sensor placement constraints.
  2. Place components with the ESP32 antenna at the board edge.
  3. Route USB, buck power, and I2C nets.
  4. Assign production MPNs for generic passives and test pads.
Create layout constraints
Assign passive MPNs
Run schematic review
Start PCB placement
Prepare layout intent
U4
D1
U3
J1
C3
Capacitance
3.3nF
C8
Capacitance
100nF
C2
Capacitance
1µF
C6
Capacitance
10µF
C9
Capacitance
10µF
C5
Capacitance
10µF
C1
Capacitance
100nF
C7
Capacitance
120pF
C4
Capacitance
4.7µF
C11
Capacitance
100nF
C10
Capacitance
1µF
C2 P2 - C3 P2
C2 P2 - C3 P2
U3 GND_6 - U3 GND_7
C9 P2 - C11 P2
GND
C9 P2 - C11 P2
C10 P2 - SW2 2
GND
C6 P2 - R7 P2
C2 P2 - C3 P2
U3 GND_10 - U4 VSS
GND
R2 P2 - U1 GND
C10 P2 - SW2 2
GND
GND
U3 GND_6 - U3 GND_7
C9 P2 - C11 P2
GND
C9 P2 - C11 P2
C10 P2 - SW2 2
C9 P2 - C11 P2
U3 GND_6 - U3 GND_7
C2 P2 - C3 P2
U3 GND_10 - U4 VSS
C6 P2 - R7 P2
C9 P2 - C11 P2
C2 P2 - C3 P2
R2 P2 - U1 GND
C9 P2 - C11 P2
C2 P2 - C3 P2
R2 P2 - U1 GND
U3 GND_6 - U3 GND_7
C2 P2 - C3 P2
GND
C6 P2 - R7 P2
U3 GND_10 - U4 VSS
GND
GND
R2 P2 - U1 GND
R13 P2 - R15 P2
C9 P1 - U4 VDD
U2 PG - R8 P1
U1 IN - TP1 P1
J1 CC1 - R1 P1
C4 P1 - U2 VIN
U3 IO3 - R14 P1
C7 P1 - U3 3V3
U3 IO2 - R11 P2
C9 P1 - U4 VDD
U3 IO3 - R14 P1
U3 IO1 - U4 SCL
U1 ~{FLT} - R15 P1
J1 DN1 - J1 DN2
C9 P1 - U4 VDD
C9 P1 - U4 VDD
U1 ~{FLT} - R15 P1
C9 P1 - U4 VDD
J1 DP1 - J1 DP2
U1 IN - TP1 P1
U3 IO1 - U4 SCL
J1 CC2 - R2 P1
U1 OUT - C2 P1
U1 IN - TP1 P1
U2 PG - R8 P1
C7 P1 - U3 3V3
C7 P1 - U3 3V3
U3 EN - R9 P2
U3 TXD - TP7 P1
U3 IO0 - U4 SDA
J1 DN1 - J1 DN2
U1 EN/UVLO - R4 P2
U1 dVdt - C3 P1
J1 CC1 - R1 P1
C10 P1 - SW2 1
C10 P1 - SW2 1
J1 DP1 - J1 DP2
U3 TXD - TP7 P1
U1 ILM - R3 P1
J1 VBUS__1 - D2 1
U3 IO0 - U4 SDA
J1 CC2 - R2 P1
U3 RXD - TP8 P1
C9 P1 - U4 VDD
J1 DN1 - J1 DN2
U2 PG - R8 P1
C10 P1 - SW2 1
U3 RXD - TP8 P1
R13 P2 - R15 P2
U3 IO1 - U4 SCL
C6 P1 - R6 P1
C6 P1 - R6 P1
U3 IO9 - R10 P2
U3 IO9 - R10 P2
C9 P1 - U4 VDD
J1 DP1 - J1 DP2
U1 ~{FLT} - R15 P1
U3 IO9 - R10 P2
L1 2 - C5 P1
J1 VBUS__1 - D2 1
U1 dVdt - C3 P1
J1 DN1 - J1 DN2
C4 P1 - U2 VIN
J1 VBUS__1 - D2 1
C9 P1 - U4 VDD
U1 IN - TP1 P1
C4 P1 - U2 VIN
U1 ILM - R3 P1
U2 FB - R6 P2
U3 IO0 - U4 SDA
J1 DN1 - J1 DN2
U3 IO0 - U4 SDA
J1 DP1 - J1 DP2
R13 P2 - R15 P2
U3 IO2 - R11 P2
U2 FB - R6 P2
U1 EN/UVLO - R4 P2
U3 IO9 - R10 P2
J1 VBUS__1 - D2 1
J1 DP1 - J1 DP2
U1 OUT - C2 P1
U3 IO1 - U4 SCL
U3 EN - R9 P2
L1 2 - C5 P1
C4 P1 - U2 VIN
R13
Resistance
4.7kΩ
D2
R8
Resistance
100kΩ
R3
Resistance
2.49kΩ
R10
Resistance
10kΩ
R2
Resistance
5.1kΩ
U2
R1
Resistance
5.1kΩ
R15
Resistance
100kΩ
SW1
TP4
TP8
R12
Resistance
4.7kΩ
SW2
TP1
TP3
R11
Resistance
10kΩ
R7
Resistance
100kΩ
R4
Resistance
1MΩ
TP5
R5
Resistance
387kΩ
TP9
TP6
R14
Resistance
1kΩ
R9
Resistance
10kΩ
TP7
TP10
TP2
R6
Resistance
450kΩ
L1
Inductance
470nH
U1
D3

Refine this doc
Ask about this doc
Firmware Starter — ESP32-C3-WROOM-02-N4
Platform & Toolchain
  • MCU/module: ESP32-C3-WROOM-02-N4
  • Framework: Arduino on PlatformIO
  • Sensor: Sensirion/Adafruit SHT4x-compatible I2C driver, SHT40 address 0x44
  • Primary debug/programming: Native USB Serial/JTAG on GPIO18/GPIO19 via USB-C
  • Recovery debug: UART TX/RX test pads on GPIO21/GPIO20
Pin Mapping

Table


FunctionGPIOSchematic netDirectionNotes
I2C SDA0I2C_SDAbidirectionalSHT40 SDA, 4.7 kΩ pull-up
I2C SCL1I2C_SCLoutputSHT40 SCL, 4.7 kΩ pull-up
Status LED3LED_STATUS_GPIOoutputThrough R14=1 kΩ to D3
eFuse fault4EFUSE_FLTinputU1 FLT open-drain, 100 kΩ pull-up
Buck power-good5BUCK_PGOODinputU2 PG open-drain, 100 kΩ pull-up
BOOT button9ESP_BOOTinput at reset10 kΩ pull-up; SW1 pulls low
USB D−18USB_DNUSBNative USB Serial/JTAG
USB D+19USB_DPUSBNative USB Serial/JTAG
UART RX20UART_RXinputRecovery test point TP8
UART TX21UART_TXoutputRecovery test point TP7
platformio.ini

Ini


[env:esp32-c3-env-node]
platform = espressif32
board = esp32-c3-devkitm-1
framework = arduino
monitor_speed = 115200
upload_speed = 921600
build_flags =
  -DARDUINO_USB_MODE=1
  -DARDUINO_USB_CDC_ON_BOOT=1
lib_deps =
  adafruit/Adafruit SHT4x Library@^1.0.5
  adafruit/Adafruit BusIO@^1.16.1
Complete Starter Firmware

Cpp


#include <Arduino.h>
#include <Wire.h>
#include <WiFi.h>
#include <Adafruit_SHT4x.h>

#define I2C_SDA_PIN          0
#define I2C_SCL_PIN          1
#define STATUS_LED_PIN       3
#define EFUSE_FLT_PIN        4
#define BUCK_PGOOD_PIN       5
#define BOOT_BUTTON_PIN      9
#define UART_RX_PIN          20
#define UART_TX_PIN          21

#define SENSOR_ADDR          0x44
#define SENSOR_PERIOD_MS     5000
#define WIFI_RETRY_LIMIT     20

const char* WIFI_SSID = "YOUR_SSID";
const char* WIFI_PASSWORD = "YOUR_PASSWORD";

Adafruit_SHT4x sht4;
unsigned long lastSensorReadMs = 0;

void initStatusPins() {
  pinMode(STATUS_LED_PIN, OUTPUT);
  digitalWrite(STATUS_LED_PIN, LOW);

  pinMode(EFUSE_FLT_PIN, INPUT_PULLUP);
  pinMode(BUCK_PGOOD_PIN, INPUT_PULLUP);
  pinMode(BOOT_BUTTON_PIN, INPUT_PULLUP);
}

void initRecoveryUart() {
  Serial1.begin(115200, SERIAL_8N1, UART_RX_PIN, UART_TX_PIN);
  Serial1.println("ESP32-C3 environmental node recovery UART online");
}

bool initSensor() {
  Wire.begin(I2C_SDA_PIN, I2C_SCL_PIN, 400000);
  if (!sht4.begin(&Wire)) {
    Serial.println("SHT40 not detected at 0x44");
    return false;
  }
  sht4.setPrecision(SHT4X_HIGH_PRECISION);
  sht4.setHeater(SHT4X_NO_HEATER);
  Serial.println("SHT40 initialized");
  return true;
}

void connectWiFi() {
  WiFi.mode(WIFI_STA);
  WiFi.begin(WIFI_SSID, WIFI_PASSWORD);
  Serial.print("Connecting to WiFi");

  int retries = 0;
  while (WiFi.status() != WL_CONNECTED && retries < WIFI_RETRY_LIMIT) {
    digitalWrite(STATUS_LED_PIN, !digitalRead(STATUS_LED_PIN));
    delay(500);
    Serial.print('.');
    retries++;
  }

  if (WiFi.status() == WL_CONNECTED) {
    digitalWrite(STATUS_LED_PIN, HIGH);
    Serial.printf("\nWiFi connected, IP=%s\n", WiFi.localIP().toString().c_str());
  } else {
    digitalWrite(STATUS_LED_PIN, LOW);
    Serial.println("\nWiFi not connected; continuing offline");
  }
}

bool powerPathHealthy() {
  bool efuseOk = digitalRead(EFUSE_FLT_PIN) == HIGH;
  bool buckOk = digitalRead(BUCK_PGOOD_PIN) == HIGH;
  if (!efuseOk) Serial.println("WARN: eFuse fault asserted");
  if (!buckOk) Serial.println("WARN: 3V3 buck power-good is low");
  return efuseOk && buckOk;
}

void readAndReportSensor() {
  sensors_event_t humidity, temp;
  if (!sht4.getEvent(&humidity, &temp)) {
    Serial.println("ERROR: SHT40 read failed");
    return;
  }

  Serial.printf("T=%.2f C, RH=%.2f %%\n", temp.temperature, humidity.relative_humidity);
  Serial1.printf("T=%.2f C, RH=%.2f %%\n", temp.temperature, humidity.relative_humidity);

  if (WiFi.status() == WL_CONNECTED) {
    // Placeholder for production data path: publish MQTT or HTTP POST here.
    // Keep this non-blocking in production firmware.
  }
}

void setup() {
  Serial.begin(115200);
  delay(500);
  Serial.println("USB-C WiFi/BLE Environmental Node starting");

  initStatusPins();
  initRecoveryUart();
  powerPathHealthy();

  if (!initSensor()) {
    for (int i = 0; i < 10; i++) {
      digitalWrite(STATUS_LED_PIN, !digitalRead(STATUS_LED_PIN));
      delay(100);
    }
  }

  connectWiFi();
}

void loop() {
  if (WiFi.status() != WL_CONNECTED) {
    digitalWrite(STATUS_LED_PIN, LOW);
    connectWiFi();
  }

  unsigned long now = millis();
  if (now - lastSensorReadMs >= SENSOR_PERIOD_MS) {
    lastSensorReadMs = now;
    powerPathHealthy();
    readAndReportSensor();
  }

  delay(10);
}
Build & Flash

Bash


pio run
pio run -t upload
pio device monitor -b 115200
To force ROM download mode if needed: hold BOOT (SW1), tap RESET/EN (SW2), release RESET, then release BOOT.
  • Platform & Toolchain

  • Pin Mapping

  • `platformio.ini`

  • Complete Starter Firmware

  • Build & Flash

USB-C WiFi BLE Environmental Node

USB-C WiFi BLE Environmental Node thumbnail
Consumer USB-C 5 V powered low-power temperature and humidity sensor node with ESP32-class Wi-Fi/BLE 5.x connectivity, USB-C sink input, protected 5 V power path, and 3.3 V digital sensor subsystem.

Properties

5

V

Consumer Electronics

RoHS

Arduino

USB

WiFi

Pricing & Availability

Distributor

Qty 1

Arrow

$2.17–$3.07

Digi-Key

$0.00

HQonline

$4.41–$4.48

LCSC

$5.95–$6.13

Mouser

$9.69

TME

$0.54

Verical

$2.92–$5.32

Controls