#include <PubSubClient.h>
#include <WiFi.h>
#include <DHTesp.h>
#include <NTPClient.h>
#include <WiFiUdp.h>

const int DHT_PIN = 15;

#define LED_BUILTIN 12
#define Buzzer 20

WiFiClient espClient;
PubSubClient mqttClient(espClient);
DHTesp dhtSensor;

WiFiUDP ntpUDP;
NTPClient timeClient(ntpUDP);

bool SchOn = false;
unsigned int SchTime;

char tempAr[6];

void setup() {
  // put your setup code here, to run once:
  Serial.begin(115200);
  setupWifi();
  setupMqtt();
  dhtSensor.setup(DHT_PIN,DHTesp::DHT22);

  timeClient.begin();
  timeClient.setTimeOffset(5.5*3600);

  pinMode(LED_BUILTIN, OUTPUT);
  digitalWrite(LED_BUILTIN, LOW);
}

void loop() {
  
  if(!mqttClient.connected()){
    connecttobroker();
  }

  mqttClient.loop();

  updatetemp();
  Serial.println(tempAr);
  mqttClient.publish("ENTC-TEMP",tempAr);
  delay(2000);

  checkSch();
  //digitalWrite(LED_BUILTIN, HIGH);

}

void setupWifi(){

  WiFi.begin("Wokwi-GUEST","");

  while(WiFi.status() != WL_CONNECTED){
    delay(500);
    Serial.print(".");
  }

Serial.println("");
Serial.println("WiFi Connected!");
Serial.println("IP Address:");
Serial.println(WiFi.localIP());

}

void setupMqtt(){
  mqttClient.setServer("test.mosquitto.org",1883);
  mqttClient.setCallback(receiveCallback);
}

void connecttobroker(){
  while(!mqttClient.connected()){
    Serial.print("Attempting to connect to MQTT......");
    if(mqttClient.connect("ESP2-2024")){
      Serial.println("Connected!");
      mqttClient.subscribe("ENTC-ON-OFF-ESP");
      mqttClient.subscribe("ENTC-SCH");
    }
      else{
        Serial.println("Failed!");
        Serial.println(mqttClient.state());
        delay(5000);
      }
  }
}

void updatetemp(){
  TempAndHumidity data = dhtSensor.getTempAndHumidity();
  String(data.temperature,2).toCharArray(tempAr,6);
}

void receiveCallback(char* topic,byte* payload,unsigned int length){
  Serial.print("Message Arrived[");
  Serial.print(topic);
  Serial.print("]");

  char payloadCharAr[length];

  for(int i=0;i<length;i++){
    Serial.print((char)payload[i]);
    payloadCharAr[i] = (char)payload[i];
  }
  Serial.println();

  if(strcmp(topic,"ENTC-ON-OFF-ESP") == 0){
    if(payloadCharAr[0] == '1'){
        tone(Buzzer,256);
    }else{
      noTone(Buzzer);
    }
  }

  if(strcmp(topic,"ENTC-SCH") == 0){
    if(payloadCharAr[0] == 'N'){
        SchOn = false;
    }else{
      SchOn = true;
      SchTime = atol(payloadCharAr);
    }
  }

}

unsigned long getTime(){
  timeClient.update();
  return timeClient.getEpochTime();
}

void checkSch(){
  if(SchOn){
    unsigned long currentTime = getTime();
    if(currentTime > SchTime){
      tone(Buzzer,256);
      SchOn = false;
      mqttClient.publish("ENTC-ON-OFF-ESP","1");
      mqttClient.publish("ENTC-SCH-ESP","0");
      Serial.println("Schedule ON");
    }
  }

}