diff --git a/README.md b/README.md index 14e17ba..6fcddf0 100644 --- a/README.md +++ b/README.md @@ -17,7 +17,7 @@ StringField explores the sensation of playing an “imaginary string” stretche | Path | What’s inside | | --- | --- | | `docs/` | Design briefs, play paradigms, sensing survey, assumption ledger, roadmap, **Touch-to-Ground Tuning Kit**, **Classroom Code Tour** | -| `docs/Sensors/` | Per‑sensor field notes: wiring, RC values, calibration rituals, expected gesture behavior | +| `docs/Sensors/` | Per‑sensor field notes: wiring, RC values, calibration rituals, expected gesture behavior (start at [`docs/Sensors/README.md`](docs/Sensors/README.md)) | | `firmware/` | PlatformIO project(s). Teensy 4.0 by default; optional ESP32 target | | `software/` | Processing + p5.js visualizers and bridges (now with gesture debugger) | | `hardware/` | Prototype notes per sensing modality + example BOM stubs | @@ -76,6 +76,8 @@ Calibration micro-rituals (two minutes per class): Need the hands‑on wiring + calibration notes? Start at `docs/Sensors/` and then go deep per sensor: +- **Sensor field notes index:** [`docs/Sensors/README.md`](docs/Sensors/README.md) for the short menu + teaching flow. + - **MaKey‑style touch‑to‑ground:** [field notes](docs/Sensors/MakeyTouch.md) for grounding, debounce, and “touch plateau” behavior. - **Time‑of‑flight (ToF):** [field notes](docs/Sensors/TimeOfFlight.md). Drop in a VL53L0X/TMF8801 board, feed its analog/filtered output to `A2`, and compile with `-D SENSOR_TOF`. The sensor class clamps the floor for noisy rooms and keeps the pin-only setup notes inline; swap in a real I²C driver later without touching `GestureEngine`. - **Piezo contact mic:** [field notes](docs/Sensors/Piezo.md). Bias a piezo disc with a megaohm resistor, clamp the extremes, and plug into `A3` with `-D SENSOR_PIEZO`. The class can _see_ hits via the onboard LED and adjust the `bias` smoothing if the room hum drifts. diff --git a/docs/SensingSurvey.md b/docs/SensingSurvey.md index ab06c67..e4f4bb7 100644 --- a/docs/SensingSurvey.md +++ b/docs/SensingSurvey.md @@ -15,6 +15,7 @@ Each of these is a short, hands‑on guide with wiring notes, RC recipes, calibration rituals, and “what the gestures should feel like.” +- Start here for the index: [Sensor Field Notes](Sensors/README.md) - [MaKey‑style Touch‑to‑Ground](Sensors/MakeyTouch.md) - [Time‑of‑Flight Proximity](Sensors/TimeOfFlight.md) - [Piezo / Contact Mic](Sensors/Piezo.md) diff --git a/docs/Sensors/README.md b/docs/Sensors/README.md new file mode 100644 index 0000000..084be5e --- /dev/null +++ b/docs/Sensors/README.md @@ -0,0 +1,23 @@ +# Sensor Field Notes Index + +_This folder is half studio notebook, half teach‑from‑the‑bench script._ Each page is a **field note** you can read aloud while wiring, calibrating, and demoing the gesture vocabulary. Expect wiring sketches, RC values, calibration rituals, and what the gestures should _feel_ like. + +If you want the fastest path: pick a sensor below, wire it, compile with the matching `-D SENSOR_*` flag, and narrate the calibration steps as you turn the knobs. + +## The sensor menu + +- **MaKey‑style touch‑to‑ground:** [`MakeyTouch.md`](MakeyTouch.md) +- **Time‑of‑flight proximity:** [`TimeOfFlight.md`](TimeOfFlight.md) +- **Piezo / contact mic:** [`Piezo.md`](Piezo.md) +- **PIR motion gate:** [`PIR.md`](PIR.md) +- **Electret mic (analog envelope):** [`ElectretMic.md`](ElectretMic.md) +- **I²S / PDM digital mic:** [`I2SMic.md`](I2SMic.md) + +## How to teach with these pages + +1. **Point at the expected signal range** (analog 0–1023, digital gate, PCM, etc.). +2. **Describe normalization** (how we map whatever the sensor gives us into 0..1). +3. **Call out failure modes** (and how to debug them live). +4. **Play the gestures** (pluck / bow / scrape) and compare how each sensor “tells the story.” + +That’s the whole vibe: tech as performance, troubleshooting as collaboration. diff --git a/firmware/src/electret_mic_sensor.cpp b/firmware/src/electret_mic_sensor.cpp index 0251e4d..cfdbc5b 100644 --- a/firmware/src/electret_mic_sensor.cpp +++ b/firmware/src/electret_mic_sensor.cpp @@ -25,7 +25,7 @@ class ElectretMicSensor : public Sensor { // AC coupling: follow bias slowly, measure swing fast. bias_ = 0.9994f * bias_ + 0.0006f * x; // tweak live if the room hums float swing = fabs(x - bias_) * gain_; - // Normalization: clamp the rectified swing into 0..1, then smooth to a + // Normalization behavior: clamp the rectified swing into 0..1, then smooth to a // performance-friendly envelope. env_ = 0.88f * env_ + 0.12f * constrain(swing, 0.0f, 1.0f); // Small floor clamp to avoid whisper-noise. Bump lower if you need pianissimo. diff --git a/firmware/src/i2s_mic_sensor.cpp b/firmware/src/i2s_mic_sensor.cpp index 1d02d78..180f691 100644 --- a/firmware/src/i2s_mic_sensor.cpp +++ b/firmware/src/i2s_mic_sensor.cpp @@ -32,7 +32,7 @@ class I2SMicSensor : public Sensor { float avg = (count > 0) ? (total / static_cast(count)) : 0.0f; // Normalize 16-bit PCM to 0..1 and overdrive slightly for quiet rooms. float normalized = constrain((avg / 32768.0f) * gain_, 0.0f, 1.0f); - // Normalization: absolute-value average -> 0..1 energy envelope with a short + // Normalization behavior: absolute-value average -> 0..1 energy envelope with a short // smoothing filter so percussive taps still show up as peaks. env_ = 0.9f * env_ + 0.1f * normalized; // Common failure modes: I2S.begin() never locks (ready_ false => silence), diff --git a/firmware/src/piezo_sensor.cpp b/firmware/src/piezo_sensor.cpp index de0be72..4ffe418 100644 --- a/firmware/src/piezo_sensor.cpp +++ b/firmware/src/piezo_sensor.cpp @@ -16,8 +16,8 @@ class PiezoSensor : public Sensor { // Expected signal range: biased piezo swing around mid-rail, sampled as 0..1023. // If raw slams 0/1023, check your clamp diodes and that the piezo isn't floating. int raw = analogRead(A3); - // Normalization: scale ADC to 0..1, subtract a slow bias, then magnify the swing - // into a 0..1 envelope that behaves like "hit energy." + // Normalization behavior: scale ADC to 0..1, subtract a slow bias, then magnify + // the swing into a 0..1 envelope that behaves like "hit energy." float x = constrain(raw / 1023.0f, 0.0f, 1.0f); bias = 0.999f * bias + 0.001f * x; // slow bias tracker; tweak in calibration session float swing = fabs(x - bias) * 2.2f; // exaggerate small hits; clip later diff --git a/firmware/src/pir_sensor.cpp b/firmware/src/pir_sensor.cpp index fda67fd..43d7865 100644 --- a/firmware/src/pir_sensor.cpp +++ b/firmware/src/pir_sensor.cpp @@ -20,7 +20,7 @@ class PirSensor : public Sensor { // Expected signal range: digital HIGH/LOW gate from the PIR comparator. bool raw_motion = digitalRead(kPirPin) == HIGH; float x = raw_motion ? 1.0f : 0.0f; - // Normalization: convert the binary gate into a smoothed 0..1 envelope so + // Normalization behavior: convert the binary gate into a smoothed 0..1 envelope so // gestures feel like motion energy rather than a square wave. // Exponential decay so a single person pass shows as a hill, not a square wave. env_ = 0.92f * env_ + 0.08f * x; diff --git a/firmware/src/time_of_flight_sensor.cpp b/firmware/src/time_of_flight_sensor.cpp index f9d2c21..79080ac 100644 --- a/firmware/src/time_of_flight_sensor.cpp +++ b/firmware/src/time_of_flight_sensor.cpp @@ -20,7 +20,8 @@ class TimeOfFlightSensor : public Sensor { // Calibrate like a lab notebook: expose the bias and smoothing knobs. Students // can anchor a “hand at 15 cm” pose and tune the filter and scaling live. static float y = 0.0f; - // Normalization: map raw ADC to 0..1 so gesture logic stays sensor-agnostic. + // Normalization behavior: map raw ADC to 0..1 so gesture logic stays sensor-agnostic, + // then low-pass to smooth jitter without erasing quick dips. float x = constrain(raw / 1023.0f, 0.0f, 1.0f); y = 0.85f * y + 0.15f * x; // slightly faster than optical to catch hand waves // Cheap floor clamp for noisy rooms; edit in class if your sensor never