diff --git a/content/posts/2023/basic/gambas-serial.md b/content/posts/2023/basic/gambas-serial.md new file mode 100644 index 0000000..8961bce --- /dev/null +++ b/content/posts/2023/basic/gambas-serial.md @@ -0,0 +1,166 @@ +--- +title: "📟 Работа с Serial в Gambas" +date: 2023-03-18T16:31:00+03:00 +draft: false +tags: [serial, basic, arduino, tutorial] +--- + +## Задача + +Получать и отправлять данные по **Serial** в Gambas. + +## Что будет использоваться + +1. UART устройство, в моём случае **Arduino Nano**. +2. Библиотека `AsyncStream.h` от **AlexGyver** для асинхронного чтения из Serial. +3. Arduino IDE для загрузки скетча в МК. +4. Среда Gambas, очевидно же. + +## Код для Arduino + +Показываю пример работы библиотеки `AsyncStream.h` со страницы на GitHub. + +```c +#include "AsyncStream.h" +AsyncStream<100> serial(&Serial, '\n'); + +void setup() { + Serial.begin(9600); +} + +void loop() { + if (serial.available()) { + Serial.println(serial.buf); + } +} +``` + +Код получает данные по `Serial` и сразу печатает его в обратно. + +В своём случает я хочу, чтобы Arduino отправляла **PONG**, +если ей передать **PING**. +А также каждые 5 секунд отправляла сообщение в Serial. + +```c +#include "AsyncStream.h" + +// Объявление AsyncStream +// 50 -- значение задержки чтения +AsyncStream<50> serial(&Serial, '\n'); + +// таймер для хранения значения millis() +unsigned long timer = 0; + +void setup() { + Serial.begin(9600); +} + +void loop() { + if (serial.available()) { + if (strcmp(serial.buf, "ping") == 0) { + Serial.println("PONG"); + } + } + + if (millis() - timer > 5000) { + Serial.println("Every 5 sec message"); + timer = millis(); + } +} +``` + +## Код для Gambas + +Подключение к Serial + +```basic +' Переменная порта +Public SerialDevice As New SerialPort + +' Метод подключения к порту +Public Sub SerialDeviceConnect() As Boolean + Dim Port As String = "/dev/ttyUSB0" + + ' если есть подключение к порту, завершаем функцию + If SerialDevice.Status Then Return False + + Print "Connecting to " & Port + + SerialDevice.PortName = Port + SerialDevice.Speed = "9600" + SerialDevice.Parity = 0 + SerialDevice.DataBits = "8" + SerialDevice.StopBits = "1" + SerialDevice.FlowControl = 0 + + Try SerialDevice.Open() + If Error Then Print "ERROR: Bad address" + +End + +' Метод, который вызывает подключение к Serial +Public Sub DeviceConnectButton_Click() + + SerialDeviceConnect() + +End +``` + +Таймер, который вызывает чтение из Serial и печает полученные данные + +```basic +' Таймер +Public Sub LogTimer_Timer() + + If SerialDevice.Status Then + Dim SerialText As String = SerialRead() + + If SerialText.Len > 0 Then Print SerialText + Endif + +End +``` + +Метод, который получает данные из Serial и печатает их + +```basic +' Метод получения команд из Serial +Public Sub SerialRead() As String + + Dim RxLen As Integer ' Длина полученных данных + Dim Rx As String ' Полученная строка + + Try Read #SerialDevice, Rx, Lof(SerialDevice) + If Error Then + Return + Else + RxLen = InStr(Rx, Chr(13)) + + If RxLen > 0 Then + Return Replace$(Rx, "\n", "") + Endif + Endif + +End +``` + +Метод, который отправляет команду в Serial + +```basic +' Отправка команд в Serial +Public Sub SerialWrite(Text As String) + + Try Write #SerialDevice, Text + If Error Then Print "Ошибка" + +End +``` + +```basic +' Метод, который вызывает подключение к Serial +Public Sub DeviceSendButton_Click() + + SerialWrite("ping") + +End +```