Какой протокол использовать?

Patriot
Offline
Зарегистрирован: 25.06.2015

Делаю выключатели света дома, планировал использовать ModBus по RS485. Сделал мастер и слейв тестовые, и ужаснулся скоростью работы. После нажатия кнопки на слейве, мастер одупляет спустя 1 секунду. До этого пользовался кастомным протоколом на базе RS485 тоже мастер-слейв, и там всё летало моментально. Тут конечно печаль. Возможно, библиотеки кривые, но те что самые популярные для arduino/esp8266.

Отсюда вопрос: посоветуйте, на что можно заменить это безобразие? Либо, может можно улучшить работу ModBus? Или у всех такая беда?

 

rkit
Offline
Зарегистрирован: 23.11.2016

Только у плохих инженеров

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

Patriot пишет:

. Сделал мастер и слейв тестовые, и ужаснулся скоростью работы. После нажатия кнопки на слейве, мастер одупляет спустя 1 секунду
Или у всех такая беда?


Вы бы показали свои "тестовые мастер и слейв", думаю причина тормозов в коде

Patriot
Offline
Зарегистрирован: 25.06.2015

Слейв, на atmega328p 8MHz. Скорость modbus на тормоза не влияет. И 4800 и 115200 - одинаково.

#include <Arduino.h>
#include <ModbusRTU.h>
// Library: mathertel/OneButton
#include "OneButton.h"

#define SLAVE_ID 2
#define MODBUS_ENABLED 3
#define MODBUS_SPEED 115200

#define NONE 0
#define CLICK 1
#define DOUBLE_CLICK 2
#define LONG_CLICK 3
#define STOP_LONG_CLICK 4

#define REGN 0
#define BTN 5

ModbusRTU mb;

OneButton button(BTN, true);

void setup() {
    button.attachClick([]() { mb.Hreg(REGN, CLICK); });
    button.attachDoubleClick([]() { mb.Hreg(REGN, DOUBLE_CLICK); });
    button.attachLongPressStart([]() { mb.Hreg(REGN, LONG_CLICK); });
    button.attachLongPressStop([]() { mb.Hreg(REGN, STOP_LONG_CLICK); });

    Serial.begin(MODBUS_SPEED, SERIAL_8N1);
    mb.begin(&Serial, MODBUS_ENABLED);
    mb.setBaudrate(MODBUS_SPEED);
    mb.slave(SLAVE_ID);

    mb.addHreg(REGN);
    mb.Hreg(REGN, NONE);
}

void loop() {
    button.tick();

    mb.task();

    yield();
}

И мастер, esp8266:

#include <Arduino.h>
// Library: emelianov/modbus-esp8266
#include <ModbusRTU.h>

#define MODBUS_ENABLED 4
#define MODBUS_SPEED 115200
#define SLAVE_ID 2

#define FIRST_REG 0
#define REG_COUNT 1

ModbusRTU mb;

bool cbStatus(Modbus::ResultCode event, uint16_t transactionId, void* data) { // Callback to monitor errors
    if (event != Modbus::EX_SUCCESS) {
        Serial.printf_P("Send result: 0x%02X, Mem: %d\n", event, ESP.getFreeHeap());
    }

    return true;
}

void setup() {
    pinMode(LED_BUILTIN, OUTPUT);
    
    Serial.begin(MODBUS_SPEED, SERIAL_8N1);
    mb.begin(&Serial, MODBUS_ENABLED);
    mb.setBaudrate(MODBUS_SPEED);
    mb.master();
}

void loop() {

    uint16_t res[REG_COUNT] = {0};

    if (!mb.slave()) {    // Check if no transaction in progress
        mb.readHreg(SLAVE_ID, FIRST_REG, res, REG_COUNT, cbStatus); // Send Read Hreg from Modbus Server

        if (res[0] == 1) {
            digitalWrite(LED_BUILTIN, LOW);
            mb.writeHreg(SLAVE_ID, FIRST_REG, 0x0, cbStatus);
        } else {
            digitalWrite(LED_BUILTIN, HIGH);
        }

        while(mb.slave()) { // Check if transaction is active
            mb.task();
            delay(10);
        }
    }

    yield();
}

 

Patriot
Offline
Зарегистрирован: 25.06.2015

В общем в библиотеке OneButton есть waitTime для определения кол-ва нажатий на кнопку. Вот оно и дает этот лаг.

 

BOOM
BOOM аватар
Offline
Зарегистрирован: 14.11.2018

Попробуй эту (я доволен её работой): https://github.com/kakmyc-github/kakmyc_btn

Kakmyc
Offline
Зарегистрирован: 15.01.2018

BOOM пишет:

Попробуй эту (я доволен её работой): https://github.com/kakmyc-github/kakmyc_btn

Там тоже есть тайм-аут для определения количества нажатий.
По умолчанию 300мс.
Но никто не запрещает его уменьшить.

v258
v258 аватар
Offline
Зарегистрирован: 25.05.2020

Попробуй эту - https://github.com/VAleSh-Soft/shButton
Там нет таймаутов ))

Kakmyc
Offline
Зарегистрирован: 15.01.2018

v258 пишет:
Попробуй эту - https://github.com/VAleSh-Soft/shButton
Там нет таймаутов ))

Ну это если мультиклики не нужны.

v258
v258 аватар
Offline
Зарегистрирован: 25.05.2020

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

kalapanga
Offline
Зарегистрирован: 23.10.2016

Так в OneButton этот период до определения клика настраивается вроде. Уменьшить его...

v258
v258 аватар
Offline
Зарегистрирован: 25.05.2020

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

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

очевидно, что дело не в библиотеке. Ошибка в концепции. Если нужна быстрая реакция на кнопки - никаких дабл-кликов и лонг-прессов там быть не должно

SergeiL
SergeiL аватар
Offline
Зарегистрирован: 05.11.2018

С выключателями освещения, комнатного, мультиклик как-то неудобно, ИМХО.

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

Я в свое время проходил все это. Были покупные выключатели, исполнительные на 433МГц, выключатели батарейные . Порой нужно было нажать их несколько раз для включения/выключения света, помехи, просаженные батареи... Отказался в пользу своих модулей на ESP8266 и обычных выключателей. И меньше по габаритам (для двух каналов) и удобнее получилось. Только освещение 9 помещений, плюс еще розетки.

Уже много лет работают, непосвященный не поймет, что это НЕ обычный выключатель и люстра. Когда все уходят, пропадают IP телефонов после закрытия входной двери из домашней LAN, весь свет и часть эл. приборов отключатся. 

С учетом того, что ванная и туалет - галогенки (5 лампочек по 50Вт - это ванная, 4*35Вт - это туалет. Светодиоды пробовал, не понравились по освещению. Это единственные лампы накаливания в квартире наверное :-) ), не помню когда их менял.  Если дверь закрыли и не было движения внутри - через две минуты свет отключается. Не закрыли дверь, и не было движения 10 минут - тоже выключается. Включение/выключение - плавное ( свой  диммер на Тини25 подключенный к ESP8266 по I2C). 

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

SergeiL пишет:

 ванная и туалет - Если дверь закрыли и не было движения внутри - через две минуты свет отключается.

уже и на унитазе спокойно не посидишь, надо постоянно руками махать, чтобы свет не гас :)

SergeiL
SergeiL аватар
Offline
Зарегистрирован: 05.11.2018

b707 пишет:

уже и на унитазе спокойно не посидишь, надо постоянно руками махать, чтобы свет не гас :)

Никто не жаловался.

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

А вот если закрыли дверь, и не было движения внутри - никого внутри нет :-)  

Для меня главный признак успешности решения, отсутствие замечаний (в смысле заметили) от домашних.

Если на вопрос поменял алгоритм - что заметили - ответ:  "Все нормально, нет неудобств, А что что-то поменялось?? - это хорошо.  :-) 

Не написал в предыдущем посте, у меня все работает локально, вне зависимости от наличия связи по Wi-Fi.

Есть связь, нет связи - решение принимается локально, а по mqtt сбрасывается только состояние, и принимаются команды.

Это только домашняя LAN:

 

Patriot
Offline
Зарегистрирован: 25.06.2015

b707 пишет:

очевидно, что дело не в библиотеке. Ошибка в концепции. Если нужна быстрая реакция на кнопки - никаких дабл-кликов и лонг-прессов там быть не должно

Согласен. Но это как раз выясняется эмпирическим путем. В итоге я просто отключил мультиклики:

button.setClickTicks(0);

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

 

 

Kakmyc
Offline
Зарегистрирован: 15.01.2018

У меня стоят выключатели и реле sonoff, задержка плавает, но вообще не напрягает. Особенно когда голосом включаешь/выключаешь

SergeiL
SergeiL аватар
Offline
Зарегистрирован: 05.11.2018

Kakmyc пишет:
У меня стоят выключатели и реле sonoff, задержка плавает, но вообще не напрягает. Особенно когда голосом включаешь/выключаешь

С голосом понятно, пока туда .. пока сюда.

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

Kakmyc
Offline
Зарегистрирован: 15.01.2018

Так там подсветка включается и щелчок реле слышно.
Т.е. условно я включаю диод на выключателе.
Включил диод==включил свет, и пофигу, что это произойдет через 1-2 секунды.

SergeiL
SergeiL аватар
Offline
Зарегистрирован: 05.11.2018

А я сделал так  :-)