
#include <SmartThingsEthernetW5x00.h>

#include <Constants.h>
#include <Device.h>
#include <Everything.h>
#include <Executor.h>
#include <InterruptSensor.h>
#include <PollingSensor.h>
#include <Sensor.h>

#include <EX_Alarm.h>
#include <EX_Switch.h>
#include <EX_Switch_Dim.h>
#include <IS_Button.h>
#include <IS_CarbonMonoxide.h>
#include <IS_Contact.h>
#include <IS_DoorControl.h>
#include <IS_Motion.h>
#include <IS_Smoke.h>
#include <PS_Illuminance.h>
#include <PS_MQ2_Smoke.h>
#include <PS_TemperatureHumidity.h>
#include <PS_Voltage.h>
#include <PS_Water.h>
#include <S_TimedRelay.h>

#define PIN_4_RESERVED 4
#define PIN_1O_RESERVED 10
#define PIN_11_RESERVED 11
#define PIN_12_RESERVED 12
#define PIN_13_RESERVED 13
#define PIN_50_RESERVED 50
#define PIN_51_RESERVED 51
#define PIN_52_RESERVED 52
#define PIN_53_RESERVED 53

// WC
#define PIN_WC_TIPKA_1 24
#define PIN_WC_TIPKA_2 25
#define PIN_WC_ALARM 26
#define PIN_WC_TEMPHUM 27
#define PIN_WC_LUC_1 28

// Hodnik
#define PIN_HODNIK_VRATA_VHOD 29
#define PIN_HODNIK_LUC_1 30
#define PIN_HODNIK_LUC_2 31
#define PIN_HODNIK_LUC_3 32
#define PIN_HODNIK_LUC_4 33
#define PIN_HODNIK_ZVONEC_TIPKA 34
#define PIN_HODNIK_OMARE_LED 35
#define PIN_HODNIK_STROP_LED 36
#define PIN_ZUNAJ_LUC 37
#define PIN_HODNIK_STOPNISCE_SENZOR 38
#define PIN_HODNIK_VRATA_SENZOR 39

// Jedilnica
#define PIN_JEDILNICA_TIPKA_1 40
#define PIN_JEDILNICA_TIPKA_2 41
#define PIN_JEDILNICA_TIPKA_3 42
#define PIN_JEDILNICA_TIPKA_4 43
#define PIN_JEDILNICA_TIPKA_5 44
#define PIN_JEDILNICA_LUC_1 45
#define PIN_JEDILNICA_LUC_2 46
#define PIN_JEDILNICA_LED 47

// Dnevna
#define PIN_DNEVNA_SOBA_LUC_VTICNICA 48
#define PIN_PODSTREHA_TEMPVLAGA 49
#define PIN_DNEVNA_SOBA_TEMPVLAGA 50

// Otroška soba
#define PIN_OTROSKA_TIPKA_1 15
#define PIN_OTROSKA_TIPKA_2 16

// MAC address, leave first octet 0x06, change others to be unique
byte mac[] = {0x06, 0x02, 0x03, 0x04, 0x05, 0x06};

// Arduino device IP Address
IPAddress ip(192, 168, 88, 206);

// Router gateway
IPAddress gateway(192, 168, 88, 1);

// LAN subnet mask
IPAddress subnet(255, 255, 255, 0);

// DNS server
IPAddress dnsserver(192, 168, 88, 1);

// port to run the http server on
const unsigned int serverPort = 8090;

// hubitat hub ip
IPAddress hubIp(192, 168, 88, 251);

// hubitat hub port
const unsigned int hubPort = 39501;

void setup() {

  // Polling Sensors
  static st::IS_Button wcTipka1(F("button1"), PIN_WC_TIPKA_1);
  static st::IS_Button wcTipka2(F("button2"), PIN_WC_TIPKA_2);
  static st::IS_Motion wcAlarm(F("motion1"), PIN_WC_ALARM, HIGH, true);
  static st::PS_TemperatureHumidity wcTempVlaga(
      F("temphumid1"), 60, 40, PIN_WC_TEMPHUM,
      st::PS_TemperatureHumidity::DHT22, "temperature1", "humidity1");

  static st::IS_Button hodnikZvonecTipka(F("button3"), PIN_HODNIK_ZVONEC_TIPKA);
  static st::IS_Motion hodnikStopnisceSenzor(
      F("motion2"), PIN_HODNIK_STOPNISCE_SENZOR, LOW, true);
  static st::IS_Motion hodnikVrataSenzor(F("motion3"), PIN_HODNIK_VRATA_SENZOR,
                                         LOW, true);

  static st::IS_Button jedilnicaTipka1(F("button4"), PIN_JEDILNICA_TIPKA_1);
  static st::IS_Button jedilnicaTipka2(F("button5"), PIN_JEDILNICA_TIPKA_2);
  static st::IS_Button jedilnicaTipka3(F("button6"), PIN_JEDILNICA_TIPKA_3);
  static st::IS_Button jedilnicaTipka4(F("button7"), PIN_JEDILNICA_TIPKA_4);
  static st::IS_Button jedilnicaTipka5(F("button8"), PIN_JEDILNICA_TIPKA_5);

  static st::IS_Button otroskaSobaTipka1(F("button9"), PIN_OTROSKA_TIPKA_1);
  static st::IS_Button otroskaSobaTipka2(F("button10"), PIN_OTROSKA_TIPKA_2);

  static st::PS_TemperatureHumidity podstrehaTempVlaga(
      F("temphumid2"), 60, 40, PIN_PODSTREHA_TEMPVLAGA,
      st::PS_TemperatureHumidity::DHT22, "temperature2", "humidity2");
  static st::PS_TemperatureHumidity dnevnaSobaTempVlaga(
      F("temphumid3"), 60, 40, PIN_DNEVNA_SOBA_TEMPVLAGA,
      st::PS_TemperatureHumidity::DHT22, "temperature3", "humidity3");

  // Executors
  static st::EX_Switch wcLuc1(F("switch1"), PIN_WC_LUC_1);

  static st::EX_Switch hodnikVrataVhod(F("switch2"), PIN_HODNIK_VRATA_VHOD);
  static st::EX_Switch hodnikLuc1(F("switch3"), PIN_HODNIK_LUC_1);
  static st::EX_Switch hodnikLuc2(F("switch4"), PIN_HODNIK_LUC_2);
  static st::EX_Switch hodnikLuc3(F("switch5"), PIN_HODNIK_LUC_3);
  static st::EX_Switch hodnikLuc4(F("switch6"), PIN_HODNIK_LUC_4);
  static st::EX_Switch hodnikOmareLed(F("switch7"), PIN_HODNIK_OMARE_LED);
  static st::EX_Switch hodnikStropLed(F("switch8"), PIN_HODNIK_STROP_LED);
  static st::EX_Switch zunajLuc(F("switch9"), PIN_ZUNAJ_LUC);

  static st::EX_Switch jedilnicaLuc1(F("switch10"), PIN_JEDILNICA_LUC_1);
  static st::EX_Switch jedilnicaLuc2(F("switch11"), PIN_JEDILNICA_LUC_2);
  static st::EX_Switch jedilnicaLed(F("switch12"), PIN_JEDILNICA_LED);

  static st::EX_Switch dnevnaSobaLucVticnica(F("switch13"),
                                             PIN_DNEVNA_SOBA_LUC_VTICNICA);

  st::Everything::debug = true;
  st::Executor::debug = true;
  st::Device::debug = true;
  st::PollingSensor::debug = true;
  st::InterruptSensor::debug = true;

  st::Everything::SmartThing = new st::SmartThingsEthernetW5x00(
      mac, ip, gateway, subnet, dnsserver, serverPort, hubIp, hubPort,
      st::receiveSmartString);

  st::Everything::init();

  // Sensors

  st::Everything::addSensor(&wcTipka2);
  st::Everything::addSensor(&wcTipka2);
  st::Everything::addSensor(&wcAlarm);
  st::Everything::addSensor(&wcTempVlaga);

  st::Everything::addSensor(&hodnikZvonecTipka);
  st::Everything::addSensor(&hodnikStopnisceSenzor);
  st::Everything::addSensor(&hodnikVrataSenzor);

  st::Everything::addSensor(&jedilnicaTipka1);
  st::Everything::addSensor(&jedilnicaTipka2);
  st::Everything::addSensor(&jedilnicaTipka3);
  st::Everything::addSensor(&jedilnicaTipka4);
  st::Everything::addSensor(&jedilnicaTipka5);

  st::Everything::addSensor(&podstrehaTempVlaga);
  st::Everything::addSensor(&dnevnaSobaTempVlaga);

  st::Everything::addSensor(&otroskaSobaTipka1);
  st::Everything::addSensor(&otroskaSobaTipka2);

  // Executors

  st::Everything::addExecutor(&wcLuc1);

  st::Everything::addExecutor(&hodnikVrataVhod);
  st::Everything::addExecutor(&hodnikLuc1);
  st::Everything::addExecutor(&hodnikLuc2);
  st::Everything::addExecutor(&hodnikLuc3);
  st::Everything::addExecutor(&hodnikLuc4);
  st::Everything::addExecutor(&hodnikOmareLed);
  st::Everything::addExecutor(&hodnikStropLed);
  st::Everything::addExecutor(&zunajLuc);

  st::Everything::addExecutor(&jedilnicaLuc1);
  st::Everything::addExecutor(&jedilnicaLuc2);
  st::Everything::addExecutor(&jedilnicaLed);

  st::Everything::addExecutor(&dnevnaSobaLucVticnica);

  st::Everything::initDevices();
}

void loop() { st::Everything::run(); }
