#include <AccelStepper.h>
#include <Wire.h>
#include <LiquidCrystal_I2C.h>
// Define LCD address and dimensions
#define LCD_ADDRESS 0x27
#define LCD_COLUMNS 16
#define LCD_ROWS 2
// Initialize the LCD object
LiquidCrystal_I2C lcd(LCD_ADDRESS, LCD_COLUMNS, LCD_ROWS);
// Define stepper motor connections
#define STEP_PIN 9
#define DIR_PIN 8
// Define button pins
#define MOTOR_BUTTON_PIN 4
#define DIRECTION_BUTTON_PIN 3
#define SETTING_BUTTON_PIN 5 // New setting and exit button pin
#define SPEED_STEPS_BUTTON_PIN 2 // New speed and steps button pin
#define MODE_BUTTON_PIN 6 // New mode button pin
// Define stepper motor parameters
int SPEED = 1000; // Speed variable
int STEPS = 100; // Steps variable
#define ACCELERATION 1000
// Initialize stepper motor object
AccelStepper stepper(AccelStepper::DRIVER, STEP_PIN, DIR_PIN);
// Variables to store button states
int motorButtonState = 0;
int lastMotorButtonState = 0;
int directionButtonState = 0;
int lastDirectionButtonState = 0;
int settingButtonState = 0; // New setting and exit button state
int lastSettingButtonState = 0; // New setting and exit button state
int speedStepsButtonState = 0; // New speed and steps button state
int lastSpeedStepsButtonState = 0; // New speed and steps button state
int modeButtonState = 0; // New mode button state
int lastModeButtonState = 0; // New mode button state
// Variable to store stepper motor state
bool stepperOn = false;
// Variable to store the current direction
int direction = 1; // 1 for forward, -1 for backward
// Variable to store the current setting option
int currentSettingOption = 0; // 0: Mode 0, 1: Mode 1, 2: Speed setting, 3: Steps setting, 4: Exit
// Variables to store saved speed and steps values
int savedSpeed = SPEED;
int savedSteps = STEPS;
// Variable to track if motor movement is complete
bool movementComplete = false;
// Variable to store initial step position
long initialPosition = 0;
void setup() {
// Set up LCD
lcd.init();
lcd.backlight();
// Set up stepper motor
stepper.setMaxSpeed(SPEED);
stepper.setAcceleration(ACCELERATION);
// Set up button pins
pinMode(MOTOR_BUTTON_PIN, INPUT_PULLUP);
pinMode(DIRECTION_BUTTON_PIN, INPUT_PULLUP);
pinMode(SETTING_BUTTON_PIN, INPUT_PULLUP); // New setting and exit button pin
pinMode(SPEED_STEPS_BUTTON_PIN, INPUT_PULLUP); // New speed and steps button pin
pinMode(MODE_BUTTON_PIN, INPUT_PULLUP); // New mode button pin
// Display initial message on LCD
lcd.setCursor(0, 0);
lcd.print("God Is My Light");
delay(1000);
lcd.clear();
lcd.setCursor(0, 0);
lcd.print("Stepper motor");
lcd.setCursor(0, 1);
lcd.print("control system");
delay(500);
lcd.clear();
}
void loop() {
// Read button states
motorButtonState = digitalRead(MOTOR_BUTTON_PIN);
directionButtonState = digitalRead(DIRECTION_BUTTON_PIN);
settingButtonState = digitalRead(SETTING_BUTTON_PIN); // New setting and exit button state
speedStepsButtonState = digitalRead(SPEED_STEPS_BUTTON_PIN); // New speed and steps button state
modeButtonState = digitalRead(MODE_BUTTON_PIN); // New mode button state
// If motor button is pressed and was not pressed before, toggle stepper state
if (motorButtonState != lastMotorButtonState && motorButtonState == LOW) {
stepperOn = !stepperOn;
if (stepperOn) {
if (currentSettingOption == 0) { // Mode 0
stepper.moveTo(1000000); // Move a very large number of steps for infinite rotation
stepper.setSpeed(SPEED * direction); // Set the speed with the current direction
} else if (currentSettingOption == 1) { // Mode 1
if (direction == 1) {
stepper.moveTo(savedSteps); // Move forward to the predetermined number of steps
} else {
stepper.moveTo(-savedSteps); // Move backward to the predetermined number of steps
}
stepper.setSpeed(savedSpeed * direction); // Set the speed with the saved speed
movementComplete = false; // Reset movement complete flag
initialPosition = stepper.currentPosition(); // Store initial position
}
} else {
stepper.stop(); // Stop the stepper motor immediately
}
}
// Toggle direction of the stepper motor if direction button is pressed
if (directionButtonState != lastDirectionButtonState && directionButtonState == LOW) {
direction *= -1; // Toggle direction
if (stepperOn) {
stepper.setSpeed(SPEED * direction); // Set the speed with the new direction
}
}
// If setting button is pressed and was not pressed before, change setting option
if (settingButtonState != lastSettingButtonState && settingButtonState == LOW) {
if (currentSettingOption == 4) { // Exit option selected
// Save speed and steps settings
savedSpeed = SPEED;
savedSteps = STEPS;
}
currentSettingOption = (currentSettingOption + 1) % 5; // Increment setting option, loop back to 0 after 4
}
// If mode button is pressed and was not pressed before, change mode
if (modeButtonState != lastModeButtonState && modeButtonState == LOW) {
currentSettingOption = (currentSettingOption + 1) % 5; // Increment mode, loop back to 0 after 4
}
// If speed and steps button is pressed and was not pressed before, increase speed and steps
if (speedStepsButtonState != lastSpeedStepsButtonState && speedStepsButtonState == LOW) {
if (currentSettingOption == 2) { // Speed setting
SPEED += 100; // Increase speed by 100 (you can adjust this value as needed)
if (currentSettingOption == 0 || currentSettingOption == 1) { // Mode 0 or 1
stepper.setSpeed(SPEED * direction); // Update stepper speed
}
} else if (currentSettingOption == 3) { // Steps setting
STEPS += 100; // Increase steps by 100 (you can adjust this value as needed)
}
}
// Update last button states
lastMotorButtonState = motorButtonState;
lastDirectionButtonState = directionButtonState;
lastSettingButtonState = settingButtonState;
lastSpeedStepsButtonState = speedStepsButtonState;
lastModeButtonState = modeButtonState;
// Update stepper motor
if (stepperOn || stepper.distanceToGo() != 0) {
stepper.run();
if (stepper.distanceToGo() == 0) { // Check if movement is complete
if (currentSettingOption == 1 && movementComplete) {
// Stop at initial position if movement is complete in Mode 1
stepper.setCurrentPosition(initialPosition);
stepper.stop();
movementComplete = false; // Reset movement complete flag
} else {
movementComplete = true; // Set movement complete flag
}
}
}
// If direction button is pressed, change direction
if (directionButtonState != lastDirectionButtonState && directionButtonState == LOW) {
direction *= -1; // Toggle direction
stepper.setSpeed(SPEED * direction); // Set the speed with the new direction
}
// Display motor status and direction on LCD
lcd.setCursor(0, 0);
lcd.print("Motor: ");
lcd.print(stepperOn ? "ON " : "OFF");
lcd.print(" :");
lcd.print(direction == 1 ? "Fwd " : "Bwd ");
// Display current setting option on LCD
lcd.setCursor(0, 1);
lcd.print("");
switch(currentSettingOption) {
case 0:
lcd.print("Mode 0 ");
break;
case 1:
lcd.print("Mode 1 ");
break;
case 2:
lcd.print("Speed: ");
lcd.print(SPEED);
break;
case 3:
lcd.print("Steps: ");
lcd.print(STEPS);
break;
case 4:
lcd.print("Exit...... ");
break;
}
}