Передать и принять Integer по Serial

MaksVV
Offline
Зарегистрирован: 06.08.2015

Хотел по быстрому настроить передачу одного integer с одной ардуины на другую. Но, так как программирую не важно, быстро не получилось. Долго искал готовый скетч, но что то с ровного места найти так и не смог.

В итоге сделал почти сам (ну подглядел часть конечно). Тему создал для таких как я, чтобы в поиске находилась. 

Гуру, поправьте если коряво сделал. Но работает вроде хорошо. 

Передача 

#include <SoftwareSerial.h>
SoftwareSerial Serial100(10,11);  // Rx, Tx  передаём через софтсериал порт 

unsigned int var = 2665; // переменная которую передаём

unsigned long prev=0; // для таймера

void setup() {
Serial100.begin(19200);

}

void loop() {

unsigned long cur=millis ();
if (cur-prev>100){ // шлём раз в 0,1 с
   
byte b1 = ( byte )( var >> 8 ); // перевод нашей переменной в два байта
byte b2 = ( byte )var;
  
  Serial100.print ("1"); // сначала шлем символ "1" 
  
  Serial100.write (b1); // далее шлём первый байт переменной
 
  Serial100.print ("2"); //далее шлём символ "2"
  
  Serial100.write (b2); //далее шлём второй байт переменной
 
  Serial100.print ("3");  // далее шлем символ "3" передача окончена
  prev=cur;}

  

}

Прием

#include <SoftwareSerial.h>
SoftwareSerial Serial100(10,11);  // приниамем через софтсериал порт 

unsigned int var; // принимаемая переменная 

// ниже байты и флаги для приема переменной
byte b0;
byte b1;
byte b2;
bool byte1read=0;
bool byte2read=0;
bool byteEnd=0;


void setup() {

Serial100.begin(19200);

}

void loop() {
 
SerialREAD();

//если флаг "можно читать переменную из 2х байтов" в true 
// то соединяем байты в переменную
if (byteEnd) {var = ( ( unsigned int )b1 << 8 ) | b2; byteEnd=0;}


}

void SerialREAD (){
if (!Serial100.available()) return; // если в буфере сериала ничего нет сразу выходим из цикла

 
 b0 = Serial100.read(); // если в буфере что-то есть читаем
if (byte1read){ if (b0!=0x31 && b0!=0x32 && b0!=0x33) {b1=b0; byte1read=0;} }// пишем в первый байт
if (byte2read){ if (b0!=0x31 && b0!=0x32 && b0!=0x33) {b2=b0; byte2read=0;} }// пишем во второй байт

if (b0==0x31) byte1read=1; // если приняли символ '1' (см. ASCII )флаг "можно писать в первый байт" в true 
if (b0==0x32) byte2read=1; // если приняли символ '2' флаг "можно писать во второй байт" в true 
if (b0==0x33) byteEnd=1;   // если приняли символ '3' флаг "можно читать переменную из 2х байтов" в true 

}

 

ulis
ulis аватар
Offline
Зарегистрирован: 09.03.2011

А как физически вы связали ардуины?

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

MaksVV, а так сложно-то? Зачем эти три символа-то? Чего просто два байта не передать? Ну, или, даже через символы, но в лоб, типа

int n = 321;
Serial.print(n):

.....

int n = Serial.parseInt();

okta
Offline
Зарегистрирован: 10.01.2015

Неее, это не наш метод. Слишком просто. Надо было вообще свой язык форматирования придумать, аля для передачи числа 341:

<number type="int" name="myFirstInt">
 <digit pos="1">3</digit>
 <digit pos="3">1</digit>
 <digit pos="2">4</digit>
</number>

Все это загонять в сериал, и парсить, парсить, парсить. Зато потом можно как развернуться))))

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

Ну, да, так круче! Сюда ещё и полномасштабный xml-engine прикрутить можно.

А вообще задача-то в совершенно буквальном смысле "как два байта переслать" :)

MaksVV
Offline
Зарегистрирован: 06.08.2015

ЕвгенийП пишет:

MaksVV, а так сложно-то? Зачем эти три символа-то? Чего просто два байта не передать? Ну, или, даже через символы, но в лоб, типа

int n = 321;
Serial.print(n):

.....

int n = Serial.parseInt();


Потому что книгу по программированию читать долго. А сделать уже надо было. Теперь знаем как проще. Наверное кому то еще пригодится.
Пс. Дуины физически рядом находятся. Соединены просто тремя проводами. Тх рх земля.

MaksVV
Offline
Зарегистрирован: 06.08.2015

ЕвгенийП пишет:

MaksVV, а так сложно-то? Зачем эти три символа-то? Чего просто два байта не передать? Ну, или, даже через символы, но в лоб, типа

int n = 321;
Serial.print(n):

.....

int n = Serial.parseInt();

У меня чего-то так не заработало. Где я не так делаю? Скетч тормозится помоему на int var = Serial.parseInt(); и дальше ничего не делает. То что по сериалу байты прилетают это верно, проверил через Serial.read()

Передача 

int var =3276;

unsigned long prev=0;

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

void loop() {
  
unsigned long cur = millis ();
if (cur - prev>1000) {Serial.print (var); prev=cur;}


}

Приём


void setup() {
   Serial.begin (9600);

}

void loop() {
 
SerialREAD ();
}

void SerialREAD (){
if (!Serial.available()) return;

 int var = Serial.parseInt ();

 
 
}

 

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

А с чего Вы взяли, что он тормозится и что он по-Вашему должен делать? Он ничего не печатает и вообще ничего не делает у Вас.

MaksVV
Offline
Зарегистрирован: 06.08.2015

на самом деле я так пробовал

#include <SoftwareSerial.h>
SoftwareSerial Serial100(10,11);
unsigned long prev=0;

 int var;
void setup() {
   Serial.begin (9600);
Serial100.begin (9600);
}

void loop() {

unsigned long cur = millis ();
if (cur - prev>100) {Serial100.println (var); prev=cur;}
 
SerialREAD ();
}

void SerialREAD (){
if (!Serial.available()) return;

 var = Serial.parseInt ();

 
 
}

 

MaksVV
Offline
Зарегистрирован: 06.08.2015

короче я так понимаю что то с вот этим связано Serial.setTimeout() 

MaksVV
Offline
Зарегистрирован: 06.08.2015

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

MaksVV
Offline
Зарегистрирован: 06.08.2015

строчку 22 убираю, данные начинают идти в сериал100, иначе - не идут

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

MaksVV пишет:
на самом деле я так пробовал

А чего сразу не сказал? Зачем мозг-то пудрить?

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

MaksVV пишет:

короче я так понимаю что то с вот этим связано Serial.setTimeout() 

И да, и нет.

Вы прочитали как parseint работает? Или тупо вставили?

Он у Вас не работает потому, что Вы слишком часто передаёте числа без разделителя. 

Работает он так

1. Читаем, если НЕ цифра и НЕ знак - ура, мы закончили
2. Если же цифра, то запомнили её
3. Ждём следующего символа или таймаута
4. Если поступил следующий символ, то идём к п.1
5. Если наступил таймаут, то ура, мы закончили

Вот, как-то так. 

Вы же передаёт часто и потом в п.3 он всегда дожидается следующей цифры.

ЧТобы этого не было передавайте между числамии какой-нибудь разделитель (пробел, например). Тогда он будет радостно вылетать.

Например, сейчас у Вас

Serial.print(12); Serial.print(34);

Между 12 и 34 нет разделителя и не наступает таймаут, потому он считает это одним числом. А если Вы сделаете. Вы гоните цифру за цифрой, а он их накапливает как рдно число.

Serial.print(12); Serial.print(' ');Serial.print(34);Serial.print(' ');

Он их нормально съест как два числа, т.к. пробел будет воспринят как разделитель. Не обязательно пробел - любая "нецифра".

 

MaksVV
Offline
Зарегистрирован: 06.08.2015

ЕвгенийП пишет:

MaksVV пишет:

короче я так понимаю что то с вот этим связано Serial.setTimeout() 

И да, и нет.

Вы прочитали как parseint работает? Или тупо вставили?

Он у Вас не работает потому, что Вы слишком часто передаёте числа без разделителя. 

Работает он так

1. Читаем, если НЕ цифра и НЕ знак - ура, мы закончили
2. Если же цифра, то запомнили её
3. Ждём следующего символа или таймаута
4. Если поступил следующий символ, то идём к п.1
5. Если наступил таймаут, то ура, мы закончили

Вот, как-то так. 

Вы же передаёт часто и потом в п.3 он всегда дожидается следующей цифры.

ЧТобы этого не было передавайте между числамии какой-нибудь разделитель (пробел, например). Тогда он будет радостно вылетать.

Например, сейчас у Вас

Serial.print(12); Serial.print(34);

Между 12 и 34 нет разделителя и не наступает таймаут, потому он считает это одним числом. А если Вы сделаете. Вы гоните цифру за цифрой, а он их накапливает как рдно число.

Serial.print(12); Serial.print(' ');Serial.print(34);Serial.print(' ');

Он их нормально съест как два числа, т.к. пробел будет воспринят как разделитель. Не обязательно пробел - любая "нецифра".

 

я почитал там сям, но так как вы объясняетете, нигде не пишут. Спасибо за ликбез. 

andrikll
Offline
Зарегистрирован: 04.08.2013

Если можно подскажите как в потоке определять начало пакета для записи в массив? Я так понимаю после считывания из буфера данные более недоступны. Иными словами буквы к буквам цыфры к цыфрам...

 

sadman41
Offline
Зарегистрирован: 19.10.2016

andrikll пишет:

Если можно подскажите как в потоке определять начало пакета для записи в массив? Я так понимаю после считывания из буфера данные более недоступны. Иными словами буквы к буквам цыфры к цыфрам...

Как минимум - можете по получению байта копировать его к себе в предварительно созданный char buffer[предполагаемая_длина_пакета+запасец].

 

andriano
andriano аватар
Offline
Зарегистрирован: 20.06.2015

andrikll пишет:

Если можно подскажите как в потоке определять начало пакета для записи в массив? Я так понимаю после считывания из буфера данные более недоступны. Иными словами буквы к буквам цыфры к цыфрам...

В Ардуино нет такого понятия как пакет. Соответственно, как сами эти пакеты организуете, так и будет работать. Можно, например, подсмотреть как организованы пакеты в наиболее распространенных протоколах и что-то аналогичное сделать самому.

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

andrikll
Offline
Зарегистрирован: 04.08.2013

 Замечательный ответ... Спрошу тогда так, если я в операторе сравнения буду проверять что прочитал,  уже эти данные я никуда не запишу!? Как узнать что внутри (буква или цыфра). Можно наверно записать в char если на передатчике serial.print(); но потом как это собирать parseInt'ом неясно.

Подытожу: можно ли как то отсортировать буквы с циыфрами и цыфры собрать парсИнт'ом? 

sadman41
Offline
Зарегистрирован: 19.10.2016

Ничерта не понял. Вам нужна волшебная команда, которая сортирует, хранит и собирает? Такой нет. Есть отдельные действия - собрать, хранить и сортировать. Вы сами их должны выстроить в соответствии с тем, какой алгоритм у вас нарисовался в голове. И это выстраивание называется программированием. Его изучают долго и кропотливо.

b707
Offline
Зарегистрирован: 26.05.2017

andrikll пишет:

Замечательный ответ...

....

Подытожу: можно ли как то отсортировать буквы с циыфрами

никак. По сериалу отправляются байты, а цифры это или буквы - вы решаете сами, для компьютера это одно и то же.

И да, вы зря иронизируете по поводу предыдущего ответа.  adriano ответил вполне по делу, просто ваш низкий уровень знаий пока не дает вам это понять.

andrikll
Offline
Зарегистрирован: 04.08.2013

Ах да, я забыл, форум же он не для помощи....ушел рыдать

b707
Offline
Зарегистрирован: 26.05.2017

andrikll пишет:

Ах да, я забыл, форум же он не для помощи....ушел рыдать

вот мне даже интересно. Вы думаете, над вами глумяться? в каком месте. интересно? вот, например, в моем последнем сообщении - что именно вы считаете глумом?

 

Еще про буквы и цифры. Вот 'a' и 'c' - это буквы или цифры? Вроде ответ очевиден. Однако если это буквы. почему их можно вычитать и складывать? Вот такой код отлично компилируется и работает. Значение x после вычитания = 2

int x = 'c' - 'a';

 

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

DetSimen
DetSimen аватар
Offline
Зарегистрирован: 25.01.2017

andrikll пишет:

 если я в операторе сравнения буду проверять что прочитал,  уже эти данные я никуда не запишу!? 

Ви таки не поверите, можно сравнивать и сохранять одновременно.  Си - это страшный язык. 

char ch;

if ((ch=Serial.read())=='цыфра или буква') 

{

   то запхать считанный ch в свой буфер

 }

 

andrikll
Offline
Зарегистрирован: 04.08.2013

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

b707
Offline
Зарегистрирован: 26.05.2017

DetSimen пишет:

Ви таки не поверите, можно сравнивать и сохранять одновременно.  Си - это страшный язык. 

а проще сначала сохранить, потом сравнивать

andrikll
Offline
Зарегистрирован: 04.08.2013

to DetSimen

вот и ответ, спасибо!

b707
Offline
Зарегистрирован: 26.05.2017

andrikll пишет:

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

какой код вам нужен? что делает-то? читает из сериал? я ж напишу, а вы опять за глум примете

byte a = Serial.read();

b707
Offline
Зарегистрирован: 26.05.2017

b707 пишет:

andrikll пишет:

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

какой код вам нужен? что делает-то? читает из сериал? я ж напишу, а вы опять за глум примете

byte a = Serial.read();

if (a == 'цифра или буква')

b707
Offline
Зарегистрирован: 26.05.2017

DetSimen пишет:

if ((ch=Serial.read())=='цыфра или буква') 

вангую, следующий вопрос будет - почему не компилиуется оператор 'цыфра или буква'

andrikll
Offline
Зарегистрирован: 04.08.2013

парсИнт не прикрутить к этой конструкции, ну соберем руками раз так....

b707
Offline
Зарегистрирован: 26.05.2017

andrikll пишет:

парсИнт не прикрутить к этой конструкции, ну соберем руками раз так....

прочитайте сообщение №13 в этой ветке - там подробно разжевано, как парсеинг пользовать.

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

andrikll пишет:

Ах да, я забыл, форум же он не для помощи...

Совершенно верно. Рад, что до Вас это дошло!

Форум, он для общения по интересам. Хотите, чтобы кто-то был заинтересован с Вами общаться - будьте интересны собеседнику. Это, кстати, касается любого общения - не только форума и Интернета.

wdrakula
wdrakula аватар
Offline
Зарегистрирован: 15.03.2016

Бин! Я один из главных "глумителей"... но тут не тот случай. Человек просто вообще не знает.

----

Андриклл, смотри:

1. есть такая штука Serial.peek(), ровно ТОЖЕ САМОЕ, что и read, но символ остается в буфере, то есть следующий read его прочтет, понял?

Это самое проссто решение, после анализа буквы через peek потом вызовешь parseInt и все.

2. Другой способ прочитать всю строку до конца в массив char. и потом анализировать. Если выберешь 2, то потом поясню...

andrikll
Offline
Зарегистрирован: 04.08.2013

стёр

andrikll
Offline
Зарегистрирован: 04.08.2013

Как я долго писал... Спасибо...Я не против глума, но если в нем есть подсказки или ответ в любой форме.... а то был глум-флуд... это уж слишком :-)

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

Мне вот даже интересно Вам 2-х летние дети интересные собеседники? Но мы же с ними общаемся.. так что то не работает правило...(поправки наверно нужны).

to wdrakula

Да с peek теперь все понятно и удобно он же и в роли эвэйлбл, как я понял, спасибо, теперь все прояснилось.

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

andrikll пишет:
Вам 2-х летние дети интересные собеседники?
Очень интересные. Они обычно говорят то, что знают и не пытаются говорить то, чего не знают.

Прочитайте внимательно свою фразу, и скажите, только честно, Вы бы поняли что тут сказано?

"После приема эти данные идут как надо, если поставить 128 и более в массиве, то сначала идет то что в массиве а потом все сбивается.... причем это каждый раз разные цыфры и каждый раз после ресета идут данные массива и через время сбиваются, более 250 не пробовал совсем, застрял на этом"

Я может тупой, но я ни хрена не понял.

b707
Offline
Зарегистрирован: 26.05.2017

andrikll пишет:

Мне вот даже интересно Вам 2-х летние дети интересные собеседники? Но мы же с ними общаемся.. так что то не работает правило...

ваша ошибка, что вы почему-то решили, что тут ясли для двухлетних. Нет, по этой аналогии тут школа, класс этак пятый и выше :) Если двухлетнего привести на урок химии в 7-м классе - много он поймет? - Ничего. Но разве это означает. что учитель - никудышный? нет, просто ребенку еще надо очень много узнать, прежде чем идти в 7-й класс.

andrikll
Offline
Зарегистрирован: 04.08.2013

 ЕвгенийП Нет не понял бы, пока я писал, дракула ответил тем что мне нужно и я стер код... спасибо!

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

b707  ванга из вас так себе 

Небыло понятно, пробовал write, print почитал как формируется эта передача, и непонятно стало как это все разделять.

#include <SoftwareSerial.h>

SoftwareSerial RX_Serial(10, 11);

int data_int=-100;

void setup()  {      
  RX_Serial.begin(1200);
  Serial.begin(9600);
                 }

void Write_Serial () { 
    RX_Serial.print(data_int);  
    RX_Serial.print("."); 
  }
    
void loop() {   
data_int++;
Write_Serial(); 
delay(20);
}

Приемник

#include <SoftwareSerial.h>

SoftwareSerial RX_Serial(10, 11); // RX, TX

byte data;
int data_int, flag_print;

void setup() { 
RX_Serial.begin(1200);  
Serial.begin(9600);  }

   void Read_Serial() { if (RX_Serial.available()) { 
    flag_print=1;
    data_int=RX_Serial.parseInt();
    data=RX_Serial.peek();     
    RX_Serial.flush();
    if(data==46) flag_print=0;
     } 
   }
  
  void Print_Serial() {
    Serial.print(data_int); Serial.print(" ");
    Serial.println(); 
    }

void loop() { 
Read_Serial ();
if (flag_print==0) {Print_Serial(); flag_print=1; }
}

Вот так все заработало. можно и в массив запереть... всем спасибо....

wdrakula

Получилось так что можно и не анализировать, после записи Serial.peek(); можно сразу serial.parseInt();

А контроль всяких начал через считанное значение перем=serial.peek();

единственное наверно parseInt не очищает буфер если там не цифры, пришлось flush добавить

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

andrikll пишет:
Вот так все заработало
Да заработать-то заработало, но ... через Альпы ведь!

Вот смотрите, у Вас есть целое число во внутреннем машинном представлении. Для того, чтобы его переслать, Вы преобразуете его в текстовый вид. Затем Вы принимаете строка и парсите её, чтобы преобразовать обратно во внутреннее представление.

Почему не передавать число прямо во внутреннем представлении? Зачем преобразовывать его в строку, а потом обратно?

andrikll
Offline
Зарегистрирован: 04.08.2013

ну так яж из группы велосипеды и костыли... 

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

А если без шуток то надо восстановить код и закинуть сюда чтоб сказали что в нем не так.

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

Что значит "не зашло". Должно заходить, куда оно нахрен денется-то?

Ну, если хотите, я могу сделать Вам пример с двумя ардуинами в протеусе. Надо?

andrikll
Offline
Зарегистрирован: 04.08.2013

Нет, у меня пример с 2-мя спаянными.. так что сейчас только восстановлю как было и заброшу.

Не догадался сделать монитор порта для передатчика.. Какие то буквы периодически появляются в разобраных на byte из int данных.

код

#include <SoftwareSerial.h>

#define dat_vol 6  //количество передаваемых цыфр integer (объем массива данных)

SoftwareSerial RX_Serial(10, 11); // RX, TX
byte mass,data;
int data_tx_int[]={127,128,129,0,130,131}, tx_count_2;
int count_start, rx_flag, count_buf, tx_count;
byte data_tx[dat_vol*2];
long count_temp_read;


void setup()  {  
  Serial.begin(9600); 
  RX_Serial.begin(1200);
              }

  void Print_Serial() {
    for(int i; i<dat_vol*2; i++) {Serial.print(data_tx[i]); Serial.print(" ");}
    Serial.println();  
              }
              
  void Write_Serial () {
    if(tx_count==0) {mass=77; RX_Serial.write(mass); RX_Serial.write(mass);}    
    mass=byte(data_tx_int[tx_count]); data_tx[tx_count_2]=mass; 
    RX_Serial.write(mass); tx_count_2++; 
    mass=byte(data_tx_int[tx_count]>>8);  data_tx[tx_count_2]=mass;  
    RX_Serial.write(mass); tx_count_2++; tx_count++;       
    if(tx_count==(dat_vol)) {tx_count=0; Print_Serial();}
                     }

 void loop() {   
    Write_Serial();
           }
 хотел вставитиь из монитора порта данные, но (буквы не копируются)..... дорисую то что вижу, 12 строк нормальных цифр (нолики от разбирания на байты)  и потом
127 0 128 0 129 0 0 0 130 0 131 0   (12-я)
 
127 0 128 0 129 0 0 0 13       ,f        ,f    129 0 0 0 130 0 131 0 (таких 3 строки)
и потом опять нормальные данные 12 строк (на передатчике) наверно это какипе нибудь разделители по таймауту.
 
ЕвгенийП
ЕвгенийП аватар
Offline
Зарегистрирован: 25.05.2015

andrikll пишет:

Какие то буквы периодически появляются в разобраных на byte из int данных.

А в строке 19 не хотите i начальное значение присвоить?

andrikll
Offline
Зарегистрирован: 04.08.2013

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

В 19 строке хочу, но онож локальное....

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

 

andrikll
Offline
Зарегистрирован: 04.08.2013

Не знаю что и сказать, все работает....

#include <SoftwareSerial.h>

#define dat_vol 6  //количество передаваемых цыфр integer (объем массива данных)

SoftwareSerial RX_Serial(10, 11); // RX, TX
byte data;
int data_rx_int[dat_vol];
int count_start, rx_flag, count_buf, count_buf_2, tx_count;
byte data_rx[dat_vol*2];
long count_temp_read;

void setup()  {  
  Serial.begin(9600); 
  RX_Serial.begin(1200);
                 }

void Read_Serial() { if (RX_Serial.available()) {
    data=RX_Serial.read();
    if(data==77) count_start++; else count_start=0;
    if(rx_flag==1) { data_rx[count_buf]=data; count_buf++;}
    if(count_start==2 && rx_flag==0) rx_flag=1; 
    if(count_buf==(dat_vol*2)) { count_buf=0; rx_flag=0; count_start=0;
    convert (); Print_Serial();}     
   }
  }
  
  void convert () {    for(int i;i<dat_vol;i++) 
     {data_rx_int[i]=data_rx[i*2]; data_rx_int[i]+=data_rx[(i*2)+1]<<8;}
    }

  void Print_Serial() {
    for(int i; i<dat_vol; i++) {Serial.print(data_rx_int[i]); Serial.print(" ");}
    Serial.println();  
                 }
 
  void loop() {   
    Read_Serial (); 
              }

У меня в исходнике было отправлять первые 5 значений (начало пакета) через for, может там небыло сброшено i и из за него сбивалось.

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

Строка 32! Вы издеваетесь? Вы же сами сказали, что там может быть всё, что угодно! Так и работает она у Вас "пока везёт". Добавите какую-нибудь строку и всё рухнет. Так трудно написать там int i = 0; ????

andrikll
Offline
Зарегистрирован: 04.08.2013

Исправил... все исправил... так что за f, в тексте (в ком порту, передатчика)? оно не мешает, но неясно что это...

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

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

andrikll
Offline
Зарегистрирован: 04.08.2013

ТХ

#include <SoftwareSerial.h>

#define dat_vol 6  //количество передаваемых цыфр integer (объем массива данных)

SoftwareSerial RX_Serial(10, 11); // RX, TX
byte mass,data;
int data_tx_int[]={1508,128,129,0,130,131}, tx_count_2;
int count_start, rx_flag, count_buf, tx_count;
byte data_tx[dat_vol*2];
long count_temp_read;


void setup()  {  
  Serial.begin(9600); 
  RX_Serial.begin(1200);
              }

  void Print_Serial() {
    for(int i=0; i<dat_vol*2; i++) {Serial.print(data_tx[i]); Serial.print(" ");}
    Serial.println();  
              }
              
  void Write_Serial () {
    if(tx_count==0) {mass=77; RX_Serial.write(mass); RX_Serial.write(mass);}    
    mass=byte(data_tx_int[tx_count]); data_tx[tx_count_2]=mass; 
    RX_Serial.write(mass); tx_count_2++; 
    mass=byte(data_tx_int[tx_count]>>8);  data_tx[tx_count_2]=mass;  
    RX_Serial.write(mass); tx_count_2++; tx_count++;       
    if(tx_count==(dat_vol)) {tx_count=0; Print_Serial();}
                     }

 void loop() {   
    Write_Serial();
           }

RX

#include <SoftwareSerial.h>

#define dat_vol 6  //количество передаваемых цыфр integer (объем массива данных)

SoftwareSerial RX_Serial(10, 11); // RX, TX
byte data;
int data_rx_int[dat_vol];
int count_start, rx_flag, count_buf, count_buf_2, tx_count;
byte data_rx[dat_vol*2];
long count_temp_read;

void setup()  {  
  Serial.begin(9600); 
  RX_Serial.begin(1200);
                 }

void Read_Serial() { if (RX_Serial.available()) {
    data=RX_Serial.read();
    if(data==77) count_start++; else count_start=0;
    if(rx_flag==1) { data_rx[count_buf]=data; count_buf++;}
    if(count_start==2 && rx_flag==0) rx_flag=1; 
    if(count_buf==(dat_vol*2)) { count_buf=0; rx_flag=0; count_start=0;
    convert (); Print_Serial();}     
   }
  }
  
  void convert () {    for(int i;i<dat_vol;i++) 
     {data_rx_int[i]=data_rx[i*2]; data_rx_int[i]+=data_rx[(i*2)+1]<<8;}
    }

  void Print_Serial() {
    for(int i=0; i<dat_vol; i++) {Serial.print(data_rx_int[i]); Serial.print(" ");}
    Serial.println();  
                 }
 
  void loop() {   
    Read_Serial (); 
              }

Первую величину массива изменил чтобы проверить предел по byte

andrikll
Offline
Зарегистрирован: 04.08.2013

Думаю что f,  это переполнение буфера, не успевает в монитор все данные слить которые получает. (задержек нет никаких на передачу)