You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

139 lines
3.0 KiB

  1. #include <stdio.h>
  2. #include <stdlib.h>
  3. #include <stdint.h>
  4. #include <wiringPi.h>
  5. #include <wiringPiI2C.h>
  6. //Preset information about MPU3050 (gyro sensor)
  7. #define MPU3050_I2C (0x69)
  8. #define MPU3050_REG (0x21)
  9. //Preset buzzer WiringPi port
  10. #define BUZZER 0
  11. //Preset button interrupt WiringPi port
  12. #define BUTTON 5
  13. //Preset button debounce time
  14. #define DEBOUNCE_MS 1000
  15. //Declaring all global variables
  16. volatile uint8_t trigger;
  17. volatile uint8_t photoTaken;
  18. volatile unsigned int prevTime = 0;
  19. volatile uint8_t btnClicked = 0;
  20. void buttonInterrupt()
  21. {
  22. //Get the current time and its difference from last interrupt
  23. unsigned int currentTime = millis();
  24. unsigned int deltaTime = currentTime - prevTime;
  25. //Check if the deltaTime from the last click is longer than the preset debounce time
  26. if (deltaTime > DEBOUNCE_MS)
  27. {
  28. //Set new values
  29. btnClicked = 1;
  30. prevTime = currentTime;
  31. if (trigger == 0)
  32. {
  33. //Set trigger and turn off buzzer
  34. trigger = 1;
  35. digitalWrite(BUZZER, LOW);
  36. }
  37. else
  38. {
  39. //Reset photoTaken and trigger
  40. photoTaken = 0;
  41. trigger = 0;
  42. //Double short beep to inform rider
  43. digitalWrite(BUZZER, HIGH);
  44. delay(100);
  45. digitalWrite(BUZZER, LOW);
  46. delay(100);
  47. digitalWrite(BUZZER, HIGH);
  48. delay(100);
  49. digitalWrite(BUZZER, LOW);
  50. }
  51. }
  52. }
  53. int main()
  54. {
  55. //Initialize photoTaken and trigger
  56. photoTaken = 0;
  57. trigger = 0;
  58. wiringPiSetup();
  59. pinMode(BUTTON, INPUT);
  60. pinMode(BUZZER, OUTPUT);
  61. //Setup ISR (button) and I2C (gyro sensor)
  62. int isrSetup = wiringPiISR(BUTTON, INT_EDGE_FALLING, &buttonInterrupt);
  63. int i2cSetup = wiringPiI2CSetup(MPU3050_I2C);
  64. //Check if setups are successful
  65. if (i2cSetup < 0||isrSetup < 0)
  66. {
  67. return 0;
  68. }
  69. //Declare 'gyroInput' to be used to contain the input from gyro sensor later
  70. int gyroInput;
  71. //Initialize 'count' to be used to keep track how many consecutive 0.1 secs had the gyro sensor stayed at 0
  72. int count = 0;
  73. //Double short beep to inform rider
  74. digitalWrite(BUZZER, HIGH);
  75. delay(100);
  76. digitalWrite(BUZZER, LOW);
  77. delay(100);
  78. digitalWrite(BUZZER, HIGH);
  79. delay(100);
  80. digitalWrite(BUZZER, LOW);
  81. while (1)
  82. {
  83. //Get gyro sensor input
  84. gyroInput = wiringPiI2CReadReg8(i2cSetup, MPU3050_REG);
  85. if (gyroInput == 0)
  86. {
  87. //Increase count if gyro sensor returns 0
  88. count++;
  89. //If the gyro sensor reading stayed at '0' consecutively for over a full second
  90. if (count > 10 && trigger == 0 && photoTaken == 0)
  91. {
  92. //Set off the buzzer
  93. digitalWrite(BUZZER, HIGH);
  94. //Allow rider 2 seconds to cancel taking photo and sending email
  95. delay(2000);
  96. if (!btnClicked)
  97. {
  98. /* If rider did not press the button after 2 seconds, send an email asking
  99. * for help from emergency contact attaching a photo taken on the spot
  100. */
  101. system("raspistill -v -o photo.jpg && ./sendMail.sh");
  102. photoTaken = 1;
  103. }
  104. //Reset button clicks
  105. btnClicked = 0;
  106. }
  107. }
  108. else
  109. {
  110. //Reset counter to 0
  111. count = 0;
  112. }
  113. //Only read value from gyro sensor every 0.1 sec
  114. delay(100);
  115. }
  116. return 0;
  117. }