ECE 5466 Team 5 Final Project · Spring 2026 · The Ohio State University
Team & Responsibilities
| Member | OSU username | Component |
|---|---|---|
| Elijah Wilt | wilt.83 |
Smart-coaster firmware (ESP32, src/firmware/) |
| Becker Cheng | cheng.1801 |
Android companion app (src/software/) |
CaffTrak is a smart beverage coaster (ESP32) paired with an Android companion app that automatically tracks caffeine and hydration. The coaster reads live drink weight on an HX711 load cell, identifies NFC-tagged containers via an MFRC522 reader, and drives a WS2812B LED ring for visual feedback. The Android app receives sip events over BLE, logs them against user-defined beverage profiles, and visualizes the day's caffeine load using an exponential decay model.
cafftrak/
├── src/
│ ├── firmware/ # ESP32 firmware (PlatformIO, C/C++)
│ │ ├── platformio.ini
│ │ ├── src/ # 7 production modules (main, weight, nfc, leds, profiles, ble_service, button)
│ │ ├── include/ # Headers (config.h is the pin/timing source of truth)
│ │ ├── hardware_tests/ # Standalone on-target per-peripheral test sketches
│ │ └── test/ # Host-side Unity unit tests (env: native)
│ └── software/ # Android companion app (Gradle, Java)
│ ├── app/src/main/java/com/example/cafftrak/ # 27 source files
│ └── app/src/main/res/ # Layouts, drawables, themes
├── metadocs/ # Design and implementation documentation
│ ├── PROJECT.md # Course project handout
│ ├── design/ # 5-phase design docs (REQUIREMENTS → INTEGRATION)
│ ├── specs/ # Implementation specs (FIRMWARE, SOFTWARE, HARDWARE, BLE_INTERFACE)
│ ├── sprints/ # Sprint plans (Sprint 0–6)
│ └── progress/ # Pre-midterm and midterm progress reports
├── deliverables/ # Course deliverables
│ ├── presentations/ # Proposal, midterm, final decks (+ midterm demo video)
│ └── report/ # IEEE-format final report (LaTeX source + compiled PDF)
├── resources/ # Course reference material (handouts, labs, pinout)
└── LICENSE # MIT
- Android Studio (Hedgehog 2023.1.1 or later) — https://developer.android.com/studio
- Android SDK (API 36) — installed via Android Studio SDK Manager
- JDK 17 — bundled with Android Studio
- PlatformIO Core (CLI) — https://docs.platformio.org/en/latest/core/installation.html
- VS Code + PlatformIO IDE extension (optional GUI alternative to the CLI) — https://platformio.org/install/ide?install=vscode
- Python 3.9+ (required by PlatformIO Core) — https://www.python.org/downloads/
Android phone running Android 8.0 (API 26) or higher with BLE support.
The smart coaster hardware is assembled from the following ten components. Datasheet links are on the component name where one exists.
| Component | Role | Qty | Unit Cost | Purchase Link |
|---|---|---|---|---|
| ESP32-DevKitC V4 | MCU, BLE radio | 1 | $6.83 | amazon.com/dp/B086YS4Z3F |
| YZC-133 5 kg bar load cell + HX711 24-bit ADC | Beverage weight sensor with strain-gauge front end | 1 | $6.00 | amazon.com/dp/B0CRCY863F |
| NXP MFRC522 NFC reader | 13.56 MHz tag reader (VSPI) | 1 | $3.33 | amazon.com/dp/B07VLDSYRW |
| WS2812B-2020 RGB LED strip | Visual feedback (70 pixels installed in enclosure) | 1 | $17.05 | amazon.com/dp/B0DWXHKYMG |
| 12 × 12 mm tactile switch | User input (tare, profile cycle) | 1 | — | Kit |
| 330 Ω resistor | WS2812B data-line series | 1 | — | Kit |
| 1000 µF / 10 V electrolytic capacitor | WS2812B inrush bulk capacitor | 1 | — | Kit |
| USB-C 5 V / 2 A power adapter | System power | 1 | — | Any |
| NTAG213 NFC stickers | Container identification | N | $0.22 | amazon.com/dp/B0CP93KTS6 |
These match src/firmware/include/config.h, the firmware's source of truth. The 5 V rail (USB-C) feeds the WS2812B strip and the HX711; the ESP32's onboard LDO supplies 3.3 V to the MCU and the MFRC522.
| Peripheral | GPIO | Interface |
|---|---|---|
| HX711 DOUT / SCK | 16 / 17 | Bit-bang serial, 5 V VCC |
| MFRC522 SS / RST / IRQ | 5 / 22 / 21 | VSPI (3.3 V), IRQ reserved |
| MFRC522 MOSI / MISO / SCK | 23 / 19 / 18 | VSPI bus |
| WS2812B Data | 27 | RMT channel 0, 330 Ω series, 5 V strip |
| Tactile Switch | 32 | INPUT_PULLUP, active-low to GND |
Avoid: GPIO 6–11 (flash), GPIO 12 (strapping), GPIO 34–39 (input-only, no internal pull-up).
For full wiring diagrams, ASCII pinouts, and electrical notes, see metadocs/specs/HARDWARE.md.
Author: Becker Cheng (cheng.1801).
The Android project lives at src/software/ and is a complete Gradle project — no file copying needed.
- Clone the repository and open
src/software/in Android Studio. - Sync Gradle when prompted. The first sync downloads the Android SDK components, AndroidX libraries, the Nordic BLE library, MPAndroidChart, and the simple-gauge widget (JitPack is already added to
settings.gradle.kts). - Connect an Android phone via USB with USB Debugging enabled.
- Run (▶) — select the connected device from the device dropdown.
- Grant Bluetooth, Location, and Notification permissions on first launch. The app will discover and connect to any nearby
CaffTrak-XXXXcoaster when you tap the connect button on the Dashboard.
Build settings: compileSdk = 36, targetSdk = 36, minSdk = 26, JavaVersion.VERSION_17, namespace com.example.cafftrak.
CLI alternative (from the repo root):
cd src/software
./gradlew assembleDebug # build debug APK
./gradlew installDebug # install on connected device
./gradlew test # unit testsAuthor: Elijah Wilt (wilt.83).
The firmware project lives at src/firmware/ as a self-contained PlatformIO project. platformio.ini pins the board (esp32dev), framework (arduino), monitor speed (115200), upload speed (921600), and every library version, so no further configuration is needed beyond installing PlatformIO Core.
pip install -U platformio
pio --versionPlatformIO will download the ESP32 toolchain and all libraries on the first pio run — no Arduino IDE or manual library setup is required.
Wire the four peripherals to the ESP32 per the pin map above. Be sure to add the 330 Ω series resistor on the WS2812B data line and the 1000 µF bulk capacitor across the LED strip's 5 V / GND.
From src/firmware/:
pio run -e esp32dev # build only
pio run -e esp32dev -t upload # build + flash
pio device monitor -b 115200 # serial monitor
# All in one go:
pio run -e esp32dev -t upload && pio device monitor -b 115200On a successful boot the serial monitor prints a banner (CaffTrak Firmware <version>) followed by per-module init lines and [boot] CaffTrak firmware ready.. The BLE radio then begins advertising as CaffTrak-XXXX (where XXXX is the last two bytes of the ESP32's BT MAC), and the Android app will discover and connect to it automatically.
platformio.ini defines four on-target test environments, one host-side native unit-test environment, and one development build of the production firmware. Each on-target test is a self-contained sketch that builds and flashes independently of the production firmware. They are useful for bringing up one peripheral at a time, capturing the load-cell calibration constant, and exercising the BLE GATT contract end-to-end.
Note for graders: the standalone test sketches in
hardware_tests/test_{weight,nfc,leds}/main.cppdo not includeconfig.h; they hard-code their own pin defines using the legacy assignments (BUTTON_PIN 27, and intest_ledsLED_DATA_PIN 32). Before flashing any of those three tests against the current wiring (LED on GPIO 27, button on GPIO 32), edit the#define BUTTON_PINline in each test'smain.cppto32, and intest_leds/main.cppchangeLED_DATA_PINto27. Thetest_all_localintegration build includesconfig.hand needs no edits.
-
test_weight— Standalone HX711 sketch. Loads any previously-saved calibration factor and tare offset from NVS (namespacecafftrak), then streams raw and calibrated load-cell readings to serial at 10 Hz. A short button press tares (averages 100 samples and writes the offset to NVS); a long press toggles a calibration mode in which the user types a known reference weight in grams over serial, and the resulting calibration factor is written to NVS.pio run -e test_weight -t upload
-
test_nfc— Standalone MFRC522 sketch. Polls the reader at 4 Hz, performs anticollision + select on any ISO 14443-3A tag in the field, and prints the UID, SAK, ATQA, and PICC type. A short button press re-initializes the reader; a long press runs the MFRC522 self-test plus a register-level diagnostic dump.pio run -e test_nfc -t upload
-
test_leds— Standalone WS2812B sketch. Cycles the strip through six built-in patterns (solid red, green, blue, white, rainbow, theatre chase), auto-advancing every 5 s. A short button press jumps to the next pattern; a long press steps the global brightness through 25 %, 50 %, 75 %, 100 % of the production 60 % brightness cap.pio run -e test_leds -t upload
-
test_all_local— Integration build that links four production modules unchanged (nfc.cpp,leds.cpp,profiles.cpp,ble_service.cpp) with three test-mode replacements inhardware_tests/test_all_local/. Adds a serial command interface (help,status,tare,profile <N>,mode,stats). Exercises the full BLE GATT contract end-to-end against the Android app.pio run -e test_all_local -t upload
-
native— Host-side unit tests forprofiles.cpp(JSON parsing, hex UID decoding, profile cycling, NFC matching, edge cases). Builds and runs on the developer machine using PlatformIO's Unity test runner, with Arduino and Preferences APIs stubbed undertest/stubs/. No board required.pio test -e native -
esp32dev_dev— Same as the productionesp32devenv but with-D DEV_MODEdefined, which enables verbose serial logging in the production modules (notably a periodic 10 s weight + drink-presence report fromtaskWeight).pio run -e esp32dev_dev -t upload
All design and implementation docs live under metadocs/:
metadocs/PROJECT.md— ECE 5466 project handout (course requirements, milestones, deadlines)metadocs/design/— 5-phase design docs (REQUIREMENTS → SPECIFICATIONS → ARCHITECTURE → COMPONENTS → INTEGRATION)metadocs/specs/— Implementation specs:FIRMWARE.md— ESP32 firmware modules, tasks, and state machinesSOFTWARE.md— Android app architecture (MVVM, Room schema, BLE layer)HARDWARE.md— Pin assignments, wiring diagrams, power budgetBLE_INTERFACE.md— GATT characteristic spec, payload formats, connect sequence
metadocs/sprints/— Sprint plans (Sprint 0–6) aligned to the course schedulemetadocs/progress/— Pre-midterm and midterm progress reports
The final IEEE-format report is in deliverables/report/final.pdf (LaTeX source under deliverables/report/). Course presentations are in deliverables/presentations/ along with the midterm demo video.
The following Arduino libraries are linked into the smart-coaster firmware. PlatformIO installs them automatically from the versions pinned in src/firmware/platformio.ini; no manual download is required.
| Library | Version | Purpose | Source |
|---|---|---|---|
bogde/HX711 |
^0.7.5 | HX711 24-bit ADC driver (load cell) | registry.platformio.org/libraries/bogde/HX711 |
miguelbalboa/MFRC522 |
^1.4.11 | MFRC522 NFC reader over SPI | registry.platformio.org/libraries/miguelbalboa/MFRC522 |
fastled/FastLED |
^3.6.0 | WS2812B LED strip driver (RMT) | registry.platformio.org/libraries/fastled/FastLED |
h2zero/NimBLE-Arduino |
^1.4.0 | NimBLE BLE peripheral stack | registry.platformio.org/libraries/h2zero/NimBLE-Arduino |
bblanchon/ArduinoJson |
^7.0.0 | JSON encode/decode (BLE profile sync, CAF8) | registry.platformio.org/libraries/bblanchon/ArduinoJson |
Android-side dependencies (Nordic BLE, MPAndroidChart, simple-gauge, Room, Material) are declared in src/software/app/build.gradle.kts.
Claude Code (Anthropic) was used to assist with portions of the firmware implementation.
Released under the MIT License — see LICENSE.