mirror of
https://github.com/Show-maket/IR-protocol.git
synced 2025-05-04 07:10:16 +00:00
signal generator
This commit is contained in:
parent
8d5b2f6e3c
commit
b272b6031c
@ -8,7 +8,7 @@
|
|||||||
|
|
||||||
IR_Decoder::IR_Decoder(const uint8_t isrPin, uint16_t addr, IR_Encoder* encPair = nullptr) : isrPin(isrPin), addrSelf(addr), encoder(encPair) {
|
IR_Decoder::IR_Decoder(const uint8_t isrPin, uint16_t addr, IR_Encoder* encPair = nullptr) : isrPin(isrPin), addrSelf(addr), encoder(encPair) {
|
||||||
// rawBuffer = new uint8_t[bufferRawSize] { 0 };
|
// rawBuffer = new uint8_t[bufferRawSize] { 0 };
|
||||||
dataBuffer = new uint8_t[bufferDataSize] { 0 };
|
dataBuffer = new uint8_t[dataByteSizeMax] { 0 };
|
||||||
prevRise = prevFall = prevPrevFall = prevPrevRise = 0;
|
prevRise = prevFall = prevPrevFall = prevPrevRise = 0;
|
||||||
start_RX();
|
start_RX();
|
||||||
}
|
}
|
||||||
@ -255,7 +255,7 @@ void IR_Decoder::start_RX() {
|
|||||||
|
|
||||||
resetAvaliable();
|
resetAvaliable();
|
||||||
isBufferOverflow = false;
|
isBufferOverflow = false;
|
||||||
memset(dataBuffer, 0x00, bufferDataSize);
|
memset(dataBuffer, 0x00, dataByteSizeMax);
|
||||||
|
|
||||||
bufBitPos = 0;
|
bufBitPos = 0;
|
||||||
isData = true;
|
isData = true;
|
||||||
@ -266,7 +266,7 @@ void IR_Decoder::start_RX() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void IR_Decoder::writeToBuffer(bool bit) {
|
void IR_Decoder::writeToBuffer(bool bit) {
|
||||||
if (i_dataBuffer >= bufferDataSize * 8 - 1) {// проверка переполнения
|
if (i_dataBuffer >= dataByteSizeMax * 8 - 1) {// проверка переполнения
|
||||||
//TODO: Буффер переполнен!
|
//TODO: Буффер переполнен!
|
||||||
isBufferOverflow = true;
|
isBufferOverflow = true;
|
||||||
}
|
}
|
||||||
|
@ -197,7 +197,6 @@ private:
|
|||||||
volatile bool isPreamb = false; // флаг начальной последовости
|
volatile bool isPreamb = false; // флаг начальной последовости
|
||||||
bool HIGH_FIRST = true; //TODO: порядок приходящих битов
|
bool HIGH_FIRST = true; //TODO: порядок приходящих битов
|
||||||
|
|
||||||
const uint8_t bufferDataSize = dataByteSizeMax; // + crc
|
|
||||||
////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////
|
||||||
void noFunc();
|
void noFunc();
|
||||||
volatile uint8_t currentSubBufferIndex; // Счетчик текущей позиции во вспомогательном буфере фронтов/спадов
|
volatile uint8_t currentSubBufferIndex; // Счетчик текущей позиции во вспомогательном буфере фронтов/спадов
|
||||||
|
@ -1,7 +1,12 @@
|
|||||||
#include "IR_Encoder.h"
|
#include "IR_Encoder.h"
|
||||||
#include "IR_Decoder.h"
|
#include "IR_Decoder.h"
|
||||||
|
|
||||||
|
#define LoopOut 12
|
||||||
|
#define ISR_Out 10
|
||||||
|
#define TestOut 13
|
||||||
|
|
||||||
IR_Encoder::IR_Encoder(uint16_t addr, uint8_t pin, uint8_t tune = 0, IR_Decoder* decPair) {
|
IR_Encoder::IR_Encoder(uint16_t addr, uint8_t pin, uint8_t tune = 0, IR_Decoder* decPair) {
|
||||||
|
sendBuffer = new uint8_t[dataByteSizeMax] { 0 };
|
||||||
ir_out = pin;
|
ir_out = pin;
|
||||||
pinMode(ir_out, OUTPUT);
|
pinMode(ir_out, OUTPUT);
|
||||||
addrSelf = addr;
|
addrSelf = addr;
|
||||||
@ -16,6 +21,7 @@ IR_Encoder::IR_Encoder(uint16_t addr, uint8_t pin, uint8_t tune = 0, IR_Decoder*
|
|||||||
IR_Encoder::~IR_Encoder() {
|
IR_Encoder::~IR_Encoder() {
|
||||||
delete [] bitHigh;
|
delete [] bitHigh;
|
||||||
delete [] bitLow;
|
delete [] bitLow;
|
||||||
|
delete [] sendBuffer;
|
||||||
};
|
};
|
||||||
|
|
||||||
void IR_Encoder::sendACK(uint16_t addrTo, uint8_t addInfo, bool forAll = false) {
|
void IR_Encoder::sendACK(uint16_t addrTo, uint8_t addInfo, bool forAll = false) {
|
||||||
@ -109,74 +115,105 @@ void IR_Encoder::_sendData(uint16_t addrTo, uint8_t* data, uint8_t len, uint8_t
|
|||||||
}
|
}
|
||||||
|
|
||||||
void IR_Encoder::rawSend(uint8_t* ptr, uint8_t len) {
|
void IR_Encoder::rawSend(uint8_t* ptr, uint8_t len) {
|
||||||
cli();
|
|
||||||
digitalToggle(9); digitalToggle(9);
|
digitalToggle(9); digitalToggle(9);
|
||||||
|
memset(sendBuffer, 0x00, dataByteSizeMax);
|
||||||
|
memcpy(sendBuffer, ptr, len);
|
||||||
|
sendLen = len;
|
||||||
|
// *sendBuffer = 0b10010011;
|
||||||
isSending = true;
|
isSending = true;
|
||||||
|
|
||||||
|
cli();
|
||||||
if (decoder != nullptr) { decoder->isPairSending = isSending; }
|
if (decoder != nullptr) { decoder->isPairSending = isSending; }
|
||||||
// #define preambToggle 2*2-1 //<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
|
// #define preambToggle 2*2-1 //<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
|
||||||
#define preambToggle ((bitPauseTakts * 2 + bitActiveTakts) * 2 - 1) //<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
|
#define preambToggle ((bitPauseTakts * 2 + bitActiveTakts) * 2 - 1) //<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
|
||||||
|
|
||||||
toggleCounter = preambToggle; // Первая генерация для первого signal
|
toggleCounter = preambToggle; // Первая генерация для первого signal
|
||||||
|
|
||||||
preambBitCounter;
|
dataBitCounter = bitPerByte - 1;
|
||||||
dataBitCounter = 3/* len * 8 */;
|
dataByteCounter = 0;
|
||||||
syncBitCounter = syncBits;
|
|
||||||
|
|
||||||
preambFrontCounter = preambPulse * 2 - 1; // -1 за счёт генерации уже на этапе сразу после инициализации
|
preambFrontCounter = preambPulse * 2 - 1; // -1 за счёт генерации уже на этапе сразу после инициализации
|
||||||
dataFrontCounter = bitPerByte * 2;
|
dataSequenceCounter = bitPerByte * 2;
|
||||||
syncFrontCounter;
|
syncSequenceCounter = syncBits * 2;
|
||||||
|
|
||||||
signal = preamb;
|
signal = preamb;
|
||||||
isSending = true;
|
isSending = true;
|
||||||
state = HIGH;
|
state = HIGH;
|
||||||
|
|
||||||
currentBit = bitHigh;
|
currentBitSequence = bitHigh;
|
||||||
sei();
|
sei();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void IR_Encoder::isr() {
|
void IR_Encoder::isr() {
|
||||||
if (!isSending) return;
|
if (!isSending) return;
|
||||||
|
|
||||||
ir_out_virtual = !ir_out_virtual && state;
|
ir_out_virtual = !ir_out_virtual && state;
|
||||||
|
|
||||||
if (toggleCounter == 0) {
|
if (toggleCounter) {
|
||||||
|
toggleCounter--;
|
||||||
|
} else {
|
||||||
IsrStart:
|
IsrStart:
|
||||||
switch (signal) {
|
switch (signal) {
|
||||||
case noSignal:
|
case noSignal:
|
||||||
|
// сброс счетчиков
|
||||||
|
// ...
|
||||||
isSending = false;
|
isSending = false;
|
||||||
return;
|
return;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case preamb:
|
case preamb:
|
||||||
if (preambFrontCounter == 0) { // Конец преамбулы, переход на следующий signal
|
if (preambFrontCounter) {
|
||||||
|
preambFrontCounter--;
|
||||||
|
toggleCounter = preambToggle; // Вторая и последующие генерации для этого signal
|
||||||
|
} else {// Конец преамбулы, переход на следующий signal
|
||||||
signal = data;
|
signal = data;
|
||||||
state = !LOW; // Инверсное состояние первой генерации следующего signal
|
state = !LOW; // Инверсное состояние первой генерации следующего signal
|
||||||
goto IsrStart; // Применение новых параметров в этй же итерации прерывания
|
goto IsrStart; // Применение новых параметров в этй же итерации прерывания
|
||||||
} else {
|
|
||||||
preambFrontCounter--;
|
|
||||||
toggleCounter = preambToggle; // Вторая и последующие генерации для этого signal
|
|
||||||
}
|
}
|
||||||
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case data:
|
case data:
|
||||||
if (dataFrontCounter == 0) { // Конец преамбулы, переход на следующий signal
|
if (dataSequenceCounter) {
|
||||||
signal = noSignal;
|
if (!(dataSequenceCounter & 1U)) { // если чётный - смена бита
|
||||||
// state = HIGH;
|
currentBitSequence = ((sendBuffer[dataByteCounter] >> dataBitCounter) & 1U) ? bitHigh : bitLow; // определение текущего бита
|
||||||
isSending = false;
|
dataBitCounter--;
|
||||||
} else {
|
}
|
||||||
toggleCounter = currentBit[!state];
|
toggleCounter = currentBitSequence[!state];
|
||||||
dataFrontCounter--;
|
dataSequenceCounter--;
|
||||||
|
} else { // Конец data, переход на следующий signal
|
||||||
|
syncLastBit = !((sendBuffer[dataByteCounter]) & 1U);
|
||||||
|
dataByteCounter++;
|
||||||
|
dataBitCounter = bitPerByte - 1;
|
||||||
|
dataSequenceCounter = bitPerByte * 2;
|
||||||
|
signal = sync;
|
||||||
|
goto IsrStart; // Применение новых параметров в этй же итерации прерывания
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// signal = (SignalPart)(~signal); // 2 -> 253, 253 -> 2
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case sync:
|
case sync:
|
||||||
// signal = (SignalPart)(~signal); // 2 -> 253, 253 -> 2
|
if (syncSequenceCounter) {
|
||||||
|
if (!(syncSequenceCounter & 1U)) { // если чётный - смена бита
|
||||||
|
if (syncSequenceCounter == 2) { // Если последний бит
|
||||||
|
currentBitSequence = ((sendBuffer[dataByteCounter]) & 0b10000000) ? bitLow : bitHigh;
|
||||||
|
} else {
|
||||||
|
currentBitSequence = syncLastBit ? bitLow : bitHigh; // определение текущего бита
|
||||||
|
syncLastBit = !syncLastBit;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
toggleCounter = currentBitSequence[!state];
|
||||||
|
syncSequenceCounter--;
|
||||||
|
} else { // Конец sync, переход на следующий signal
|
||||||
|
signal = data;
|
||||||
|
syncSequenceCounter = syncBits * 2;
|
||||||
|
|
||||||
|
if (dataByteCounter >= sendLen) { // определение конца данных
|
||||||
|
signal = noSignal;
|
||||||
|
}
|
||||||
|
goto IsrStart; // Применение новых параметров в этй же итерации прерывания
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
@ -185,9 +222,7 @@ void IR_Encoder::isr() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
state = !state;
|
state = !state;
|
||||||
|
}
|
||||||
|
|
||||||
} else { toggleCounter--; }
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
22
IR_Encoder.h
22
IR_Encoder.h
@ -46,23 +46,27 @@ private:
|
|||||||
enum SignalPart : uint8_t {
|
enum SignalPart : uint8_t {
|
||||||
noSignal = 0,
|
noSignal = 0,
|
||||||
preamb = 1,
|
preamb = 1,
|
||||||
data = 2, // 2 должен инвертироваться в sync
|
data = 2,
|
||||||
sync = (uint8_t)~(uint8_t)2U // 253 должен инвертироваться в data
|
sync = 3
|
||||||
};
|
};
|
||||||
|
|
||||||
|
uint8_t sendLen;
|
||||||
|
uint8_t* sendBuffer; /// @brief Буффер данных для отправки
|
||||||
|
|
||||||
volatile bool isSending = false;
|
volatile bool isSending = false;
|
||||||
// volatile bool genState = HIGH;
|
// volatile bool genState = HIGH;
|
||||||
|
|
||||||
volatile bool state; /// @brief Текущий уровень генерации
|
volatile bool state; /// @brief Текущий уровень генерации
|
||||||
volatile uint8_t toggleCounter; /// @brief Счётчик переключений
|
|
||||||
volatile uint8_t preambBitCounter;
|
volatile uint8_t dataByteCounter;
|
||||||
|
|
||||||
|
volatile uint8_t toggleCounter; /// @brief Счётчик переключений
|
||||||
volatile uint8_t dataBitCounter;
|
volatile uint8_t dataBitCounter;
|
||||||
volatile uint8_t syncBitCounter;
|
|
||||||
|
|
||||||
volatile uint8_t preambFrontCounter;
|
volatile uint8_t preambFrontCounter;
|
||||||
volatile uint8_t dataFrontCounter;
|
volatile uint8_t dataSequenceCounter;
|
||||||
volatile uint8_t syncFrontCounter;
|
volatile uint8_t syncSequenceCounter;
|
||||||
|
volatile bool syncLastBit;
|
||||||
|
|
||||||
struct BitSequence {
|
struct BitSequence {
|
||||||
uint8_t low;
|
uint8_t low;
|
||||||
@ -76,7 +80,7 @@ private:
|
|||||||
(bitPauseTakts + bitActiveTakts) * 2 - 1,
|
(bitPauseTakts + bitActiveTakts) * 2 - 1,
|
||||||
(bitPauseTakts) * 2 - 1
|
(bitPauseTakts) * 2 - 1
|
||||||
};
|
};
|
||||||
uint8_t* currentBit;
|
uint8_t* currentBitSequence = bitLow;
|
||||||
|
|
||||||
// uint8_t bitSequence[2];
|
// uint8_t bitSequence[2];
|
||||||
|
|
||||||
|
@ -96,8 +96,8 @@ typedef uint16_t crc_t;
|
|||||||
|
|
||||||
#define dataByteSizeMax (msgBytes + addrBytes + addrBytes + bytePerPack + crcBytes)
|
#define dataByteSizeMax (msgBytes + addrBytes + addrBytes + bytePerPack + crcBytes)
|
||||||
// размер msg в битах // размер короткой посылки в битах
|
// размер msg в битах // размер короткой посылки в битах
|
||||||
#define dataBitSize ((8 + syncBits) * dataByteSizeMax) // размер посылки с данными в битах
|
// #define dataBitSize ((8 + syncBits) * dataByteSizeMax) // размер посылки с данными в битах
|
||||||
#define bufferBitSizeMax (dataBitSize) // Размер буффера в битах
|
// #define bufferBitSizeMax (dataBitSize) // Размер буффера в битах
|
||||||
|
|
||||||
//const auto x = bufferBitSizeMax;
|
//const auto x = bufferBitSizeMax;
|
||||||
#define preambFronts (preambPulse*2) // количество фронтов преамбулы
|
#define preambFronts (preambPulse*2) // количество фронтов преамбулы
|
||||||
@ -113,6 +113,8 @@ typedef uint16_t crc_t;
|
|||||||
#define bitTime (bitTakts*carrierPeriod) // Общая длительность бита
|
#define bitTime (bitTakts*carrierPeriod) // Общая длительность бита
|
||||||
#define tolerance 300U
|
#define tolerance 300U
|
||||||
|
|
||||||
|
#define preambToggle ((bitPauseTakts * 2 + bitActiveTakts) * 2 - 1)
|
||||||
|
|
||||||
|
|
||||||
class IR_FOX {
|
class IR_FOX {
|
||||||
private:
|
private:
|
||||||
|
Loading…
x
Reference in New Issue
Block a user