#include <Wire.h>
#include <LiquidCrystal_I2C.h>
#include <MPU6050.h>
LiquidCrystal_I2C lcd(0x27, 16, 2);
MPU6050 mpu;
#define buzzer 2
#define led 3
#define THRESHOLD 400
#define DEADBAND 40
#define BUZ_TIME 5000
#define READ_INTERVAL 2000
#define LCD_INTERVAL 2000
#define CALIB_TIME 4000
long lastRead = 0;
long lastLCD = 0;
bool alarmOn = false;
long alarmStart = 0;
bool calibrating = true;
long calibStart = 0;
long baseX = 0, baseY = 0, baseZ = 0;
long calibCount = 0;
long x, y, z;
long magnitude;
long lastX=9999, lastY=9999, lastZ=9999;
void setup() {
Wire.begin();
Serial.begin(9600);
mpu.initialize();
pinMode(buzzer, OUTPUT);
pinMode(led, OUTPUT);
noTone(buzzer);
lcd.init();
lcd.backlight();
lcd.clear();
lcd.print(" DETECTOR DE ");
lcd.setCursor(0,1);
lcd.print(" TERREMOTO ");
delay(1200);
lcd.clear();
lcd.print("CALIBRANDO...");
calibStart = millis();
}
void loop() {
unsigned long now = millis();
if (calibrating) {
int16_t ax, ay, az;
mpu.getAcceleration(&ax, &ay, &az);
baseX += ax;
baseY += ay;
baseZ += az;
calibCount++;
if (now - calibStart >= CALIB_TIME) {
baseX /= calibCount;
baseY /= calibCount;
baseZ /= calibCount;
calibrating = false;
lcd.clear();
lcd.print(" X Y Z ");
Serial.println("CALIBRAÇÃO FEITA!");
Serial.print("BaseX="); Serial.println(baseX);
Serial.print("BaseY="); Serial.println(baseY);
Serial.print("BaseZ="); Serial.println(baseZ);
}
return;
}
if (now - lastRead >= READ_INTERVAL) {
lastRead = now;
int16_t ax, ay, az;
mpu.getAcceleration(&ax, &ay, &az);
x = ax - baseX;
y = ay - baseY;
z = az - baseZ;
if (abs(x) < DEADBAND) x = 0;
if (abs(y) < DEADBAND) y = 0;
if (abs(z) < DEADBAND) z = 0;
magnitude = sqrt(x*x + y*y + z*z);
Serial.print("X="); Serial.print(x);
Serial.print(" Y="); Serial.print(y);
Serial.print(" Z="); Serial.print(z);
Serial.print(" | Mag="); Serial.println(magnitude);
if (!alarmOn && magnitude > THRESHOLD) {
alarmOn = true;
alarmStart = now;
lcd.clear();
lcd.setCursor(0,0);
lcd.print("TERREMOTO!!!");
tone(buzzer, 1000);
digitalWrite(led, HIGH);
}
}
if (alarmOn) {
if (now - alarmStart >= BUZ_TIME) {
alarmOn = false;
noTone(buzzer);
digitalWrite(led, LOW);
lcd.clear();
lcd.print(" X Y Z ");
lastX = lastY = lastZ = 9999;
}
return;
}
if (now - lastLCD >= LCD_INTERVAL) {
lastLCD = now;
if (x != lastX || y != lastY || z != lastZ) {
lastX = x; lastY = y; lastZ = z;
lcd.setCursor(0,1);
lcd.print(padValue(x));
lcd.setCursor(6,1);
lcd.print(padValue(y));
lcd.setCursor(11,1);
lcd.print(padValue(z));
}
}
}
String padValue(long v) {
String s = String(v);
while (s.length() < 4) s = " " + s;
if (s.length() > 4) s = s.substring(0,4);
return s;
}