Getting Started with the ProtoCentral Sensything CAP
Introduction
The ProtoCentral Sensything CAP is a 4-channel wireless capacitance measurement board built around the Texas Instruments FDC1004 16-bit Δ-Σ capacitance-to-digital converter and an Espressif ESP32-S3 dual-core SoC with onboard Wi-Fi and Bluetooth Low Energy. The combination gives you laboratory-grade capacitance readings on four independent channels and streams them out over USB serial, BLE, or Wi-Fi — no separate microcontroller, no analog tuning, and no calibration sketches needed.
Capacitance sensing is a remarkably general-purpose technique. The FDC1004 measures the dielectric properties of whatever sits between two electrodes, which makes the same board useful for proximity detection (a finger approaching a copper pad), liquid-level sensing through a non-conductive tank wall (the dielectric of water vs. air), material identification (different liquids have different dielectric constants), gesture sensing, touchless user interfaces, and a long tail of research and IoT applications.
The board is fully open-source — KiCad schematics and PCB files under CERN-OHL-P v2, and the SensythingCore Arduino library under MIT.
Note: Sensything CAP is intended for research, prototyping, and educational use. It is not certified for safety-critical industrial process control, food-contact, or medical applications without your own validation.
Key Features
- TI FDC1004 — 16-bit capacitance-to-digital converter, 4 channels, single-ended and differential modes
- ESP32-S3-WROOM-1 — dual-core 240 MHz Xtensa LX7 with 8 MB Flash and 2 MB PSRAM
- Wi-Fi 802.11 b/g/n + Bluetooth Low Energy 5.0 — onboard, no external radio module
- USB-C for power, programming, and data
- Onboard Li-Po / Li-Ion charger (MCP73831) and MAX17048 fuel gauge — JST-PH 2.0 mm battery connector for true standalone / field operation (battery not included)
- microSD card slot with SDIO interface for high-speed local logging
- Qwiic / STEMMA QT I²C connector for adding sensors / displays without solder
- Extra SPI header — ESP32-S3 SPI brought out to a 100-mil 0.1″ pin header for expansion
- Open-source hardware (CERN-OHL-P v2) and firmware (MIT) — full KiCad files, ready-to-flash example sketches
What’s in the Box
- 1 × ProtoCentral Sensything CAP board (ESP32-S3 + FDC1004)
- A USB-C cable is not included; any data-capable USB-C cable works
- Battery is not included; if you intend to run the board untethered, add a 3.7 V single-cell Li-Po / Li-Ion battery with a JST-PH 2.0 mm 2-pin connector (the standard LiPo pigtail shipped by Adafruit / SparkFun). See Powering from a battery below.
Specifications
| Parameter | Value |
|---|---|
| MCU | Espressif ESP32-S3-WROOM-1 (240 MHz dual-core, 8 MB Flash, 2 MB PSRAM) |
| Capacitance sensor | TI FDC1004 (16-bit Δ-Σ, 4 channels) |
| Channels | 4 (single-ended) or 2 (differential pairs) |
| Measurement range | ±15 pF (with auto CAPDAC offset) |
| Resolution | Sub-femtofarad |
| Sample rate | Up to 100 SPS per channel (configurable in software, default ~10 Hz) |
| Wireless | Wi-Fi 802.11 b/g/n · Bluetooth Low Energy 5.0 |
| Local storage | microSD via SDIO |
| Connectivity | USB-C · Qwiic JST SH (I²C) · 100-mil SPI header · 4× capacitance input pads |
| Power | USB-C 5 V · single-cell Li-Po / Li-Ion via JST-PH 2.0 mm (onboard MCP73831 charger @ 455 mA, MAX17048 fuel gauge) |
| Hardware licence | CERN-OHL-P v2 |
| Firmware licence | MIT |
Hardware Setup
Plug & Power
The simplest first-light setup needs nothing except a USB-C cable:
- Plug a data-capable USB-C cable into the board.
- Plug the other end into your computer.
- The onboard power LED comes on. The ESP32-S3 boots, your OS recognises it as a virtual COM port, and the board is ready to flash.
For untethered / field operation, plug a single-cell Li-Po or Li-Ion battery into the JST-PH 2.0 mm connector — see Powering from a battery below for the full story.
Powering from a battery (standalone / field use)
The Sensything CAP is designed to be run from a single-cell Li-Po or Li-Ion battery for wireless field deployments, wearable prototypes, and any time you want to walk away from the USB cable. Everything needed for safe Li-chemistry operation is already on the board:
- Microchip MCP73831 single-cell linear charger, configured for ~455 mA charge current (set by a 2.2 kΩ R_PROG resistor — the formula is
I_CHG = 1000 / R_PROG) - Maxim MAX17048 I²C fuel gauge — reports cell voltage and state-of-charge percentage with no calibration
- Automatic source switching between USB-C and battery
- JST-PH 2.0 mm 2-pin battery connector (the standard LiPo pigtail used by Adafruit, SparkFun, and most hobby Li-Po cell suppliers)
What battery to use
- 1S (single-cell) Li-Po or Li-Ion only, 3.7 V nominal / 4.2 V fully charged. Capacity up to several Ah is fine; the MCP73831’s 455 mA charge rate stays within a safe 1C charge for any pack ≥ 500 mAh.
- The battery must include its own protection PCB (over-discharge / over-charge / short-circuit). Bare unprotected cells are unsafe — almost all retail LiPos already include this.
- Connector must be JST-PH 2.0 mm, polarity matching the silkscreen marks next to the board’s JST socket. Double-check polarity with a multimeter before plugging in if you’ve crimped your own pigtail — reversed polarity will damage the charger IC.
Do not connect 2S packs, NiMH packs, alkaline batteries, or anything other than a single 3.7 V Li-chemistry cell. The MCP73831 is a 4.2 V single-cell charger and will be destroyed by higher input voltages.
Plug-in behaviour
- Battery only (no USB) — the board boots from the battery, the 3.3 V system rail comes up, and the ESP32-S3 runs as usual.
- USB-C connected, battery plugged in — the system runs from USB and the MCP73831 starts charging the battery. The on-board CHG LED stays lit while charging and turns off at ~4.2 V termination. You can keep the board running indefinitely on USB; it will not over-charge.
- Hot-swap — unplugging USB while running on battery (or vice versa) is seamless; the ESP32-S3 does not reboot.
Reading battery state in firmware
The MAX17048 fuel gauge is on the same I²C bus as the FDC1004 (I²C address 0x36), so no extra wiring is needed. SensythingCore does not yet wrap the fuel gauge in a board-level API, but because it sits on the shared bus you can talk to it directly from your sketch using any standard MAX17048 Arduino library — for example, the SparkFun MAX1704x Fuel Gauge library — and read the cell voltage and state-of-charge percentage with no calibration.
Approximate runtime per 1 000 mAh pack
Actual runtime depends on sample rate, radio activity, and SD writes — these are first-order estimates:
| Use case | Typical current | Runtime per 1 000 mAh |
|---|---|---|
| Idle USB off, sensor sampling at 10 Hz | ~40 mA | ~25 h |
| BLE streaming + sensor sampling | ~80 mA | ~12 h |
| Wi-Fi streaming + sensor sampling | ~160 mA | ~6 h |
| Wi-Fi + SD logging at 100 Hz | ~200 mA | ~5 h |
A 500–1 000 mAh pack is the sweet spot for handheld / wearable builds; 2 000–3 000 mAh is more appropriate for multi-day field logging. For deployments longer than a day, plan to either swap batteries or run the board off a USB power bank.
Capacitance input pads
Four numbered pads on the edge of the board (CIN0 / CIN1 / CIN2 / CIN3) are the FDC1004’s measurement inputs. Wire your sensing electrodes — copper tape on a tank wall, a PCB pad, two parallel wires, etc. — to these pads with as short a lead as practical. Long leads add stray capacitance that the FDC1004 has to subtract out via its CAPDAC stage; for clean readings, keep wiring under ~10 cm and route it away from EMI sources.
For proximity / touch sensing, a single pad in single-ended mode is the usual setup: the pad is one plate of the capacitor, the surrounding environment (you, mostly) acts as the other.
For liquid-level sensing, two parallel copper strips taped vertically along the outside of a non-metallic tank work well in differential mode (CIN0–CIN1 paired). The dielectric constant between the strips changes as the liquid level rises past them.
Qwiic / STEMMA QT
The Qwiic socket on the side breaks out the same I²C bus the FDC1004 sits on (3.3 V tolerant). You can chain other Qwiic-compatible peripherals (OLED displays, RTC modules, environmental sensors) without soldering. The FDC1004 itself sits at I²C address 0x50 and is wired internally — the Qwiic chain only sees external peripherals.
Optional: microSD
A microSD card slid into the side slot lets the board log measurements locally to a CSV file at full sample rate, untethered from the PC. The SD interface uses SDIO (4-bit) for high throughput.
Arduino IDE Setup
Sensything CAP is programmed through the Arduino IDE. ESP32-S3 support has to be installed first:
- Open the Arduino IDE (version 2.x recommended).
- Go to File → Preferences and add this URL to Additional Boards Manager URLs:
https://espressif.github.io/arduino-esp32/package_esp32_index.json - Go to Tools → Board → Boards Manager…, search for “esp32”, and install esp32 by Espressif Systems (version 2.0.0 or newer).
- Select the right board and options under Tools:
| Tools menu setting | Value |
|---|---|
| Board | ESP32S3 Dev Module |
| USB Mode | Hardware CDC and JTAG |
| USB CDC On Boot | Enabled |
| Upload Mode | UART0 / Hardware CDC |
| PSRAM | QSPI PSRAM |
| Partition Scheme | Huge APP (3 MB No OTA / 1 MB SPIFFS) |
| Upload Speed | 921600 |
- Plug in the board, then pick the serial port under Tools → Port (it appears as a USB JTAG/serial debug unit).
Installing the Library
The Sensything CAP shares a unified Arduino library with the rest of the ESP32-S3 Sensything family — install two libraries:
- Open the Arduino IDE
- Go to Sketch → Include Library → Manage Libraries…
- Install “SensythingCore” (the platform library — board init, USB / BLE / Wi-Fi / SD streaming, command interface)
- Install “ProtoCentral FDC1004 Capacitive Sensor Library” (the underlying capacitance-sensor driver)
- (Optional, only if you also have a Sensything OX board) Install “Protocentral AFE4490”
Both required libraries auto-install their dependencies.
Your First Capacitance Reading
Open the bundled example sketch:
File → Examples → SensythingCore → 01.SensythingCAP → 01.Basic → Cap_USB_Streaming
Or paste the equivalent four lines into a fresh sketch:
#include <SensythingCore.h>
SensythingCap sensything;
void setup() {
if (!sensything.initPlatform()) {
// Halt if init fails — usually means the FDC1004 didn't respond on I2C
while (true) delay(1000);
}
// Optional: change sample rate (default 10 Hz, i.e. 100 ms interval)
// sensything.setSampleRate(50); // 20 Hz
}
void loop() {
sensything.update(); // measure + stream + handle commands
}
Upload
- Click Upload in the Arduino IDE.
- If the upload stalls or you see “Failed to connect”, press and hold the BOOT button on the board, then briefly tap RESET, release BOOT, and try Upload again. (This forces the ESP32-S3 into download mode — only needed if your USB stack doesn’t auto-trigger it.)
Open the Serial Monitor
- Tools → Serial Monitor
- Baud rate: 115200
- Line ending: Newline
You should see lines like:
📊 timestamp,ch0_pf,ch1_pf,ch2_pf,ch3_pf,capdac_0,capdac_1,capdac_2,capdac_3,status_flags,count
📊 1523,12.3456,15.6789,10.2345,13.4567,5,5,5,5,0x00,1
📊 1623,12.3478,15.6801,10.2367,13.4589,5,5,5,5,0x00,2
Each line is one sample: a millisecond timestamp, four channels of capacitance in picofarads, four CAPDAC offset values (the FDC1004’s auto-zeroing register per channel), a status bitmask, and a running sample counter. The 📊 prefix is there so you can grep through mixed log output.
Try it live
Touch any of the four CIN pads with your finger and watch that channel’s value swing by hundreds of femtofarads. Tape a short copper strip to CIN0 → put your hand near it → see the smooth ramp as your hand approaches. That’s the proximity-sensing primitive in roughly five lines of Arduino.
Built-in serial commands
Type any of these into the Serial Monitor (with Newline line-ending) — they take effect on the running sketch without re-flashing:
| Command | What it does |
|---|---|
help |
Print every command and its arguments |
status |
Print board status — sample rate, enabled interfaces, sample count, etc. |
set_rate <ms> |
Set the inter-sample interval. set_rate 100 → 10 Hz, set_rate 20 → 50 Hz. Range 20–10 000 ms. |
start_all / stop_all |
Enable / disable USB + BLE + Wi-Fi + SD all at once |
reset_count |
Zero the running sample counter |
Status flags decoded
The status_flags column is a hex bitmask:
| Bit | Meaning |
|---|---|
0x01 |
Channel 0 measurement failed |
0x02 |
Channel 1 measurement failed |
0x04 |
Channel 2 measurement failed |
0x08 |
Channel 3 measurement failed |
0x40 |
CAPDAC adjusting — normal during the first ~1 s after boot or after a large input change |
Anything other than 0x00 (or 0x40 immediately after a swing) usually means an open / unconnected channel — connect a pad or short the input to ground to clear it.
Streaming over BLE / Wi-Fi / SD
The update() loop drives all four output paths through the same data pipeline. Toggle them at runtime:
void setup() {
sensything.initPlatform(); // USB on by default
sensything.enableBLE(true); // start BLE advertising
sensything.enableWiFi(true, "YourSSID", "pwd"); // join Wi-Fi + start WS
sensything.enableSDCard(true); // start logging to /sd/log.csv
}
The library implements the OPENVIEW wire protocol on BLE, so the OpenView 2 mobile app (iOS / Android) discovers and connects to the board automatically. The Wi-Fi mode brings up a WebSocket on port 81 and a built-in browser dashboard on port 80 for quick visualisation from any phone / laptop on the same network.
The built-in Wi-Fi web dashboard
Once the board joins your Wi-Fi network, point any browser on the same network to http://<board-ip>/ to see a live dashboard with all four capacitance channels charting in real time — no app install, no native client, just a phone or laptop on the same SSID. The status serial command prints the assigned IP address as soon as Wi-Fi associates.
Visualizing with OpenView
Sensything CAP exposes its data over BLE in the OpenView protocol, so the OpenView 2 setup guide covers the entire mobile workflow — install on iOS / Android, scan, pair, and stream. Desktop OpenView 2 (Windows / Linux ZIP) doesn’t pair over BLE; for desktop use, plug the board in over USB-C and watch the CSV stream in any serial-monitor tool, or use the WebSocket / web dashboard described above.
Troubleshooting
initPlatform() returns false / sketch hangs at boot
- The FDC1004 didn’t answer on I²C. Check the on-board solder joints (rare, but the I²C lines are surface-mount). Run an I²C scanner sketch — the FDC1004 should appear at
0x50. - Power: a damaged USB cable that supplies only ~4.5 V can starve the 3.3 V LDO. Try a different cable.
Compilation errors
- “ESP32S3 Dev Module not found” → install the esp32 by Espressif Systems core via Boards Manager (≥ 2.0.0).
- “SensythingCore.h: No such file” → install the SensythingCore library from Library Manager.
- “FDC1004.h: No such file” → install ProtoCentral FDC1004 Capacitive Sensor Library from Library Manager.
Upload fails / “Failed to connect to ESP32-S3”
- Press and hold BOOT, briefly tap RESET, release BOOT, then click Upload.
- Check the cable is data-capable (some USB-C cables are charge-only).
- Drop the upload speed to 115 200 in Tools → Upload Speed.
All four channels read zero / very small values
- The CIN pads are open — wire at least one of them to a copper electrode. Floating capacitance inputs are noisy and tend to saturate near zero with
0x40set in the status flags. - For differential mode, both pads of the pair (e.g. CIN0 and CIN1) need to be wired.
Readings drift over minutes / hours
- Capacitance is temperature-sensitive. Allow a 5–10 minute warm-up after first power-up before relying on absolute values.
- For long-term proximity / liquid-level sensing, log a baseline trace and use changes relative to baseline rather than absolute pF values.
BLE doesn’t show up in OpenView 2 mobile
- Confirm
sensything.enableBLE(true)is insetup(). - iOS sometimes caches stale BLE peripherals — toggle Bluetooth off / on in iOS Settings, then re-scan.
- See the BLE-specific troubleshooting tips on the OpenView 2 setup guide.
Wi-Fi mode connects but the dashboard doesn’t load
statusover the serial monitor should print the assigned IP. Browse tohttp://<ip>/from a device on the same network.- If your network has client isolation enabled (common on guest Wi-Fi), the dashboard won’t be reachable — connect both the board and the client to the same trusted SSID.
Resources
- Source code & examples: github.com/Protocentral/SensythingCore
- Hardware design files (KiCad): github.com/Protocentral/protocentral_sensything_hardware
- Schematic PDF: pc_sensything_cap_v1_r2_schematic.pdf
- FDC1004 datasheet (TI): ti.com/product/FDC1004
- ESP32-S3-WROOM-1 datasheet (Espressif): espressif.com/…/esp32-s3-wroom-1_wroom-1u_datasheet_en.pdf
- OpenView 2 setup guide: setup guide · source on GitHub
- FDC1004 capacitance-sensing app notes (TI):
Licenses
- Hardware: CERN Open Hardware Licence v2 — Permissive (CERN-OHL-P v2)
- Software / Library: MIT License
- Documentation: Creative Commons Share-alike 4.0 International (CC BY-SA 4.0)