Как объединить символы приходячие через UART в слово?

Zahar
Zahar аватар
Offline
Зарегистрирован: 16.11.2013
Здравствуйте.
Я собрал лед куб и теперь пишу программу для него. 
Но я столкнулся с проблеммой. Мне нужно чтобы когда я посылаю какое нибудь слово через UART (RS232) программа исполняла какоенибудь действие в зависимости от рутины. Код который я написал работает только на один символ. А как сделать чтобы он работал на целое слово? 
Это только пример кода. Весь код страниц на двадцать.
 
Помогите пожалуйста.

char incomingByte;
void setup()
{
  Serial.begin(9600);
}
void loop()
{
  // Если что то пришло в порт то программа в зависимости от if
 // запускает определенную рутину.
  if (Serial.available() > 0) {
    incomingByte= Serial.read();
  }
  if (incomingByte=='Cube') {
        Serial.println("Cube");
            Cube();
  }
  if (incomingByte=='Salute') {
    Serial.println("Salute");
      Salute();
    }
   if (incomingByte=='Spirala') {
    Serial.println("Spirala");
         Spirala();
    }
   if (incomingByte=='Rain') {
    Serial.println("Rain");
          Rain();
     }
  }
void Cube(){
  // Здесь программа что то исполняет
}
  void Salute(){
    // Здесь программа что то исполняет
   }
void Spirala(){
  // Здесь программа что то исполняет
}
void Rain(){
  // Здесь программа что то исполняет
}

 

 

Zahar
Zahar аватар
Offline
Зарегистрирован: 16.11.2013

Зарание извините за мой РУССКИЙ

AS
Offline
Зарегистрирован: 12.03.2014

а почему бы вам прочитанные символы не собирать в массив? http://arduino.ru/forum/programmirovanie/s-com-portom-chto-ne-poimu#comment-60692 что-то типа такого..

ourlive
Offline
Зарегистрирован: 26.05.2012

собрать отдельные символы в строку, очевидно же

String bufer=""; //глобальная переменная



// использовать отдельной функцией (желательно)
if (Serial.available() > 0) {
  char ByteRead=Serial.read(); //чтение данных с порта
   if (ByteRead==char(13)) { //окончание строки
    //передача данных на обработку (обычно отдельная функция анализатор)
   bufer="";}  //освобождение буфера
   else {bufer=bufer+char(ByteRead);}  //накопление данных в буфер
  }

 

Zahar
Zahar аватар
Offline
Зарегистрирован: 16.11.2013

ourlive пишет:

собрать отдельные символы в строку, очевидно же

String bufer=""; //глобальная переменная



// использовать отдельной функцией (желательно)
if (Serial.available() > 0) {
  char ByteRead=Serial.read(); //чтение данных с порта
   if (ByteRead==char(13)) { //окончание строки
    //передача данных на обработку (обычно отдельная функция анализатор)
   bufer="";}  //освобождение буфера
   else {bufer=bufer+char(ByteRead);}  //накопление данных в буфер
  }

 

Большое спасибо.
Я только не понял как и где нужно объявить переменную bufer из 10-ой строки  ?
ourlive
Offline
Зарегистрирован: 26.05.2012
Zahar
Zahar аватар
Offline
Зарегистрирован: 16.11.2013

Я попробовал  адаптировать ваш код под свои нужды. Однако у меня что то не получается.

Когда я пишу в COM слово "test" он почемуто не заходит в void analyzer().

Обьясните пожалуста где ошибка?

String bufer=""; //глобальная переменная

void setup(){
Serial.begin(9600);
 Serial.println( "Start");
}

void loop(){
// использовать отдельной функцией (желательно)
if (Serial.available() > 0) {
char ByteRead=Serial.read(); //чтение данных с порта
  //if (ByteRead==char(13)) { //окончание строки
 if (ByteRead=='\0') {
  analyzer();//передача данных на обработку (обычно отдельная функция анализатор)
 bufer="";  //освобождение буфера
 }
 else {bufer=bufer+char(ByteRead);}  //накопление данных в буфер 
}
}
void analyzer()
{
if (bufer=="test"){
 Serial.println( "ok");
} 
}

 

com
Offline
Зарегистрирован: 06.09.2013

ну вы же сами себе и ответили - пишете "test", а это никаким боком не '\0' :)

отмониторьте, какие именно символы/байты прилетают в обработчик, когда вы пишете этот свой "test", и все вопросы снимутся

leshak
Offline
Зарегистрирован: 29.09.2011

Так пример который вам дали, вы же сами и поломали:

 //if (ByteRead==char(13)) { //окончание строки

 

ourlive
Offline
Зарегистрирован: 26.05.2012
String bufer="";

void setup(){ 
 Serial.begin(9600); 
 Serial.println("duino started");
}

void loop(){
read_serial();

}

void read_serial() {
  if (Serial.available() > 0) {
  char ByteRead=Serial.read();  //чтение данных с порта
   if (ByteRead==char(13)) {  //окончание строки
   analyzer();   //передача данных на обработку
   bufer="";}  //освобождение буфера
   else {bufer=bufer+char(ByteRead);}   ///накопление данных в буфер
  }
}

void analyzer() {
if (bufer.length()>1) {Serial.println("!!!!");} //если буфер не пустой
if (bufer=="test") {Serial.print("read: ");Serial.println(bufer);} //если принято слово "test"
else {Serial.print(bufer.length());Serial.print(" ");Serial.println(bufer);}
}
ourlive
Offline
Зарегистрирован: 26.05.2012

строк тут очень мало, сложены они из самых простых функций, разберитесь как оно работает

leshak
Offline
Зарегистрирован: 29.09.2011

Так как-то легче читается код:

String bufer="";

void setup(){ 
  Serial.begin(9600); 
  Serial.println("duino started");
}

void loop(){
  read_serial();

}

void read_serial() {
  if (Serial.available() > 0) {
    char ByteRead=Serial.read();  //чтение данных с порта
    if (ByteRead==13) {  //возврат каретки
      analyzer();   //передача данных на обработку
      bufer="";
    }  //освобождение буфера
    else {
      ///накопление данных в буфер
      if(ByteRead!=10)bufer=bufer+char(ByteRead); // символ "новая строка" \n, нам в буффере не нужен
    }   
  }
}

void analyzer() {
  if (bufer.length()>1) {
    Serial.println("!!!!");
  } //если буфер не пустой
  if (bufer=="test") {
    Serial.print("read: ");
    Serial.println(bufer);
  } //если принято слово "test"

}

 

ourlive
Offline
Зарегистрирован: 26.05.2012

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

leshak
Offline
Зарегистрирован: 29.09.2011

Да ради бога :) Дело вкуса.  Ctrl-T в ArduinoIDE все расставляет по своим местам :)

Я там еще обработку \n, добавил. Мало-ли какой Line Ending выставлен в терминале. А то он у вас тоже попадал в буффер и потом выводился в println, будет давать лишний перевод строки.

Не считая того, что сама комманда может не распознатся. Так как "test\n" не равно "test"

 

ourlive
Offline
Зарегистрирован: 26.05.2012

замечание верное, хотел я упомянуть, но забыл, команда гарантированно не распознаётся из-за char(10), пример просто выдернул из недавнего скетча где уже всё на процессинг завязано.

Zahar
Zahar аватар
Offline
Зарегистрирован: 16.11.2013
leshak Добрый вечер
У меня всё равно не работает
Методом тыка я понял что не срабатывает 16 строка
Тоесть порт не видит символа "возврат каретки"
Почему это происхоит?
 

 

leshak
Offline
Зарегистрирован: 29.09.2011

Zahar пишет:

leshak Добрый вечер
У меня всё равно не работает
Методом тыка я понял что не срабатывает 16 строка
Это самый верный метод. Именно так и осваиватся все :) 95% работы вы уже сделали - нашли место проблемы :)
 
Zahar пишет:

Тоесть порт не видит символа "возврат каретки"Почему это происхоит?
 
Наиболее веротяный ответ: тяжело искать черную кошку в черной комнате. Особенно если ее нет :)
Так вот, что-бы увидеть "символ", нужно что-бы кто-то его послал.
 
Открывайте Serial Monitor. Переводите глаза на его нижний правый угол. Там скорость ком-порта. Чуть левее его Выпадающий список Line Ending. Это и есть "что послать в конце строке".
 
"No line Ending" - Ничего не посылать (скорее всего у вас это и стоит).
"New line" - символ новой строки
"Carriage return" - перевод каретки
"Both NL & CR" - и символ новой строки и символ перевода каретки.
 
По идее вам "покатят" два последних варианта.
 
 
 
Zahar
Zahar аватар
Offline
Зарегистрирован: 16.11.2013
Я думал что символ возврата каретки посылается автоматически с нажатием интер. :(
Огромное всем спасибо !!!