#include <Arduino.h>
#line 1 "C:\\Users\\espi_\\Documents\\Arduino\\4. Bell Systems\\1. Main Projects\\Project - Vesper\\Project - Vesper.ino"
#include <WiFi.h>
#include <AsyncMqttClient.h>
#include <ArduinoJson.h>
#include <FS.h>
#include <SPIFFS.h>
#include <string>
#include <Wire.h>
#include <Adafruit_PCF8574.h>

#define PCF8574_ADDR 0x24
Adafruit_PCF8574 relays;

AsyncMqttClient mqttClient;

class melody_attributes {
public:
	uint16_t id;						  					// The (internal) ID of the selected melody. Not specificly used anywhere atm. Might be used later.
	std::string name = "melody1";                   // Name of the Melody saved. Will be used to read the file: /name.bin
	uint16_t speed = 500;                     // Time to wait per beat. (In Miliseconds)
  uint32_t duration = 15000;          // Total Duration that program will run (In Miliseconds)
	uint32_t loop_duration = 0;					// Duration of the playback per segment
	uint32_t interval = 0;         			// Indicates the Duration of the Interval between finished segments, IF "inf" is true
  bool infinite_play = false;         // Infinite Loop Indicator (If True the melody will loop forever or until stoped, with pauses of "interval" in between loops)
	bool isPlaying = false;;						// Indicates if the Melody is actually Playing right now.
	bool isPaused = false;							// If playing, indicates if the Melody is Paused
	uint64_t startTime = 0;							// The time-point the Melody started Playing
	uint64_t loopStartTime = 0;					// The time-point the current segment started Playing
	bool hardStop = false;							// Flags a hardstop, immediately.
	uint64_t pauseTime = 0;							// The time-point the melody paused

	void play() {
		isPlaying = true;
		hardStop = false;
		startTime = loopStartTime = millis();
		Serial.println("Plbck: PLAY");
	}

	void forceStop() {
		hardStop = true;
		isPlaying = false;
		Serial.println("Plbck: FORCE STOP");
	}

	void stop() {
		hardStop = false;
		isPlaying = false;
		Serial.println("Plbck: STOP");
	}

	void pause() {
		isPaused = true;
		Serial.println("Plbck: PAUSE");
	}

	void unpause() {
		isPaused = false;
		loopStartTime = millis();
		Serial.println("Plbck: RESUME");
	}

};

melody_attributes melody;
std::vector<uint16_t> melody_steps;

#include "config.h"
#include "functions.hpp"
#include "MQTT_Message_Handling.hpp"
#include "MQTT_WiFi_Utilities.hpp"
#include "PlaybackControls.hpp"
#include "bellEngine.hpp"



TaskHandle_t bellEngineHandle = NULL;



#line 79 "C:\\Users\\espi_\\Documents\\Arduino\\4. Bell Systems\\1. Main Projects\\Project - Vesper\\Project - Vesper.ino"
void setup();
#line 117 "C:\\Users\\espi_\\Documents\\Arduino\\4. Bell Systems\\1. Main Projects\\Project - Vesper\\Project - Vesper.ino"
void loop();
#line 79 "C:\\Users\\espi_\\Documents\\Arduino\\4. Bell Systems\\1. Main Projects\\Project - Vesper\\Project - Vesper.ino"
void setup()
{
  // Initialize Serial Communications & I2C Bus (for debugging)
	Serial.begin(115200);
  delay(50);

	// Initialize PCF8574
	Wire.begin(4,15);
	relays.begin(PCF8574_ADDR, &Wire);
	// Initialize Relays
	for (uint8_t p=0; p<6; p++){
		relays.pinMode(p, OUTPUT);
		relays.digitalWrite(p, HIGH);
	}

  // Initialize SPIFFS
  if (!SPIFFS.begin(true)) {  // 'true' means format SPIFFS if initialization fails
    Serial.println("Failed to mount SPIFFS");
    return;
  }
  Serial.println("SPIFFS mounted successfully");
	delay(50);


  // Initialize WiFi and MQTT
	WiFi.onEvent(WiFiEvent);
	InitMqtt();
	ConnectWiFi_STA();
  delay(1000);

  xTaskCreatePinnedToCore(bellEngine,"bellEngine", 8192, NULL, 1, &bellEngineHandle, 1);
  xTaskCreatePinnedToCore(durationTimer, "durationTimer", 8192, NULL, 2, NULL, 1);
	xTaskCreatePinnedToCore(relayControlTask, "Relay Control Task", 2048, NULL, 2, NULL, 1);

	loadRelayTimings();

}

void loop()
{
}

