1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108
| const byte buzzPin = 8;
const unsigned int toneFreq = 500;
const unsigned int maxDistanceBeep = 1000; // in cm. Start beeping if distance less than 10m
const unsigned int minDistanceBeep = 40; // in cm. continuous beep if distance less than 40cm
uint16_t distance = 2 * maxDistanceBeep;
// very crude TF03-100 reading interface based on https://acroname.com/sites/default/files/assets/tf03_product_manual_v0.4_en.pdf
// protocol: receive at 115200 bauds 8N1, (100Hz by default)
// Byte0 Byte1 Byte2 Byte3 Byte4 Byte5 Byte6 Byte7 Byte8
// 0x59 0x59 dLSB dMSB xxxx xxxx xxxx xxxx cksum
// with Low 8 bits of cksum = Byte0 + Byte2 +... + Byte7
enum : byte {START0, START1, DLOW, DHIGH, BYTE4, BYTE5, BYTE6, BYTE7, CKSUM} parserState = START0;
bool acquisition() {
static uint16_t d = 0;
static byte checksum = 0 ;
bool acquired = false;
int rec = Serial.read();
if (rec != -1) {
uint16_t wordReceived = rec & 0xFF;
switch (parserState) {
case START0:
if (wordReceived == 0x59) parserState = START1;
break;
case START1:
if (wordReceived == 0x59) {
d = 0;
checksum = 0x59 + 0x59;
parserState = DLOW;
}
else parserState = START0;
break;
case DLOW:
d = wordReceived;
checksum += wordReceived;
parserState = DHIGH;
break;
case DHIGH:
d |= (wordReceived << 8);
checksum += wordReceived;
parserState = BYTE4;
break;
case BYTE4:
checksum += wordReceived;
parserState = BYTE5;
break;
case BYTE5:
checksum += wordReceived;
parserState = BYTE6;
break;
case BYTE6:
checksum += wordReceived;
parserState = BYTE7;
break;
case BYTE7:
checksum += wordReceived;
parserState = CKSUM;
break;
case CKSUM:
if (wordReceived == checksum) {
distance = d;
acquired = true;
}
parserState = START0;
break;
}
}
return acquired;
}
void audioFeedback(uint16_t d)
{
static uint32_t lastTrigger;
if (d > maxDistanceBeep) digitalWrite(buzzPin, LOW); // pin LOW = pas de beep
else if (d < minDistanceBeep) digitalWrite(buzzPin, HIGH); // pin HIGH = beep continu
else {
if (millis() - lastTrigger >= d) { // impulsion de 30ms sur la pin de sortie quand on doit faire un beep
digitalWrite(buzzPin, HIGH);
delay(30);
digitalWrite(buzzPin, LOW);
lastTrigger = millis();
}
}
}
void setup() {
Serial.begin(115200);
pinMode(buzzPin, OUTPUT);
pinMode(LED_BUILTIN, OUTPUT);
}
void loop() {
acquisition();
audioFeedback(distance);
} |