Передача данных с помощью APC 220

vvadim
Offline
Зарегистрирован: 23.05.2012

Управляю дистанционно шаговым двигателем (пример из библиотеки AccelStepper). Получается только при мапировании значения potVal и при этом идёт дерганье и  запаздывание. Может нужно передавать  сразу значение potVal до 1024 (4 байта). Если да, то как правильно потом прочитать?

код передатчика



int pot = A0;
int potVal;
void setup()
{ 
  pinMode(pot, INPUT);
  Serial.begin(57600);
}
void loop()
{  
  potVal = analogRead(pot);
  potVal = map(potVal, 0, 1024, 0, 255);
  Serial.write(potVal);
} 

код приёмника




#include <AccelStepper.h>
AccelStepper stepper(1, 9, 8);
int potVal;
void setup()
{  
  stepper.setMaxSpeed(1500);
  Serial.begin(57600);  
}
void loop()
{
  if(Serial.available()>0) {
    potVal = Serial.read();
    potVal = map(potVal, 0, 255, 0, 1200);
    stepper.moveTo(potVal);
    stepper.setSpeed(1000);
    stepper.runSpeedToPosition();
  }
}

 

maksim
Offline
Зарегистрирован: 12.02.2012

Что за "западание" в вашем понимании не понятно, а вот дергания от потенциометра. Так же 1024 это не 4 байта, а 10 бит, которые поместятся в 2 байтах. Дергание устраняется добавлением зоны нечувствительности. И стоит поставить задержку и отправлять данные только при изменении, что бы не засерать передачу черезмерным количеством данных, кстати может из-за этого и происходит  "западание". 

int pot = A0;
int dead = 2;
int potVal, potValprev;

void setup()
{ 
  Serial.begin(57600);
}

void loop()
{  
  potVal = analogRead(pot);
  if(potVal < potValprev-dead || potVal > potValprev+dead)
  {
    potValprev = potVal;
    potVal = map(potVal, 0, 1024, 0, 255);
    Serial.write(potVal);
    delay(20);
  }
} 

 

vvadim
Offline
Зарегистрирован: 23.05.2012

 Уже при  delay(2); дёрганье пропало. Но задержка всё равно есть - даже при медленном повороте потенциометра шаговик не успевает за ним. В примере без Serial всё работает отлично.

 

maksim
Offline
Зарегистрирован: 12.02.2012

Ну так увеличте ускорение 

stepper.setAcceleration(3000);

 

maksim
Offline
Зарегистрирован: 12.02.2012

Для мгновенной передачи надо было покупать модули с интерфейсом SPI, а не UART, так же может эта задержка настраивается в самих модулях, так как модуль может ждать или накапливать определенное количество байт перед отправкой очередного пакета.

vvadim
Offline
Зарегистрирован: 23.05.2012

Я эти модули взял потому что их успешно используют вертолётчики. Сам разобраться в передаче данных пока не могу, но понимаю, что нужно граммотно организовать передачу значений potVal ( в моём случае ). Mожет проблема в двойном мапировании, может нужно передавать два байта и соответственно читать их ( а это я не знаю как сделать, хотя бы для эксперимента)

vvadim
Offline
Зарегистрирован: 23.05.2012

Правильно ли отправить 2 байта таким образом (potVal = 1023)

int pot = A0;
byte bytes[2];
int potVal;
void setup()
{ 
  pinMode(pot, INPUT);
  Serial.begin(57600);
}
void loop() 
{
  potVal = analogRead(pot);  
  bytes[0] = potVal & 255; 
  bytes[1] = (potVal & 768) >> 8; 
  Serial.write( bytes,2); 
}

 

vvadim
Offline
Зарегистрирован: 23.05.2012

Получилось отправить и прочитать 2 байта

код передатчика



int pot = A0;
int potVal;
byte LSB;
byte MSB;
void setup()
{ 
  pinMode(pot, INPUT);
  Serial.begin(57600);
}
void loop()
{  
  potVal = analogRead(pot);
  LSB = potVal & 0xff;
  MSB = (potVal >> 8) & 0xff;
  Serial.write(LSB);
  Serial.write(MSB);
} 

код приёмника




#include <AccelStepper.h>
AccelStepper stepper(1, 9, 8);
int potVal;
byte LSB;
byte MSB;
void setup()
{  
  stepper.setMaxSpeed(1500);
  Serial.begin(57600);  
}
void loop()
{
  if(Serial.available()>1) {
    MSB = Serial.read();
    LSB = Serial.read();
    potVal = word(MSB, LSB);
    potVal = map(potVal, 0, 1023, 0, 1200);
    stepper.moveTo(potVal);
    stepper.setSpeed(1500);
    stepper.runSpeedToPosition();
  }
}

Но вращение шаговика всё равно дискретное по сравнению с управлением напрямую без Serial.      Куда теперь идти и где копать?

maksim
Offline
Зарегистрирован: 12.02.2012

vvadim пишет:

Я эти модули взял потому что их успешно используют вертолётчики.

Откуда у вас такая информация? Ссылочку хоть одну можно, где ставят этот комплект на РУ и тем более вертолета?

vvadim
Offline
Зарегистрирован: 23.05.2012
maksim
Offline
Зарегистрирован: 12.02.2012

Если бы вы сами внимательнее прочитали для чего применяют эти модули вертолетчики, то для РУ его не купили бы. Самое первое предложение по вашей ссылке: 
"Впервые увидев GSC был впечатлен интерфейсом с красивым и понятным отображением телеметрии."

Ключевое слово телеметрия - то есть применяют эти модули для отправки данных о состоянии различных датчикойа не для управления моделью.

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

vvadim
Offline
Зарегистрирован: 23.05.2012

Я читал, что в основном этот модуль используется для телеметрии. Моя задача не требует мгновенных изменений положения двигателя, а плавного движения вслед за поворотом потенциометра. Поэтому на нём и остановился.

maksim
Offline
Зарегистрирован: 12.02.2012

Во-первых, вы и не измеряете положение двигателя. 
Во-вторых, в вашем случае "не мгновенно" и "плавно вслед за поворотом потенциометра" - несовместимые вещи, попробуйте добавить задержку в передающий скейтч и соединить по сериалу:

int pot = A0;
int potVal;
byte LSB;
byte MSB;
void setup()
{ 
  pinMode(pot, INPUT);
  Serial.begin(57600);
}
void loop()
{  
  potVal = analogRead(pot);
  LSB = potVal & 0xff;
  MSB = (potVal >> 8) & 0xff;
  Serial.write(LSB);
  Serial.write(MSB);
  delay(500);
} 

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