Что нам стоит ЧПУ привод построить

Не так давно я озаботился вопросом, как бы сделать привод для систем ЧПУ на коллекторном двигателе, да еще и с обратной связью, и что бы работал по Modbus RTU.

В распоряжении у меня имелись, Arduino UNO, Драйвер на L298N, коллекторный двигатель от привода сиденья автомобиля марки AEG на 12В, щелевой фотопрерыватель 2 шт.

С начала я спаял платку с 2-мя фотопрерывателями, вот по такой схеме.



В готовом виде это всё выглядит так:

image

Суть данной некрасивой вещи — спичка пересекает с начала первый прерыватель, потом второй, так микроконтроллер понимает в какую сторону вращается мотор.

Все соединения выглядят так:

d2 — первый фотопрерыватель;
d3 — второй фотопрерыватель;
d5 — выход шим для вращения влево;
d6 — выход шим для вращения вправо;

Всё было соединено и я засел за написание кода, в итоги муки мои родили следующее:

#include <ModbusRtu.h>
#define ID 1
//Задаём ведомому адрес, последовательный порт, выход управления TX
Modbus slave(ID, 0, 0);
int8_t state = 0;   //состояние соединения
uint16_t au16data[11];// массив данных modbus

#include <PID_v1.h> //биилиотека и настройки ПИД регулятора
double Setpoint1, Input1, Output1;
double Setpoint2, Input2, Output2;
double Kp = 1, Ki = 2.5, Kd = 0.5;
PID myPID1(&Input1, &Output1, &Setpoint1, Kp, Ki, Kd, DIRECT);    //1-й вращает в одну сторону
PID myPID2(&Input2, &Output2, &Setpoint2, Kp, Ki, Kd, REVERSE); //2-й вращает в другую

int LeftPWM = 5;  //шим вращения в одну сторону
int RightPWM = 6; //шим вращения в другую сторону
volatile byte EncA, EncB = 0; //переменные для работы с прерываниями
volatile int Position = 0; //текущая позиция мотора
int SetPosition = 0; //в какую позицию поставить мотор

void setup()
{
  slave.begin(9600);
  pinMode (LeftPWM, OUTPUT);
  pinMode (RightPWM, OUTPUT);
  attachInterrupt(0, ChangePosition1, FALLING); // привязываем 0-е(pin2) прерывание к функции ChangePosition1()
  attachInterrupt(1, ChangePosition2, FALLING); // привязываем 1-е(pin3) прерывание к функции ChangePosition2()
  Setpoint1 = 0;
  Setpoint2 = 0;
  digitalWrite (LeftPWM, LOW);
  digitalWrite (RightPWM, LOW);
}
//обработка прерывания 0
void ChangePosition1() //кто долго мучался с энкодером вот вам простой код для понимания!
{
  EncA = 1;
  if (EncA == 1 && EncB == 1)
  {
    EncA = 0;
    EncB = 0;
    Position++;
  }
}
//обработка прерывания 1
void ChangePosition2()
{
  EncB = 1;
  if (EncA == 1 && EncB == 1)
  {
    EncA = 0;
    EncB = 0;
    Position--;
  }
}
void loop()
{
  //Работа с ModBus
  // обработка сообщений
  state = slave.poll(au16data, 11);
  //Запись в регистры
  au16data[2] = Position;//текущее положение
  //Чтение из регистров
  SetPosition = au16data[3];//установить положение
  //Запись служебных регистров
  au16data[8] = slave.getInCnt();  //входящих пакетов
  au16data[9] = slave.getOutCnt(); //исходящих пакетов
  au16data[10] = slave.getErrCnt();//ошибок

  if (SetPosition == Position) //если нужная позиция равна текущей
  {
    myPID1.SetMode(MANUAL);
    myPID2.SetMode(MANUAL);
    Output1 = 0;
    Output2 = 0;
    digitalWrite (LeftPWM, LOW);
    digitalWrite (RightPWM, LOW);
  }
  if (SetPosition < Position)
  {
    myPID2.SetMode(AUTOMATIC);
    Setpoint2 = SetPosition;
    Input2 = Position;
    myPID2.Compute();
    analogWrite (LeftPWM, Output2);
    digitalWrite (RightPWM, LOW);
  }
  if (SetPosition > Position)
  {
    myPID1.SetMode(AUTOMATIC);
    Setpoint1 = SetPosition;
    Input1 = Position;
    myPID1.Compute();
    analogWrite (RightPWM, Output1);
    digitalWrite (LeftPWM, LOW);
  }
}

А теперь дело за частью на компьютере. Что бы это все двигать была выбрана SinplLight SCADA, парни дают её самодельщикам бесплатно. Итак — вот так выглядят настройки в скаде.

image

image

image

Интерфейс был сделан такой:

image

В итоге получили подчинение двигателя ползунку в скаде, разгоняется и тормозит двигатель плавно, если вручную прокручивать якорь мотора, он не дает этого делать, и возвращается назад. Спасибо за внимание. И вот общий вид на беспорядок.

image
Поделиться публикацией
Похожие публикации
Ой, у вас баннер убежал!

Ну. И что?
Реклама
Комментарии 11
  • +7
    Только вместо спички нужно хотя бы колесико от старой мышки, а-то шаг в один оборот — как-то совсем худо. Но тут уже другая песня, как это совместить с двумя (примененными у вас) датчиками скорости вращения? И с «дребезгами» то еще шаманство. Так вот делаешь-делаешь, а потом с бубном танцуешь, проходит половина года и думаешь: «Блин, лучше бы шаговик заводской купил и уже всё бы работало давно» — по себе сужу — делал ось Z, варил что-то, люфты убирал, подгонял каретку от печатной машинки (в итоге купил оси, опоры и всё хламье на нее тысячи за 3 и всё как часы). Сколько времени потрачено на плохо работающую железяку. «Городить» имеет смысл только если штуковина либо не выпускается вообще, либо если она заоблачно дорогая. Время дороже (личное, свободное). Мое мнение.
    • 0
      Вроде, взято до редуктора, так что не 1 импульс на оборот, а 100-500.
      Видео бы не помешало.
    • +3
      Какой шаг вы сможете отследить на ходовом винте? 0.1мм 0.01мм меньше?
      С какой скоростью можно двигать по оси?
      При условии, что все остальное покупается — ходовой винт с гайкой, а лучше ШВП, подшипники и прочее, имеет ли смысл экономить на шаговике с драйвером?
      • 0
        Люфт на червячном редукторе ШВП что в статье будет больше 0.1 мм так что не заворачивайтесь. Точность механических частей что на фото подходит разве что для прецизионного открывания форточки :)
      • +2

        Если как написано выше вместо спички воткнуть диск энкодера, расстояние между фотодатчиками подобрать чтобы направление определялось, то сотки может и трудно будет ловить, но момент и скорость у такого движка в разы лучше чем у шаговика за ту же цену.
        Если еще поколдовать то получится неплохая серва, а их цены уже стоят того чтобы поколдовать.

        • 0
          Ох у вас и код)) Если есть желание его улучшить — давайте через личку.
          • 0
            Спасибо за отклики на мою статью, эта статья больше как пособие для новичков все самое простое и много комментариев в коде, надеюсь кому-то это поможет.
            • 0
              купить можно многое, но есть такое слово хобби, интерес самому сделать,
              человек хочет сделать серву, а мощные сервы сильно подороже шаговиков,
              erepbs продолжайте, интересно будет посмотреть на Ваш результат, успехов!
              • 0
                Я в похожем проекте для обратной связи использовал моторчик от игрушки к качестве тахогенератора. Зато никакой дискретности, с какой скоростью двигатель работает, в таком же виде я получаю на аналоговом входе ардуины.
                • 0
                  Интересно. Спасибо.
                  А где конкретно он это будет применяться?
                  И еще вопрос: про Modbus RTU вы ничего не сказали, можно тут немного подробней?
                  ПС
                  Спичка рулит) Я обычно изоленту клею)
                  • 0
                    Просто некоторые разъяснения для начинающих, мои опыты.

                  Только полноправные пользователи могут оставлять комментарии. Войдите, пожалуйста.

                  Самое читаемое