Управление двигателем с помощью монитора последовательного порта.

GetLucky777
Offline
Зарегистрирован: 12.10.2018
Всем привет, недавно начал знакомиться с Arduino, потребовалось управлять двигателем через монитор последовательного порта. 
К сожалению постоянного доступа к Arduino для проверки у меня нет, поэтому прошу вас посмотреть правильно ли написано. В интернете находил решения без использования переменных типа string, поэтому и спрашиваю. Всем заранее спасибо за ответ.

const int M1_Fwd=7;
const int M1_Rev=8;
const int PWM1=5;
String Value="";

void setup()
{
  pinMode(M1_Fwd,OUTPUT);
  pinMode(M1_Rev,OUTPUT);
  pinMode(PWM1,OUTPUT);
  Serial.begin(9600);
}

void loop() 
{
  if (Serial.available())
  {
    Value=Serial.readString();
    if (Value=="Pusk\n")
    {
      Serial.println("Forward direction");
      digitalWrite(M1_Fwd,HIGH);
      digitalWrite(M1_Rev,LOW);
      for (int i=0; i<151; i++)
      {
        analogWrite(PWM1, i);
        delay(20);
      }
    }
    else if (Value=="Rev\n")
    {
      Serial.println("Reverse direction");
      digitalWrite(M1_Fwd,LOW);
      digitalWrite(M1_Rev,HIGH);
      for (int i=0; i<151; i++)
      {
        analogWrite(PWM1, i);
        delay(20);
      }
    }
    else if (Value=="Stop\n")
    {
      Serial.println("Stop");
     int pin;
     pin=digitalRead(M1_Fwd);
     if (pin==HIGH)
     {
      digitalWrite(M1_Fwd,HIGH);
      digitalWrite(M1_Rev,LOW);
      for (int i=150; i>=0; i--)
      {
        analogWrite(PWM1, i);
        delay(20);
      }
     }
     else if (pin==LOW)
     {
      digitalWrite(M1_Fwd,LOW);
      digitalWrite(M1_Rev,HIGH);
      for (int i=150; i>=0; i--)
      {
        analogWrite(PWM1, i);
        delay(20);
      }
     }
    }
  }
  Value="";
}

 

ЕвгенийП
ЕвгенийП аватар
Онлайн
Зарегистрирован: 25.05.2015

GetLucky777 пишет:

К сожалению постоянного доступа к Arduino для проверки у меня нет, поэтому прошу вас посмотреть правильно ли написано.

Можно вот с этого места поподробнее? Что значит "нет"? У Вас нет 200 рублей, чтобы её купить и даже нет лишнего получаса, чтобы скачать эмулятор в протеусе? 

GetLucky777 пишет:

прошу вас посмотреть правильно ли написано

А вот Вы скажите, вот такая программа правильно написана?

void setup(void) {}
void loop(void) {}

Ну, как?

Программа не бывает правильной или неправильной пока неизвестно что и как она должна делать. Вы же этого не описали. Поэтому единственный возможный ответ - "Вам виднее"

И да, сразу, предупреждая возражения, фраза

GetLucky777 пишет:

управлять двигателем через монитор последовательного порта.

Это не описание "что и как она должна делать"

GetLucky777
Offline
Зарегистрирован: 12.10.2018

Спасибо, понял. Вот описание: при вводе в поле ввода монитора порта слова Pusk, скважность ШИМа должна плавно меняться на 150, двигатель должен вращаться по часовой стрелке. При вводе  слова Rev все тоже самое, только в другую сторону. При вводе слова Stop вращение двигателя должно остановиться.  

sadman41
Онлайн
Зарегистрирован: 19.10.2016

Если нет ардуины, берите Thinkercad. Там и код проверите и схему красиво накидаете.

На мой взгляд тут есть и глупость, есть и скользкий момент. Что вы будете делать с этим знанием?

ЕвгенийП
ЕвгенийП аватар
Онлайн
Зарегистрирован: 25.05.2015

Так про протеус я уже писал, но, видать не очень-то и надо.

sadman41
Онлайн
Зарегистрирован: 19.10.2016

Можно и протеус, я не против. Просто в thinkercad даже студенты могут разобраться минут за пять.

GetLucky777
Offline
Зарегистрирован: 12.10.2018

Хорошо, попробую Tinkercad

GetLucky777
Offline
Зарегистрирован: 12.10.2018

Sadman41, спасибо огромное за Tindercat!!! Все заработало, все проверено! Отказался от string.

 

const int M1_Fwd=7;
const int M1_Rev=8;
const int PWM1=5;
String Value="";

void setup()
{
  pinMode(M1_Fwd,OUTPUT);
  pinMode(M1_Rev,OUTPUT);
  pinMode(PWM1,OUTPUT);
  Serial.begin(9600);
  Serial.println("Print Forward for CW");
  Serial.println("Print Reverse for CCW");
  Serial.println("Print Stop for stop");
}

void loop() 
{
  while (Serial.available()>0)
  {
    delay(3);
    char znach=Serial.read();
    Value+=znach;
  }
    if (Value=="Forward")
    {
      Serial.println("Forward direction");
      digitalWrite(M1_Fwd,HIGH);
      digitalWrite(M1_Rev,LOW);
      for (int i=0; i<151; i++)
      {
        analogWrite(PWM1, i);
        delay(20);
      }
    }
    else if (Value=="Reverse")
    {
      Serial.println("Reverse direction");
      digitalWrite(M1_Fwd,LOW);
      digitalWrite(M1_Rev,HIGH);
      for (int i=0; i<151; i++)
      {
        analogWrite(PWM1, i);
        delay(20);
      }
    }
    else if (Value=="Stop")
    {
     Serial.println("Stop");
     int pin=digitalRead(M1_Fwd);
     if (pin==HIGH)
     {
      digitalWrite(M1_Fwd,HIGH);
      digitalWrite(M1_Rev,LOW);
      for (int i=150; i>=0; i--)
      {
        analogWrite(PWM1, i);
        delay(20);
      }
     }
     else if (pin==LOW)
     {
      digitalWrite(M1_Fwd,LOW);
      digitalWrite(M1_Rev,HIGH);
      for (int i=150; i>=0; i--)
      {
        analogWrite(PWM1, i);
        delay(20);
      }
     }
    }
    Value="";
  }

 

sadman41
Онлайн
Зарегистрирован: 19.10.2016

Не отказались, конечно, ну да ладно. И спасибо скажете автодеску... или кто там это замутил.

Вот лично мне кажется, что весь блок Stop можно просто одним циклом на снижение заменить. Потому как вы там повторно устанавливаете на пинах тот же режим, что и был ранее.

GetLucky777
Offline
Зарегистрирован: 12.10.2018

Я так сделал, чтобы всегда было плавное торможение. Ведь если например был реверс, то и тормозить он должен из реверса. А если я поставлю условие как при прямом вращении, двигатель резко остановится. А так получается программа определяет какая команда была подана последней и плавно тормозит мотор...

sadman41
Онлайн
Зарегистрирован: 19.10.2016

Я не вижу разницы. В обоих комбинациях цикл торможения одинаков - снижается пульс на PWM. Зачем ставить на IN1/IN2 еще раз то, что уже установлено?

GetLucky777
Offline
Зарегистрирован: 12.10.2018

Предположим что сейчас мотор вращается в прямом направлении, то есть IN1-HIGH, IN2-LOW. Если поставить в цикле торможения наоборот, то есть IN1-LOW, а IN2-HIGH, то двигатель сначала уйдет в реверс, а потом оттуда затормозит до нуля. Мне же необходимо, чтобы он не менял свое направление, а просто тормозил. Если же делать например IN1-LOW и IN2-LOW, то скорость просто станет 0, без постепенного снижения.

sadman41
Онлайн
Зарегистрирован: 19.10.2016

У меня, конечно, в голове мотора с драйвером, чтобы промоделировать все это, но вы просто пропробуйте оставить один цикл. В эмуляторе ничего не сгорит. Не сработает, так не сработает - вернете все на старое место.

GetLucky777
Offline
Зарегистрирован: 12.10.2018

Я как раз таки смоделировал все это в Tinkercade поэтому так уверенно и пишу)

sadman41
Онлайн
Зарегистрирован: 19.10.2016

Ну, смотрите сами... Лично мне кажется, что если (HIGH == digitalRead(M1_Fwd)), то это говорит только о том, что ранее был установлен Forward direction и повторно выставлять его особого смысла нет.

GetLucky777
Offline
Зарегистрирован: 12.10.2018

Точно, вы правы.