Concept:
The concept for this device was to create a doorbell that could be used navigated and used with little to no eyesight required. My goal was to eliminate the component of doorbell interactions where the user has to navigate on the door to find the button and ring the doorbell. I ended up settling on a doormat that senses when a person is present and then greets the user and prompts them to stomp a specified amount of times for desired interactions. The actions were made to resemble those of a traditional answering machine: stomp once to hear the address, stomp twice to ring the doorbell, stomp three times to hear the options again. Going further into the design, I think it would be helpful to add a message component so the user could leave a message to the resident if they want. I think it would also be helpful for security sake to incorporate a notification system to the resident is notified of any users on their doorstep and a picture is captured of whoever is there.
Electrical Schematic:
Demo Video:
Code:
/* Warning Machine for Something Approaching */ #include <Audio.h> #include <Wire.h> #include <SPI.h> #include <SD.h> #include <SerialFlash.h> AudioPlaySdWav playWav; AudioOutputMQS mqs1; //xy=625,279 AudioConnection patchCord1(playWav, 0, mqs1, 0); AudioConnection patchCord2(playWav, 1, mqs1, 1); // Use these with the Teensy 3.5 & 3.6 SD card #define SDCARD_CS_PIN BUILTIN_SDCARD #define SDCARD_MOSI_PIN 11 // not actually used #define SDCARD_SCK_PIN 13 // not actually used #define pressurePlate 14 String message = ""; int stompCounter = 0; void setup() { // put your setup code here, to run once: Serial.begin(9600); // Audio connections require memory to work. For more // detailed information, see the MemoryAndCpuUsage example AudioMemory(8); // Comment these out if not using the audio adaptor board. // This may wait forever if the SDA & SCL pins lack // pullup resistors SPI.setMOSI(SDCARD_MOSI_PIN); SPI.setSCK(SDCARD_SCK_PIN); if (!(SD.begin(SDCARD_CS_PIN))) { // stop here, but print a message repetitively while (1) { Serial.println("Unable to access the SD card"); delay(500); } } pinMode(pressurePlate, INPUT); } void loop() { // put your main code here, to run repeatedly bool someoneOnPressurePlate = doPlatePresenceCheck(); if (someoneOnPressurePlate) { doPressurePlateCheck(); } Serial.print("Pressure Plate Reading: "); Serial.print(analogRead(pressurePlate)); Serial.print("\t"); Serial.print("Stomp Counter: "); Serial.print(stompCounter); Serial.print("\t"); // Serial.print("Pressure Plate Pressence: "); // Serial.print(someoneOnPressurePlate); // Serial.print("\t"); Serial.print("Message: "); Serial.print(message); Serial.print("\t"); Serial.println(""); delay(5); } void playSound(const char *filename) { playWav.play(filename); delay(25); while (playWav.isPlaying()) { } } bool doPlatePresenceCheck() { int standingThreshold = 600; int standingTimeThreshold = 2000; // [ms] static bool timingStand = false; static bool someoneOnPressurePlate = false; static unsigned long standingTime = 0; int plateReading = analogRead(pressurePlate); if (plateReading > standingThreshold) { if (!timingStand) { timingStand = true; standingTime = millis(); } } else if (plateReading < standingThreshold) { timingStand = false; someoneOnPressurePlate = false; } if (timingStand && millis() - standingTime > standingTimeThreshold) { if (!someoneOnPressurePlate) { playSound("Initial Greeting.WAV"); playSound("Options Sound.WAV"); } timingStand = false; someoneOnPressurePlate = true; } return someoneOnPressurePlate; } void doPressurePlateCheck() { int debounceTime = 300; int stompThreshold = 900; int countTimerThreshold = 3000; // [ms] static bool DEBOUNCE = false; static bool timeDebounce = false; static bool countStart = false; static unsigned long debounceTimer = 0; static unsigned long countTimer = 0; int pressureReading = analogRead(pressurePlate); if (!DEBOUNCE && pressureReading > stompThreshold) { if (!countStart) { countStart = true; countTimer = millis(); } DEBOUNCE = true; stompCounter += 1; } if (millis() - countTimer > countTimerThreshold || stompCounter > 3) { actionBasedOnStompCount(stompCounter); countStart = false; stompCounter = 0; } if (DEBOUNCE && timeDebounce) { timeDebounce = false; debounceTimer = millis(); } if (millis() - debounceTimer > debounceTime) { DEBOUNCE = false; timeDebounce = true; } } void actionBasedOnStompCount(int stompCount) { if (stompCount == 1) { //user wants to read address message = "Read Address"; playSound("Address Sound.WAV"); } else if (stompCount == 2) { //user wants to ring doorbell message = "Ring Doorbell"; playSound("Doorbell Sound.WAV"); } else if (stompCount == 3) { //user wants to leave message message = "Reading Options Again"; playSound("Options Sound.WAV"); } }