// https://wokwi.com/projects/419072038170188801
 
# include <ezButton.h>

int balance;
bool hasMinimum;
const int minimumBalance = 40;
const int waterCost = 5;    // 5 credits for waterTick

// water - do we want it? is it aready running?

bool wantsWater;  // unused in 4 plus
bool isWatering;
 
const unsigned long waterTick = 777;  // milliseconds of water per waterCost credits

ezButton coinButton(2), waterButton(3);

const byte waterRequest = 6;
const byte waterControl = 7;

unsigned long now;    // the time. always.

void setup() {
  Serial.begin(115200);
  Serial.println("no free water.\n");

  coinButton.setDebounceTime(20);
  waterButton.setDebounceTime(20);

  pinMode(waterControl, OUTPUT);
  pinMode(waterRequest, OUTPUT);

  balance = 0;
  hasMinimum = false;   // if you didn't know now you know
}


// loop calls the version we are working on, which should alway run
// each subsequent version builds on success

void loop()
{
  loop4();
}

void loop4() {

  now = millis();

  static int printedBalance = -1;
  if (printedBalance != balance) {
    Serial.print("balance = ");
    Serial.println(balance);

    printedBalance = balance;
  }

// water in units of time here waterTick
// can't get here without money
  if (isWatering) {
    static unsigned long lastDebit;
    if (now - lastDebit > waterTick) {
      balance -= waterCost;
      if (balance < 0) {  // gack! does this give away a free unit of water?
        balance = 0;
        Serial.println(".        INSERT MORE COINS");
//        wantsWater = false; // who cares what this deadbeat _wants_?
        isWatering = false;
      }

      lastDebit = now;
    }
  }

// input. let ezButton have a look at the buttons
  coinButton.loop();
  waterButton.loop();
  
  bool coinInput = coinButton.isPressed();
  if (coinInput) {
    balance += 10;
    if (balance > minimumBalance) hasMinimum = true;    // may already be true
  }

  bool waterInput = waterButton.isPressed();
  if (waterInput) {
    if (isWatering) 
      isWatering = false;
    else
      if (balance && hasMinimum)
        isWatering = true;
      else {
        isWatering = false;
        hasMinimum = false;   // the real rinse before repeat
        Serial.println("INSERT COINS");
      }
  }

//  isWatering = wantsWater;

// OUTPUT adjust status LEDs and turn on or off the water
  digitalWrite(waterRequest, wantsWater ? HIGH : LOW);
  digitalWrite(waterControl, isWatering);
}


























void loop2() {

  now = millis();

  static int printedBalance = -1;
  if (printedBalance != balance) {
    Serial.print("balance = ");
    Serial.println(balance);

    printedBalance = balance;
  }

// input. let ezButton have a lok at the buttons
  coinButton.loop();
  waterButton.loop();
  
  if (coinButton.isPressed()) {
    balance += 10;
  }

  bool waterInput = waterButton.isPressed();

  if (waterInput) {
    if (isWatering) {
      wantsWater = !wantsWater;
    }
    else {
      if (balance) {
        wantsWater = true;
        isWatering = true;
      }
      else {
        wantsWater = false;
        Serial.println("INSERT COINS");
      }
    }
  }

  isWatering = wantsWater;

// OUTPUT adjust status LEDs and turn on or off the water
  digitalWrite(waterRequest, wantsWater ? HIGH : LOW);
  digitalWrite(waterControl, isWatering);
}

void loop1() {

  now = millis();

  static int printedBalance = -1;
  if (printedBalance != balance) {
    Serial.print("balance = ");
    Serial.println(balance);

    printedBalance = balance;
  }

// input. let ezButton have a lok at the buttons
  coinButton.loop();
  waterButton.loop();
  
  if (coinButton.isPressed()) {
    balance += 10;
  }

  if (waterButton.isPressed())
    wantsWater = !wantsWater;


// OUTPUT adjust status LEDs and turn on or off the water
  digitalWrite(waterRequest, wantsWater ? HIGH : LOW);
}

void loop0() {

  now = millis();

  static int printedBalance = -1;
  if (printedBalance != balance) {
    Serial.print("balance = ");
    Serial.println(balance);

    printedBalance = balance;
  }

// input. let ezButton have a lok at the buttons
  coinButton.loop();
  waterButton.loop();
  
  if (coinButton.isPressed()) {
    balance += 10;
  }
}