#1 Re: Програмування Arduino » Правильно инициализировать экземпляр класса SoftSerial в своем классе. » 2021-04-23 23:31:08

Kaka пише:

Да, почему, если Вам подходит, то и флаг в руки.

Но. Иногда, ни с того ни с сего, без видимых причин, вдруг будут теряться байты. Нечасто, но будут. Если задача позволяет на это забить, то и слава Богу.

Благодарю за ответ. Действительно потери будут, тем более что библиотека SoftSerial используется. И при переключении считывателей методом listen об этом прямо сказано.
Но, как верно замечено, указанная задача это позволяет.
Мной пока не придумано, как можно реализовать по другому.

#2 Re: Програмування Arduino » Правильно инициализировать экземпляр класса SoftSerial в своем классе. » 2021-04-23 21:55:36

Kaka пише:

Но, работать всё равно будет криво.

Проверяли с периодом опроса в 25 миллисекунд все 4 считывателя. Для задачи СКУД (турникет) подходит. Для более критичных по времени задач - нужно думать.
Подскажите, может что мы не заметили?

#3 Re: Програмування Arduino » Правильно инициализировать экземпляр класса SoftSerial в своем классе. » 2021-04-23 14:47:21

Сам отвечу:
Не знаю или я таки правильно провожу инициализацию экземпляра SoftSerial с позиции синтаксиса, но  конструкция приведенная выше все же отрабатывает правильно.

Потому вопрос оказался не в инициализации.
Все дело в том, что библиотека SoftSerial работает на прием только на одновременно один входной пин в одно и то же время... (Ну да, дочитать нормально описание библиотеки, перед написанием на форум, у меня мозгов не хватило.. big_smile )
Соответственно в библиотеке SoftSerial реализован метод listen().
Решение простое - переключать считыватели по очереди.

Пока в тестовом варианте реализовано коряво так:

void loop() {
  if (millis() - ChangeListenTimer >= 500) {   // таймер на 500 мс (2 раза в сек)
    ChangeListenTimer = millis();
    if (rfidExit.rfidGetListen() == true) {
      rfidVhod.rfidSetListen(true);
      rfidExit.rfidSetListen(false);
    } else {
      rfidVhod.rfidSetListen(false);
      rfidExit.rfidSetListen(true);
    }
  }

  if (rfidExit.rfidGetListen()) {
    rfidExit.readRfid();
  }

  if (rfidVhod.rfidGetListen()) {
    rfidVhod.readRfid();
  }
}

Соответственно в код описания класса добавлено:

  public:
       bool rfidGetListen();
    void rfidSetListen(bool state = false);

  private:
        bool _flagListen;

А в код реализации класса:

void RDM6300::rfidSetListen(bool state) {
  _flagListen = state;
  if (_flagListen == true) {
    _RFID.listen();
  }
}

bool RDM6300::rfidGetListen() {
  return _flagListen;
}

Не знаю, может кому и понадобится, потому оставлю это сдесь.

#4 Програмування Arduino » Правильно инициализировать экземпляр класса SoftSerial в своем классе. » 2021-04-23 13:06:47

Black Wolf
відповідей: 5

Доброго времени суток!
Есть у меня необходимость сделать обработку нескольких считывателей RDM6300 125Kгц. Для этого решено написать свой класс.
По одиночке все работает) Как только, инициализируется 2 датчика - работает только инициализированый последним.
Примечание - ранее писал на языке не поддерживающем ООП. Прошу не пинать ногами.

Сам класс:

#include <SoftwareSerial.h>
class RDM6300 {
  public:
    RDM6300(byte pinSignal, byte pinDenyLed, byte pinAllowLed);
    void static initBuzzer(byte pinBuzzer);
    static void buzzer(byte Povtor, int Millisec = 400, int Tone = 1000);
    void setLed(bool DenyLed = 1, bool AllowLed = 1);
    void initRfid();
    void testLed();
    void readRfid();

  private:
    byte _pinSignal;
    byte _pinDenyLed;
    byte _pinAllowLed;
    static byte _pinBuzzer;
    SoftwareSerial _RFID = SoftwareSerial(0, 0); // Вот эта недоконструкция мной была использована 
                                                                //для хоть какой-то инициализации.
    static int _rx_counter;
    static byte _rx_data[14]; // 1+10+2+11
    void pauseRead();
    byte _ascii_char_to_num(byte a);
    void printResultReadRfid();
    bool _flagPause;

};

Код инициализации:

RDM6300::RDM6300(byte pinSignal, byte pinDenyLed, byte pinAllowLed) {
  _pinSignal = pinSignal;
  _pinDenyLed = pinDenyLed;
  _pinAllowLed = pinAllowLed;
}

void RDM6300::initRfid() {
  pinMode(_pinDenyLed, OUTPUT);
  pinMode(_pinAllowLed, OUTPUT);
  _RFID = SoftwareSerial(_pinSignal, 0);   //Вот в этом месте срабатывает переназначение на нужный пин SoftSerial.
                                                       // но только в датчике, инициированом последним в setup().
  _RFID.begin(9600);
  testLed();
  buzzer(1);
}

Инициализация:

#define BuzzerPin A3
byte RDM6300::_pinBuzzer;
int RDM6300::_rx_counter;
byte RDM6300::_rx_data[14]; // 1+10+2+11

RDM6300 rfidVhod(7, A4, A5);
RDM6300 rfidExit(6, A1, A2);



void setup() {
  Serial.begin(9600);
  RDM6300::initBuzzer(BuzzerPin);
  
  rfidExit.initRfid();
  rfidVhod.initRfid(); //Вот этот будет работать..

  initNetwork();
  printDHCP_test();

}

Насколько я понимаю, я не создаю в каждом екземпляре класса новый обьект SoftSerial.
Подскажите как его правильно создать в своем классе (Замена вот этого: 

SoftwareSerial _RFID = SoftwareSerial(0, 0);

)?
Или я чего-то совсем не понимаю?

Підвал форуму