Шаговый двигатель 28BYJ-48. Прошу помощи в доработке класса

Здравствуйте.

Билиотека Stepper.h c этим двигателем работает некорректно.

В приведенном скетче пытаюсь создать класс MOTORS для управления 28BYJ-48.
Метод mkstep поворачивает двигатель на один шаг. Направление задается параметром arrow2 (строка 80).
Скетч рабочий.

Прошу помощи в доработке конструктора класса, если он здесь имеется.
В конструкторе четыре пина (2,3,4,5) должны настроится на выход. Это строки 8-11;
Чтобы эти пины были видны в методе mkstep (строка 17), созданы строки 12-15.

Спасибо.

class MOTORS
{
  private:
    int pin11, pin22, pin33, pin44;
  public:
    MOTORS(int pin1, int pin2, int pin3, int pin4)
    {
      pinMode(pin1, OUTPUT);
      pinMode(pin2, OUTPUT);
      pinMode(pin3, OUTPUT);
      pinMode(pin4, OUTPUT);
      pin11 = pin1;
      pin22 = pin2;
      pin33 = pin3;
      pin44 = pin4;
    }
    void mkstep(bool arrow)
    {
      static unsigned long moment2;
      while (millis() - moment2 < 2)
      {
      }
      moment2 = millis();
      static byte array1[] = {1, 0, 0, 1};
      static byte array2[] = {1, 1, 0, 0};
      static byte array3[] = {0, 1, 1, 0};
      static byte array4[] = {0, 0, 1, 1};
      static byte uk;
      digitalWrite(pin11, array1[uk]);
      digitalWrite(pin22, array2[uk]);
      digitalWrite(pin33, array3[uk]);
      digitalWrite(pin44, array4[uk]);
      if (arrow == true)
      {
        switch (uk)
        {
          case 0: uk = 3;
            break;
          case 1: uk = 0;
            break;
          case 2: uk = 1;
            break;
          case 3: uk = 2;
            break;
        }
      }
      else
      {
        switch (uk)
        {
          case 0: uk = 1;
            break;
          case 1: uk = 2;
            break;
          case 2: uk = 3;
            break;
          case 3: uk = 0;
            break;
        }
      }
    }
};

// подключение шагового двигателя
#define IN1 2
#define IN2 3
#define IN3 4
#define IN4 5

MOTORS Stmt(IN1, IN2, IN3, IN4);

byte arrow2;

void setup()
{

}
void loop()
{
  Stmt.mkstep(arrow2);
}

Чо надо то тогда? Я так и не понял.

А проблема-то в чём?

Правильно ли создан конструктор? И конструктор ли это?

Ну, тогда завтра уже.

Спасибо! Буду ждать столько, сколко нужно. Принцип “работает и ладно” меня почему-то не устраивает. А клыссы в C++ для меня темный лес.

Если про функцию с 6 по 16, то да - это конструктор.
Но форум, видимо не читаешь… Петрович недавно только писал, что private использовать нужно только когда понимаешь и это очень нужно (в понимании - вообще труба, как я вижу?). А в остальных случаях нужно использовать protected для защиты от прямого доступа к членам класса.

Вот поэтому я и обратился за помощью.

Ну так исправить не забудь.

Сейчас узнаю, что это, исправлю.

А пока добавил такую строку: Stmt.pin11=10;
и получил ошибку, которую и ожидал:
int MOTORS::pin11' is private within this context

Заменил на protected

int MOTORS::pin11' is protected within this context

замените на public :laughing:

че хотите, непонятно!

Я хочу, чтобы эта переменная pin11 была недоступна. Поэтому в строке 3 скетча #1 поставил private, а BOOM говорит, что там нужен protected.
А я разницы пока не вижу. Сейчас изучаю эти тонкости.

Недоступна где?
В классе? В наследнике класса?

Ща Петрович меня побьет … :blush:

Бить он меня будет завтра. Недоступна для пользователя этим классом.

Инициализировать “железо” в конструкторе класса - не очень хорошая идея.
В Си (и Си++) все глобальные переменные инициализируются ДО первого исполняемого оператора программы. То есть конструктор класса будет вызван до того, как произойдет инициализация всего “железа” по умолчанию. И здесь много потенциальных конфликтов.
Если класс требует инициализации “железа”, лучше делать это в отдельном методе (например, init() или setup()), вызываемом из тела программы, например, из функции setup().

Куда добавил? Если в скетч, то все правильно, private и protected поля класса извне не доступны

Если таки нужен доступ извне, то вот

Мне это и нужно.

Я хочу, чтобы эта переменная pin11 была недоступна . Поэтому в строке 3 скетча #1 поставил private , а BOOM говорит, что там нужен protected .

В #10 я показал, что при private, что при protected доступ к этой переменной закрыт.

Надо делать примерно так?

void setup()
{
...
Stmt.begin();
...
}

Не заморачивайся этим пока. Когда поймешь, что к чему, тогда protected и применяй

@andriano в #15 гворит, что Инициализировать “железо” в конструкторе класса - не очень хорошая идея.

Правильно ли я добавил и применяю метод start() в setup? Этот скетч работает.

class MOTORS
{
  private:
    int pin11, pin22, pin33, pin44;
  public:
    MOTORS(int pin1, int pin2, int pin3, int pin4)
    {
      pin11 = pin1;
      pin22 = pin2;
      pin33 = pin3;
      pin44 = pin4;
    }
    void mkstep(bool arrow)
    {
      static unsigned long moment2;
      while (millis() - moment2 < 2)
      {
      }
      moment2 = millis();
      static byte array1[] = {1, 0, 0, 1};
      static byte array2[] = {1, 1, 0, 0};
      static byte array3[] = {0, 1, 1, 0};
      static byte array4[] = {0, 0, 1, 1};
      static byte uk;
      digitalWrite(pin11, array1[uk]);
      digitalWrite(pin22, array2[uk]);
      digitalWrite(pin33, array3[uk]);
      digitalWrite(pin44, array4[uk]);
      if (arrow == true)
      {
        switch (uk)
        {
          case 0: uk = 3;
            break;
          case 1: uk = 0;
            break;
          case 2: uk = 1;
            break;
          case 3: uk = 2;
            break;
        }
      }
      else
      {
        switch (uk)
        {
          case 0: uk = 1;
            break;
          case 1: uk = 2;
            break;
          case 2: uk = 3;
            break;
          case 3: uk = 0;
            break;
        }
      }
    }
    void start()
    {
      pinMode(pin11, OUTPUT);
      pinMode(pin22, OUTPUT);
      pinMode(pin33, OUTPUT);
      pinMode(pin44, OUTPUT);
    }
};

// подключение шагового двигателя
#define IN1 2
#define IN2 3
#define IN3 4
#define IN4 5

MOTORS Stmt(IN1, IN2, IN3, IN4);

byte arrow2;

void setup()
{
Stmt.start();
}
void loop()
{
  Stmt.mkstep(arrow2);
}