Протокол обмена данными и удаленный вызов функций (RPC)
- Войдите на сайт для отправки комментариев
Здравствуйте!
Приспичило мне подружить дуину и процессинг, чтобы слали друг-другу данные.
Дуина должна посылать на комп все события происходящие, т.е. данные сенсоров, изменения положения реле и т.п. в формате: время+ событие.
Комп эти данные должен получать и обрабатывать - строить графики, вести статистику.
И в свою очередь может изменять настройки и запускать занания на дуине (максимальная температура, минимальная температура, включить свет\выключить свет и т.п.)
Чтобы данные не терялись на Srial порте, как это часто бывает - нужна пакетная передача, т.е. добавлять маркеры в начало и конец. + проверять целостность пакета. А в идеале еще и шифровать его.
т.е. получаем структуру: START+DATA+CHECKSUM+END
думаю что он маркера конца можно отказаться, для краткости.
По этой теме нашел вот такую классную статью:
http://robocraft.ru/blog/1090.html
Сделал все как там, но код каботает не так как хотелось бы и столкнулся со сложностью парсинга строки: т.е. необходимо расписывать полотно Switch\Case ... чего очень делать нехочется... Да и еще пришел к выводу, что нужно присылать подтверждения об успешной передаче пакета или ошибке, чтобы выслать повторно..
Так пришел к библиотеке Firmata
Но напрямую управлять пинами ардуины мне не нужно - она должна быть по максимуму автономной...
Так наткнулся на библиотеку TinyRPC http://roboforum.ru/forum2/topic8627.html
Суть в том, что можно получить доступ над любой функцией в коде ардуино..
Но вот засада: эта библиотека не устанавливается! т.е. для установки, там требуется заменить файлы в папке lib (чтобы добавить кнопку в интерфейс Arduino IDE) -но после этого Arduino IDE - отказывается запускаться... Я так понимаю что это из-за того, что библиотека сделана для ARduino IDE alpha..
В любом случае - вопрос такой: как можно сделать тоже самое в ручную??
Или может быть есть рабочая библиотека для этих целей?
на всякий случай привожу код примера из tinyRPC:
Сам скетч:
// Include TinyRpc library
#include <tinyrpc.h>
#define LED 13
int num, c;
char str[100];
void TurnLed(int state);
void setup() {
pinMode(LED, OUTPUT);
Serial.begin(57600);
}
void loop()
{
// Read string from uart
num = 0;
while(Serial.available() == 0) delay(100);
while((c = Serial.read()) != '\n')
{
if(c != -1)
{
str[num] = c;
num++;
}
}
// Run TinyRpc library routines
json_node* root = json_parse(str);
char* rep = json_execute(root);
// Send back response
Serial.println(rep);
free(rep);
json_free(root);
}
void TurnLed(int state)
{
if (state)
digitalWrite(LED, HIGH);
else
digitalWrite(LED, LOW);
}
Код класса на С#, который должен создаваться при клике на кнопке:
using System;
using System.Collections.Generic;
using System.Linq;
using System.IO.Ports;
using System.Text;
namespace TinyRpc
{
public class RemoteObject
{
private SerialPort sport;
public RemoteObject(string port, int BaudRate)
{
sport = new SerialPort(port);
sport.BaudRate = BaudRate;
sport.Open();
}
public void TurnLed(int state)
{
string command = "{\"method\": 0, \"params\": {" +"\"state\":" + state.ToString();
command += "}}";
sport.Write(command + "\n");
}
}
}
В результате на стороне компа можно вызывать функции таким же образом как в Фирмате, например:
int t=Arduino.GetTemp(1);
Вопрос - как починить либу.. или как это сделать руками или какая рабочая либа может делать тоже самое?
У меня тоже была такая проблема. В смысле - проблема протокола для обмена данными. Сидел, сочинял, что-то получалось, что-то новое всплывало. И когда мне надоело топтаться на месте, я, заметив что "события" в системе происходят не так уж часто, просто заставил комп постоянно переспрашивать дуню "что нового?" на скорости 9600. Ну она ему и отвечает что произошло за последние милисекунды.
Над размером пакета в этом случае можно не заморачиваться, т.к. придёт ровно столько сколько заложено на тот или иной ответ.