Disable tap detection by default, simplify tracking

This commit is contained in:
2026-03-24 23:30:06 +01:00
parent 14e9c96f55
commit a7082c9022
3 changed files with 7 additions and 34 deletions

View File

@@ -5,7 +5,7 @@
#define FEATURE_CONFIG_SERVICE
#define FEATURE_TELEMETRY
#define FEATURE_IMU_STREAM
#define FEATURE_TAP_DETECTION
// #define FEATURE_TAP_DETECTION
#define FEATURE_TEMP_COMPENSATION
#define FEATURE_AUTO_RECAL
#define FEATURE_BATTERY_MONITOR

View File

@@ -17,7 +17,6 @@
#include "imu.h"
#include "ble_config.h"
#include "battery.h"
#include "tap.h"
#include "buttons.h"
#include <bluefruit.h>
#include <Adafruit_LittleFS.h>
@@ -116,10 +115,6 @@ bool pendingReset = false;
bool pendingOTA = false;
#endif
// Jerk-based shock detection - freeze cursor during tap impacts, doesn't work well yet!
unsigned long shockFreezeUntil = 0;
float prevAx = 0, prevAy = 0, prevAz = 0; // previous frame's accel for Δa
const unsigned long SHOCK_FREEZE_MS = 80; // hold freeze after last spike
ChargeStatus lastChargeStatus = CHGSTAT_DISCHARGING;
@@ -220,8 +215,6 @@ void setup() {
#endif
calibrateGyroBias();
// Seed previous-accel for jerk detection so first frame doesn't spike
prevAx = imu.readFloatAccelX(); prevAy = imu.readFloatAccelY(); prevAz = imu.readFloatAccelZ();
sleepManagerInit();
@@ -304,7 +297,7 @@ void loop() {
#endif
}
if (pendingCal) { pendingCal = false; calibrateGyroBias(); prevAx = imu.readFloatAccelX(); prevAy = imu.readFloatAccelY(); prevAz = imu.readFloatAccelZ(); }
if (pendingCal) { pendingCal = false; calibrateGyroBias(); }
if (pendingReset) { pendingReset = false; factoryReset(); }
#ifdef FEATURE_OTA
if (pendingOTA) {
@@ -372,30 +365,16 @@ void loop() {
float gy = (imu.readFloatGyroY() - biasGY - correction) * (PI/180.0f); // pitch → cursor Y
float gz = (imu.readFloatGyroZ() - biasGZ - correction) * (PI/180.0f); // yaw → cursor X
float ax = imu.readFloatAccelX();
float ay = imu.readFloatAccelY();
float az = imu.readFloatAccelZ();
// Axis diagnostic — send 'd' over serial to enable
if (diagUntil && now < diagUntil) {
static unsigned long lastDiagPrint = 0;
if (now - lastDiagPrint >= 100) { lastDiagPrint = now;
Serial.print("[DIAG] gx="); Serial.print(gx,3);
Serial.print(" gy="); Serial.print(gy,3);
Serial.print(" gz="); Serial.print(gz,3);
Serial.print(" | ax="); Serial.print(ax,3);
Serial.print(" ay="); Serial.print(ay,3);
Serial.print(" az="); Serial.println(az,3);
Serial.print(" gz="); Serial.println(gz,3);
}
} else if (diagUntil) { diagUntil = 0; Serial.println("[DIAG] Done"); }
// Jerk-based shock detection - freeze cursor during tap impacts, doesn't work well yet
float jx = (ax - prevAx) / dt, jy = (ay - prevAy) / dt, jz = (az - prevAz) / dt;
float jerkSq = jx*jx + jy*jy + jz*jz;
prevAx = ax; prevAy = ay; prevAz = az;
bool shocked = cfg.tapFreezeEnabled && ((jerkSq > cfg.jerkThreshold) || (now < shockFreezeUntil));
if (cfg.tapFreezeEnabled && jerkSq > cfg.jerkThreshold) shockFreezeUntil = now + SHOCK_FREEZE_MS;
// Direct axis mapping (empirically verified via diagnostic)
float yawRate = gz; // gyroZ = pan left/right → cursor X
float pitchRate = gy; // gyroY = nod up/down → cursor Y
@@ -421,7 +400,7 @@ void loop() {
#ifdef FEATURE_AUTO_RECAL
if ((cfg.featureFlags & FLAG_AUTO_RECAL_ENABLED) && idle && idleStartMs != 0 && (now - idleStartMs >= AUTO_RECAL_MS)) {
Serial.println("[AUTO-CAL] Long idle - recalibrating...");
idleStartMs = 0; calibrateGyroBias(); prevAx = imu.readFloatAccelX(); prevAy = imu.readFloatAccelY(); prevAz = imu.readFloatAccelZ(); return;
idleStartMs = 0; calibrateGyroBias(); return;
}
#endif
@@ -430,12 +409,7 @@ void loop() {
static float smoothX = 0.0f, smoothY = 0.0f;
if (shocked) {
// Shock freeze - discard accumulated sub-pixel motion and suppress output
smoothX = smoothY = 0.0f;
accumX = accumY = 0.0f;
flags |= 0x08; // bit3 = shock freeze active
} else if (idle) {
if (idle) {
smoothX = smoothY = 0.0f;
accumX = accumY = 0.0f;
flags |= 0x01;
@@ -462,6 +436,7 @@ void loop() {
if (now < streamBackoffUntil) {
// Backing off - host TX buffer congested, skip to avoid 100ms block
} else {
float ax = imu.readFloatAccelX(), ay = imu.readFloatAccelY(), az = imu.readFloatAccelZ();
ImuPacket pkt;
pkt.gyroX_mDPS = (int16_t)constrain(gx*(180.f/PI)*1000.f, -32000, 32000);
pkt.gyroZ_mDPS = (int16_t)constrain(gz*(180.f/PI)*1000.f, -32000, 32000);

View File

@@ -61,7 +61,7 @@ static void lsmWrite(uint8_t reg, uint8_t val) {
Wire1.endTransmission();
}
// ISR
// ISR
static void imuInt1ISR() {
imuWakeFlag = true;
}
@@ -206,10 +206,8 @@ void sleepManagerWakeIMU() {
// Reset motion filter state to prevent a cursor jump on the first frame.
extern float accumX, accumY;
extern float prevAx, prevAy, prevAz;
extern unsigned long lastTime;
accumX = accumY = 0.0f;
prevAx = 0.0f; prevAy = 0.0f; prevAz = 0.0f;
lastTime = millis();
sleepStage = SLEEP_AWAKE;