Alternative to IRSend RAW command.

It is not practical to send long streams of data using the existing IRSend RAW command as it is limited by the size of the mqtt buffer.

The format for this command is:
        IRSend raw,<freq>,<hdr_mrk>,<hdr_spc>,<bit_mrk>,<zer_spc>,<one_spc>,<bit_str>
where,
        <freq>    = carrier freq (default 0, 38kHz)
        <hdr_mrk> = header mark (ms)
        <hdr_spc> = header space (ms)
        <bit_mrk> = bit mark (ms)
        <zer_spc> = zero space (ms)
        <one_spc> = one space (ms)
        <bit_str> = bit stream data (stream of ones and zeroes)

This command makes use of the output of the raw IR decoder from https://github.com/ToniA/Raw-IR-decoder-for-Arduino

USAGE:

Example rawirdecode output:

        Number of symbols: 75
        Symbols:
        Hh010101101000111011001110000000001100110000000001100000000000000010001100
        Bytes:
        00:  0101|0110 | 6A | 01101010
        01:  1000|1110 | 71 | 01110001
        02:  1100|1110 | 73 | 01110011
        03:  0000|0000 | 00 | 00000000
        04:  1100|1100 | 33 | 00110011
        05:  0000|0001 | 80 | 10000000
        06:  1000|0000 | 01 | 00000001
        07:  0000|0000 | 00 | 00000000
        08:  1000|1100 | 31 | 00110001
        6A,71,73,00,33,80,01,00,31
        Timings (in us):
        PAUSE SPACE:  0
        HEADER MARK:  8620
        HEADER SPACE: 4260
        BIT MARK:     544
        ZERO SPACE:   411
        ONE SPACE:    1496
        Decoding known protocols...
        Unknown protocol
        Bytecount: 9

Corresponding command:

        IRSend raw,0,8620,4260,544,411,1496,010101101000111011001110000000001100110000000001100000000000000010001100
This commit is contained in:
GP Orcullo 2019-04-09 17:41:32 +08:00
parent be385ecb5c
commit b3e8d3c143
1 changed files with 63 additions and 16 deletions

View File

@ -542,32 +542,79 @@ bool IrSendCommand(void)
if (strstr(XdrvMailbox.data, "{") == nullptr) { // If no JSON it must be rawdata
// IRSend frequency, rawdata, rawdata ...
// or IRSend raw,<freq>,<header mark>,<header space>,<bit mark>,<zero space>,<one space>,<bit stream>
char *p;
char *str = strtok_r(XdrvMailbox.data, ", ", &p);
if (p == nullptr) {
error = IE_INVALID_RAWDATA;
} else {
uint16_t freq = atoi(str);
if (!freq) { freq = 38000; } // Default to 38kHz
uint16_t count = 0;
char *q = p;
for (; *q; count += (*q++ == ','));
if (0 == count) {
error = IE_INVALID_RAWDATA;
} else { // At least two raw data values
count++;
uint16_t raw_array[count]; // It's safe to use stack for up to 240 packets (limited by mqtt_data length)
uint8_t i = 0;
for (str = strtok_r(nullptr, ", ", &p); str && i < count; str = strtok_r(nullptr, ", ", &p)) {
raw_array[i++] = strtoul(str, nullptr, 0); // Allow decimal (5246996) and hexadecimal (0x501014) input
if (!freq && (*str != '0')) { // first parameter is a string
uint16_t count = 0;
char *q = p;
for (; *q; count += (*q++ == ','));
if (count != 6) { // parameters must be exactly 6
error = IE_INVALID_RAWDATA;
} else {
str = strtok_r(NULL, ", ", &p);
freq = atoi(str);
if (!freq) { freq = 38000; } // Default to 38kHz
str = strtok_r(NULL, ", ", &p);
uint16_t hdr_mrk = atoi(str); // header mark
str = strtok_r(NULL, ", ", &p);
uint16_t hdr_spc = atoi(str); // header space
str = strtok_r(NULL, ", ", &p);
uint16_t bit_mrk = atoi(str); // bit mark
str = strtok_r(NULL, ", ", &p);
uint16_t zer_spc = atoi(str); // zero space
str = strtok_r(NULL, ", ", &p);
uint16_t one_spc = atoi(str); // one space
if (!hdr_mrk || !hdr_spc || !bit_mrk || !zer_spc || !one_spc) {
error = IE_INVALID_RAWDATA;
} else {
uint16_t raw_array[strlen(p)*2+3]; // header + bits + end
uint16_t i = 0;
raw_array[i++] = hdr_mrk;
raw_array[i++] = hdr_spc;
for (; *p; *p++) {
if (*p == '0') {
raw_array[i++] = bit_mrk;
raw_array[i++] = zer_spc;
} else {
raw_array[i++] = bit_mrk;
raw_array[i++] = one_spc;
}
}
raw_array[i++] = bit_mrk; // trailing mark
irsend_active = true;
irsend->sendRaw(raw_array, i, freq);
}
}
} else {
if (!freq) { freq = 38000; } // Default to 38kHz
uint16_t count = 0;
char *q = p;
for (; *q; count += (*q++ == ','));
if (0 == count) {
error = IE_INVALID_RAWDATA;
} else { // At least two raw data values
count++;
uint16_t raw_array[count]; // It's safe to use stack for up to 240 packets (limited by mqtt_data length)
uint8_t i = 0;
for (str = strtok_r(nullptr, ", ", &p); str && i < count; str = strtok_r(nullptr, ", ", &p)) {
raw_array[i++] = strtoul(str, nullptr, 0); // Allow decimal (5246996) and hexadecimal (0x501014) input
}
// AddLog_P2(LOG_LEVEL_DEBUG, PSTR("IRS: Count %d, Freq %d, Arr[0] %d, Arr[count -1] %d"), count, freq, raw_array[0], raw_array[count -1]);
irsend_active = true;
irsend->sendRaw(raw_array, count, freq);
if (!count) {
Response_P(S_JSON_COMMAND_SVALUE, command, D_JSON_FAILED);
irsend_active = true;
irsend->sendRaw(raw_array, count, freq);
if (!count) {
Response_P(S_JSON_COMMAND_SVALUE, command, D_JSON_FAILED);
}
}
}
}