#include <Stepper.h>
#define BUTTON_START_STOP 7
#define BUTTON_LEFT 5
#define BUTTON_RIGHT 6
#define MAX_SPEED 100
#define PIN_POTENTIOMETER A0
const int stepsPerRevolution = 200;
class Motor : public Stepper
{
public:
Motor(int number_of_steps, int motor_pin_1, int motor_pin_2, int motor_pin_3, int motor_pin_4) :
Stepper(number_of_steps, motor_pin_1, motor_pin_2, motor_pin_3, motor_pin_4)
{
_motorSpeed = 0;
_directionRight = true;
_working = false;
}
~Motor() = default;
void startStop()
{
if(_working)
{
_working = false;
}
else
{
_working = true;
}
}
void setRotationRight()
{
_directionRight = true;
}
void setRotationLeft()
{
_directionRight = false;
}
void setSpeed(long whatSpeed)
{
if(whatSpeed > 0)
{
_motorSpeed = whatSpeed;
Stepper::setSpeed(whatSpeed);
}
else
{
_motorSpeed = 0;
}
}
void step(int numberSteps)
{
if(_working && _motorSpeed > 0)
{
if(_directionRight)
{
Stepper::step(numberSteps);
}
else
{
Stepper::step(-numberSteps);
}
}
}
private:
int _motorSpeed;
bool _directionRight;
bool _working;
};
template<int samplesNum>
class AverageFilter
{
public:
AverageFilter(int pin)
{
pinIn = pin;
}
int operator()()
{
sum -= samples[curIndex];
samples[curIndex] = analogRead(pinIn);
sum += samples[curIndex];
curIndex = (curIndex + 1) % samplesNum;
return sum/samplesNum;
}
private:
int pinIn;
long long sum = 0;
long long samples[samplesNum]{};
int curIndex = 0;
};
template<typename T>
class Button
{
public:
Button(T* object, void (T::*action)(void), int pinB)
{
_object = object;
_action =action;
_lastButton = LOW;
_curButton = LOW;
_pinButton = pinB;
pinMode(pinB, INPUT_PULLUP);
}
~Button() = default;
void process()
{
_curButton = debounce();
if (_lastButton == HIGH && _curButton == LOW)
{
(_object->*_action)();
}
_lastButton = _curButton;
}
private:
T* _object;
void (T::*_action)(void);
int _lastButton;
int _curButton;
int _pinButton;
int debounce ()
{
int current = digitalRead(_pinButton);
if(_lastButton != current)
{
delay(5);
current = digitalRead(_pinButton);
}
return current;
}
};
Motor motor(stepsPerRevolution, 8, 9, 10, 11);
AverageFilter<10> filter(PIN_POTENTIOMETER);
Button<Motor> startStopButton(&motor, &Motor::startStop, BUTTON_START_STOP);
Button<Motor> goRightButton(&motor, &Motor::setRotationRight, BUTTON_RIGHT);
Button<Motor> goLeftButton(&motor, &Motor::setRotationLeft, BUTTON_LEFT);
void setup() {
pinMode(PIN_POTENTIOMETER, INPUT);
analogReference(DEFAULT);
}
void loop()
{
const int k = 2;//кол-во шагов двигателя за один цикл Arduino
startStopButton.process();
goRightButton.process();
goLeftButton.process();
int motorSpeed = map(filter(), 0, 1023, 0, MAX_SPEED);
motor.setSpeed(motorSpeed);
motor.step(k);
}
uno:A5.2
uno:A4.2
uno:AREF
uno:GND.1
uno:13
uno:12
uno:11
uno:10
uno:9
uno:8
uno:7
uno:6
uno:5
uno:4
uno:3
uno:2
uno:1
uno:0
uno:IOREF
uno:RESET
uno:3.3V
uno:5V
uno:GND.2
uno:GND.3
uno:VIN
uno:A0
uno:A1
uno:A2
uno:A3
uno:A4
uno:A5
stepper1:A-
stepper1:A+
stepper1:B+
stepper1:B-
btn1:1.l
btn1:2.l
btn1:1.r
btn1:2.r
btn2:1.l
btn2:2.l
btn2:1.r
btn2:2.r
btn3:1.l
btn3:2.l
btn3:1.r
btn3:2.r
pot1:GND
pot1:SIG
pot1:VCC