Code doesn't work as I expect it to.

Hi, I’d like help with some coding.

The ultimate goal of this project is to remind the user to drink water at 1-hour intervals if the person hasn’t drunk any water since the last hour. In the following code, I’m using an ultrasonic sensor, LCD and a piezo buzzer. When the user hasn’t drunk water in the last hour, the piezo buzzer beeps twice. However, when I try the following code, the buzzer keeps beeping continuously even when the distance(measured by the sensor) remains the same for one hour (which means the person hasn’t drunk any or less water in the past hour). I have set the interval to 5 seconds for quick results.

Thank you for your help in advance.

//Adds the liquid crystal library 
#include <LiquidCrystal.h>

//defines note to be played by buzzer
#define NOTE_G4 392

//defines lcd pin numbers
LiquidCrystal lcd(12, 11, 5, 4, 3, 2);

//defines buzzer pin number
const int kPinSpeaker = 9;

// defines ultra sonic sensor pin numbers
const int trigPin = 8;
const int echoPin = 7;

// defines variables
long duration;
long volume;
long interval = 2000;//3600000; //1 hour
unsigned long previousmillis = 0;
double pdist = 0;
double cdist = 0; 
double mcons = 4.5; //128ml. Minimum consumption of water the person has to take every hour;
boolean displayed = false;


void setup() {
pinMode(echoPin, INPUT); // Sets the echoPin as an Input
pinMode(trigPin, OUTPUT); // Sets the trigPin as an Output
Serial.begin(9600); // Starts the serial communication 
lcd.begin(16, 2); // Starts the lcd communication 
}

void loop() {
// Clears the trigPin
digitalWrite(trigPin, LOW);
delayMicroseconds(2);

// Sets the trigPin on HIGH state for 10 micro seconds
digitalWrite(trigPin, HIGH);
delayMicroseconds(10);
digitalWrite(trigPin, LOW);

// Reads the echoPin, returns the sound wave travel time in microseconds
duration = pulseIn(echoPin, HIGH);

//Converting the distance to cm
double cdist = duration / 29 / 2;
Serial.println(cdist);

 //Finds the volume of remaining height in the bottle
double volume_of_rem_height = 3.14*3*3*(cdist);
Serial.println(1800-volume_of_rem_height);

//Displays the amount of mililetres left for the user to drink for proper hydration on the LCD
if (!displayed) {
         lcd.clear();
         lcd.print(1800-volume_of_rem_height);
         displayed = false;
      }
      
//Checking whether user drinks water every 1 hour or not
unsigned long currentmillis = millis();
if(currentmillis - previousmillis >= interval){  //THIS IS WHERE I REQUIRE ASSISTANCE
  if(cdist >= pdist + mcons){
    pdist = cdist;
    previousmillis = currentmillis;
    }
   else if(cdist <= pdist + mcons){
    tone(kPinSpeaker, NOTE_G4, 500);
    delay(500);  
    tone(kPinSpeaker, NOTE_G4, 500);
    pdist = cdist;
    previousmillis = currentmillis;
   }
  }
}

I have set the interval to 5 seconds for quick results.

But you have not put any Serial.print() statements in the code to learn what it is doing. Why not?

previousmillis and currentmillis are lousy names. That the value came from a call to millis() is completely irrelevant. There is a reason that previousmillis is assigned a value. The name of the variable should reflect that reason, such as lastTimeWaterWasConsumed. currentmillis is, obviously, now, so why not use now as the name?

delay() and millis() do NOT belong in the same sketch.

Thank you for your reply. I shall change the names. I used delay and millis to test something. However, I require more help in the section I have mentioned in the code. If you know how to do this, please let me know.

I'd slow down the ultrasonic sensor to allow time for the sound waves to dissipate.

Could you take a reading every 5 seconds... that seems frequent enough.