#include <LiquidCrystal_I2C.h>
#include <Wire.h> // Include the Wire library for I2C communication
#include <Servo.h>
/* Servo setup */
#define SERVO_PIN_RED 6 // Servo for Malboro Red
#define SERVO_PIN_GREEN 9 // Servo for Mighty Green
#define SERVO_PIN_EXTRA 11 // Servo for Extra
#define SERVO_OPEN_POS 0
#define SERVO_CLOSED_POS 90
Servo redGateServo;
Servo greenGateServo;
Servo extraServo;
/* Display */
LiquidCrystal_I2C lcd(0x27, 16, 2); // Change the I2C address if needed
/* Button Pins */
const int greenButtonPin = 7; // Connect the green button to digital pin 7
const int redButtonPin = 8; // Connect the red button to digital pin 8
const int insertButtonPin = 2; // Connect the insert button to digital pin 2
const int doubleClickButtonPin = 3; // Connect the double-click button to digital pin 3
const int extraButtonPin = 4; // Connect the extra button to digital pin 4
/* LED Pins */
const int redLedPin = 13; // Connect the red LED to digital pin 13
const int greenLedPin = 10; // Connect the green LED to digital pin 10
const int yellowLedPin = 5; // Connect the yellow LED to digital pin 5
const int buzzerPin = 12; // Connect the buzzer to digital pin 12
int credit = 0; // Variable to keep track of the inserted amount
void setup() {
lcd.init(); // Initialize the LCD
lcd.backlight(); // Turn on the backlight
redGateServo.attach(SERVO_PIN_RED);
redGateServo.write(SERVO_CLOSED_POS); // Initialize the red gate as closed
greenGateServo.attach(SERVO_PIN_GREEN);
greenGateServo.write(SERVO_CLOSED_POS); // Initialize the green gate as closed
extraServo.attach(SERVO_PIN_EXTRA);
extraServo.write(SERVO_CLOSED_POS); // Initialize the extra gate as closed
pinMode(greenButtonPin, INPUT_PULLUP); // Set the green button pin as input with pull-up resistor
pinMode(redButtonPin, INPUT_PULLUP); // Set the red button pin as input with pull-up resistor
pinMode(insertButtonPin, INPUT_PULLUP); // Set the insert button pin as input with pull-up resistor
pinMode(doubleClickButtonPin, INPUT_PULLUP); // Set the double-click button pin as input with pull-up resistor
pinMode(extraButtonPin, INPUT_PULLUP); // Set the extra button pin as input with pull-up resistor
pinMode(redLedPin, OUTPUT); // Set the red LED pin as output
pinMode(greenLedPin, OUTPUT); // Set the green LED pin as output
pinMode(yellowLedPin, OUTPUT); // Set the yellow LED pin as output
pinMode(buzzerPin, OUTPUT); // Set the buzzer pin as output
digitalWrite(redLedPin, LOW); // Turn off the red LED initially
digitalWrite(greenLedPin, LOW); // Turn off the green LED initially
digitalWrite(yellowLedPin, LOW); // Turn off the yellow LED initially
// Initial display setup (no blinking)
lcd.setCursor(0, 0);
lcd.print("VENDO CIGARETTES");
lcd.setCursor(0, 1);
lcd.print("Credit: 0");
}
void loop() {
// Check if the double-click button is pressed
if (digitalRead(doubleClickButtonPin) == LOW) {
credit += 5; // Add 5 pesos to the credit
updateCreditDisplay();
digitalWrite(buzzerPin, HIGH); // Activate the buzzer
delay(200); // Wait for a short time
digitalWrite(buzzerPin, LOW); // Deactivate the buzzer
}
// Check if credit is 10 or more and enter selection mode
if (credit >= 10) {
digitalWrite(yellowLedPin, HIGH); // Turn on the yellow LED
lcd.setCursor(0, 1);
lcd.print("MALBORO/MIGHTY");
} else {
digitalWrite(yellowLedPin, LOW); // Turn off the yellow LED
}
// Check if credit is enough to access the items
if (credit >= 10) {
// Check if the green button is pressed
if (digitalRead(greenButtonPin) == LOW) {
dispenseMalboroRed();
}
// Check if the red button is pressed
if (digitalRead(redButtonPin) == LOW && credit >= 9) {
dispenseMightyGreen();
}
}
// Check if the extra button is pressed and have credit
if (digitalRead(extraButtonPin) == LOW && credit > 0) {
openExtraServo(credit);
}
// If credit is not enough, display the credit amount
if (credit < 10) {
lcd.setCursor(0, 1);
lcd.print("Credit: " + String(credit));
}
}
void dispenseMalboroRed() {
lcd.clear();
lcd.print("MALBORO RED");
delay(500); // Wait for 1 second
redGateServo.write(SERVO_OPEN_POS); // Open the red gate
digitalWrite(redLedPin, HIGH); // Turn on the red LED
digitalWrite(yellowLedPin, LOW); // Turn off the yellow LED
delay(500); // Keep the gate open for 1 second (faster)
redGateServo.write(SERVO_CLOSED_POS); // Close the red gate
digitalWrite(redLedPin, LOW); // Turn off the red LED
credit -= 10; // Deduct the price from credit
updateCreditDisplay();
delay(1000); // Wait for 1 second before displaying "INSERT 5 PESOS" again
// Reset the display after dispensing
lcd.setCursor(0, 0);
lcd.print("VENDO CIGARETTES");
lcd.setCursor(0, 1);
lcd.print("Credit: " + String(credit));
}
void dispenseMightyGreen() {
lcd.clear();
lcd.print("MIGHTY GREEN");
delay(500); // Wait for 1 second
greenGateServo.write(SERVO_OPEN_POS); // Open the green gate
digitalWrite(greenLedPin, HIGH); // Turn on the green LED
digitalWrite(yellowLedPin, LOW); // Turn off the yellow LED
delay(500); // Keep the gate open for 1 second (faster)
greenGateServo.write(SERVO_CLOSED_POS); // Close the green gate
digitalWrite(greenLedPin, LOW); // Turn off the green LED
credit -= 9; // Deduct the price from credit
updateCreditDisplay();
delay(1000); // Wait for 1 second before displaying "INSERT 5 PESOS" again
// Reset the display after dispensing
lcd.setCursor(0, 0);
lcd.print("VENDO CIGARETTES");
lcd.setCursor(0, 1);
lcd.print("Credit: " + String(credit));
}
void updateCreditDisplay() {
lcd.setCursor(0, 1); // Set cursor to row 1, column 0
lcd.print("Credit: " + String(credit));
}
void openExtraServo(int times) {
for (int i = 0; i < times; i++) {
extraServo.write(SERVO_OPEN_POS);
delay(500);
extraServo.write(SERVO_CLOSED_POS);
delay(500);
credit--; // Decrement credit after each servo operation
updateCreditDisplay();
}
}