Update IRremoteESP8266 library to 2.6.3.10

Update IRremoteESP8266 library to 2.6.3.10
This commit is contained in:
Theo Arends 2019-07-21 16:01:43 +02:00
parent 3a3e5a9464
commit 81184436f3
243 changed files with 20273 additions and 9299 deletions

View File

@ -1,66 +0,0 @@
language: c
env:
- BD=esp8266:esp8266:nodemcuv2:xtal=80,eesz=4M3M,ip=lm2f,exception=disabled
- BD=esp8266:esp8266:d1_mini:xtal=80,eesz=4M3M,ip=lm2f,exception=disabled
before_install:
- "/sbin/start-stop-daemon --start --quiet --pidfile /tmp/custom_xvfb_1.pid --make-pidfile --background --exec /usr/bin/Xvfb -- :1 -ac -screen 0 1280x1024x16"
- sleep 3
- export DISPLAY=:1.0
- wget http://downloads.arduino.cc/arduino-1.8.8-linux64.tar.xz
- tar xf arduino-1.8.8-linux64.tar.xz
- sudo mv arduino-1.8.8 /usr/local/share/arduino
- sudo ln -s /usr/local/share/arduino/arduino /usr/local/bin/arduino
- wget https://raw.githubusercontent.com/google/styleguide/gh-pages/cpplint/cpplint.py
install:
- ln -s $PWD /usr/local/share/arduino/libraries/
- git clone https://github.com/tzapu/WiFiManager.git /usr/local/share/arduino/libraries/WiFiManager
- git clone https://github.com/knolleary/pubsubclient.git /usr/local/share/arduino/libraries/PubSubClient
- git clone https://github.com/bblanchon/ArduinoJson.git --branch 5.x /usr/local/share/arduino/libraries/ArduinoJson
- arduino --pref "boardsmanager.additional.urls=http://arduino.esp8266.com/stable/package_esp8266com_index.json" --save-prefs
- arduino --install-boards esp8266:esp8266
- arduino --board $BD --save-prefs
- arduino --pref "compiler.warning_level=all" --save-prefs
- sudo apt-get install jq
- sudo pip install pylint
script:
# Check that everything compiles.
- arduino --verify --board $BD $PWD/examples/IRrecvDemo/IRrecvDemo.ino
- arduino --verify --board $BD $PWD/examples/IRGCSendDemo/IRGCSendDemo.ino
- arduino --verify --board $BD $PWD/examples/IRGCTCPServer/IRGCTCPServer.ino
- arduino --verify --board $BD $PWD/examples/IRServer/IRServer.ino
- arduino --verify --board $BD $PWD/examples/IRrecvDumpV2/IRrecvDumpV2.ino
- arduino --verify --board $BD $PWD/examples/IRsendDemo/IRsendDemo.ino
- arduino --verify --board $BD $PWD/examples/JVCPanasonicSendDemo/JVCPanasonicSendDemo.ino
- arduino --verify --board $BD $PWD/examples/TurnOnDaikinAC/TurnOnDaikinAC.ino
- arduino --verify --board $BD $PWD/examples/TurnOnFujitsuAC/TurnOnFujitsuAC.ino
- arduino --verify --board $BD $PWD/examples/TurnOnKelvinatorAC/TurnOnKelvinatorAC.ino
- arduino --verify --board $BD $PWD/examples/TurnOnMitsubishiAC/TurnOnMitsubishiAC.ino
- arduino --verify --board $BD $PWD/examples/IRsendProntoDemo/IRsendProntoDemo.ino
- arduino --verify --board $BD $PWD/examples/TurnOnTrotecAC/TurnOnTrotecAC.ino
- arduino --verify --board $BD $PWD/examples/LGACSend/LGACSend.ino
- arduino --verify --board $BD $PWD/examples/TurnOnArgoAC/TurnOnArgoAC.ino
- arduino --verify --board $BD $PWD/examples/IRMQTTServer/IRMQTTServer.ino
- arduino --verify --board $BD $PWD/examples/TurnOnToshibaAC/TurnOnToshibaAC.ino
- arduino --verify --board $BD $PWD/examples/ControlSamsungAC/ControlSamsungAC.ino
- arduino --verify --board $BD $PWD/examples/TurnOnPanasonicAC/TurnOnPanasonicAC.ino
- arduino --verify --board $BD $PWD/examples/TurnOnMitsubishiHeavyAc/TurnOnMitsubishiHeavyAc.ino
# Also check the tools programs compile.
- (cd tools; make all)
# Check for lint issues.
- shopt -s nullglob
- python cpplint.py --extensions=c,cc,cpp,ino --headers=h,hpp {src,test,tools}/*.{h,c,cc,cpp,hpp,ino} examples/*/*.{h,c,cc,cpp,hpp,ino}
- pylint {src,test,tools}/*.py
- shopt -u nullglob
# Build and run the unit tests.
- (cd test; make run)
- (cd tools; make run_tests)
# Check the version numbers match.
- LIB_VERSION=$(egrep "^#define\s+_IRREMOTEESP8266_VERSION_\s+" src/IRremoteESP8266.h | cut -d\" -f2)
- test ${LIB_VERSION} == "$(jq -r .version library.json)"
- grep -q "^version=${LIB_VERSION}$" library.properties
notifications:
email:
on_success: change
on_failure: change

View File

@ -1,19 +0,0 @@
[platformio]
lib_extra_dirs = ../../
src_dir=.
[common]
build_flags =
lib_deps_builtin =
lib_deps_external =
lib_ldf_mode = chain+
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
lib_ldf_mode = ${common.lib_ldf_mode}
build_flags = ${common.build_flags}
lib_deps =
${common.lib_deps_builtin}
${common.lib_deps_external}

View File

@ -1,19 +0,0 @@
[platformio]
lib_extra_dirs = ../../
src_dir=.
[common]
build_flags =
lib_deps_builtin =
lib_deps_external =
lib_ldf_mode = chain+
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
lib_ldf_mode = ${common.lib_ldf_mode}
build_flags = ${common.build_flags}
lib_deps =
${common.lib_deps_builtin}
${common.lib_deps_external}

View File

@ -1,19 +0,0 @@
[platformio]
lib_extra_dirs = ../../
src_dir=.
[common]
build_flags =
lib_deps_builtin =
lib_deps_external =
lib_ldf_mode = chain+
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
lib_ldf_mode = ${common.lib_ldf_mode}
build_flags = ${common.build_flags}
lib_deps =
${common.lib_deps_builtin}
${common.lib_deps_external}

View File

@ -1,42 +0,0 @@
[platformio]
lib_extra_dirs = ../../
src_dir=.
[common]
build_flags = -DMQTT_MAX_PACKET_SIZE=768
lib_ldf_mode = chain+
lib_deps_builtin =
lib_deps_external =
PubSubClient
WifiManager@0.14
ArduinoJson
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
lib_ldf_mode = ${common.lib_ldf_mode}
build_flags = ${common.build_flags}
lib_deps =
${common.lib_deps_builtin}
${common.lib_deps_external}
[env:d1_mini]
platform=espressif8266
framework=arduino
board=d1_mini
lib_ldf_mode = ${common.lib_ldf_mode}
build_flags = ${common.build_flags}
lib_deps =
${common.lib_deps_builtin}
${common.lib_deps_external}
[env:d1_mini_no_mqtt]
platform=espressif8266
framework=arduino
board=d1_mini
lib_ldf_mode = ${common.lib_ldf_mode}
build_flags = ${common.build_flags} -DMQTT_ENABLE=false
lib_deps =
${common.lib_deps_builtin}
${common.lib_deps_external}

View File

@ -1,19 +0,0 @@
[platformio]
lib_extra_dirs = ../../
src_dir=.
[common]
build_flags =
lib_deps_builtin =
lib_deps_external =
lib_ldf_mode = chain+
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
lib_ldf_mode = ${common.lib_ldf_mode}
build_flags = ${common.build_flags}
lib_deps =
${common.lib_deps_builtin}
${common.lib_deps_external}

View File

@ -1,19 +0,0 @@
[platformio]
lib_extra_dirs = ../../
src_dir=.
[common]
build_flags =
lib_deps_builtin =
lib_deps_external =
lib_ldf_mode = chain+
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
lib_ldf_mode = ${common.lib_ldf_mode}
build_flags = ${common.build_flags}
lib_deps =
${common.lib_deps_builtin}
${common.lib_deps_external}

View File

@ -1,19 +0,0 @@
[platformio]
lib_extra_dirs = ../../
src_dir=.
[common]
build_flags =
lib_deps_builtin =
lib_deps_external =
lib_ldf_mode = chain+
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
lib_ldf_mode = ${common.lib_ldf_mode}
build_flags = ${common.build_flags}
lib_deps =
${common.lib_deps_builtin}
${common.lib_deps_external}

View File

@ -1,19 +0,0 @@
[platformio]
lib_extra_dirs = ../../
src_dir=.
[common]
build_flags =
lib_deps_builtin =
lib_deps_external =
lib_ldf_mode = chain+
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
lib_ldf_mode = ${common.lib_ldf_mode}
build_flags = ${common.build_flags}
lib_deps =
${common.lib_deps_builtin}
${common.lib_deps_external}

View File

@ -1,19 +0,0 @@
[platformio]
lib_extra_dirs = ../../
src_dir=.
[common]
build_flags =
lib_deps_builtin =
lib_deps_external =
lib_ldf_mode = chain+
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
lib_ldf_mode = ${common.lib_ldf_mode}
build_flags = ${common.build_flags}
lib_deps =
${common.lib_deps_builtin}
${common.lib_deps_external}

View File

@ -1,19 +0,0 @@
[platformio]
lib_extra_dirs = ../../
src_dir=.
[common]
build_flags =
lib_deps_builtin =
lib_deps_external =
lib_ldf_mode = chain+
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
lib_ldf_mode = ${common.lib_ldf_mode}
build_flags = ${common.build_flags}
lib_deps =
${common.lib_deps_builtin}
${common.lib_deps_external}

View File

@ -1,19 +0,0 @@
[platformio]
lib_extra_dirs = ../../
src_dir=.
[common]
build_flags =
lib_deps_builtin =
lib_deps_external =
lib_ldf_mode = chain+
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
lib_ldf_mode = ${common.lib_ldf_mode}
build_flags = ${common.build_flags}
lib_deps =
${common.lib_deps_builtin}
${common.lib_deps_external}

View File

@ -1,19 +0,0 @@
[platformio]
lib_extra_dirs = ../../
src_dir=.
[common]
build_flags =
lib_deps_builtin =
lib_deps_external =
lib_ldf_mode = chain+
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
lib_ldf_mode = ${common.lib_ldf_mode}
build_flags = ${common.build_flags}
lib_deps =
${common.lib_deps_builtin}
${common.lib_deps_external}

View File

@ -1,19 +0,0 @@
[platformio]
lib_extra_dirs = ../../
src_dir=.
[common]
build_flags =
lib_deps_builtin =
lib_deps_external =
lib_ldf_mode = chain+
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
lib_ldf_mode = ${common.lib_ldf_mode}
build_flags = ${common.build_flags}
lib_deps =
${common.lib_deps_builtin}
${common.lib_deps_external}

View File

@ -1,19 +0,0 @@
[platformio]
lib_extra_dirs = ../../
src_dir=.
[common]
build_flags =
lib_deps_builtin =
lib_deps_external =
lib_ldf_mode = chain+
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
lib_ldf_mode = ${common.lib_ldf_mode}
build_flags = ${common.build_flags}
lib_deps =
${common.lib_deps_builtin}
${common.lib_deps_external}

View File

@ -1,19 +0,0 @@
[platformio]
lib_extra_dirs = ../../
src_dir=.
[common]
build_flags =
lib_deps_builtin =
lib_deps_external =
lib_ldf_mode = chain+
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
lib_ldf_mode = ${common.lib_ldf_mode}
build_flags = ${common.build_flags}
lib_deps =
${common.lib_deps_builtin}
${common.lib_deps_external}

View File

@ -1,19 +0,0 @@
[platformio]
lib_extra_dirs = ../../
src_dir=.
[common]
build_flags =
lib_deps_builtin =
lib_deps_external =
lib_ldf_mode = chain+
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
lib_ldf_mode = ${common.lib_ldf_mode}
build_flags = ${common.build_flags}
lib_deps =
${common.lib_deps_builtin}
${common.lib_deps_external}

View File

@ -1,19 +0,0 @@
[platformio]
lib_extra_dirs = ../../
src_dir=.
[common]
build_flags =
lib_deps_builtin =
lib_deps_external =
lib_ldf_mode = chain+
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
lib_ldf_mode = ${common.lib_ldf_mode}
build_flags = ${common.build_flags}
lib_deps =
${common.lib_deps_builtin}
${common.lib_deps_external}

View File

@ -1,19 +0,0 @@
[platformio]
lib_extra_dirs = ../../
src_dir=.
[common]
build_flags =
lib_deps_builtin =
lib_deps_external =
lib_ldf_mode = chain+
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
lib_ldf_mode = ${common.lib_ldf_mode}
build_flags = ${common.build_flags}
lib_deps =
${common.lib_deps_builtin}
${common.lib_deps_external}

View File

@ -1,19 +0,0 @@
[platformio]
lib_extra_dirs = ../../
src_dir=.
[common]
build_flags =
lib_deps_builtin =
lib_deps_external =
lib_ldf_mode = chain+
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
lib_ldf_mode = ${common.lib_ldf_mode}
build_flags = ${common.build_flags}
lib_deps =
${common.lib_deps_builtin}
${common.lib_deps_external}

View File

@ -1,19 +0,0 @@
[platformio]
lib_extra_dirs = ../../
src_dir=.
[common]
build_flags =
lib_deps_builtin =
lib_deps_external =
lib_ldf_mode = chain+
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
lib_ldf_mode = ${common.lib_ldf_mode}
build_flags = ${common.build_flags}
lib_deps =
${common.lib_deps_builtin}
${common.lib_deps_external}

View File

@ -1,19 +0,0 @@
[platformio]
lib_extra_dirs = ../../
src_dir=.
[common]
build_flags =
lib_deps_builtin =
lib_deps_external =
lib_ldf_mode = chain+
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
lib_ldf_mode = ${common.lib_ldf_mode}
build_flags = ${common.build_flags}
lib_deps =
${common.lib_deps_builtin}
${common.lib_deps_external}

View File

@ -1,29 +0,0 @@
[platformio]
lib_extra_dirs = .
src_dir = examples/IRrecvDumpV2
[common]
build_flags =
lib_deps_builtin =
lib_deps_external =
lib_ldf_mode = chain+
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
lib_ldf_mode = ${common.lib_ldf_mode}
build_flags = ${common.build_flags}
lib_deps =
${common.lib_deps_builtin}
${common.lib_deps_external}
[env:d1_mini]
platform = espressif8266
framework = arduino
board = d1_mini
lib_ldf_mode = ${common.lib_ldf_mode}
build_flags = ${common.build_flags}
lib_deps =
${common.lib_deps_builtin}
${common.lib_deps_external}

View File

@ -1,48 +0,0 @@
#ifndef IRUTILS_H_
#define IRUTILS_H_
// Copyright 2017 David Conran
#ifndef UNIT_TEST
#include <Arduino.h>
#endif
#define __STDC_LIMIT_MACROS
#include <stdint.h>
#ifndef ARDUINO
#include <string>
#endif
#include "IRremoteESP8266.h"
#include "IRrecv.h"
uint64_t reverseBits(uint64_t input, uint16_t nbits);
#ifdef ARDUINO // Arduino's & C++'s string implementations can't co-exist.
String uint64ToString(uint64_t input, uint8_t base = 10);
String typeToString(const decode_type_t protocol,
const bool isRepeat = false);
void serialPrintUint64(uint64_t input, uint8_t base = 10);
String resultToSourceCode(const decode_results *results);
String resultToTimingInfo(const decode_results *results);
String resultToHumanReadableBasic(const decode_results *results);
String resultToHexidecimal(const decode_results *result);
String htmlEscape(const String unescaped);
#else // ARDUINO
std::string uint64ToString(uint64_t input, uint8_t base = 10);
std::string typeToString(const decode_type_t protocol,
const bool isRepeat = false);
std::string resultToSourceCode(const decode_results *results);
std::string resultToTimingInfo(const decode_results *results);
std::string resultToHumanReadableBasic(const decode_results *results);
std::string resultToHexidecimal(const decode_results *result);
std::string htmlEscape(const std::string unescaped);
#endif // ARDUINO
bool hasACState(const decode_type_t protocol);
uint16_t getCorrectedRawLength(const decode_results *results);
uint8_t sumBytes(uint8_t *start, const uint16_t length, const uint8_t init = 0);
uint8_t xorBytes(uint8_t *start, const uint16_t length, const uint8_t init = 0);
uint16_t countBits(const uint8_t *start, const uint16_t length,
const bool ones = true, const uint16_t init = 0);
uint16_t countBits(const uint64_t data, const uint8_t length,
const bool ones = true, const uint16_t init = 0);
uint64_t invertBits(const uint64_t data, const uint16_t nbits);
decode_type_t strToDecodeType(const char *str);
#endif // IRUTILS_H_

View File

@ -1,264 +0,0 @@
/*
Node MCU/ESP8266 Sketch to emulate Argo Ulisse 13 DCI remote
Controls Argo Ulisse 13 DCI A/C
Copyright 2017 Schmolders
*/
#include "ir_Argo.h"
#include <algorithm>
#include "IRremoteESP8266.h"
#include "IRutils.h"
// Constants
// using SPACE modulation. MARK is always const 400u
const uint16_t kArgoHdrMark = 6400;
const uint16_t kArgoHdrSpace = 3300;
const uint16_t kArgoBitMark = 400;
const uint16_t kArgoOneSpace = 2200;
const uint16_t kArgoZeroSpace = 900;
#if SEND_ARGO
// Send an Argo A/C message.
//
// Args:
// data: An array of kArgoStateLength bytes containing the IR command.
//
// Status: ALPHA / Untested.
void IRsend::sendArgo(unsigned char data[], uint16_t nbytes, uint16_t repeat) {
// Check if we have enough bytes to send a proper message.
if (nbytes < kArgoStateLength) return;
// TODO(kaschmo): validate
sendGeneric(kArgoHdrMark, kArgoHdrSpace, kArgoBitMark, kArgoOneSpace,
kArgoBitMark, kArgoZeroSpace, 0, 0, // No Footer.
data, nbytes, 38, false, repeat, kDutyDefault);
}
#endif // SEND_ARGO
IRArgoAC::IRArgoAC(uint16_t pin) : _irsend(pin) { stateReset(); }
void IRArgoAC::begin() { _irsend.begin(); }
#if SEND_ARGO
void IRArgoAC::send(const uint16_t repeat) {
checksum(); // Create valid checksum before sending
_irsend.sendArgo(argo, kArgoStateLength, repeat);
}
#endif // SEND_ARGO
void IRArgoAC::checksum() {
uint8_t sum = 2; // Corresponds to byte 11 being constant 0b01
uint8_t i;
// Only add up bytes to 9. byte 10 is 0b01 constant anyway.
// Assume that argo array is MSB first (left)
for (i = 0; i < 10; i++) sum += argo[i];
sum = sum % 256; // modulo 256
// Append sum to end of array
// Set const part of checksum bit 10
argo[10] = 0b00000010;
argo[10] += sum << 2; // Shift up 2 bits and append to byte 10
argo[11] = sum >> 6; // Shift down 6 bits and add in two LSBs of bit 11
}
void IRArgoAC::stateReset() {
for (uint8_t i = 0; i < kArgoStateLength; i++) argo[i] = 0x0;
// Argo Message. Store MSB left.
// Default message:
argo[0] = 0b10101100; // LSB first (as sent) 0b00110101; //const preamble
argo[1] = 0b11110101; // LSB first: 0b10101111; //const preamble
// Keep payload 2-9 at zero
argo[10] = 0b00000010; // Const 01, checksum 6bit
argo[11] = 0b00000000; // Checksum 2bit
this->off();
this->setTemp(20);
this->setRoomTemp(25);
this->setCoolMode(kArgoCoolAuto);
this->setFan(kArgoFanAuto);
}
uint8_t* IRArgoAC::getRaw() {
checksum(); // Ensure correct bit array before returning
return argo;
}
void IRArgoAC::on() {
// state = ON;
ac_state = 1;
// Bit 5 of byte 9 is on/off
// in MSB first
argo[9] = argo[9] | 0b00100000; // Set ON/OFF bit to 1
}
void IRArgoAC::off() {
// state = OFF;
ac_state = 0;
// in MSB first
// bit 5 of byte 9 to off
argo[9] = argo[9] & 0b11011111; // Set on/off bit to 0
}
void IRArgoAC::setPower(bool state) {
if (state)
on();
else
off();
}
uint8_t IRArgoAC::getPower() { return ac_state; }
void IRArgoAC::setMax(bool state) {
max_mode = state;
if (max_mode)
argo[9] |= 0b00001000;
else
argo[9] &= 0b11110111;
}
bool IRArgoAC::getMax() { return max_mode; }
// Set the temp in deg C
// Sending 0 equals +4
void IRArgoAC::setTemp(uint8_t temp) {
if (temp < kArgoMinTemp)
temp = kArgoMinTemp;
else if (temp > kArgoMaxTemp)
temp = kArgoMaxTemp;
// Store in attributes
set_temp = temp;
// offset 4 degrees. "If I want 12 degrees, I need to send 8"
temp -= 4;
// Settemp = Bit 6,7 of byte 2, and bit 0-2 of byte 3
// mask out bits
// argo[13] & 0x00000100; // mask out ON/OFF Bit
argo[2] &= 0b00111111;
argo[3] &= 0b11111000;
argo[2] += temp << 6; // append to bit 6,7
argo[3] += temp >> 2; // remove lowest to bits and append in 0-2
}
uint8_t IRArgoAC::getTemp() { return set_temp; }
// Set the speed of the fan
void IRArgoAC::setFan(uint8_t fan) {
// Set the fan speed bits, leave low 4 bits alone
fan_mode = fan;
// Mask out bits
argo[3] &= 0b11100111;
// Set fan mode at bit positions
argo[3] += fan << 3;
}
uint8_t IRArgoAC::getFan() { return fan_mode; }
void IRArgoAC::setFlap(uint8_t flap) {
flap_mode = flap;
// TODO(kaschmo): set correct bits for flap mode
}
uint8_t IRArgoAC::getFlap() { return flap_mode; }
uint8_t IRArgoAC::getMode() {
// return cooling 0, heating 1
return ac_mode;
}
void IRArgoAC::setCoolMode(uint8_t mode) {
ac_mode = 0; // Set ac mode to cooling
cool_mode = mode;
// Mask out bits, also leave bit 5 on 0 for cooling
argo[2] &= 0b11000111;
// Set cool mode at bit positions
argo[2] += mode << 3;
}
uint8_t IRArgoAC::getCoolMode() { return cool_mode; }
void IRArgoAC::setHeatMode(uint8_t mode) {
ac_mode = 1; // Set ac mode to heating
heat_mode = mode;
// Mask out bits
argo[2] &= 0b11000111;
// Set heating bit
argo[2] |= 0b00100000;
// Set cool mode at bit positions
argo[2] += mode << 3;
}
uint8_t IRArgoAC::getHeatMode() { return heat_mode; }
void IRArgoAC::setNight(bool state) {
night_mode = state;
if (night_mode)
// Set bit at night position: bit 2
argo[9] |= 0b00000100;
else
argo[9] &= 0b11111011;
}
bool IRArgoAC::getNight() { return night_mode; }
void IRArgoAC::setiFeel(bool state) {
ifeel_mode = state;
if (ifeel_mode)
// Set bit at iFeel position: bit 7
argo[9] |= 0b10000000;
else
argo[9] &= 0b01111111;
}
bool IRArgoAC::getiFeel() { return ifeel_mode; }
void IRArgoAC::setTime() {
// TODO(kaschmo): use function call from checksum to set time first
}
void IRArgoAC::setRoomTemp(uint8_t temp) {
temp -= 4;
// Mask out bits
argo[3] &= 0b00011111;
argo[4] &= 0b11111100;
argo[3] += temp << 5; // Append to bit 5,6,7
argo[4] += temp >> 3; // Remove lowest 3 bits and append in 0,1
}
// Convert a standard A/C Fan speed into its native fan speed.
uint8_t IRArgoAC::convertFan(const stdAc::fanspeed_t speed) {
switch (speed) {
case stdAc::fanspeed_t::kMin:
case stdAc::fanspeed_t::kLow:
return kArgoFan1;
case stdAc::fanspeed_t::kMedium:
return kArgoFan2;
case stdAc::fanspeed_t::kHigh:
case stdAc::fanspeed_t::kMax:
return kArgoFan3;
default:
return kArgoFanAuto;
}
}
// Convert a standard A/C Fan speed into its native fan speed.
uint8_t IRArgoAC::convertSwingV(const stdAc::swingv_t position) {
switch (position) {
case stdAc::swingv_t::kHighest:
return kArgoFlapFull;
case stdAc::swingv_t::kHigh:
return kArgoFlap5;
case stdAc::swingv_t::kMiddle:
return kArgoFlap4;
case stdAc::swingv_t::kLow:
return kArgoFlap3;
case stdAc::swingv_t::kLowest:
return kArgoFlap1;
default:
return kArgoFlapAuto;
}
}

View File

@ -1,117 +0,0 @@
// Copyright 2018, 2019 David Conran
#include "IRrecv.h"
#include "IRsend.h"
#include "IRutils.h"
// EEEEEEE LL EEEEEEE CCCCC TTTTTTT RRRRRR AAA
// EE LL EE CC C TTT RR RR AAAAA
// EEEEE LL EEEEE CC TTT RRRRRR AA AA
// EE LL EE CC C TTT RR RR AAAAAAA
// EEEEEEE LLLLLLL EEEEEEE CCCCC TTT RR RR AA AA
// Electra A/C added by crankyoldgit
//
// Equipment it seems compatible with:
// * <Add models (A/C & remotes) you've gotten it working with here>
// Ref:
// https://github.com/markszabo/IRremoteESP8266/issues/527
// https://github.com/markszabo/IRremoteESP8266/issues/642
// Constants
const uint16_t kElectraAcHdrMark = 9166;
const uint16_t kElectraAcBitMark = 646;
const uint16_t kElectraAcHdrSpace = 4470;
const uint16_t kElectraAcOneSpace = 1647;
const uint16_t kElectraAcZeroSpace = 547;
const uint32_t kElectraAcMessageGap = kDefaultMessageGap; // Just a guess.
#if SEND_ELECTRA_AC
// Send a Electra message
//
// Args:
// data: Contents of the message to be sent. (Guessing MSBF order)
// nbits: Nr. of bits of data to be sent. Typically kElectraAcBits.
// repeat: Nr. of additional times the message is to be sent.
//
// Status: Alpha / Needs testing against a real device.
//
void IRsend::sendElectraAC(uint8_t data[], uint16_t nbytes, uint16_t repeat) {
for (uint16_t r = 0; r <= repeat; r++)
sendGeneric(kElectraAcHdrMark, kElectraAcHdrSpace, kElectraAcBitMark,
kElectraAcOneSpace, kElectraAcBitMark, kElectraAcZeroSpace,
kElectraAcBitMark, kElectraAcMessageGap, data, nbytes,
38000, // Complete guess of the modulation frequency.
false, // Send data in LSB order per byte
0, 50);
}
#endif
#if DECODE_ELECTRA_AC
// Decode the supplied Electra A/C message.
//
// Args:
// results: Ptr to the data to decode and where to store the decode result.
// nbits: The number of data bits to expect. Typically kElectraAcBits.
// strict: Flag indicating if we should perform strict matching.
// Returns:
// boolean: True if it can decode it, false if it can't.
//
// Status: Beta / Probably works.
//
bool IRrecv::decodeElectraAC(decode_results *results, uint16_t nbits,
bool strict) {
if (nbits % 8 != 0) // nbits has to be a multiple of nr. of bits in a byte.
return false;
if (strict) {
if (nbits != kElectraAcBits)
return false; // Not strictly a ELECTRA_AC message.
}
if (results->rawlen < 2 * nbits + kHeader + kFooter - 1)
return false; // Can't possibly be a valid ELECTRA_AC message.
uint16_t offset = kStartOffset;
// Message Header
if (!matchMark(results->rawbuf[offset++], kElectraAcHdrMark)) return false;
if (!matchSpace(results->rawbuf[offset++], kElectraAcHdrSpace)) return false;
// Data Section
match_result_t data_result;
uint16_t dataBitsSoFar = 0;
// Keep reading bytes until we either run out of section or state to fill.
for (uint16_t i = 0; offset <= results->rawlen - 16 && i < nbits / 8;
i++, dataBitsSoFar += 8, offset += data_result.used) {
data_result = matchData(&(results->rawbuf[offset]), 8, kElectraAcBitMark,
kElectraAcOneSpace, kElectraAcBitMark,
kElectraAcZeroSpace, kTolerance, 0, false);
if (data_result.success == false) return false; // Fail
results->state[i] = data_result.data;
}
// Message Footer
if (!matchMark(results->rawbuf[offset++], kElectraAcBitMark)) return false;
if (offset <= results->rawlen &&
!matchAtLeast(results->rawbuf[offset++], kElectraAcMessageGap))
return false;
// Compliance
if (strict) {
if (dataBitsSoFar != nbits) return false;
// Verify the checksum.
if (sumBytes(results->state, (dataBitsSoFar / 8) - 1) !=
results->state[(dataBitsSoFar / 8) - 1]) return false;
}
// Success
results->decode_type = ELECTRA_AC;
results->bits = dataBitsSoFar;
// No need to record the state as we stored it as we decoded it.
// As we use result->state, we don't record value, address, or command as it
// is a union data type.
return true;
}
#endif // DECODE_ELECTRA_AC

View File

@ -1,556 +0,0 @@
// Copyright 2017 Jonny Graham, David Conran
#include "ir_Fujitsu.h"
#include <algorithm>
#ifndef ARDUINO
#include <string>
#endif
#include "IRsend.h"
#include "IRutils.h"
// Fujitsu A/C support added by Jonny Graham & David Conran
// Equipment it seems compatible with:
// * Fujitsu ASYG30LFCA with remote AR-RAH2E
// * Fujitsu AST9RSGCW with remote AR-DB1
// * <Add models (A/C & remotes) you've gotten it working with here>
// Ref:
// These values are based on averages of measurements
const uint16_t kFujitsuAcHdrMark = 3324;
const uint16_t kFujitsuAcHdrSpace = 1574;
const uint16_t kFujitsuAcBitMark = 448;
const uint16_t kFujitsuAcOneSpace = 1182;
const uint16_t kFujitsuAcZeroSpace = 390;
const uint16_t kFujitsuAcMinGap = 8100;
#if SEND_FUJITSU_AC
// Send a Fujitsu A/C message.
//
// Args:
// data: An array of bytes containing the IR command.
// nbytes: Nr. of bytes of data in the array. Typically one of:
// kFujitsuAcStateLength
// kFujitsuAcStateLength - 1
// kFujitsuAcStateLengthShort
// kFujitsuAcStateLengthShort - 1
// repeat: Nr. of times the message is to be repeated.
// (Default = kFujitsuAcMinRepeat).
//
// Status: BETA / Appears to be working.
//
void IRsend::sendFujitsuAC(unsigned char data[], uint16_t nbytes,
uint16_t repeat) {
sendGeneric(kFujitsuAcHdrMark, kFujitsuAcHdrSpace, kFujitsuAcBitMark,
kFujitsuAcOneSpace, kFujitsuAcBitMark, kFujitsuAcZeroSpace,
kFujitsuAcBitMark, kFujitsuAcMinGap, data, nbytes, 38, false,
repeat, 50);
}
#endif // SEND_FUJITSU_AC
// Code to emulate Fujitsu A/C IR remote control unit.
// Initialise the object.
IRFujitsuAC::IRFujitsuAC(uint16_t pin, fujitsu_ac_remote_model_t model)
: _irsend(pin) {
setModel(model);
stateReset();
}
void IRFujitsuAC::setModel(fujitsu_ac_remote_model_t model) {
_model = model;
switch (model) {
case ARDB1:
_state_length = kFujitsuAcStateLength - 1;
_state_length_short = kFujitsuAcStateLengthShort - 1;
break;
default:
_state_length = kFujitsuAcStateLength;
_state_length_short = kFujitsuAcStateLengthShort;
}
}
// Reset the state of the remote to a known good state/sequence.
void IRFujitsuAC::stateReset() {
_temp = 24;
_fanSpeed = kFujitsuAcFanHigh;
_mode = kFujitsuAcModeCool;
_swingMode = kFujitsuAcSwingBoth;
_cmd = kFujitsuAcCmdTurnOn;
buildState();
}
// Configure the pin for output.
void IRFujitsuAC::begin() { _irsend.begin(); }
#if SEND_FUJITSU_AC
// Send the current desired state to the IR LED.
void IRFujitsuAC::send(const uint16_t repeat) {
getRaw();
_irsend.sendFujitsuAC(remote_state, getStateLength(), repeat);
}
#endif // SEND_FUJITSU_AC
void IRFujitsuAC::buildState() {
remote_state[0] = 0x14;
remote_state[1] = 0x63;
remote_state[2] = 0x00;
remote_state[3] = 0x10;
remote_state[4] = 0x10;
bool fullCmd = false;
switch (_cmd) {
case kFujitsuAcCmdTurnOff:
remote_state[5] = 0x02;
break;
case kFujitsuAcCmdStepHoriz:
remote_state[5] = 0x79;
break;
case kFujitsuAcCmdStepVert:
remote_state[5] = 0x6C;
break;
default:
switch (_model) {
case ARRAH2E:
remote_state[5] = 0xFE;
break;
case ARDB1:
remote_state[5] = 0xFC;
break;
}
fullCmd = true;
break;
}
if (fullCmd) { // long codes
uint8_t tempByte = _temp - kFujitsuAcMinTemp;
// Nr. of bytes in the message after this byte.
remote_state[6] = _state_length - 7;
remote_state[7] = 0x30;
remote_state[8] = (_cmd == kFujitsuAcCmdTurnOn) | (tempByte << 4);
remote_state[9] = _mode | 0 << 4; // timer off
remote_state[10] = _fanSpeed | _swingMode << 4;
remote_state[11] = 0; // timerOff values
remote_state[12] = 0; // timerOff/On values
remote_state[13] = 0; // timerOn values
if (_model == ARRAH2E)
remote_state[14] = 0x20;
else
remote_state[14] = 0x00;
uint8_t checksum = 0;
uint8_t checksum_complement = 0;
if (_model == ARRAH2E) {
checksum = sumBytes(remote_state + _state_length_short,
_state_length - _state_length_short - 1);
} else if (_model == ARDB1) {
checksum = sumBytes(remote_state, _state_length - 1);
checksum_complement = 0x9B;
}
// and negate the checksum and store it in the last byte.
remote_state[_state_length - 1] = checksum_complement - checksum;
} else { // short codes
if (_model == ARRAH2E)
// The last byte is the inverse of penultimate byte
remote_state[_state_length_short - 1] =
~remote_state[_state_length_short - 2];
// Zero the rest of the state.
for (uint8_t i = _state_length_short; i < kFujitsuAcStateLength; i++)
remote_state[i] = 0;
}
}
uint8_t IRFujitsuAC::getStateLength() {
buildState(); // Force an update of the internal state.
if ((_model == ARRAH2E && remote_state[5] != 0xFE) ||
(_model == ARDB1 && remote_state[5] != 0xFC))
return _state_length_short;
else
return _state_length;
}
// Return a pointer to the internal state date of the remote.
uint8_t* IRFujitsuAC::getRaw() {
buildState();
return remote_state;
}
void IRFujitsuAC::buildFromState(const uint16_t length) {
switch (length) {
case kFujitsuAcStateLength - 1:
case kFujitsuAcStateLengthShort - 1:
setModel(ARDB1);
break;
default:
setModel(ARRAH2E);
}
switch (remote_state[6]) {
case 8:
setModel(ARDB1);
break;
case 9:
setModel(ARRAH2E);
break;
}
setTemp((remote_state[8] >> 4) + kFujitsuAcMinTemp);
if (remote_state[8] & 0x1)
setCmd(kFujitsuAcCmdTurnOn);
else
setCmd(kFujitsuAcCmdStayOn);
setMode(remote_state[9] & 0b111);
setFanSpeed(remote_state[10] & 0b111);
setSwing(remote_state[10] >> 4);
switch (remote_state[5]) {
case kFujitsuAcCmdTurnOff:
case kFujitsuAcCmdStepHoriz:
case kFujitsuAcCmdStepVert:
setCmd(remote_state[5]);
break;
}
}
bool IRFujitsuAC::setRaw(const uint8_t newState[], const uint16_t length) {
if (length > kFujitsuAcStateLength) return false;
for (uint16_t i = 0; i < kFujitsuAcStateLength; i++) {
if (i < length)
remote_state[i] = newState[i];
else
remote_state[i] = 0;
}
buildFromState(length);
return true;
}
// Set the requested power state of the A/C to off.
void IRFujitsuAC::off() { _cmd = kFujitsuAcCmdTurnOff; }
void IRFujitsuAC::stepHoriz() {
switch (_model) {
case ARDB1:
break; // This remote doesn't have a horizontal option.
default:
_cmd = kFujitsuAcCmdStepHoriz;
}
}
void IRFujitsuAC::stepVert() { _cmd = kFujitsuAcCmdStepVert; }
// Set the requested command of the A/C.
void IRFujitsuAC::setCmd(uint8_t cmd) {
switch (cmd) {
case kFujitsuAcCmdTurnOff:
case kFujitsuAcCmdTurnOn:
case kFujitsuAcCmdStayOn:
case kFujitsuAcCmdStepVert:
_cmd = cmd;
break;
case kFujitsuAcCmdStepHoriz:
if (_model != ARDB1) // AR-DB1 remote doesn't have step horizontal.
_cmd = cmd;
// FALLTHRU
default:
_cmd = kFujitsuAcCmdStayOn;
break;
}
}
uint8_t IRFujitsuAC::getCmd() { return _cmd; }
bool IRFujitsuAC::getPower() { return _cmd != kFujitsuAcCmdTurnOff; }
// Set the temp. in deg C
void IRFujitsuAC::setTemp(uint8_t temp) {
temp = std::max((uint8_t)kFujitsuAcMinTemp, temp);
temp = std::min((uint8_t)kFujitsuAcMaxTemp, temp);
_temp = temp;
}
uint8_t IRFujitsuAC::getTemp() { return _temp; }
// Set the speed of the fan
void IRFujitsuAC::setFanSpeed(uint8_t fanSpeed) {
if (fanSpeed > kFujitsuAcFanQuiet)
fanSpeed = kFujitsuAcFanHigh; // Set the fan to maximum if out of range.
_fanSpeed = fanSpeed;
}
uint8_t IRFujitsuAC::getFanSpeed() { return _fanSpeed; }
// Set the requested climate operation mode of the a/c unit.
void IRFujitsuAC::setMode(uint8_t mode) {
if (mode > kFujitsuAcModeHeat)
mode = kFujitsuAcModeHeat; // Set the mode to maximum if out of range.
_mode = mode;
}
uint8_t IRFujitsuAC::getMode() { return _mode; }
// Set the requested swing operation mode of the a/c unit.
void IRFujitsuAC::setSwing(uint8_t swingMode) {
switch (_model) {
case ARDB1:
// Set the mode to max if out of range
if (swingMode > kFujitsuAcSwingVert) swingMode = kFujitsuAcSwingVert;
break;
case ARRAH2E:
default:
// Set the mode to max if out of range
if (swingMode > kFujitsuAcSwingBoth) swingMode = kFujitsuAcSwingBoth;
}
_swingMode = swingMode;
}
uint8_t IRFujitsuAC::getSwing() { return _swingMode; }
bool IRFujitsuAC::validChecksum(uint8_t state[], uint16_t length) {
uint8_t sum = 0;
uint8_t sum_complement = 0;
uint8_t checksum = state[length - 1];
switch (length) {
case kFujitsuAcStateLengthShort: // ARRAH2E
return state[length - 1] == (uint8_t)~state[length - 2];
case kFujitsuAcStateLength - 1: // ARDB1
sum = sumBytes(state, length - 1);
sum_complement = 0x9B;
break;
case kFujitsuAcStateLength: // ARRAH2E
sum = sumBytes(state + kFujitsuAcStateLengthShort,
length - 1 - kFujitsuAcStateLengthShort);
break;
default: // Includes ARDB1 short.
return true; // Assume the checksum is valid for other lengths.
}
return checksum == (uint8_t)(sum_complement - sum); // Does it match?
}
// Convert a standard A/C mode into its native mode.
uint8_t IRFujitsuAC::convertMode(const stdAc::opmode_t mode) {
switch (mode) {
case stdAc::opmode_t::kCool:
return kFujitsuAcModeCool;
case stdAc::opmode_t::kHeat:
return kFujitsuAcModeHeat;
case stdAc::opmode_t::kDry:
return kFujitsuAcModeDry;
case stdAc::opmode_t::kFan:
return kFujitsuAcModeFan;
default:
return kFujitsuAcModeAuto;
}
}
// Convert a standard A/C Fan speed into its native fan speed.
uint8_t IRFujitsuAC::convertFan(stdAc::fanspeed_t speed) {
switch (speed) {
case stdAc::fanspeed_t::kMin:
return kFujitsuAcFanQuiet;
case stdAc::fanspeed_t::kLow:
return kFujitsuAcFanLow;
case stdAc::fanspeed_t::kMedium:
return kFujitsuAcFanMed;
case stdAc::fanspeed_t::kHigh:
case stdAc::fanspeed_t::kMax:
return kFujitsuAcFanHigh;
default:
return kFujitsuAcFanAuto;
}
}
// Convert the internal state into a human readable string.
#ifdef ARDUINO
String IRFujitsuAC::toString() {
String result = "";
#else
std::string IRFujitsuAC::toString() {
std::string result = "";
#endif // ARDUINO
result += F("Power: ");
if (getPower())
result += F("On");
else
result += F("Off");
result += F(", Mode: ");
result += uint64ToString(getMode());
switch (getMode()) {
case kFujitsuAcModeAuto:
result += F(" (AUTO)");
break;
case kFujitsuAcModeCool:
result += F(" (COOL)");
break;
case kFujitsuAcModeHeat:
result += F(" (HEAT)");
break;
case kFujitsuAcModeDry:
result += F(" (DRY)");
break;
case kFujitsuAcModeFan:
result += F(" (FAN)");
break;
default:
result += F(" (UNKNOWN)");
}
result += F(", Temp: ");
result += uint64ToString(getTemp());
result += F("C, Fan: ");
result += uint64ToString(getFanSpeed());
switch (getFanSpeed()) {
case kFujitsuAcFanAuto:
result += F(" (AUTO)");
break;
case kFujitsuAcFanHigh:
result += F(" (HIGH)");
break;
case kFujitsuAcFanMed:
result += F(" (MED)");
break;
case kFujitsuAcFanLow:
result += F(" (LOW)");
break;
case kFujitsuAcFanQuiet:
result += F(" (QUIET)");
break;
}
result += F(", Swing: ");
switch (getSwing()) {
case kFujitsuAcSwingOff:
result += F("Off");
break;
case kFujitsuAcSwingVert:
result += F("Vert");
break;
case kFujitsuAcSwingHoriz:
result += F("Horiz");
break;
case kFujitsuAcSwingBoth:
result += F("Vert + Horiz");
break;
default:
result += F("UNKNOWN");
}
result += F(", Command: ");
switch (getCmd()) {
case kFujitsuAcCmdStepHoriz:
result += F("Step vane horizontally");
break;
case kFujitsuAcCmdStepVert:
result += F("Step vane vertically");
break;
default:
result += F("N/A");
}
return result;
}
#if DECODE_FUJITSU_AC
// Decode a Fujitsu AC IR message if possible.
// Places successful decode information in the results pointer.
// Args:
// results: Ptr to the data to decode and where to store the decode result.
// nbits: The number of data bits to expect. Typically kFujitsuAcBits.
// strict: Flag to indicate if we strictly adhere to the specification.
// Returns:
// boolean: True if it can decode it, false if it can't.
//
// Status: ALPHA / Untested.
//
// Ref:
//
bool IRrecv::decodeFujitsuAC(decode_results* results, uint16_t nbits,
bool strict) {
uint16_t offset = kStartOffset;
uint16_t dataBitsSoFar = 0;
// Have we got enough data to successfully decode?
if (results->rawlen < (2 * kFujitsuAcMinBits) + kHeader + kFooter - 1)
return false; // Can't possibly be a valid message.
// Compliance
if (strict) {
switch (nbits) {
case kFujitsuAcBits:
case kFujitsuAcBits - 8:
case kFujitsuAcMinBits:
case kFujitsuAcMinBits + 8:
break;
default:
return false; // Must be called with the correct nr. of bits.
}
}
// Header
if (!matchMark(results->rawbuf[offset++], kFujitsuAcHdrMark)) return false;
if (!matchSpace(results->rawbuf[offset++], kFujitsuAcHdrSpace)) return false;
// Data (Fixed signature)
match_result_t data_result =
matchData(&(results->rawbuf[offset]), kFujitsuAcMinBits - 8,
kFujitsuAcBitMark, kFujitsuAcOneSpace, kFujitsuAcBitMark,
kFujitsuAcZeroSpace, kTolerance, kMarkExcess, false);
if (data_result.success == false) return false; // Fail
if (data_result.data != 0x1010006314) return false; // Signature failed.
dataBitsSoFar += kFujitsuAcMinBits - 8;
offset += data_result.used;
results->state[0] = 0x14;
results->state[1] = 0x63;
results->state[2] = 0x00;
results->state[3] = 0x10;
results->state[4] = 0x10;
// Keep reading bytes until we either run out of message or state to fill.
for (uint16_t i = 5;
offset <= results->rawlen - 16 && i < kFujitsuAcStateLength;
i++, dataBitsSoFar += 8, offset += data_result.used) {
data_result = matchData(
&(results->rawbuf[offset]), 8, kFujitsuAcBitMark, kFujitsuAcOneSpace,
kFujitsuAcBitMark, kFujitsuAcZeroSpace, kTolerance, kMarkExcess, false);
if (data_result.success == false) break; // Fail
results->state[i] = data_result.data;
}
// Footer
if (offset > results->rawlen ||
!matchMark(results->rawbuf[offset++], kFujitsuAcBitMark))
return false;
// The space is optional if we are out of capture.
if (offset < results->rawlen &&
!matchAtLeast(results->rawbuf[offset], kFujitsuAcMinGap))
return false;
// Compliance
if (strict) {
if (dataBitsSoFar != nbits) return false;
}
results->decode_type = FUJITSU_AC;
results->bits = dataBitsSoFar;
// Compliance
switch (dataBitsSoFar) {
case kFujitsuAcMinBits:
// Check if this values indicate that this should have been a long state
// message.
if (results->state[5] == 0xFC) return false;
return true; // Success
case kFujitsuAcMinBits + 8:
// Check if this values indicate that this should have been a long state
// message.
if (results->state[5] == 0xFE) return false;
// The last byte needs to be the inverse of the penultimate byte.
if (results->state[5] != (uint8_t)~results->state[6]) return false;
return true; // Success
case kFujitsuAcBits - 8:
// Long messages of this size require this byte be correct.
if (results->state[5] != 0xFC) return false;
break;
case kFujitsuAcBits:
// Long messages of this size require this byte be correct.
if (results->state[5] != 0xFE) return false;
break;
default:
return false; // Unexpected size.
}
if (!IRFujitsuAC::validChecksum(results->state, dataBitsSoFar / 8))
return false;
// Success
return true; // All good.
}
#endif // DECODE_FUJITSU_AC

View File

@ -1,17 +0,0 @@
// Copyright 2017 David Conran
#ifndef IR_LG_H_
#define IR_LG_H_
// L GGGG
// L G
// L G GG
// L G G
// LLLLL GGG
#define __STDC_LIMIT_MACROS
#include <stdint.h>
uint8_t calcLGChecksum(uint16_t data);
#endif // IR_LG_H_

View File

@ -1,267 +0,0 @@
// Copyright 2009 Ken Shirriff
// Copyright 2017 David Conran
#include <algorithm>
#include "IRrecv.h"
#include "IRsend.h"
#include "IRutils.h"
// SSSS H H AAA RRRR PPPP
// S H H A A R R P P
// SSS HHHHH AAAAA RRRR PPPP
// S H H A A R R P
// SSSS H H A A R R P
// Equipment it seems compatible with:
// * Sharp LC-52D62U
// * <Add models (devices & remotes) you've gotten it working with here>
//
// Constants
// period time = 1/38000Hz = 26.316 microseconds.
// Ref:
// GlobalCache's IR Control Tower data.
// http://www.sbprojects.com/knowledge/ir/sharp.php
const uint16_t kSharpTick = 26;
const uint16_t kSharpBitMarkTicks = 10;
const uint16_t kSharpBitMark = kSharpBitMarkTicks * kSharpTick;
const uint16_t kSharpOneSpaceTicks = 70;
const uint16_t kSharpOneSpace = kSharpOneSpaceTicks * kSharpTick;
const uint16_t kSharpZeroSpaceTicks = 30;
const uint16_t kSharpZeroSpace = kSharpZeroSpaceTicks * kSharpTick;
const uint16_t kSharpGapTicks = 1677;
const uint16_t kSharpGap = kSharpGapTicks * kSharpTick;
// Address(5) + Command(8) + Expansion(1) + Check(1)
const uint64_t kSharpToggleMask =
((uint64_t)1 << (kSharpBits - kSharpAddressBits)) - 1;
const uint64_t kSharpAddressMask = ((uint64_t)1 << kSharpAddressBits) - 1;
const uint64_t kSharpCommandMask = ((uint64_t)1 << kSharpCommandBits) - 1;
#if (SEND_SHARP || SEND_DENON)
// Send a (raw) Sharp message
//
// Args:
// data: Contents of the message to be sent.
// nbits: Nr. of bits of data to be sent. Typically kSharpBits.
// repeat: Nr. of additional times the message is to be sent.
//
// Status: BETA / Previously working fine.
//
// Notes:
// This procedure handles the inversion of bits required per protocol.
// The protocol spec says to send the LSB first, but legacy code & usage
// has us sending the MSB first. Grrrr. Normal invocation of encodeSharp()
// handles this for you, assuming you are using the correct/standard values.
// e.g. sendSharpRaw(encodeSharp(address, command));
//
// Ref:
// http://www.sbprojects.com/knowledge/ir/sharp.htm
// http://lirc.sourceforge.net/remotes/sharp/GA538WJSA
// http://www.mwftr.com/ucF08/LEC14%20PIC%20IR.pdf
// http://www.hifi-remote.com/johnsfine/DecodeIR.html#Sharp
void IRsend::sendSharpRaw(uint64_t data, uint16_t nbits, uint16_t repeat) {
for (uint16_t i = 0; i <= repeat; i++) {
// Protocol demands that the data be sent twice; once normally,
// then with all but the address bits inverted.
// Note: Previously this used to be performed 3 times (normal, inverted,
// normal), however all data points to that being incorrect.
for (uint8_t n = 0; n < 2; n++) {
sendGeneric(0, 0, // No Header
kSharpBitMark, kSharpOneSpace, kSharpBitMark, kSharpZeroSpace,
kSharpBitMark, kSharpGap, data, nbits, 38, true,
0, // Repeats are handled already.
33);
// Invert the data per protocol. This is always called twice, so it's
// retured to original upon exiting the inner loop.
data ^= kSharpToggleMask;
}
}
}
// Encode a (raw) Sharp message from it's components.
//
// Args:
// address: The value of the address to be sent.
// command: The value of the address to be sent. (8 bits)
// expansion: The value of the expansion bit to use. (0 or 1, typically 1)
// check: The value of the check bit to use. (0 or 1, typically 0)
// MSBfirst: Flag indicating MSB first or LSB first order. (Default: false)
// Returns:
// An uint32_t containing the raw Sharp message for sendSharpRaw().
//
// Status: BETA / Should work okay.
//
// Notes:
// Assumes the standard Sharp bit sizes.
// Historically sendSharp() sends address & command in
// MSB first order. This is actually incorrect. It should be sent in LSB
// order. The behaviour of sendSharp() hasn't been changed to maintain
// backward compatibility.
//
// Ref:
// http://www.sbprojects.com/knowledge/ir/sharp.htm
// http://lirc.sourceforge.net/remotes/sharp/GA538WJSA
// http://www.mwftr.com/ucF08/LEC14%20PIC%20IR.pdf
uint32_t IRsend::encodeSharp(uint16_t address, uint16_t command,
uint16_t expansion, uint16_t check,
bool MSBfirst) {
// Mask any unexpected bits.
address &= ((1 << kSharpAddressBits) - 1);
command &= ((1 << kSharpCommandBits) - 1);
expansion &= 1;
check &= 1;
if (!MSBfirst) { // Correct bit order if needed.
address = reverseBits(address, kSharpAddressBits);
command = reverseBits(command, kSharpCommandBits);
}
// Concatinate all the bits.
return (address << (kSharpCommandBits + 2)) | (command << 2) |
(expansion << 1) | check;
}
// Send a Sharp message
//
// Args:
// address: Address value to be sent.
// command: Command value to be sent.
// nbits: Nr. of bits of data to be sent. Typically kSharpBits.
// repeat: Nr. of additional times the message is to be sent.
//
// Status: DEPRICATED / Previously working fine.
//
// Notes:
// This procedure has a non-standard invocation style compared to similar
// sendProtocol() routines. This is due to legacy, compatibility, & historic
// reasons. Normally the calling syntax version is like sendSharpRaw().
// This procedure transmits the address & command in MSB first order, which is
// incorrect. This behaviour is left as-is to maintain backward
// compatibility with legacy code.
// In short, you should use sendSharpRaw(), encodeSharp(), and the correct
// values of address & command instead of using this, & the wrong values.
//
// Ref:
// http://www.sbprojects.com/knowledge/ir/sharp.htm
// http://lirc.sourceforge.net/remotes/sharp/GA538WJSA
// http://www.mwftr.com/ucF08/LEC14%20PIC%20IR.pdf
void IRsend::sendSharp(uint16_t address, uint16_t command, uint16_t nbits,
uint16_t repeat) {
sendSharpRaw(encodeSharp(address, command, 1, 0, true), nbits, repeat);
}
#endif // (SEND_SHARP || SEND_DENON)
#if (DECODE_SHARP || DECODE_DENON)
// Decode the supplied Sharp message.
//
// Args:
// results: Ptr to the data to decode and where to store the decode result.
// nbits: Nr. of data bits to expect. Typically kSharpBits.
// strict: Flag indicating if we should perform strict matching.
// expansion: Should we expect the expansion bit to be set. Default is true.
// Returns:
// boolean: True if it can decode it, false if it can't.
//
// Status: STABLE / Working fine.
//
// Note:
// This procedure returns a value suitable for use in sendSharpRaw().
// TODO(crankyoldgit): Need to ensure capture of the inverted message as it can
// be missed due to the interrupt timeout used to detect an end of message.
// Several compliance checks are disabled until that is resolved.
// Ref:
// http://www.sbprojects.com/knowledge/ir/sharp.php
// http://www.mwftr.com/ucF08/LEC14%20PIC%20IR.pdf
// http://www.hifi-remote.com/johnsfine/DecodeIR.html#Sharp
bool IRrecv::decodeSharp(decode_results *results, uint16_t nbits, bool strict,
bool expansion) {
if (results->rawlen < 2 * nbits + kFooter - 1)
return false; // Not enough entries to be a Sharp message.
// Compliance
if (strict) {
if (nbits != kSharpBits) return false; // Request is out of spec.
// DISABLED - See TODO
#ifdef UNIT_TEST
// An in spec message has the data sent normally, then inverted. So we
// expect twice as many entries than to just get the results.
if (results->rawlen < 2 * (2 * nbits + kFooter)) return false;
#endif
}
uint64_t data = 0;
uint16_t offset = kStartOffset;
// No header
// But try to auto-calibrate off the initial mark signal.
if (!matchMark(results->rawbuf[offset], kSharpBitMark, 35)) return false;
// Calculate how long the common tick time is based on the header mark.
uint32_t tick = results->rawbuf[offset] * kRawTick / kSharpBitMarkTicks;
// Data
for (uint16_t i = 0; i < nbits; i++, offset++) {
// Use a higher tolerance value for kSharpBitMark as it is quite small.
if (!matchMark(results->rawbuf[offset++], kSharpBitMarkTicks * tick, 35))
return false;
if (matchSpace(results->rawbuf[offset], kSharpOneSpaceTicks * tick))
data = (data << 1) | 1; // 1
else if (matchSpace(results->rawbuf[offset], kSharpZeroSpaceTicks * tick))
data <<= 1; // 0
else
return false;
}
// Footer
if (!match(results->rawbuf[offset++], kSharpBitMarkTicks * tick))
return false;
if (offset < results->rawlen &&
!matchAtLeast(results->rawbuf[offset], kSharpGapTicks * tick))
return false;
// Compliance
if (strict) {
// Check the state of the expansion bit is what we expect.
if ((data & 0b10) >> 1 != expansion) return false;
// The check bit should be cleared in a normal message.
if (data & 0b1) return false;
// DISABLED - See TODO
#ifdef UNIT_TEST
// Grab the second copy of the data (i.e. inverted)
// Header
// i.e. The inter-data/command repeat gap.
if (!matchSpace(results->rawbuf[offset++], kSharpGapTicks * tick))
return false;
// Data
uint64_t second_data = 0;
for (uint16_t i = 0; i < nbits; i++, offset++) {
// Use a higher tolerance value for kSharpBitMark as it is quite small.
if (!matchMark(results->rawbuf[offset++], kSharpBitMarkTicks * tick, 35))
return false;
if (matchSpace(results->rawbuf[offset], kSharpOneSpaceTicks * tick))
second_data = (second_data << 1) | 1; // 1
else if (matchSpace(results->rawbuf[offset], kSharpZeroSpaceTicks * tick))
second_data <<= 1; // 0
else
return false;
}
// Footer
if (!match(results->rawbuf[offset++], kSharpBitMarkTicks * tick))
return false;
if (offset < results->rawlen &&
!matchAtLeast(results->rawbuf[offset], kSharpGapTicks * tick))
return false;
// Check that second_data has been inverted correctly.
if (data != (second_data ^ kSharpToggleMask)) return false;
#endif // UNIT_TEST
}
// Success
results->decode_type = SHARP;
results->bits = nbits;
results->value = data;
// Address & command are actually transmitted in LSB first order.
results->address = reverseBits(data, nbits) & kSharpAddressMask;
results->command =
reverseBits((data >> 2) & kSharpCommandMask, kSharpCommandBits);
return true;
}
#endif // (DECODE_SHARP || DECODE_DENON)

View File

@ -1,162 +0,0 @@
// Copyright 2017 stufisher
#include "ir_Trotec.h"
#include <algorithm>
#include "IRremoteESP8266.h"
#include "IRutils.h"
// Constants
const uint16_t kTrotecHdrMark = 5952;
const uint16_t kTrotecHdrSpace = 7364;
const uint16_t kTrotecOneMark = 592;
const uint16_t kTrotecOneSpace = 1560;
const uint16_t kTrotecZeroMark = 592;
const uint16_t kTrotecZeroSpace = 592;
const uint16_t kTrotecGap = 6184;
const uint16_t kTrotecGapEnd = 1500; // made up value
#if SEND_TROTEC
void IRsend::sendTrotec(unsigned char data[], uint16_t nbytes,
uint16_t repeat) {
if (nbytes < kTrotecStateLength) return;
for (uint16_t r = 0; r <= repeat; r++) {
sendGeneric(kTrotecHdrMark, kTrotecHdrSpace, kTrotecOneMark,
kTrotecOneSpace, kTrotecZeroMark, kTrotecZeroSpace,
kTrotecOneMark, kTrotecGap, data, nbytes, 36, false,
0, // Repeats handled elsewhere
50);
// More footer
enableIROut(36);
mark(kTrotecOneMark);
space(kTrotecGapEnd);
}
}
#endif // SEND_TROTEC
IRTrotecESP::IRTrotecESP(uint16_t pin) : _irsend(pin) { stateReset(); }
void IRTrotecESP::begin() { _irsend.begin(); }
#if SEND_TROTEC
void IRTrotecESP::send(const uint16_t repeat) {
checksum();
_irsend.sendTrotec(remote_state, kTrotecStateLength, repeat);
}
#endif // SEND_TROTEC
void IRTrotecESP::checksum() {
uint8_t sum = 0;
for (uint8_t i = 2; i < 8; i++) sum += remote_state[i];
remote_state[8] = sum & 0xFF;
}
void IRTrotecESP::stateReset() {
for (uint8_t i = 2; i < kTrotecStateLength; i++) remote_state[i] = 0x0;
remote_state[0] = kTrotecIntro1;
remote_state[1] = kTrotecIntro2;
setPower(false);
setTemp(kTrotecDefTemp);
setSpeed(kTrotecFanMed);
setMode(kTrotecAuto);
}
uint8_t* IRTrotecESP::getRaw() {
checksum();
return remote_state;
}
void IRTrotecESP::setPower(const bool on) {
if (on)
remote_state[2] |= kTrotecPowerBit;
else
remote_state[2] &= ~kTrotecPowerBit;
}
bool IRTrotecESP::getPower() { return remote_state[2] & kTrotecPowerBit; }
void IRTrotecESP::setSpeed(const uint8_t fan) {
uint8_t speed = std::min(fan, kTrotecFanHigh);
remote_state[2] = (remote_state[2] & 0b11001111) | (speed << 4);
}
uint8_t IRTrotecESP::getSpeed() { return (remote_state[2] & 0b00110000) >> 4; }
void IRTrotecESP::setMode(const uint8_t mode) {
switch (mode) {
case kTrotecAuto:
case kTrotecCool:
case kTrotecDry:
case kTrotecFan:
remote_state[2] = (remote_state[2] & 0b11111100) | mode;
return;
default:
this->setMode(kTrotecAuto);
}
}
uint8_t IRTrotecESP::getMode() { return remote_state[2] & 0b00000011; }
void IRTrotecESP::setTemp(const uint8_t celsius) {
uint8_t temp = std::max(celsius, kTrotecMinTemp);
temp = std::min(temp, kTrotecMaxTemp);
remote_state[3] = (remote_state[3] & 0x80) | (temp - kTrotecMinTemp);
}
uint8_t IRTrotecESP::getTemp() {
return (remote_state[3] & 0b01111111) + kTrotecMinTemp;
}
void IRTrotecESP::setSleep(bool sleep) {
if (sleep)
remote_state[3] |= kTrotecSleepBit;
else
remote_state[3] &= ~kTrotecSleepBit;
}
bool IRTrotecESP::getSleep(void) { return remote_state[3] & kTrotecSleepBit; }
void IRTrotecESP::setTimer(const uint8_t timer) {
if (timer)
remote_state[5] |= kTrotecTimerBit;
else
remote_state[5] &= ~kTrotecTimerBit;
remote_state[6] = (timer > kTrotecMaxTimer) ? kTrotecMaxTimer : timer;
}
uint8_t IRTrotecESP::getTimer() { return remote_state[6]; }
// Convert a standard A/C mode into its native mode.
uint8_t IRTrotecESP::convertMode(const stdAc::opmode_t mode) {
switch (mode) {
case stdAc::opmode_t::kCool:
return kTrotecCool;
case stdAc::opmode_t::kDry:
return kTrotecDry;
case stdAc::opmode_t::kFan:
return kTrotecFan;
// Note: No Heat mode.
default:
return kTrotecAuto;
}
}
// Convert a standard A/C Fan speed into its native fan speed.
uint8_t IRTrotecESP::convertFan(const stdAc::fanspeed_t speed) {
switch (speed) {
case stdAc::fanspeed_t::kMin:
case stdAc::fanspeed_t::kLow:
return kTrotecFanLow;
case stdAc::fanspeed_t::kMedium:
return kTrotecFanMed;
case stdAc::fanspeed_t::kHigh:
case stdAc::fanspeed_t::kMax:
return kTrotecFanHigh;
default:
return kTrotecFanMed;
}
}

View File

@ -1,561 +0,0 @@
// Copyright 2017 David Conran
#include "IRrecv_test.h"
#include "IRrecv.h"
#include "IRremoteESP8266.h"
#include "IRsend.h"
#include "IRsend_test.h"
#include "gtest/gtest.h"
// Tests for the IRrecv object.
TEST(TestIRrecv, DefaultBufferSize) {
IRrecv irrecv_default(1);
EXPECT_EQ(kRawBuf, irrecv_default.getBufSize());
}
TEST(TestIRrecv, LargeBufferSize) {
IRrecv irrecv_large(3, 1024);
EXPECT_EQ(1024, irrecv_large.getBufSize());
}
TEST(TestIRrecv, SmallBufferSize) {
IRrecv irrecv_small(4, 80);
EXPECT_EQ(80, irrecv_small.getBufSize());
}
TEST(TestIRrecv, MediumBufferSize) {
IRrecv irrecv_medium(4, 512);
EXPECT_EQ(512, irrecv_medium.getBufSize());
}
TEST(TestIRrecv, IRrecvDestructor) {
IRrecv *irrecv_ptr = new IRrecv(1);
EXPECT_EQ(kRawBuf, irrecv_ptr->getBufSize());
delete irrecv_ptr;
irrecv_ptr = new IRrecv(1, 1234);
EXPECT_EQ(1234, irrecv_ptr->getBufSize());
delete irrecv_ptr;
irrecv_ptr = new IRrecv(1, 123);
EXPECT_EQ(123, irrecv_ptr->getBufSize());
delete irrecv_ptr;
}
// Tests for copyIrParams()
TEST(TestCopyIrParams, CopyEmpty) {
irparams_t src;
irparams_t dst;
uint16_t test_size = 1234;
src.bufsize = test_size;
src.rawlen = 0;
src.rawbuf = new uint16_t[test_size];
src.overflow = false;
dst.bufsize = 4567;
dst.rawlen = 123;
dst.rawbuf = new uint16_t[test_size];
dst.overflow = true;
// Confirm we are looking at different memory for the buffers.
ASSERT_NE(src.rawbuf, dst.rawbuf);
IRrecv irrecv(4);
irrecv.copyIrParams(&src, &dst);
ASSERT_EQ(src.bufsize, dst.bufsize);
ASSERT_EQ(src.rawlen, dst.rawlen);
ASSERT_NE(src.rawbuf, dst.rawbuf); // Pointers, not content.
ASSERT_EQ(src.overflow, dst.overflow);
// Contents of the buffers needs to match.
EXPECT_EQ(0, memcmp(src.rawbuf, dst.rawbuf, src.bufsize * sizeof(uint16_t)));
}
TEST(TestCopyIrParams, CopyNonEmpty) {
irparams_t src;
irparams_t dst;
uint16_t test_size = 1234;
src.bufsize = test_size;
src.rawlen = 67;
src.rawbuf = new uint16_t[test_size];
src.rawbuf[0] = 0xF00D;
src.rawbuf[1] = 0xBEEF;
src.rawbuf[test_size - 1] = 0xDEAD;
src.overflow = true;
dst.bufsize = 0;
dst.rawlen = 0;
dst.rawbuf = new uint16_t[test_size];
dst.overflow = false;
// Confirm we are looking at different memory for the buffers.
ASSERT_NE(src.rawbuf, dst.rawbuf);
// and that they differ before we test.
EXPECT_NE(0, memcmp(src.rawbuf, dst.rawbuf, src.bufsize * sizeof(uint16_t)));
IRrecv irrecv(4);
irrecv.copyIrParams(&src, &dst);
ASSERT_EQ(src.bufsize, dst.bufsize);
EXPECT_EQ(test_size, dst.bufsize);
ASSERT_EQ(src.rawlen, dst.rawlen);
EXPECT_EQ(67, dst.rawlen);
ASSERT_EQ(src.overflow, dst.overflow);
EXPECT_TRUE(dst.overflow);
ASSERT_NE(src.rawbuf, dst.rawbuf); // Pointers, not content.
// Contents of the buffers needs to match.
EXPECT_EQ(0, memcmp(src.rawbuf, dst.rawbuf, src.bufsize * sizeof(uint16_t)));
// Check the canary values.
EXPECT_EQ(0xF00D, dst.rawbuf[0]);
EXPECT_EQ(0xBEEF, dst.rawbuf[1]);
EXPECT_EQ(0xDEAD, dst.rawbuf[test_size - 1]);
}
// Tests for decode().
// Test decode of a NEC message.
TEST(TestDecode, DecodeNEC) {
IRsendTest irsend(0);
IRrecv irrecv(1);
irsend.begin();
irsend.reset();
irsend.sendNEC(0x807F40BF);
irsend.makeDecodeResult();
ASSERT_TRUE(irrecv.decode(&irsend.capture));
EXPECT_EQ(NEC, irsend.capture.decode_type);
EXPECT_EQ(kNECBits, irsend.capture.bits);
EXPECT_EQ(0x807F40BF, irsend.capture.value);
}
// Test decode of a JVC message.
TEST(TestDecode, DecodeJVC) {
IRsendTest irsend(0);
IRrecv irrecv(1);
irsend.begin();
irsend.reset();
irsend.sendJVC(0xC2B8);
irsend.makeDecodeResult();
ASSERT_TRUE(irrecv.decode(&irsend.capture));
EXPECT_EQ(JVC, irsend.capture.decode_type);
EXPECT_EQ(kJvcBits, irsend.capture.bits);
EXPECT_EQ(0xC2B8, irsend.capture.value);
}
// Test decode of a LG message.
TEST(TestDecode, DecodeLG) {
IRsendTest irsend(0);
IRrecv irrecv(1);
irsend.begin();
irsend.reset();
irsend.sendLG(0x4B4AE51);
irsend.makeDecodeResult();
ASSERT_TRUE(irrecv.decode(&irsend.capture));
EXPECT_EQ(LG, irsend.capture.decode_type);
EXPECT_EQ(kLgBits, irsend.capture.bits);
EXPECT_EQ(0x4B4AE51, irsend.capture.value);
irsend.reset();
irsend.sendLG(0xB4B4AE51, kLg32Bits);
irsend.makeDecodeResult();
ASSERT_TRUE(irrecv.decode(&irsend.capture));
EXPECT_EQ(LG, irsend.capture.decode_type);
EXPECT_EQ(kLg32Bits, irsend.capture.bits);
EXPECT_EQ(0xB4B4AE51, irsend.capture.value);
}
// Test decode of a Panasonic message.
TEST(TestDecode, DecodePanasonic) {
IRsendTest irsend(0);
IRrecv irrecv(1);
irsend.begin();
irsend.reset();
irsend.sendPanasonic64(0x40040190ED7C);
irsend.makeDecodeResult();
ASSERT_TRUE(irrecv.decodePanasonic(&irsend.capture, kPanasonicBits, true));
EXPECT_EQ(PANASONIC, irsend.capture.decode_type);
EXPECT_EQ(kPanasonicBits, irsend.capture.bits);
EXPECT_EQ(0x40040190ED7C, irsend.capture.value);
}
// Test decode of a Samsun message.
TEST(TestDecode, DecodeSamsung) {
IRsendTest irsend(0);
IRrecv irrecv(1);
irsend.begin();
irsend.reset();
irsend.sendSAMSUNG(0xE0E09966);
irsend.makeDecodeResult();
ASSERT_TRUE(irrecv.decode(&irsend.capture));
EXPECT_EQ(SAMSUNG, irsend.capture.decode_type);
EXPECT_EQ(kSamsungBits, irsend.capture.bits);
EXPECT_EQ(0xE0E09966, irsend.capture.value);
}
// Test decode of a Sherwood message.
TEST(TestDecode, DecodeSherwood) {
IRsendTest irsend(0);
IRrecv irrecv(1);
irsend.begin();
irsend.reset();
irsend.sendSherwood(0x807F40BF);
irsend.makeDecodeResult();
ASSERT_TRUE(irrecv.decode(&irsend.capture));
// Sherwood codes are really NEC codes.
EXPECT_EQ(NEC, irsend.capture.decode_type);
EXPECT_EQ(kNECBits, irsend.capture.bits);
EXPECT_EQ(0x807F40BF, irsend.capture.value);
}
// Test decode of a Whynter message.
TEST(TestDecode, DecodeWhynter) {
IRsendTest irsend(0);
IRrecv irrecv(1);
irsend.begin();
irsend.reset();
irsend.sendWhynter(0x87654321);
irsend.makeDecodeResult();
ASSERT_TRUE(irrecv.decode(&irsend.capture));
EXPECT_EQ(WHYNTER, irsend.capture.decode_type);
EXPECT_EQ(kWhynterBits, irsend.capture.bits);
EXPECT_EQ(0x87654321, irsend.capture.value);
}
// Test decode of Sony messages.
TEST(TestDecode, DecodeSony) {
IRsendTest irsend(0);
IRrecv irrecv(1);
irsend.begin();
// Synthesised Normal Sony 20-bit message.
irsend.reset();
irsend.sendSony(irsend.encodeSony(kSony20Bits, 0x1, 0x1, 0x1));
irsend.makeDecodeResult();
ASSERT_TRUE(irrecv.decode(&irsend.capture));
EXPECT_EQ(SONY, irsend.capture.decode_type);
EXPECT_EQ(kSony20Bits, irsend.capture.bits);
EXPECT_EQ(0x81080, irsend.capture.value);
// Synthesised Normal Sony 15-bit message.
irsend.reset();
irsend.sendSony(irsend.encodeSony(kSony15Bits, 21, 1), kSony15Bits);
irsend.makeDecodeResult();
ASSERT_TRUE(irrecv.decode(&irsend.capture));
EXPECT_EQ(SONY, irsend.capture.decode_type);
EXPECT_EQ(kSony15Bits, irsend.capture.bits);
EXPECT_EQ(0x5480, irsend.capture.value);
// Synthesised Normal Sony 12-bit message.
irsend.reset();
irsend.sendSony(irsend.encodeSony(kSony12Bits, 21, 1), kSony12Bits);
irsend.makeDecodeResult();
ASSERT_TRUE(irrecv.decode(&irsend.capture));
EXPECT_EQ(SONY, irsend.capture.decode_type);
EXPECT_EQ(kSony12Bits, irsend.capture.bits);
EXPECT_EQ(0xA90, irsend.capture.value);
}
// Test decode of Sharp messages.
TEST(TestDecode, DecodeSharp) {
IRsendTest irsend(0);
IRrecv irrecv(1);
irsend.begin();
irsend.reset();
irsend.sendSharpRaw(0x454A);
irsend.makeDecodeResult();
ASSERT_TRUE(irrecv.decode(&irsend.capture));
EXPECT_EQ(SHARP, irsend.capture.decode_type);
EXPECT_EQ(kSharpBits, irsend.capture.bits);
EXPECT_EQ(0x454A, irsend.capture.value);
}
// Test decode of Sanyo messages.
TEST(TestDecode, DecodeSanyo) {
IRsendTest irsend(0);
IRrecv irrecv(1);
irsend.begin();
irsend.reset();
irsend.sendSanyoLC7461(0x2468DCB56A9);
irsend.makeDecodeResult();
ASSERT_TRUE(irrecv.decode(&irsend.capture));
EXPECT_EQ(SANYO_LC7461, irsend.capture.decode_type);
EXPECT_EQ(kSanyoLC7461Bits, irsend.capture.bits);
EXPECT_EQ(0x2468DCB56A9, irsend.capture.value);
}
// Test decode of RC-MM messages.
TEST(TestDecode, DecodeRCMM) {
IRsendTest irsend(0);
IRrecv irrecv(1);
irsend.begin();
// Normal RCMM 24-bit message.
irsend.reset();
irsend.sendRCMM(0xe0a600);
irsend.makeDecodeResult();
ASSERT_TRUE(irrecv.decode(&irsend.capture));
EXPECT_EQ(RCMM, irsend.capture.decode_type);
EXPECT_EQ(kRCMMBits, irsend.capture.bits);
EXPECT_EQ(0xe0a600, irsend.capture.value);
// Normal RCMM 12-bit message.
irsend.reset();
irsend.sendRCMM(0x600, 12);
irsend.makeDecodeResult();
ASSERT_TRUE(irrecv.decode(&irsend.capture));
EXPECT_EQ(RCMM, irsend.capture.decode_type);
EXPECT_EQ(12, irsend.capture.bits);
EXPECT_EQ(0x600, irsend.capture.value);
// Normal RCMM 32-bit message.
irsend.reset();
irsend.sendRCMM(0x28e0a600, 32);
irsend.makeDecodeResult();
ASSERT_TRUE(irrecv.decode(&irsend.capture));
EXPECT_EQ(RCMM, irsend.capture.decode_type);
EXPECT_EQ(32, irsend.capture.bits);
EXPECT_EQ(0x28e0a600, irsend.capture.value);
}
// Test decode of Mitsubishi messages.
TEST(TestDecode, DecodeMitsubishi) {
IRsendTest irsend(0);
IRrecv irrecv(1);
irsend.begin();
irsend.reset();
irsend.sendMitsubishi(0xC2B8);
irsend.makeDecodeResult();
ASSERT_TRUE(irrecv.decode(&irsend.capture));
EXPECT_EQ(MITSUBISHI, irsend.capture.decode_type);
EXPECT_EQ(kMitsubishiBits, irsend.capture.bits);
EXPECT_EQ(0xC2B8, irsend.capture.value);
}
// Test decode of RC-5/RC-5X messages.
TEST(TestDecode, DecodeRC5) {
IRsendTest irsend(0);
IRrecv irrecv(1);
irsend.begin();
// Normal RC-5 12-bit message.
irsend.reset();
irsend.sendRC5(0x175);
irsend.makeDecodeResult();
ASSERT_TRUE(irrecv.decode(&irsend.capture));
EXPECT_EQ(RC5, irsend.capture.decode_type);
EXPECT_EQ(kRC5Bits, irsend.capture.bits);
EXPECT_EQ(0x175, irsend.capture.value);
// Synthesised Normal RC-5X 13-bit message.
irsend.reset();
irsend.sendRC5(irsend.encodeRC5X(0x02, 0x41, true), kRC5XBits);
irsend.makeDecodeResult();
ASSERT_TRUE(irrecv.decode(&irsend.capture));
EXPECT_EQ(RC5X, irsend.capture.decode_type);
EXPECT_EQ(kRC5XBits, irsend.capture.bits);
EXPECT_EQ(0x1881, irsend.capture.value);
}
// Test decode of RC-6 messages.
TEST(TestDecode, DecodeRC6) {
IRsendTest irsend(0);
IRrecv irrecv(1);
irsend.begin();
// Normal RC-6 Mode 0 (20-bit) message.
irsend.reset();
irsend.sendRC6(0x175);
irsend.makeDecodeResult();
ASSERT_TRUE(irrecv.decode(&irsend.capture));
EXPECT_EQ(RC6, irsend.capture.decode_type);
EXPECT_EQ(kRC6Mode0Bits, irsend.capture.bits);
EXPECT_EQ(0x175, irsend.capture.value);
// Normal RC-6 36-bit message.
irsend.reset();
irsend.sendRC6(0xC800F742A, kRC6_36Bits);
irsend.makeDecodeResult();
ASSERT_TRUE(irrecv.decode(&irsend.capture));
EXPECT_EQ(RC6, irsend.capture.decode_type);
EXPECT_EQ(kRC6_36Bits, irsend.capture.bits);
EXPECT_EQ(0xC800F742A, irsend.capture.value);
}
// Test decode of Dish messages.
TEST(TestDecode, DecodeDish) {
IRsendTest irsend(0);
IRrecv irrecv(1);
irsend.begin();
irsend.reset();
irsend.sendDISH(0x9C00);
irsend.makeDecodeResult();
ASSERT_TRUE(irrecv.decode(&irsend.capture));
EXPECT_EQ(DISH, irsend.capture.decode_type);
EXPECT_EQ(kDishBits, irsend.capture.bits);
EXPECT_EQ(0x9C00, irsend.capture.value);
}
// Test decode of Denon messages.
TEST(TestDecode, DecodeDenon) {
IRsendTest irsend(0);
IRrecv irrecv(1);
irsend.begin();
// Normal Denon 15-bit message. (Sharp)
irsend.reset();
irsend.sendDenon(0x2278);
irsend.makeDecodeResult();
ASSERT_TRUE(irrecv.decode(&irsend.capture));
EXPECT_EQ(DENON, irsend.capture.decode_type);
EXPECT_EQ(DENON_BITS, irsend.capture.bits);
EXPECT_EQ(0x2278, irsend.capture.value);
// Legacy Denon 14-bit message.
irsend.reset();
irsend.sendDenon(0x1278, kDenonLegacyBits);
irsend.makeDecodeResult();
ASSERT_TRUE(irrecv.decode(&irsend.capture));
EXPECT_EQ(DENON, irsend.capture.decode_type);
EXPECT_EQ(DENON_BITS, irsend.capture.bits);
EXPECT_EQ(0x1278, irsend.capture.value);
// Normal Denon 48-bit message. (Panasonic/Kaseikyo)
irsend.reset();
irsend.sendDenon(0x2A4C028D6CE3, DENON_48_BITS);
irsend.makeDecodeResult();
ASSERT_TRUE(irrecv.decode(&irsend.capture));
EXPECT_EQ(DENON, irsend.capture.decode_type);
EXPECT_EQ(DENON_48_BITS, irsend.capture.bits);
EXPECT_EQ(0x2A4C028D6CE3, irsend.capture.value);
}
// Test decode of Coolix messages.
TEST(TestDecode, DecodeCoolix) {
IRsendTest irsend(0);
IRrecv irrecv(1);
irsend.begin();
irsend.reset();
irsend.sendCOOLIX(0x123456);
irsend.makeDecodeResult();
ASSERT_TRUE(irrecv.decode(&irsend.capture));
EXPECT_EQ(COOLIX, irsend.capture.decode_type);
EXPECT_EQ(kCoolixBits, irsend.capture.bits);
EXPECT_EQ(0x123456, irsend.capture.value);
}
// Test decode of Aiwa messages.
TEST(TestDecode, DecodeAiwa) {
IRsendTest irsend(0);
IRrecv irrecv(1);
irsend.begin();
irsend.reset();
irsend.sendAiwaRCT501(0x7F);
irsend.makeDecodeResult();
ASSERT_TRUE(irrecv.decode(&irsend.capture));
EXPECT_EQ(AIWA_RC_T501, irsend.capture.decode_type);
EXPECT_EQ(kAiwaRcT501Bits, irsend.capture.bits);
EXPECT_EQ(0x7F, irsend.capture.value);
}
// Test matchData() on space encoded data.
TEST(TestMatchData, SpaceEncoded) {
IRsendTest irsend(0);
IRrecv irrecv(1);
irsend.begin();
uint16_t space_encoded_raw[11] = {500, 500, 500, 1500, 499, 499,
501, 1501, 499, 1490, 500};
match_result_t result;
irsend.reset();
irsend.sendRaw(space_encoded_raw, 11, 38000);
irsend.makeDecodeResult();
result = irrecv.matchData(irsend.capture.rawbuf + 1, 5, 500, 1500, 500, 500);
ASSERT_TRUE(result.success);
EXPECT_EQ(0b01011, result.data);
EXPECT_EQ(10, result.used);
irsend.reset();
irsend.sendRaw(space_encoded_raw, 11, 38000);
irsend.makeDecodeResult();
result = irrecv.matchData(irsend.capture.rawbuf + 1, 5, 500, 1000, 500, 500);
ASSERT_FALSE(result.success);
}
// Test matchData() on mark encoded data.
TEST(TestMatchData, MarkEncoded) {
IRsendTest irsend(0);
IRrecv irrecv(1);
irsend.begin();
uint16_t mark_encoded_raw[11] = {500, 500, 1500, 500, 499, 499,
1501, 501, 1499, 490, 500};
match_result_t result;
irsend.reset();
irsend.sendRaw(mark_encoded_raw, 11, 38000);
irsend.makeDecodeResult();
// MSBF order.
result = irrecv.matchData(irsend.capture.rawbuf + 1, 5, 1500, 500, 500, 500);
ASSERT_TRUE(result.success);
EXPECT_EQ(0b01011, result.data);
EXPECT_EQ(10, result.used);
// LSBF order.
result = irrecv.matchData(irsend.capture.rawbuf + 1, 5, 1500, 500, 500, 500,
kTolerance, kMarkExcess, false);
ASSERT_TRUE(result.success);
EXPECT_EQ(0b11010, result.data); // Bits reversed of the previous test.
EXPECT_EQ(10, result.used);
irsend.reset();
irsend.sendRaw(mark_encoded_raw, 11, 38000);
irsend.makeDecodeResult();
// MSBF order.
result = irrecv.matchData(irsend.capture.rawbuf + 1, 5, 1000, 500, 500, 500);
ASSERT_FALSE(result.success);
// LSBF order.
result = irrecv.matchData(irsend.capture.rawbuf + 1, 5, 1000, 500, 500, 500,
kTolerance, kMarkExcess, false);
ASSERT_FALSE(result.success);
}
// Test matchData() on "equal total bit time" encoded data.
TEST(TestMatchData, EqualTotalBitTimeEncoded) {
IRsendTest irsend(0);
IRrecv irrecv(1);
irsend.begin();
uint16_t equal_encoded_raw[11] = {500, 1500, 1500, 500, 499, 1499,
1501, 501, 1499, 490, 500};
match_result_t result;
irsend.reset();
irsend.sendRaw(equal_encoded_raw, 11, 38000);
irsend.makeDecodeResult();
result = irrecv.matchData(irsend.capture.rawbuf + 1, 5, 1500, 500, 500, 1500);
ASSERT_TRUE(result.success);
EXPECT_EQ(0b01011, result.data);
EXPECT_EQ(10, result.used);
irsend.reset();
irsend.sendRaw(equal_encoded_raw, 11, 38000);
irsend.makeDecodeResult();
result = irrecv.matchData(irsend.capture.rawbuf + 1, 5, 1000, 500, 500, 1000);
ASSERT_FALSE(result.success);
}
// Test matchData() on arbitrary encoded data.
TEST(TestMatchData, ArbitraryEncoded) {
IRsendTest irsend(0);
IRrecv irrecv(1);
irsend.begin();
uint16_t arbitrary_encoded_raw[11] = {500, 1500, 3000, 1000, 499, 1499,
3001, 1001, 2999, 990, 500};
match_result_t result;
irsend.reset();
irsend.sendRaw(arbitrary_encoded_raw, 11, 38000);
irsend.makeDecodeResult();
result =
irrecv.matchData(irsend.capture.rawbuf + 1, 5, 3000, 1000, 500, 1500);
ASSERT_TRUE(result.success);
EXPECT_EQ(0b01011, result.data);
EXPECT_EQ(10, result.used);
irsend.reset();
irsend.sendRaw(arbitrary_encoded_raw, 11, 38000);
irsend.makeDecodeResult();
result = irrecv.matchData(irsend.capture.rawbuf + 1, 5, 1000, 500, 500, 1000);
ASSERT_FALSE(result.success);
}

View File

@ -1,99 +0,0 @@
// Copyright 2018 David Conran
#include "IRrecv.h"
#include "IRrecv_test.h"
#include "IRsend.h"
#include "IRsend_test.h"
#include "gtest/gtest.h"
// Tests for sendElectraAC().
// Test sending typical data only.
TEST(TestSendElectraAC, SendDataOnly) {
IRsendTest irsend(0);
irsend.begin();
uint8_t data[kElectraAcStateLength] = {0xC3, 0x87, 0xF6, 0x28, 0x60,
0x00, 0x20, 0x00, 0x00, 0x20,
0x00, 0x05, 0x0D};
irsend.sendElectraAC(data);
EXPECT_EQ(
"f38000d50"
"m9166s4470"
"m646s1647m646s1647m646s547m646s547m646s547m646s547m646s1647m646s1647"
"m646s1647m646s1647m646s1647m646s547m646s547m646s547m646s547m646s1647"
"m646s547m646s1647m646s1647m646s547m646s1647m646s1647m646s1647m646s1647"
"m646s547m646s547m646s547m646s1647m646s547m646s1647m646s547m646s547"
"m646s547m646s547m646s547m646s547m646s547m646s1647m646s1647m646s547"
"m646s547m646s547m646s547m646s547m646s547m646s547m646s547m646s547"
"m646s547m646s547m646s547m646s547m646s547m646s1647m646s547m646s547"
"m646s547m646s547m646s547m646s547m646s547m646s547m646s547m646s547"
"m646s547m646s547m646s547m646s547m646s547m646s547m646s547m646s547"
"m646s547m646s547m646s547m646s547m646s547m646s1647m646s547m646s547"
"m646s547m646s547m646s547m646s547m646s547m646s547m646s547m646s547"
"m646s1647m646s547m646s1647m646s547m646s547m646s547m646s547m646s547"
"m646s1647m646s547m646s1647m646s1647m646s547m646s547m646s547m646s547"
"m646s100000",
irsend.outputStr());
}
// Tests for decodeElectraAC().
// Decode normal ElectraAC messages.
TEST(TestDecodeElectraAC, SyntheticDecode) {
IRsendTest irsend(0);
IRrecv irrecv(0);
irsend.begin();
// Synthesised Normal ElectraAC message.
irsend.reset();
uint8_t expectedState[kElectraAcStateLength] = {0xC3, 0x87, 0xF6, 0x28, 0x60,
0x00, 0x20, 0x00, 0x00, 0x20,
0x00, 0x05, 0x0D};
irsend.sendElectraAC(expectedState);
irsend.makeDecodeResult();
EXPECT_TRUE(irrecv.decode(&irsend.capture));
EXPECT_EQ(ELECTRA_AC, irsend.capture.decode_type);
EXPECT_EQ(kElectraAcBits, irsend.capture.bits);
EXPECT_STATE_EQ(expectedState, irsend.capture.state, irsend.capture.bits);
}
// Decode a recorded example
TEST(TestDecodeElectraAC, RealExampleDecode) {
IRsendTest irsend(0);
IRrecv irrecv(0);
irsend.begin();
// Real ElectraAC message.
// Ref: https://github.com/markszabo/IRremoteESP8266/issues/527
uint16_t rawData[211] = {
9166, 4470, 642, 1632, 642, 1632, 668, 534, 666, 534, 668, 534,
614, 536, 640, 1636, 640, 1646, 694, 1662, 612, 1628, 642, 1666,
664, 532, 668, 534, 666, 534, 666, 532, 666, 1644, 642, 532,
640, 1634, 668, 1632, 642, 538, 666, 1660, 610, 1666, 664, 1632,
642, 1672, 610, 536, 666, 534, 694, 532, 666, 1636, 614, 538,
666, 1632, 642, 536, 666, 544, 692, 534, 640, 558, 640, 534,
640, 540, 666, 534, 638, 1666, 638, 1636, 640, 550, 666, 534,
640, 540, 666, 534, 640, 540, 666, 536, 638, 540, 666, 536,
638, 550, 664, 536, 638, 540, 664, 536, 638, 540, 666, 534,
638, 1640, 664, 536, 692, 546, 664, 536, 664, 536, 664, 536,
664, 546, 612, 532, 636, 538, 664, 536, 664, 546, 612, 538,
638, 538, 638, 538, 664, 536, 690, 538, 662, 538, 664, 538,
662, 548, 664, 536, 662, 538, 662, 562, 638, 564, 636, 564,
636, 1668, 582, 556, 652, 572, 612, 568, 636, 564, 610, 570,
636, 556, 616, 550, 656, 566, 610, 570, 632, 578, 608, 1640,
662, 562, 642, 1686, 582, 570, 634, 566, 604, 576, 636, 566,
610, 578, 634, 1664, 584, 590, 660, 1636, 610, 1642, 664, 590,
610, 590, 636, 566, 634, 568, 686}; // UNKNOWN 9AD8CDB5
uint8_t expectedState[kElectraAcStateLength] = {0xC3, 0x87, 0xF6, 0x28, 0x60,
0x00, 0x20, 0x00, 0x00, 0x20,
0x00, 0x05, 0x0D};
irsend.reset();
irsend.sendRaw(rawData, 211, 38000);
irsend.makeDecodeResult();
ASSERT_TRUE(irrecv.decode(&irsend.capture));
ASSERT_EQ(ELECTRA_AC, irsend.capture.decode_type);
EXPECT_EQ(kElectraAcBits, irsend.capture.bits);
EXPECT_STATE_EQ(expectedState, irsend.capture.state, irsend.capture.bits);
}

View File

@ -1,560 +0,0 @@
// Copyright 2017 Jonny Graham, David Conran
#include "IRrecv_test.h"
#include "IRsend.h"
#include "IRsend_test.h"
#include "ir_Fujitsu.h"
#include "gtest/gtest.h"
template<typename T, size_t size>
::testing::AssertionResult ArraysMatch(const T (&expected)[size],
const T* actual) {
for (size_t i(0); i < size; ++i) {
if (expected[i] != actual[i]) {
int e = expected[i];
int a = actual[i];
return ::testing::AssertionFailure() << "array[" << i
<< "] (" << std::hex << a << std::dec << ") != expected[" << i
<< "] (" << std::hex << e << std::dec << ")";
}
}
return ::testing::AssertionSuccess();
}
// Tests for Fujitsu A/C methods.
// Test sending typical data only.
TEST(TestIRFujitsuACClass, GetRawDefault) {
IRFujitsuAC fujitsu = IRFujitsuAC(4); // AR-RAH2E
fujitsu.setCmd(kFujitsuAcCmdTurnOn);
fujitsu.setSwing(kFujitsuAcSwingBoth);
fujitsu.setMode(kFujitsuAcModeCool);
fujitsu.setFanSpeed(kFujitsuAcFanHigh);
fujitsu.setTemp(24);
uint8_t expected_arrah2e[16] = {
0x14, 0x63, 0x00, 0x10, 0x10, 0xFE, 0x09, 0x30,
0x81, 0x01, 0x31, 0x00, 0x00, 0x00, 0x20, 0xFD};
EXPECT_TRUE(ArraysMatch(expected_arrah2e, fujitsu.getRaw()));
EXPECT_EQ(kFujitsuAcStateLength, fujitsu.getStateLength());
EXPECT_EQ("Power: On, Mode: 1 (COOL), Temp: 24C, Fan: 1 (HIGH), "
"Swing: Vert + Horiz, Command: N/A", fujitsu.toString());
uint8_t expected_ardb1[15] = {
0x14, 0x63, 0x00, 0x10, 0x10, 0xFC, 0x08, 0x30,
0x81, 0x01, 0x31, 0x00, 0x00, 0x00, 0x1D};
fujitsu.setModel(ARDB1);
EXPECT_TRUE(ArraysMatch(expected_ardb1, fujitsu.getRaw()));
EXPECT_EQ(kFujitsuAcStateLength - 1, fujitsu.getStateLength());
EXPECT_EQ("Power: On, Mode: 1 (COOL), Temp: 24C, Fan: 1 (HIGH), "
"Swing: Vert + Horiz, Command: N/A", fujitsu.toString());
}
TEST(TestIRFujitsuACClass, GetRawTurnOff) {
IRFujitsuAC fujitsu = IRFujitsuAC(4);
fujitsu.setModel(ARRAH2E);
fujitsu.off();
uint8_t expected_arrah2e[7] = {0x14, 0x63, 0x0, 0x10, 0x10, 0x02, 0xFD};
EXPECT_TRUE(ArraysMatch(expected_arrah2e, fujitsu.getRaw()));
EXPECT_EQ(kFujitsuAcStateLengthShort, fujitsu.getStateLength());
EXPECT_EQ("Power: Off, Mode: 1 (COOL), Temp: 24C, Fan: 1 (HIGH), "
"Swing: Vert + Horiz, Command: N/A", fujitsu.toString());
fujitsu.setModel(ARDB1);
uint8_t expected_ardb1[6] = {0x14, 0x63, 0x0, 0x10, 0x10, 0x02};
EXPECT_TRUE(ArraysMatch(expected_ardb1, fujitsu.getRaw()));
EXPECT_EQ(kFujitsuAcStateLengthShort - 1, fujitsu.getStateLength());
EXPECT_EQ("Power: Off, Mode: 1 (COOL), Temp: 24C, Fan: 1 (HIGH), "
"Swing: Vert + Horiz, Command: N/A", fujitsu.toString());
}
TEST(TestIRFujitsuACClass, GetRawStepHoriz) {
IRFujitsuAC fujitsu = IRFujitsuAC(4);
fujitsu.stepHoriz();
uint8_t expected[7] = {0x14, 0x63, 0x0, 0x10, 0x10, 0x79, 0x86};
EXPECT_TRUE(ArraysMatch(expected, fujitsu.getRaw()));
EXPECT_EQ(kFujitsuAcStateLengthShort, fujitsu.getStateLength());
EXPECT_EQ("Power: On, Mode: 1 (COOL), Temp: 24C, Fan: 1 (HIGH), "
"Swing: Vert + Horiz, Command: Step vane horizontally",
fujitsu.toString());
}
TEST(TestIRFujitsuACClass, GetRawStepVert) {
IRFujitsuAC fujitsu = IRFujitsuAC(4);
fujitsu.setModel(ARRAH2E);
fujitsu.stepVert();
uint8_t expected_arrah2e[7] = {0x14, 0x63, 0x0, 0x10, 0x10, 0x6C, 0x93};
EXPECT_TRUE(ArraysMatch(expected_arrah2e, fujitsu.getRaw()));
EXPECT_EQ(kFujitsuAcStateLengthShort, fujitsu.getStateLength());
EXPECT_EQ("Power: On, Mode: 1 (COOL), Temp: 24C, Fan: 1 (HIGH), "
"Swing: Vert + Horiz, Command: Step vane vertically",
fujitsu.toString());
fujitsu.setModel(ARDB1);
fujitsu.stepVert();
uint8_t expected_ardb1[6] = {0x14, 0x63, 0x0, 0x10, 0x10, 0x6C};
EXPECT_TRUE(ArraysMatch(expected_ardb1, fujitsu.getRaw()));
EXPECT_EQ(kFujitsuAcStateLengthShort - 1,
fujitsu.getStateLength());
EXPECT_EQ("Power: On, Mode: 1 (COOL), Temp: 24C, Fan: 1 (HIGH), "
"Swing: Vert + Horiz, Command: Step vane vertically",
fujitsu.toString());
}
TEST(TestIRFujitsuACClass, GetRawWithSwingHoriz) {
IRFujitsuAC fujitsu = IRFujitsuAC(4);
fujitsu.setCmd(kFujitsuAcCmdStayOn);
fujitsu.setSwing(kFujitsuAcSwingHoriz);
fujitsu.setMode(kFujitsuAcModeCool);
fujitsu.setFanSpeed(kFujitsuAcFanQuiet);
fujitsu.setTemp(25);
uint8_t expected[16] = {0x14, 0x63, 0x0, 0x10, 0x10, 0xFE, 0x9, 0x30,
0x90, 0x1, 0x24, 0x0, 0x0, 0x0, 0x20, 0xFB};
EXPECT_TRUE(ArraysMatch(expected, fujitsu.getRaw()));
EXPECT_EQ("Power: On, Mode: 1 (COOL), Temp: 25C, Fan: 4 (QUIET), "
"Swing: Horiz, Command: N/A",
fujitsu.toString());
}
TEST(TestIRFujitsuACClass, GetRawWithFan) {
IRFujitsuAC fujitsu = IRFujitsuAC(4);
fujitsu.setCmd(kFujitsuAcCmdStayOn);
fujitsu.setSwing(kFujitsuAcSwingHoriz);
fujitsu.setMode(kFujitsuAcModeFan);
fujitsu.setFanSpeed(kFujitsuAcFanMed);
fujitsu.setTemp(20); // temp doesn't matter for fan
// but it is sent by the RC anyway
fujitsu.setModel(ARRAH2E);
uint8_t expected_arrah2e[16] = {
0x14, 0x63, 0x0, 0x10, 0x10, 0xFE, 0x9, 0x30,
0x40, 0x3, 0x22, 0x0, 0x0, 0x0, 0x20, 0x4B};
EXPECT_TRUE(ArraysMatch(expected_arrah2e, fujitsu.getRaw()));
EXPECT_EQ(kFujitsuAcStateLength, fujitsu.getStateLength());
EXPECT_EQ("Power: On, Mode: 3 (FAN), Temp: 20C, Fan: 2 (MED), Swing: Horiz, "
"Command: N/A", fujitsu.toString());
fujitsu.setModel(ARDB1);
uint8_t expected_ardb1[15] = {
0x14, 0x63, 0x0, 0x10, 0x10, 0xFC, 0x8, 0x30,
0x40, 0x3, 0x22, 0x0, 0x0, 0x0, 0x6B};
EXPECT_TRUE(ArraysMatch(expected_ardb1, fujitsu.getRaw()));
EXPECT_EQ(kFujitsuAcStateLength - 1, fujitsu.getStateLength());
EXPECT_EQ("Power: On, Mode: 3 (FAN), Temp: 20C, Fan: 2 (MED), Swing: Horiz, "
"Command: N/A", fujitsu.toString());
}
TEST(TestIRFujitsuACClass, SetRaw) {
IRFujitsuAC fujitsu = IRFujitsuAC(0);
EXPECT_EQ(kFujitsuAcStateLength, fujitsu.getStateLength());
uint8_t expected_default_arrah2e[kFujitsuAcStateLength] = {
0x14, 0x63, 0x00, 0x10, 0x10, 0xFE, 0x09, 0x30,
0x81, 0x01, 0x31, 0x00, 0x00, 0x00, 0x20, 0xFD};
EXPECT_TRUE(ArraysMatch(expected_default_arrah2e, fujitsu.getRaw()));
EXPECT_EQ("Power: On, Mode: 1 (COOL), Temp: 24C, Fan: 1 (HIGH), "
"Swing: Vert + Horiz, Command: N/A", fujitsu.toString());
// Now set a new state via setRaw();
// This state is a real state from an AR-DB1 remote.
uint8_t new_state1[kFujitsuAcStateLength - 1] = {
0x14, 0x63, 0x00, 0x10, 0x10, 0xFC, 0x08, 0x30,
0x30, 0x01, 0x00, 0x00, 0x00, 0x00, 0x9F};
fujitsu.setRaw(new_state1, kFujitsuAcStateLength - 1);
EXPECT_EQ(kFujitsuAcStateLength - 1, fujitsu.getStateLength());
EXPECT_TRUE(ArraysMatch(new_state1, fujitsu.getRaw()));
EXPECT_EQ("Power: On, Mode: 1 (COOL), Temp: 19C, Fan: 0 (AUTO), "
"Swing: Off, Command: N/A", fujitsu.toString());
}
TEST(TestSendFujitsuAC, GenerateMessage) {
IRFujitsuAC fujitsu = IRFujitsuAC(4);
IRsendTest irsend(4);
fujitsu.begin();
irsend.begin();
fujitsu.setCmd(kFujitsuAcCmdStayOn);
fujitsu.setSwing(kFujitsuAcSwingBoth);
fujitsu.setMode(kFujitsuAcModeCool);
fujitsu.setFanSpeed(kFujitsuAcFanHigh);
fujitsu.setTemp(24);
EXPECT_EQ(kFujitsuAcFanHigh, fujitsu.getFanSpeed());
EXPECT_EQ(kFujitsuAcModeCool, fujitsu.getMode());
EXPECT_EQ(24, fujitsu.getTemp());
EXPECT_EQ(kFujitsuAcSwingBoth, fujitsu.getSwing());
EXPECT_EQ(kFujitsuAcCmdStayOn, fujitsu.getCmd());
irsend.reset();
irsend.sendFujitsuAC(fujitsu.getRaw(), kFujitsuAcStateLength);
EXPECT_EQ(
"f38000d50"
"m3324s1574"
"m448s390m448s390m448s1182m448s390m448s1182m448s390m448s390m448s390"
"m448s1182m448s1182m448s390m448s390m448s390m448s1182m448s1182m448s390"
"m448s390m448s390m448s390m448s390m448s390m448s390m448s390m448s390"
"m448s390m448s390m448s390m448s390m448s1182m448s390m448s390m448s390"
"m448s390m448s390m448s390m448s390m448s1182m448s390m448s390m448s390"
"m448s390m448s1182m448s1182m448s1182m448s1182m448s1182m448s1182m448s1182"
"m448s1182m448s390m448s390m448s1182m448s390m448s390m448s390m448s390"
"m448s390m448s390m448s390m448s390m448s1182m448s1182m448s390m448s390"
"m448s390m448s390m448s390m448s390m448s390m448s390m448s390m448s1182"
"m448s1182m448s390m448s390m448s390m448s390m448s390m448s390m448s390"
"m448s1182m448s390m448s390m448s390m448s1182m448s1182m448s390m448s390"
"m448s390m448s390m448s390m448s390m448s390m448s390m448s390m448s390"
"m448s390m448s390m448s390m448s390m448s390m448s390m448s390m448s390"
"m448s390m448s390m448s390m448s390m448s390m448s390m448s390m448s390"
"m448s390m448s390m448s390m448s390m448s390m448s1182m448s390m448s390"
"m448s390m448s1182m448s1182m448s1182m448s1182m448s1182m448s1182m448s1182"
"m448s8100",
irsend.outputStr());
}
TEST(TestSendFujitsuAC, GenerateShortMessage) {
IRFujitsuAC fujitsu = IRFujitsuAC(4);
IRsendTest irsend(4);
fujitsu.begin();
irsend.begin();
fujitsu.off();
EXPECT_EQ(kFujitsuAcCmdTurnOff, fujitsu.getCmd());
irsend.reset();
irsend.sendFujitsuAC(fujitsu.getRaw(), kFujitsuAcStateLengthShort);
EXPECT_EQ(
"f38000d50"
"m3324s1574m448s390m448s390m448s1182m448s390m448s1182m448s390m448s390m448"
"s390m448s1182m448s1182m448s390m448s390m448s390m448s1182m448s1182m448s390"
"m448s390m448s390m448s390m448s390m448s390m448s390m448s390m448s390m448s390"
"m448s390m448s390m448s390m448s1182m448s390m448s390m448s390m448s390m448s390"
"m448s390m448s390m448s1182m448s390m448s390m448s390m448s390m448s1182m448s390"
"m448s390m448s390m448s390m448s390m448s390m448s1182m448s390m448s1182m448"
"s1182m448s1182m448s1182m448s1182m448s1182m448s8100",
irsend.outputStr());
}
// Issue #275
TEST(TestSendFujitsuAC, Issue275) {
IRFujitsuAC fujitsu = IRFujitsuAC(4);
IRsendTest irsend(4);
fujitsu.begin();
irsend.begin();
irsend.reset();
fujitsu.setCmd(kFujitsuAcCmdTurnOff);
irsend.sendFujitsuAC(fujitsu.getRaw(), kFujitsuAcStateLengthShort);
EXPECT_EQ(
"f38000d50"
// Header
"m3324s1574"
// 0 0 1 0 1 0 0 0 (0x28)
"m448s390m448s390m448s1182m448s390m448s1182m448s390m448s390m448s390"
// 1 1 0 0 0 1 1 0 (0xC6)
"m448s1182m448s1182m448s390m448s390m448s390m448s1182m448s1182m448s390"
// 0 0 0 0 0 0 0 0 (0x00)
"m448s390m448s390m448s390m448s390m448s390m448s390m448s390m448s390"
// 0 0 0 0 1 0 0 0 (0x08)
"m448s390m448s390m448s390m448s390m448s1182m448s390m448s390m448s390"
// 0 0 0 0 1 0 0 0 (0x08)
"m448s390m448s390m448s390m448s390m448s1182m448s390m448s390m448s390"
// 0 1 0 0 0 0 0 0 (0x40)
"m448s390m448s1182m448s390m448s390m448s390m448s390m448s390m448s390"
// 1 0 1 1 1 1 1 1 (0xBF)
"m448s1182m448s390m448s1182m448s1182m448s1182m448s1182m448s1182m448s1182"
// Footer
"m448s8100", irsend.outputStr());
irsend.reset();
// Per report in Issue #275
uint16_t off[115] = {
3350, 1650,
450, 400, 450, 450, 450, 1250, 450, 400, 450, 1250, 450, 400, 450, 400,
450, 400, 450, 1250, 450, 1250, 450, 400, 450, 400, 450, 400, 450, 1250,
450, 1250, 450, 400, 450, 400, 450, 400, 450, 400, 450, 400, 450, 400,
450, 400, 450, 400, 450, 400, 450, 400, 450, 400, 450, 400, 450, 400,
450, 1250, 450, 400, 450, 400, 450, 400, 450, 400, 450, 400, 450, 400,
450, 400, 450, 1250, 450, 400, 450, 400, 450, 400, 450, 400, 450, 1250,
450, 400, 450, 400, 450, 400, 450, 400, 450, 400, 450, 400, 450, 1250,
450, 400, 450, 1250, 450, 1250, 450, 1250, 450, 1250, 450, 1250,
450, 1250, 450};
irsend.sendRaw(off, 115, 38);
EXPECT_EQ(
"f38000d50"
// Header
"m3350s1650"
// 0 0 1 0 1 0 0 0 (0x28)
"m450s400m450s450m450s1250m450s400m450s1250m450s400m450s400m450s400"
// 1 1 0 0 0 1 1 0 (0xC6)
"m450s1250m450s1250m450s400m450s400m450s400m450s1250m450s1250m450s400"
// 0 0 0 0 0 0 0 0 (0x00)
"m450s400m450s400m450s400m450s400m450s400m450s400m450s400m450s400"
// 0 0 0 0 1 0 0 0 (0x08)
"m450s400m450s400m450s400m450s400m450s1250m450s400m450s400m450s400"
// 0 0 0 0 1 0 0 0 (0x08)
"m450s400m450s400m450s400m450s400m450s1250m450s400m450s400m450s400"
// 0 1 0 0 0 0 0 0 (0x40)
"m450s400m450s1250m450s400m450s400m450s400m450s400m450s400m450s400"
// 1 0 1 1 1 1 1 1 (0xBF)
"m450s1250m450s400m450s1250m450s1250m450s1250m450s1250m450s1250m450s1250"
// Footer
"m450",
irsend.outputStr());
}
TEST(TestDecodeFujitsuAC, SyntheticShortMessages) {
IRsendTest irsend(0);
IRFujitsuAC fujitsu = IRFujitsuAC(0);
IRrecv irrecv(0);
irsend.begin();
irsend.reset();
fujitsu.setModel(ARRAH2E);
fujitsu.setCmd(kFujitsuAcCmdTurnOff);
irsend.sendFujitsuAC(fujitsu.getRaw(), fujitsu.getStateLength());
irsend.makeDecodeResult();
EXPECT_TRUE(irrecv.decode(&irsend.capture));
ASSERT_EQ(FUJITSU_AC, irsend.capture.decode_type);
ASSERT_EQ(kFujitsuAcMinBits + 8, irsend.capture.bits);
uint8_t expected_arrah2e[7] = {0x14, 0x63, 0x0, 0x10, 0x10, 0x02, 0xFD};
EXPECT_TRUE(ArraysMatch(expected_arrah2e, irsend.capture.state));
irsend.reset();
fujitsu.setModel(ARDB1);
fujitsu.setCmd(kFujitsuAcCmdTurnOff);
irsend.sendFujitsuAC(fujitsu.getRaw(), fujitsu.getStateLength());
irsend.makeDecodeResult();
EXPECT_TRUE(irrecv.decode(&irsend.capture));
ASSERT_EQ(FUJITSU_AC, irsend.capture.decode_type);
ASSERT_EQ(kFujitsuAcMinBits, irsend.capture.bits);
uint8_t expected_ardb1[6] = {0x14, 0x63, 0x0, 0x10, 0x10, 0x02};
EXPECT_TRUE(ArraysMatch(expected_ardb1, irsend.capture.state));
}
TEST(TestDecodeFujitsuAC, SyntheticLongMessages) {
IRsendTest irsend(0);
IRFujitsuAC fujitsu = IRFujitsuAC(0);
IRrecv irrecv(0);
irsend.begin();
irsend.reset();
fujitsu.setModel(ARRAH2E);
fujitsu.setCmd(kFujitsuAcCmdStayOn);
fujitsu.setSwing(kFujitsuAcSwingVert);
fujitsu.setMode(kFujitsuAcModeCool);
fujitsu.setFanSpeed(kFujitsuAcFanQuiet);
fujitsu.setTemp(18);
irsend.sendFujitsuAC(fujitsu.getRaw(), fujitsu.getStateLength());
ASSERT_EQ(kFujitsuAcStateLength, fujitsu.getStateLength());
irsend.makeDecodeResult();
EXPECT_TRUE(irrecv.decodeFujitsuAC(&irsend.capture));
ASSERT_EQ(FUJITSU_AC, irsend.capture.decode_type);
ASSERT_EQ(kFujitsuAcBits, irsend.capture.bits);
uint8_t expected_arrah2e[kFujitsuAcStateLength] = {
0x14, 0x63, 0x00, 0x10, 0x10, 0xFE, 0x09, 0x30,
0x20, 0x01, 0x14, 0x00, 0x00, 0x00, 0x20, 0x7B};
EXPECT_TRUE(ArraysMatch(expected_arrah2e, irsend.capture.state));
fujitsu.setRaw(irsend.capture.state, irsend.capture.bits / 8);
EXPECT_EQ(kFujitsuAcStateLength, fujitsu.getStateLength());
EXPECT_EQ("Power: On, Mode: 1 (COOL), Temp: 18C, Fan: 4 (QUIET), "
"Swing: Vert, Command: N/A", fujitsu.toString());
irsend.reset();
fujitsu.setModel(ARDB1);
irsend.sendFujitsuAC(fujitsu.getRaw(), fujitsu.getStateLength());
irsend.makeDecodeResult();
EXPECT_TRUE(irrecv.decode(&irsend.capture));
ASSERT_EQ(FUJITSU_AC, irsend.capture.decode_type);
ASSERT_EQ(kFujitsuAcBits - 8, irsend.capture.bits);
uint8_t expected_ardb1[kFujitsuAcStateLength - 1] = {
0x14, 0x63, 0x00, 0x10, 0x10, 0xFC, 0x08, 0x30,
0x20, 0x01, 0x14, 0x00, 0x00, 0x00, 0x9B};
EXPECT_TRUE(ArraysMatch(expected_ardb1, irsend.capture.state));
fujitsu.setRaw(irsend.capture.state, irsend.capture.bits / 8);
EXPECT_EQ(kFujitsuAcStateLength - 1, fujitsu.getStateLength());
EXPECT_EQ("Power: On, Mode: 1 (COOL), Temp: 18C, Fan: 4 (QUIET), "
"Swing: Vert, Command: N/A", fujitsu.toString());
}
TEST(TestDecodeFujitsuAC, RealShortARDB1OffExample) {
IRsendTest irsend(0);
IRrecv irrecv(0);
IRFujitsuAC fujitsu = IRFujitsuAC(0);
irsend.begin();
irsend.reset();
// "Off" Message recorded from an AR-DB1 remote.
uint16_t rawData[99] = {
3310, 1636, 440, 386, 440, 394, 442, 1210, 442, 390, 414, 1220,
444, 390, 446, 380, 446, 380, 436, 1216, 438, 1214, 438, 388,
438, 386, 438, 396, 410, 1222, 440, 1220, 442, 384, 442, 384,
442, 384, 442, 382, 444, 382, 442, 382, 444, 380, 446, 380,
446, 380, 444, 380, 436, 390, 436, 388, 436, 388, 438, 1214,
438, 386, 438, 388, 438, 386, 440, 386, 440, 384, 442, 384,
442, 384, 442, 1210, 444, 382, 444, 382, 444, 382, 444, 380,
446, 1206, 436, 390, 436, 388, 436, 388, 438, 388, 438, 396,
420, 388, 436};
irsend.sendRaw(rawData, 99, 38000);
irsend.makeDecodeResult();
EXPECT_TRUE(irrecv.decode(&irsend.capture));
ASSERT_EQ(FUJITSU_AC, irsend.capture.decode_type);
ASSERT_EQ(kFujitsuAcMinBits, irsend.capture.bits);
uint8_t expected[6] = {0x14, 0x63, 0x0, 0x10, 0x10, 0x02};
EXPECT_TRUE(ArraysMatch(expected, irsend.capture.state));
fujitsu.setRaw(irsend.capture.state, irsend.capture.bits / 8);
EXPECT_EQ(kFujitsuAcStateLengthShort - 1, fujitsu.getStateLength());
EXPECT_EQ("Power: Off, Mode: 0 (AUTO), Temp: 16C, Fan: 0 (AUTO), "
"Swing: Off, Command: N/A", fujitsu.toString());
}
TEST(TestDecodeFujitsuAC, RealLongARDB1Example) {
IRsendTest irsend(0);
IRrecv irrecv(0);
IRFujitsuAC fujitsu = IRFujitsuAC(0);
irsend.begin();
irsend.reset();
uint16_t rawData1[243] = {
3316, 1632, 444, 390, 438, 388, 436, 1216, 438, 388, 438, 1214,
438, 388, 438, 386, 440, 386, 440, 1212, 440, 1210, 442, 392,
412, 396, 442, 392, 444, 1208, 444, 1208, 444, 380, 444, 380,
446, 380, 436, 390, 436, 390, 436, 390, 436, 388, 438, 388,
438, 388, 438, 388, 438, 386, 438, 386, 440, 384, 440, 1210,
442, 384, 442, 382, 442, 384, 442, 384, 442, 382, 442, 382,
444, 382, 444, 1208, 444, 382, 444, 380, 446, 380, 436, 390,
436, 390, 436, 1214, 438, 1214, 438, 1212, 440, 1212, 440, 1220,
412, 1222, 440, 394, 442, 382, 442, 382, 444, 1208, 444, 382,
444, 380, 446, 380, 446, 380, 434, 390, 436, 388, 438, 388,
438, 388, 438, 1214, 438, 1212, 440, 386, 440, 394, 412, 1222,
440, 394, 442, 384, 442, 384, 442, 382, 442, 1208, 444, 390,
414, 394, 442, 1216, 446, 380, 436, 390, 436, 390, 436, 388,
436, 390, 436, 388, 438, 386, 440, 386, 440, 386, 438, 1212,
440, 386, 440, 384, 440, 384, 442, 392, 412, 396, 440, 394,
442, 382, 444, 382, 444, 382, 444, 380, 444, 380, 444, 382,
444, 380, 446, 380, 436, 388, 436, 390, 436, 388, 438, 388,
438, 388, 438, 388, 438, 386, 440, 386, 440, 386, 442, 384,
440, 386, 442, 384, 440, 384, 442, 384, 442, 382, 442, 382,
444, 1208, 444, 382, 444, 1208, 444, 380, 446, 1206, 436, 390,
436, 1216, 436};
irsend.sendRaw(rawData1, 243, 38000);
irsend.makeDecodeResult();
EXPECT_TRUE(irrecv.decode(&irsend.capture));
ASSERT_EQ(FUJITSU_AC, irsend.capture.decode_type);
ASSERT_EQ(kFujitsuAcBits - 8, irsend.capture.bits);
uint8_t expected1[kFujitsuAcStateLength - 1] = {
0x14, 0x63, 0x00, 0x10, 0x10, 0xFC, 0x08, 0x30,
0x21, 0x01, 0x04, 0x00, 0x00, 0x00, 0xAA};
EXPECT_TRUE(ArraysMatch(expected1, irsend.capture.state));
fujitsu.setRaw(irsend.capture.state, irsend.capture.bits / 8);
EXPECT_EQ(kFujitsuAcStateLength - 1, fujitsu.getStateLength());
EXPECT_EQ("Power: On, Mode: 1 (COOL), Temp: 18C, Fan: 4 (QUIET), "
"Swing: Off, Command: N/A", fujitsu.toString());
irsend.reset();
uint16_t rawData2[243] = {
3316, 1630, 436, 398, 438, 386, 438, 1212, 440, 384, 440, 1212,
442, 384, 442, 392, 414, 394, 442, 1218, 446, 1206, 436, 390,
436, 388, 438, 388, 438, 1214, 440, 1212, 440, 384, 442, 384,
442, 384, 442, 382, 444, 382, 444, 382, 444, 380, 446, 380,
444, 380, 436, 390, 436, 388, 438, 396, 418, 388, 438, 1232,
410, 396, 440, 394, 442, 384, 442, 384, 442, 382, 442, 392,
414, 392, 444, 1216, 446, 380, 436, 390, 436, 396, 418, 390,
436, 398, 438, 1214, 440, 1212, 440, 1210, 442, 1208, 444, 1216,
416, 1218, 444, 388, 436, 390, 436, 388, 438, 1214, 440, 386,
438, 386, 440, 386, 440, 384, 442, 384, 442, 384, 442, 382,
444, 382, 444, 1206, 446, 1206, 436, 390, 436, 388, 438, 388,
438, 386, 440, 394, 410, 396, 440, 1220, 442, 1210, 442, 392,
414, 394, 442, 1218, 446, 406, 410, 388, 436, 390, 436, 390,
436, 388, 438, 386, 440, 386, 440, 386, 440, 386, 440, 384,
442, 384, 442, 384, 442, 382, 444, 382, 444, 380, 446, 380,
446, 380, 436, 390, 436, 390, 436, 388, 438, 386, 438, 388,
438, 386, 440, 386, 440, 384, 442, 384, 442, 384, 442, 384,
442, 382, 444, 382, 444, 380, 446, 380, 446, 380, 436, 390,
436, 388, 436, 388, 438, 386, 438, 386, 440, 386, 440, 1212,
440, 1210, 442, 1210, 442, 1208, 444, 1208, 436, 390, 436, 388,
436, 1214, 440};
irsend.sendRaw(rawData2, 243, 38000);
irsend.makeDecodeResult();
EXPECT_TRUE(irrecv.decode(&irsend.capture));
ASSERT_EQ(FUJITSU_AC, irsend.capture.decode_type);
ASSERT_EQ(kFujitsuAcBits - 8, irsend.capture.bits);
uint8_t expected2[kFujitsuAcStateLength - 1] = {
0x14, 0x63, 0x00, 0x10, 0x10, 0xFC, 0x08, 0x30,
0x30, 0x01, 0x00, 0x00, 0x00, 0x00, 0x9F};
EXPECT_TRUE(ArraysMatch(expected2, irsend.capture.state));
fujitsu.setRaw(irsend.capture.state, irsend.capture.bits / 8);
EXPECT_EQ(kFujitsuAcStateLength - 1, fujitsu.getStateLength());
EXPECT_EQ("Power: On, Mode: 1 (COOL), Temp: 19C, Fan: 0 (AUTO), "
"Swing: Off, Command: N/A", fujitsu.toString());
}
TEST(TestDecodeFujitsuAC, Issue414) {
IRsendTest irsend(0);
IRrecv irrecv(0);
IRFujitsuAC fujitsu = IRFujitsuAC(0);
// Capture as supplied by arpmota
uint16_t rawData[259] = {3352, 1574, 480, 350, 480, 346, 480, 1190, 458, 346,
508, 1140, 480, 346, 506, 346, 458, 346, 480, 1168, 480, 1192, 452, 374,
458, 346, 480, 346, 508, 1168, 480, 1140, 480, 346, 506, 346, 458, 346,
480, 346, 480, 346, 480, 346, 484, 372, 454, 374, 456, 346, 508, 318,
480, 374, 458, 374, 480, 318, 480, 1196, 452, 346, 480, 346, 484, 342,
484, 346, 480, 374, 458, 346, 506, 318, 508, 1170, 452, 346, 480, 374,
458, 346, 506, 318, 480, 1196, 452, 1190, 458, 1162, 480, 1196, 452,
1170, 480, 1190, 458, 1164, 480, 1196, 480, 318, 508, 346, 456, 1192,
480, 346, 456, 374, 452, 346, 480, 374, 458, 342, 484, 346, 508, 346,
456, 342, 512, 1164, 458, 1164, 508, 346, 456, 346, 480, 1190, 456, 342,
484, 346, 506, 346, 456, 374, 452, 346, 508, 346, 458, 1164, 508, 346,
458, 374, 452, 1168, 480, 374, 480, 318, 480, 374, 456, 346, 508, 318,
480, 346, 484, 374, 480, 318, 484, 342, 484, 374, 480, 318, 484, 342,
484, 346, 508, 318, 508, 346, 458, 346, 506, 318, 480, 374, 458, 346,
506, 318, 480, 346, 484, 374, 480, 318, 482, 372, 456, 346, 508, 318,
506, 348, 456, 342, 484, 346, 508, 318, 484, 374, 480, 318, 508, 318,
484, 346, 508, 318, 480, 374, 456, 346, 508, 346, 480, 318, 480, 346,
484, 374, 480, 320, 484, 1164, 508, 346, 458, 342, 512, 1164, 458, 1190,
454, 346, 484, 1164, 508, 346, 458, 1164, 480, 350, 480, 374, 480};
uint8_t state[16] = {
0x14, 0x63, 0x00, 0x10, 0x10, 0xFE, 0x09, 0x30, 0x81, 0x04, 0x00, 0x00,
0x00, 0x00, 0x20, 0x2B};
irsend.begin();
irsend.reset();
irsend.sendRaw(rawData, 259, 38000);
irsend.makeDecodeResult();
EXPECT_TRUE(irrecv.decode(&irsend.capture));
ASSERT_EQ(FUJITSU_AC, irsend.capture.decode_type);
ASSERT_EQ(kFujitsuAcBits, irsend.capture.bits);
EXPECT_TRUE(ArraysMatch(state, irsend.capture.state));
fujitsu.setRaw(irsend.capture.state, irsend.capture.bits / 8);
EXPECT_EQ(kFujitsuAcStateLength, fujitsu.getStateLength());
EXPECT_EQ("Power: On, Mode: 4 (HEAT), Temp: 24C, Fan: 0 (AUTO), "
"Swing: Off, Command: N/A", fujitsu.toString());
// Resend it using the state this time.
irsend.reset();
irsend.sendFujitsuAC(state, 16);
irsend.makeDecodeResult();
EXPECT_TRUE(irrecv.decode(&irsend.capture));
ASSERT_EQ(FUJITSU_AC, irsend.capture.decode_type);
ASSERT_EQ(kFujitsuAcBits, irsend.capture.bits);
EXPECT_TRUE(ArraysMatch(state, irsend.capture.state));
EXPECT_EQ(
"f38000d50"
"m3324s1574"
"m448s390m448s390m448s1182m448s390m448s1182m448s390m448s390m448s390"
"m448s1182m448s1182m448s390m448s390m448s390m448s1182m448s1182m448s390"
"m448s390m448s390m448s390m448s390m448s390m448s390m448s390m448s390"
"m448s390m448s390m448s390m448s390m448s1182m448s390m448s390m448s390"
"m448s390m448s390m448s390m448s390m448s1182m448s390m448s390m448s390"
"m448s390m448s1182m448s1182m448s1182m448s1182m448s1182m448s1182m448s1182"
"m448s1182m448s390m448s390m448s1182m448s390m448s390m448s390m448s390"
"m448s390m448s390m448s390m448s390m448s1182m448s1182m448s390m448s390"
"m448s1182m448s390m448s390m448s390m448s390m448s390m448s390m448s1182"
"m448s390m448s390m448s1182m448s390m448s390m448s390m448s390m448s390"
"m448s390m448s390m448s390m448s390m448s390m448s390m448s390m448s390"
"m448s390m448s390m448s390m448s390m448s390m448s390m448s390m448s390"
"m448s390m448s390m448s390m448s390m448s390m448s390m448s390m448s390"
"m448s390m448s390m448s390m448s390m448s390m448s390m448s390m448s390"
"m448s390m448s390m448s390m448s390m448s390m448s1182m448s390m448s390"
"m448s1182m448s1182m448s390m448s1182m448s390m448s1182m448s390m448s390"
"m448s8100", irsend.outputStr());
}

View File

@ -33,8 +33,8 @@ Before creating bug reports, please check [this list](#before-submitting-a-bug-r
#### Before Submitting A Bug Report
* **Check the [Troubleshooting Guide](https://github.com/markszabo/IRremoteESP8266/wiki/Troubleshooting-Guide).** You might be able to find the cause of the problem and fix it yourself. Most importantly, check if you can reproduce the problem in the latest version (a.k.a. 'master') of the library.
* **Perform a [cursory search](https://github.com/issues?q=+is%3Aissue+repo%3Amarkszabo/IRremoteESP8266)** to see if the problem is already reported. If it has **and the issue is still open**, add a comment to the existing issue instead of opening a new one.
* **Check the [Troubleshooting Guide](https://github.com/crankyoldgit/IRremoteESP8266/wiki/Troubleshooting-Guide).** You might be able to find the cause of the problem and fix it yourself. Most importantly, check if you can reproduce the problem in the latest version (a.k.a. 'master') of the library.
* **Perform a [cursory search](https://github.com/issues?q=+is%3Aissue+repo%3Acrankyoldgit/IRremoteESP8266)** to see if the problem is already reported. If it has **and the issue is still open**, add a comment to the existing issue instead of opening a new one.
#### How Do I Submit A (Good) Bug Report?
@ -53,7 +53,7 @@ Provide more context by answering these questions:
* **Can you reproduce the problem in one of the code examples?**
* **Did the problem start happening recently** (e.g. after updating to a new version of Arduino or the library) or was this always a problem?
* If the problem started happening recently, **can you reproduce the problem in an older version of the library?** What's the most recent version in which the problem doesn't happen? You can download older versions of the library from [the releases page](https://github.com/markszabo/IRremoteESP8266/releases).
* If the problem started happening recently, **can you reproduce the problem in an older version of the library?** What's the most recent version in which the problem doesn't happen? You can download older versions of the library from [the releases page](https://github.com/crankyoldgit/IRremoteESP8266/releases).
* **Can you reliably reproduce the issue?** If not, provide details about how often the problem happens and under which conditions it normally happens.
Include details about your configuration, circuit and environment:

View File

@ -2,7 +2,7 @@
### Main contributors & maintainers
- [Mark Szabo](https://github.com/markszabo/) : Initial IR sending on ESP8266
- [Sébastien Warin](https://github.com/sebastienwarin/) (http://sebastien.warin.fr) : Initial IR receiving on ESP8266
- [David Conran](https://github.com/crankyoldgit/)
- [David Conran](https://github.com/crankyoldgit/) : ESP32 support and pretty much everything else.
- [Roi Dayan](https://github.com/roidayan/)
- [Marcos de Alcântara Marinho](https://github.com/marcosamarinho/)
- [Massimiliano Pinto](https://github.com/pintomax/)
@ -15,6 +15,6 @@
- [Fabien Valthier](https://github.com/hcoohb)
- [Ajay Pala](https://github.com/ajaypala/)
All contributors can be found on the [contributors site](https://github.com/markszabo/IRremoteESP8266/graphs/contributors).
All contributors can be found on the [contributors site](https://github.com/crankyoldgit/IRremoteESP8266/graphs/contributors).
### Contributors of the [original project](https://github.com/z3t0/Arduino-IRremote) can be found on the [original project's contributors page](https://github.com/z3t0/Arduino-IRremote/blob/master/Contributors.md)

View File

@ -1,6 +1,6 @@
_(Please use this template for reporting issues. You can delete what ever is not relevant. Giving us this information will help us help you faster. Please also read the [FAQ](https://github.com/markszabo/IRremoteESP8266/wiki/Frequently-Asked-Questions) & [Troubleshooting Guide](https://github.com/markszabo/IRremoteESP8266/wiki/Troubleshooting-Guide). Your problem may already have an answer there.)_
_(Please use this template for reporting issues. You can delete what ever is not relevant. Giving us this information will help us help you faster. Please also read the [FAQ](https://github.com/crankyoldgit/IRremoteESP8266/wiki/Frequently-Asked-Questions) & [Troubleshooting Guide](https://github.com/crankyoldgit/IRremoteESP8266/wiki/Troubleshooting-Guide). Your problem may already have an answer there.)_
### Version/revison of the library used
### Version/revision of the library used
_Typically located in the `library.json` & `src/IRremoteESP8266.h` files in the root directory of the library.
e.g. v2.0.0, or 'master' as at 1st of June, 2017. etc._
@ -30,9 +30,9 @@ _What can we do to (pref. reliably) repeat what is happening?_
_Include all relevant code snippets or links to the actual code files. Tip: [How to quote your code so it is still readable](https://github.com/adam-p/markdown-here/wiki/Markdown-Cheatsheet#code)._
#### Circuit diagram and hardware used (if applicable)
_Link to an image of the circuit diagram used. Part number of the IR receiver module etc._
_Link to an image of the circuit diagram used. Part number of the IR receiver module etc. ESP8266 or ESP32 board type._
### I have followed the steps in the [Troubleshooting Guide](https://github.com/markszabo/IRremoteESP8266/wiki/Troubleshooting-Guide) & read the [FAQ](https://github.com/markszabo/IRremoteESP8266/wiki/Frequently-Asked-Questions)
### I have followed the steps in the [Troubleshooting Guide](https://github.com/crankyoldgit/IRremoteESP8266/wiki/Troubleshooting-Guide) & read the [FAQ](https://github.com/crankyoldgit/IRremoteESP8266/wiki/Frequently-Asked-Questions)
_Yes/No._
### Has this library/code previously worked as expected for you?

View File

@ -8,8 +8,12 @@
# vi/vim
**/*.swp
# vscode
.vscode
## Build environments
# Platformio
**/.pio/
**/.pioenvs/
**/.piolibdeps/
**/.clang_complete

View File

@ -0,0 +1,73 @@
language: c
env:
- BD=esp8266:esp8266:nodemcuv2:xtal=80,eesz=4M3M,ip=lm2f,exception=disabled
# - BD=esp8266:esp8266:d1_mini:xtal=80,eesz=4M3M,ip=lm2f,exception=disabled
before_install:
- "/sbin/start-stop-daemon --start --quiet --pidfile /tmp/custom_xvfb_1.pid --make-pidfile --background --exec /usr/bin/Xvfb -- :1 -ac -screen 0 1280x1024x16"
- sleep 3
- export DISPLAY=:1.0
- wget http://downloads.arduino.cc/arduino-1.8.8-linux64.tar.xz
- tar xf arduino-1.8.8-linux64.tar.xz
- sudo mv arduino-1.8.8 /usr/local/share/arduino
- sudo ln -s /usr/local/share/arduino/arduino /usr/local/bin/arduino
- wget https://raw.githubusercontent.com/google/styleguide/gh-pages/cpplint/cpplint.py
install:
- ln -s $PWD /usr/local/share/arduino/libraries/
- git clone https://github.com/tzapu/WiFiManager.git /usr/local/share/arduino/libraries/WiFiManager
- git clone https://github.com/knolleary/pubsubclient.git /usr/local/share/arduino/libraries/PubSubClient
- git clone https://github.com/bblanchon/ArduinoJson.git --branch 5.x /usr/local/share/arduino/libraries/ArduinoJson
- arduino --pref "boardsmanager.additional.urls=http://arduino.esp8266.com/stable/package_esp8266com_index.json" --save-prefs
- arduino --install-boards esp8266:esp8266
- arduino --board $BD --save-prefs
- arduino --pref "compiler.warning_level=all" --save-prefs
- sudo apt-get install jq
- sudo apt-get purge python-enum34
- sudo apt-get install pylint3
script: echo Running checks
notifications:
email:
on_success: change
on_failure: change
jobs:
include:
- script:
# Check that everything compiles. (Part 1)
- arduino --verify --board $BD $PWD/examples/IRrecvDemo/IRrecvDemo.ino 2> /dev/null
- arduino --verify --board $BD $PWD/examples/IRGCSendDemo/IRGCSendDemo.ino 2> /dev/null
- arduino --verify --board $BD $PWD/examples/IRGCTCPServer/IRGCTCPServer.ino 2> /dev/null
- arduino --verify --board $BD $PWD/examples/IRServer/IRServer.ino 2> /dev/null
- arduino --verify --board $BD $PWD/examples/IRrecvDumpV2/IRrecvDumpV2.ino 2> /dev/null
- arduino --verify --board $BD $PWD/examples/IRsendDemo/IRsendDemo.ino 2> /dev/null
- arduino --verify --board $BD $PWD/examples/JVCPanasonicSendDemo/JVCPanasonicSendDemo.ino 2> /dev/null
- arduino --verify --board $BD $PWD/examples/TurnOnDaikinAC/TurnOnDaikinAC.ino 2> /dev/null
- arduino --verify --board $BD $PWD/examples/TurnOnFujitsuAC/TurnOnFujitsuAC.ino 2> /dev/null
- arduino --verify --board $BD $PWD/examples/TurnOnKelvinatorAC/TurnOnKelvinatorAC.ino 2> /dev/null
- arduino --verify --board $BD $PWD/examples/TurnOnMitsubishiAC/TurnOnMitsubishiAC.ino 2> /dev/null
- script:
# Check that everything compiles. (Part 2)
- arduino --verify --board $BD $PWD/examples/IRsendProntoDemo/IRsendProntoDemo.ino 2> /dev/null
- arduino --verify --board $BD $PWD/examples/TurnOnTrotecAC/TurnOnTrotecAC.ino 2> /dev/null
- arduino --verify --board $BD $PWD/examples/LGACSend/LGACSend.ino 2> /dev/null
- arduino --verify --board $BD $PWD/examples/TurnOnArgoAC/TurnOnArgoAC.ino 2> /dev/null
- arduino --verify --board $BD $PWD/examples/IRMQTTServer/IRMQTTServer.ino 2> /dev/null
- arduino --verify --board $BD $PWD/examples/TurnOnToshibaAC/TurnOnToshibaAC.ino 2> /dev/null
- arduino --verify --board $BD $PWD/examples/ControlSamsungAC/ControlSamsungAC.ino 2> /dev/null
- arduino --verify --board $BD $PWD/examples/TurnOnPanasonicAC/TurnOnPanasonicAC.ino 2> /dev/null
- arduino --verify --board $BD $PWD/examples/TurnOnMitsubishiHeavyAc/TurnOnMitsubishiHeavyAc.ino 2> /dev/null
- arduino --verify --board $BD $PWD/examples/DumbIRRepeater/DumbIRRepeater.ino 2> /dev/null
- arduino --verify --board $BD $PWD/examples/SmartIRRepeater/SmartIRRepeater.ino 2> /dev/null
- script:
# Check the version numbers match.
- LIB_VERSION=$(egrep "^#define\s+_IRREMOTEESP8266_VERSION_\s+" src/IRremoteESP8266.h | cut -d\" -f2)
- test ${LIB_VERSION} == "$(jq -r .version library.json)"
- grep -q "^version=${LIB_VERSION}$" library.properties
# Check the tools programs compile.
- (cd tools; make all)
# Check for lint issues.
- shopt -s nullglob
- python cpplint.py --extensions=c,cc,cpp,ino --headers=h,hpp {src,test,tools}/*.{h,c,cc,cpp,hpp,ino} examples/*/*.{h,c,cc,cpp,hpp,ino}
- pylint3 -d F0001 {src,test,tools}/*.py
- shopt -u nullglob
# Build and run the unit tests.
- (cd test; make run)
- (cd tools; make run_tests)

View File

@ -1,18 +1,19 @@
# IRremote ESP8266 Library
[![Build Status](https://travis-ci.org/markszabo/IRremoteESP8266.svg?branch=master)](https://travis-ci.org/markszabo/IRremoteESP8266)
[![Build Status](https://travis-ci.org/crankyoldgit/IRremoteESP8266.svg?branch=master)](https://travis-ci.org/crankyoldgit/IRremoteESP8266)
[![arduino-library-badge](https://www.ardu-badge.com/badge/IRremoteESP8266.svg?)](https://www.ardu-badge.com/IRremoteESP8266)
[![Average time to resolve an issue](http://isitmaintained.com/badge/resolution/markszabo/IRremoteESP8266.svg)](http://isitmaintained.com/project/markszabo/IRremoteESP8266 "Average time to resolve an issue")
[![Percentage of issues still open](http://isitmaintained.com/badge/open/markszabo/IRremoteESP8266.svg)](http://isitmaintained.com/project/markszabo/IRremoteESP8266 "Percentage of issues still open")
[![GitLicense](https://gitlicense.com/badge/markszabo/IRremoteESP8266)](https://gitlicense.com/license/markszabo/IRremoteESP8266)
[![Average time to resolve an issue](http://isitmaintained.com/badge/resolution/crankyoldgit/IRremoteESP8266.svg)](http://isitmaintained.com/project/crankyoldgit/IRremoteESP8266 "Average time to resolve an issue")
[![Percentage of issues still open](http://isitmaintained.com/badge/open/crankyoldgit/IRremoteESP8266.svg)](http://isitmaintained.com/project/crankyoldgit/IRremoteESP8266 "Percentage of issues still open")
[![GitLicense](https://gitlicense.com/badge/crankyoldgit/IRremoteESP8266)](https://gitlicense.com/license/crankyoldgit/IRremoteESP8266)
This library enables you to **send _and_ receive** infra-red signals on an [ESP8266 using the Arduino framework](https://github.com/esp8266/Arduino) using common 940nm IR LEDs and common IR receiver modules. e.g. TSOP{17,22,24,36,38,44,48}* etc.
This library enables you to **send _and_ receive** infra-red signals on an [ESP8266](https://github.com/esp8266/Arduino) or an
[ESP32](https://github.com/espressif/arduino-esp32) using the [Arduino framework](https://www.arduino.cc/) using common 940nm IR LEDs and common IR receiver modules. e.g. TSOP{17,22,24,36,38,44,48}* demodulators etc.
## v2.6.0 Now Available
Version 2.6.0 of the library is now [available](https://github.com/markszabo/IRremoteESP8266/releases/latest). You can view the [Release Notes](ReleaseNotes.md) for all the significant changes.
## v2.6.3 Now Available
Version 2.6.3 of the library is now [available](https://github.com/crankyoldgit/IRremoteESP8266/releases/latest). You can view the [Release Notes](ReleaseNotes.md) for all the significant changes.
#### Upgrading from pre-v2.0
Usage of the library has been slightly changed in v2.0. You will need to change your usage to work with v2.0 and beyond. You can read more about the changes required on our [Upgrade to v2.0](https://github.com/markszabo/IRremoteESP8266/wiki/Upgrading-to-v2.0) page.
Usage of the library has been slightly changed in v2.0. You will need to change your usage to work with v2.0 and beyond. You can read more about the changes required on our [Upgrade to v2.0](https://github.com/crankyoldgit/IRremoteESP8266/wiki/Upgrading-to-v2.0) page.
#### Upgrading from pre-v2.5
The library has changed from using constants declared as `#define` to
@ -29,11 +30,15 @@ something you likely should not have. You should be able to quickly determine
the new name from the old. e.g. `CONSTANT_NAME` to `kConstantName`.
Use common sense or examining the library's code if this does affect code.
## Supported protocols
You can find the details of which protocols & devices are supported
[here](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/SupportedProtocols.md).
## Troubleshooting
Before reporting an issue or asking for help, please try to follow our [Troubleshooting Guide](https://github.com/markszabo/IRremoteESP8266/wiki/Troubleshooting-Guide) first.
Before reporting an issue or asking for help, please try to follow our [Troubleshooting Guide](https://github.com/crankyoldgit/IRremoteESP8266/wiki/Troubleshooting-Guide) first.
## Frequently Asked Questions
Some common answers to common questions and problems are on our [F.A.Q. wiki page](https://github.com/markszabo/IRremoteESP8266/wiki/Frequently-Asked-Questions).
Some common answers to common questions and problems are on our [F.A.Q. wiki page](https://github.com/crankyoldgit/IRremoteESP8266/wiki/Frequently-Asked-Questions).
## Installation
##### Official releases via the Arduino IDE v1.8+ (Windows & Linux)
@ -43,7 +48,7 @@ Some common answers to common questions and problems are on our [F.A.Q. wiki pag
1. Select the version you wish to install and click _"Install"_.
##### Manual Installation for Windows
1. Click on _"Clone or Download"_ button, then _"[Download ZIP](https://github.com/markszabo/IRremoteESP8266/archive->master.zip)"_ on the page.
1. Click on _"Clone or Download"_ button, then _"[Download ZIP](https://github.com/crankyoldgit/IRremoteESP8266/archive->master.zip)"_ on the page.
1. Extract the contents of the downloaded zip file.
1. Rename the extracted folder to _"IRremoteESP8266"_.
1. Move this folder to your libraries directory. (under windows: `C:\Users\YOURNAME\Documents\Arduino\libraries\`)
@ -53,7 +58,7 @@ Some common answers to common questions and problems are on our [F.A.Q. wiki pag
##### Using Git to install library ( Linux )
```
cd ~/Arduino/libraries
git clone https://github.com/markszabo/IRremoteESP8266.git
git clone https://github.com/crankyoldgit/IRremoteESP8266.git
```
###### To Update to the latest version of the library
```
@ -74,6 +79,6 @@ Available [here](.github/Contributors.md)
## Library History
This library was originally based on Ken Shirriff's work (https://github.com/shirriff/Arduino-IRremote/)
[Mark Szabo](https://github.com/markszabo/IRremoteESP8266) has updated the IRsend class to work on ESP8266 and [Sebastien Warin](https://github.com/sebastienwarin/IRremoteESP8266) the receiving & decoding part (IRrecv class).
[Mark Szabo](https://github.com/crankyoldgit/IRremoteESP8266) has updated the IRsend class to work on ESP8266 and [Sebastien Warin](https://github.com/sebastienwarin/IRremoteESP8266) the receiving & decoding part (IRrecv class).
As of v2.0, the library was almost entirely re-written with the ESP8266's resources in mind.

View File

@ -1,5 +1,93 @@
# Release Notes
## _v2.6.3 (20190704)_
**[Bug Fixes]**
- IRMQTTServer: REPLAY_DECODED_AC_MESSAGE not working. (#784, #797)
- ESP32: Ensure `IRrecv`'s GPIO is set to input mode. (#774)
**[Features]**
- IRMQTTServer: Show available sketch space for OTA uploads. (#795)
- Experimental detailed support for Electra/AUX protocol (#788)
- IRMQTTServer: Ability to resend existing climate state via MQTT & HTTP (#784)
- Daikin160: Add detailed & common a/c support. (#777)
- Experimental detailed support for Neoclima protocol. (#767)
- Gree: add WiFi and IFeel bits (#770)
- Handle A/Cs with toggles better. (#758)
- IRMQTTServer: Allow sending/receiving climate via JSON over MQTT. (#763)
**[Misc]**
- Move converting of IR A/C messages out of example code. (#798)
- Reduce example code size and complexity (#790)
- Change `ControlSamsungAC` example to not use `sendExtended()` (#792)
- IRMQTTServer: Add MQTT_CLIMATE_IR_SEND_ON_RESTART compile-time flag. (#784)
- Refactor A/C's toString()'s to reduce code size. Saves ~3.5k (#782)
- Add sanity tests for unexpected conditions in IRrecv. (#773)
- IRMQTTServer: Fixed the HA config documentation (missing '-') (#776)
- Improve `mkkeywords` tool. (#766)
- Refactor with generic decode routines in `IRrecv` class. Saves ~7k. (#765)
## _v2.6.2 (20190616)_
**[Features]**
- Initial support for the ESP32 architecture & boards. (#742)
- Add changable GPIO settings to IRMQTTServer. (#730)
- IRMQTTServer: Enforce a repeat for all Coolix calls (#752)
- Basic DAIKIN 160bit send and decode. (#754)
- Add example code for a Smart(er) IR Repeater. (#740)
- Enforce Samsung A/C Quiet & Powerful mutual exclusivity.
**[Misc]**
- IRMQTTServer: Add some memory alloc safety checks. (#749)
- Move some ToString() functions to IRac.cpp (#748)
- Increase tolerance value for TCL112AC protocol. (#745)
- Fix compiler warning in IRutils_test.cpp (#756)
- Scrape Supported Protocols and generate SupportedProtocols.md (#755)
- Make supported device info more organised. (#753)
## _v2.6.1 (20190609)_
**[Breaking Changes]**
- Major rework/breaking changes to Argo A/C support. (#705)
**[Bug Fixes]**
- Correct `set/getQuiet` for Samsung A/C (#736)
- Add missing `on/off()` to IRCoolixAC class. (#725)
- Daikin `set/getEye()` uses wrong bit. (#711)
- IRMQTTServer: Continue to use same Temperature units. (#710)
- Fixed a bug with `setMode()`/`getMode()` for HAIER_AC. (#705)
**[Features]**
- Add set/getPowerful for Samsung A/C (#736)
- Add `calibrate()` to all the A/C classes. (#735)
- IRMQTTServer: Add sequencing for sending MQTT IR commands. (#723)
- Add support for Fujitsu AR-REB1E & AR-JW2 remotes. (#718)
- Add Beta `decodeTrotec()` support. (#719)
- Add experimental `decodeArgo()` support. (#717)
- Support for Goodweather A/Cs. (#715)
- Add `DISABLE_CAPTURE_WHILE_TRANSMITTING` feature to IRMQTTServer. (#713)
- Support for Lixil Inax Toilet protocol. (#712)
- Add `set/getWeeklyTimerEnable()` to Daikin (#711)
- IRMQTTServer: Update Common A/C settings based on received IR messages. (#705)
- Add day of week to DAIKIN protocol (#699)
- Add limited support for Sharp A/C (#696)
- SAMSUNG_AC: Make sure special power mode messages are sent. (#695)
- Add `set/getPowerful()` (turbo) to DAIKIN216 (#693)
**[Misc]**
- Add kPeriodOffset for CPU Freq of 160MHz. (#729)
- Example code for a Dumb IR repeater. (#737)
- Update swing handling for Fujitsu A/Cs. (#724)
- Add function to convert `decode_results` to `sendRaw()` array. (#721)
- Attempt to reduce heap fragmentation from strings. (#707)
- Update Fujitsu A/C example code to safer settings (#716)
- Enforce better `const` usage in IRUtils. (#708)
- Attempt to reduce heap fragmentation by A/C `toString()`s. (#694)
- Minor changes to DAIKIN216 timings and features. (#693)
## _v2.6.0 (20190430)_
**[Bug Fixes]**

View File

@ -0,0 +1,132 @@
<!--- WARNING: Do NOT edit this file directly.
It is generated by './tools/scrape_supported_devices.py'.
Last generated: Thu Jul 4 13:48:54 2019 --->
# IR Protocols supported by this library
| Protocol | Brand | Model | A/C Model | Detailed A/C Support |
| --- | --- | --- | --- | --- |
| [Aiwa](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Aiwa.cpp) | **Aiwa** | RC-T501 RCU | | - |
| [Argo](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Argo.cpp) | **[Argo](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Argo.h)** | Ulisse 13 DCI Mobile Split A/C | | Yes |
| [Carrier](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Carrier.cpp) | **Carrier/Surrey** | 42QG5A55970 remote<BR>53NGK009/012 Inverter<BR>619EGX0090E0 A/C<BR>619EGX0120E0 A/C<BR>619EGX0180E0 A/C<BR>619EGX0220E0 A/C | | - |
| [Coolix](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Coolix.cpp) | **[Beko](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Coolix.h)** | BINR 070/071 split-type A/C<BR>BINR 070/071 split-type A/C<BR>RG57K7(B)/BGEF Remote<BR>RG57K7(B)/BGEF Remote | | Yes |
| [Coolix](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Coolix.cpp) | **[Midea](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Coolix.h)** | MS12FU-10HRDN1-QRD0GW(B) A/C<BR>MS12FU-10HRDN1-QRD0GW(B) A/C<BR>MSABAU-07HRFN1-QRD0GW A/C (circa 2016)<BR>MSABAU-07HRFN1-QRD0GW A/C (circa 2016)<BR>RG52D/BGE Remote<BR>RG52D/BGE Remote | | Yes |
| [Daikin](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Daikin.cpp) | **[Daikin](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Daikin.h)** | ARC423A5 remote<BR>ARC433** remote<BR>ARC433B69 remote<BR>ARC477A1 remote<BR>FTE12HV2S A/C<BR>FTXZ25NV1B A/C<BR>FTXZ35NV1B A/C<BR>FTXZ50NV1B A/C | | Yes |
| [Denon](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Denon.cpp) | **Unknown** | | | - |
| [Dish](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Dish.cpp) | **DISH NETWORK** | echostar 301 | | - |
| [Electra](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Electra.cpp) | **[AUX](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Electra.h)** | KFR-35GW/BpNFW=3 A/C<BR>YKR-T/011 remote | | Yes |
| [Fujitsu](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Fujitsu.cpp) | **[Fujitsu](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Fujitsu.h)** | AR-DB1 remote<BR>AR-RAE1E remote<BR>AR-RAH2E remote<BR>AR-REB1E remote<BR>AST9RSGCW A/C<BR>ASYG30LFCA A/C<BR>ASYG7LMCA A/C | ARDB1<BR>ARJW2<BR>ARRAH2E<BR>ARREB1E | Yes |
| [Fujitsu](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Fujitsu.cpp) | **[Fujitsu General](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Fujitsu.h)** | AR-JW2 remote | ARDB1<BR>ARJW2<BR>ARRAH2E<BR>ARREB1E | Yes |
| [GICable](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_GICable.cpp) | **Unknown** | | | - |
| [GlobalCache](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_GlobalCache.cpp) | **Unknown** | | | - |
| [Goodweather](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Goodweather.cpp) | **[Goodweather](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Goodweather.h)** | ZH/JT-03 remote | | Yes |
| [Gree](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Gree.cpp) | **[EKOKAI](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Gree.h)** | A/C | | Yes |
| [Gree](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Gree.cpp) | **[RusClimate](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Gree.h)** | EACS/I-09HAR_X/N3 A/C<BR>YAW1F remote | | Yes |
| [Gree](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Gree.cpp) | **[Ultimate](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Gree.h)** | Heat Pump | | Yes |
| [Haier](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Haier.cpp) | **[Haier](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Haier.h)** | HSU-09HMC203 A/C<BR>HSU07-HEA03 remote<BR>YR-W02 remote | | Yes |
| [Hitachi](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Hitachi.cpp) | **[Hitachi](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Hitachi.h)** | LT0541-HTA remote<BR>RAS-35THA6 remote<BR>Series VI A/C (Circa 2007) | | Yes |
| [Inax](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Inax.cpp) | **Lixil** | Inax DT-BA283 Toilet | | - |
| [JVC](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_JVC.cpp) | **Unknown** | | | - |
| [Kelvinator](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Kelvinator.cpp) | **[Kelvinator](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Kelvinator.h)** | KSV26CRC A/C<BR>KSV26HRC A/C<BR>KSV35CRC A/C<BR>KSV35HRC A/C<BR>KSV53HRC A/C<BR>KSV62HRC A/C<BR>KSV70CRC A/C<BR>KSV70HRC A/C<BR>KSV80HRC A/C<BR>YALIF Remote | | Yes |
| [LG](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_LG.cpp) | **[LG](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_LG.h)** | 6711A20083V remote<BR>6711A20083V remote<BR>AKB74395308 remote<BR>AKB74395308 remote | | Yes |
| [Lasertag](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Lasertag.cpp) | **Unknown** | | | - |
| [Lego](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Lego.cpp) | **LEGO Power Functions** | IR Receiver | | - |
| [Lutron](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Lutron.cpp) | **Unknown** | | | - |
| [MWM](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_MWM.cpp) | **Unknown** | | | - |
| [Magiquest](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Magiquest.cpp) | **[Unknown](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Magiquest.h)** | | | Yes |
| [Midea](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Midea.cpp) | **[Pioneer System](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Midea.h)** | RUBO18GMFILCAD A/C (18K BTU)<BR>RYBO12GMFILCAD A/C (12K BTU) | | Yes |
| [Mitsubishi](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Mitsubishi.cpp) | **[Mitsubishi](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Mitsubishi.h)** | HC3000 Projector<BR>TV | | Yes |
| [MitsubishiHeavy](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_MitsubishiHeavy.cpp) | **[Mitsubishi Heavy Industries](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_MitsubishiHeavy.h)** | RKX502A001C remote<BR>RLA502A700B remote<BR>SRKxxZJ-S A/C<BR>SRKxxZM-S A/C<BR>SRKxxZMXA-S A/C | | Yes |
| [NEC](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_NEC.cpp) | **[Unknown](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_NEC.h)** | | | Yes |
| [Neoclima](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Neoclima.cpp) | **[Neoclima](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Neoclima.h)** | NS-09AHTI A/C<BR>NS-09AHTI A/C<BR>ZH/TY-01 remote<BR>ZH/TY-01 remote | | Yes |
| [Nikai](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Nikai.cpp) | **Unknown** | | | - |
| [Panasonic](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Panasonic.cpp) | **[Panasonic](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Panasonic.h)** | A75C2311 remote (CKP)<BR>A75C3704 remote<BR>A75C3747 remote<BR>A75C3747 remote<BR>A75C3747 remote<BR>A75C3747 remote<BR>CKP series A/C<BR>CS-ME10CKPG A/C<BR>CS-ME12CKPG A/C<BR>CS-ME14CKPG A/C<BR>CS-YW9MKD A/C<BR>CS-Z9RKR A/C<BR>DKE series A/C<BR>JKE series A/C<BR>NKE series A/C<BR>RKR series A/C<BR>TV | CKP<BR>DKE<BR>JKE<BR>LKE<BR>NKE<BR>RKR | Yes |
| [Pioneer](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Pioneer.cpp) | **Unknown** | | | - |
| [Pronto](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Pronto.cpp) | **Unknown** | | | - |
| [RC5_RC6](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_RC5_RC6.cpp) | **Unknown** | | | - |
| [RCMM](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_RCMM.cpp) | **Microsoft** | XBOX 360 | | - |
| [Samsung](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Samsung.cpp) | **[Samsung](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Samsung.h)** | AR12HSSDBWKNEU A/C<BR>AR12KSFPEWQNET A/C<BR>IEC-R03 remote<BR>UA55H6300 TV | | Yes |
| [Sanyo](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Sanyo.cpp) | **Unknown** | | | - |
| [Sharp](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Sharp.cpp) | **[Sharp](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Sharp.h)** | AY-ZP40KR A/C<BR>LC-52D62U TV | | Yes |
| [Sherwood](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Sherwood.cpp) | **Sherwood** | RC-138 remote<BR>RD6505(B) Receiver | | - |
| [Sony](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Sony.cpp) | **Unknown** | | | - |
| [Tcl](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Tcl.cpp) | **[Leberg](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Tcl.h)** | LBS-TOR07 A/C | | Yes |
| [Teco](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Teco.cpp) | **[Unknown](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Teco.h)** | | | Yes |
| [Toshiba](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Toshiba.cpp) | **[Toshiba](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Toshiba.h)** | Akita EVO II<BR>RAS 18SKP-ES<BR>RAS-B13N3KV2<BR>RAS-B13N3KVP-E<BR>WC-L03SE<BR>WH-TA04NE | | Yes |
| [Trotec](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Trotec.cpp) | **[Unknown](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Trotec.h)** | | | Yes |
| [Vestel](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Vestel.cpp) | **[Vestel](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Vestel.h)** | BIOX CXP-9 A/C (9K BTU) | | Yes |
| [Whirlpool](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Whirlpool.cpp) | **[Whirlpool](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Whirlpool.h)** | DG11J1-04 remote<BR>DG11J1-3A remote<BR>DG11J1-91 remote<BR>SPIS409L A/C<BR>SPIS412L A/C<BR>SPIW409L A/C<BR>SPIW412L A/C<BR>SPIW418L A/C | DG11J13A<BR>DG11J191 | Yes |
| [Whynter](https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/ir_Whynter.cpp) | **Whynter** | ARC-110WD A/C | | - |
## Send only protocols:
- GLOBALCACHE
- PRONTO
- RAW
- SHERWOOD
## Send & decodable protocols:
- AIWA_RC_T501
- ARGO
- CARRIER_AC
- COOLIX
- DAIKIN
- DAIKIN160
- DAIKIN2
- DAIKIN216
- DENON
- DISH
- ELECTRA_AC
- FUJITSU_AC
- GICABLE
- GOODWEATHER
- GREE
- HAIER_AC
- HAIER_AC_YRW02
- HITACHI_AC
- HITACHI_AC1
- HITACHI_AC2
- INAX
- JVC
- KELVINATOR
- LASERTAG
- LEGOPF
- LG
- LG2
- LUTRON
- MAGIQUEST
- MIDEA
- MITSUBISHI
- MITSUBISHI2
- MITSUBISHI_AC
- MITSUBISHI_HEAVY_152
- MITSUBISHI_HEAVY_88
- MWM
- NEC
- NEC_LIKE
- NEOCLIMA
- NIKAI
- PANASONIC
- PANASONIC_AC
- PIONEER
- RC5
- RC5X
- RC6
- RCMM
- SAMSUNG
- SAMSUNG36
- SAMSUNG_AC
- SANYO
- SANYO_LC7461
- SHARP
- SHARP_AC
- SONY
- TCL112AC
- TECO
- TOSHIBA_AC
- TROTEC
- VESTEL_AC
- WHIRLPOOL_AC
- WHYNTER

View File

@ -6,7 +6,7 @@
* TL;DR: The IR LED needs to be driven by a transistor for a good result.
*
* Suggested circuit:
* https://github.com/markszabo/IRremoteESP8266/wiki#ir-sending
* https://github.com/crankyoldgit/IRremoteESP8266/wiki#ir-sending
*
* Common mistakes & tips:
* * Don't just connect the IR LED directly to the pin, it won't
@ -23,9 +23,7 @@
* * ESP-01 modules are tricky. We suggest you use a module with more GPIOs
* for your first time. e.g. ESP-12 etc.
*/
#ifndef UNIT_TEST
#include <Arduino.h>
#endif
#include <IRremoteESP8266.h>
#include <IRsend.h>
#include <ir_Samsung.h>
@ -57,31 +55,29 @@ void setup() {
}
void loop() {
// Turn the A/C unit on and set to cooling mode.
// Power changes require we send an extended message.
Serial.println("Sending an extended IR command to A/C ...");
// Turn the A/C unit on
Serial.println("Turn on the A/C ...");
ac.on();
ac.send();
printState();
delay(15000); // wait 15 seconds
// and set to cooling mode.
Serial.println("Set the A/C mode to cooling ...");
ac.setMode(kSamsungAcCool);
ac.sendExtended();
ac.send();
printState();
delay(15000); // wait 15 seconds
// Increase the fan speed.
Serial.println("Sending a normal IR command to A/C ...");
Serial.println("Set the fan to high and the swing on ...");
ac.setFan(kSamsungAcFanHigh);
ac.send();
printState();
delay(15000);
// Change to swing the fan.
Serial.println("Sending a normal IR command to A/C ...");
ac.setSwing(true);
ac.send();
printState();
delay(15000);
// Change to Fan mode, lower the speed, and stop the swing.
Serial.println("Sending a normal IR command to A/C ...");
Serial.println("Set the A/C to fan only with a low speed, & no swing ...");
ac.setSwing(false);
ac.setMode(kSamsungAcFan);
ac.setFan(kSamsungAcFanLow);
@ -90,10 +86,9 @@ void loop() {
delay(15000);
// Turn the A/C unit off.
// Power changes require we send an extended message.
Serial.println("Sending an extended IR command to A/C ...");
Serial.println("Turn off the A/C ...");
ac.off();
ac.sendExtended();
ac.send();
printState();
delay(15000); // wait 15 seconds
}

View File

@ -0,0 +1,18 @@
[platformio]
src_dir = .
[env]
lib_extra_dirs = ../../
lib_ldf_mode = deep+
lib_ignore = examples
build_flags =
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
[env:esp32dev]
platform = espressif32
framework = arduino
board = esp32dev

View File

@ -0,0 +1,130 @@
/*
* IRremoteESP8266: DumbIRRepeater.ino - Record and playback IR codes.
* Copyright 2019 David Conran (crankyoldgit)
*
* This program will try to capture incoming IR messages and replay them back.
* It doesn't use any of the advanced detection features, thus it will just
* replay the messages at fixed modulated frequency (kFrequency) and a 50% duty
* cycle.
*
* Note:
* This might NOT be the frequency of the incoming message, so some replayed
* messages may not work. The frequency of incoming messages & duty cycle is
* lost at the point of the Hardware IR demodulator. The ESP can't see it.
*
* W A R N I N G
* This code is just for educational/example use only. No help will be given
* to you to make it do something else, or to make it work with some
* weird device or circuit, or to make it more usable or practical.
* If it works for you. Great. If not, Congratulations on changing/fixing it.
*
* An IR detector/demodulator must be connected to the input, kRecvPin.
* An IR LED circuit must be connected to the output, kIrLedPin.
*
* Example circuit diagrams (both are needed):
* https://github.com/crankyoldgit/IRremoteESP8266/wiki#ir-receiving
* https://github.com/crankyoldgit/IRremoteESP8266/wiki#ir-sending
*
* Common mistakes & tips:
* * Don't just connect the IR LED directly to the pin, it won't
* have enough current to drive the IR LED effectively.
* * Make sure you have the IR LED polarity correct.
* See: https://learn.sparkfun.com/tutorials/polarity/diode-and-led-polarity
* * Some digital camera/phones can be used to see if the IR LED is flashed.
* Replace the IR LED with a normal LED if you don't have a digital camera
* when debugging.
* * Avoid using the following pins unless you really know what you are doing:
* * Pin 0/D3: Can interfere with the boot/program mode & support circuits.
* * Pin 1/TX/TXD0: Any serial transmissions from the ESP will interfere.
* * Pin 3/RX/RXD0: Any serial transmissions to the ESP will interfere.
* * ESP-01 modules are tricky. We suggest you use a module with more GPIOs
* for your first time. e.g. ESP-12 etc.
*
* Changes:
* Version 1.0: June, 2019
* - Initial version.
*/
#include <Arduino.h>
#include <IRsend.h>
#include <IRrecv.h>
#include <IRremoteESP8266.h>
#include <IRutils.h>
// ==================== start of TUNEABLE PARAMETERS ====================
// The GPIO an IR detector/demodulator is connected to. Recommended: 14 (D5)
const uint16_t kRecvPin = 14;
// GPIO to use to control the IR LED circuit. Recommended: 4 (D2).
const uint16_t kIrLedPin = 4;
// The Serial connection baud rate.
// NOTE: Make sure you set your Serial Monitor to the same speed.
const uint32_t kBaudRate = 115200;
// As this program is a special purpose capture/resender, let's use a larger
// than expected buffer so we can handle very large IR messages.
// i.e. Up to 512 bits.
const uint16_t kCaptureBufferSize = 1024;
// kTimeout is the Nr. of milli-Seconds of no-more-data before we consider a
// message ended.
const uint8_t kTimeout = 50; // Milli-Seconds
// kFrequency is the modulation frequency all messages will be replayed at.
const uint16_t kFrequency = 38000; // in Hz. e.g. 38kHz.
// ==================== end of TUNEABLE PARAMETERS ====================
// The IR transmitter.
IRsend irsend(kIrLedPin);
// The IR receiver.
IRrecv irrecv(kRecvPin, kCaptureBufferSize, kTimeout, false);
// Somewhere to store the captured message.
decode_results results;
// This section of code runs only once at start-up.
void setup() {
irrecv.enableIRIn(); // Start up the IR receiver.
irsend.begin(); // Start up the IR sender.
Serial.begin(kBaudRate, SERIAL_8N1);
while (!Serial) // Wait for the serial connection to be establised.
delay(50);
Serial.println();
Serial.print("DumbIRRepeater is now running and waiting for IR input "
"on Pin ");
Serial.println(kRecvPin);
Serial.print("and will retransmit it on Pin ");
Serial.println(kIrLedPin);
}
// The repeating section of the code
void loop() {
// Check if an IR message has been received.
if (irrecv.decode(&results)) { // We have captured something.
// The capture has stopped at this point.
// Convert the results into an array suitable for sendRaw().
// resultToRawArray() allocates the memory we need for the array.
uint16_t *raw_array = resultToRawArray(&results);
// Find out how many elements are in the array.
uint16_t length = getCorrectedRawLength(&results);
// Send it out via the IR LED circuit.
irsend.sendRaw(raw_array, length, kFrequency);
// Resume capturing IR messages. It was not restarted until after we sent
// the message so we didn't capture our own message.
irrecv.resume();
// Deallocate the memory allocated by resultToRawArray().
delete [] raw_array;
// Display a crude timestamp & notification.
uint32_t now = millis();
Serial.printf(
"%06u.%03u: A message that was %d entries long was retransmitted.\n",
now / 1000, now % 1000, length);
}
yield(); // Or delay(milliseconds); This ensures the ESP doesn't WDT reset.
}

View File

@ -0,0 +1,18 @@
[platformio]
src_dir = .
[env]
lib_extra_dirs = ../../
lib_ldf_mode = deep+
lib_ignore = examples
build_flags =
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
[env:esp32dev]
platform = espressif32
framework = arduino
board = esp32dev

View File

@ -17,7 +17,7 @@
* TL;DR: The IR LED needs to be driven by a transistor for a good result.
*
* Suggested circuit:
* https://github.com/markszabo/IRremoteESP8266/wiki#ir-sending
* https://github.com/crankyoldgit/IRremoteESP8266/wiki#ir-sending
*
* Common mistakes & tips:
* * Don't just connect the IR LED directly to the pin, it won't
@ -36,9 +36,7 @@
* for your first time. e.g. ESP-12 etc.
*/
#ifndef UNIT_TEST
#include <Arduino.h>
#endif
#include <IRremoteESP8266.h>
#include <IRsend.h>

View File

@ -0,0 +1,18 @@
[platformio]
src_dir = .
[env]
lib_extra_dirs = ../../
lib_ldf_mode = deep+
lib_ignore = examples
build_flags =
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
[env:esp32dev]
platform = espressif32
framework = arduino
board = esp32dev

View File

@ -37,10 +37,13 @@
* can check your wifi router for it's address.
*/
#ifndef UNIT_TEST
#include <Arduino.h>
#endif
#if defined(ESP8266)
#include <ESP8266WiFi.h>
#endif // ESP8266
#if defined(ESP32)
#include <WiFi.h>
#endif // ESP32
#include <IRremoteESP8266.h>
#include <IRsend.h>
#include <WiFiClient.h>

View File

@ -0,0 +1,18 @@
[platformio]
src_dir = .
[env]
lib_extra_dirs = ../../
lib_ldf_mode = deep+
lib_ignore = examples
build_flags =
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
[env:esp32dev]
platform = espressif32
framework = arduino
board = esp32dev

View File

@ -18,17 +18,38 @@
#define MQTT_ENABLE true // Whether or not MQTT is used at all.
#endif // MQTT_ENABLE
#ifndef EXAMPLES_ENABLE
// Whether or not examples are included. `false` saves ~2.5K of program space.
#define EXAMPLES_ENABLE true
#endif // EXAMPLES_ENABLE
// ---------------------- Board Related Settings -------------------------------
// NOTE: Make sure you set your Serial Monitor to the same speed.
#define BAUD_RATE 115200 // Serial port Baud rate.
// GPIO the IR LED is connected to/controlled by. GPIO 4 = D2.
#define IR_LED 4 // <=- CHANGE_ME (optional)
// define IR_LED 3 // For an ESP-01 we suggest you use RX/GPIO3/Pin 7.
// Change if you need multiple independent send gpios & topics. (MQTT only)
const uint8_t kNrOfIrTxGpios = 1;
// Default GPIO the IR LED is connected to/controlled by. GPIO 4 = D2.
// For an ESP-01 we suggest you use RX/GPIO3/Pin 7. i.e. kDefaultIrLed = 3
// Note: A value of -1 means unused.
const int8_t kDefaultIrLed = 4; // <=- CHANGE_ME (optional)
// GPIO the IR RX module is connected to/controlled by. e.g. GPIO 14 = D5.
// Comment this out to disable receiving/decoding IR messages entirely.
#define IR_RX 14 // <=- CHANGE_ME (optional)
// **DANGER** Optional flag to invert the output. (default = false)
// `false`: The LED is illuminated when the GPIO is HIGH.
// `true`: The LED is illuminated when GPIO is LOW rather than HIGH.
// Setting this to something other than the default could
// easily destroy your IR LED if you are overdriving it.
// Unless you *REALLY* know what you are doing, don't change this.
const bool kInvertTxOutput = false;
// Default GPIO the IR demodulator is connected to/controlled by. GPIO 14 = D5.
const int8_t kDefaultIrRx = 14; // <=- CHANGE_ME (optional)
// Enable/disable receiving/decoding IR messages entirely.
// Note: IR_RX costs about 40k+ of program memory.
#define IR_RX true
// Should we use PULLUP on the IR Rx gpio?
#define IR_RX_PULLUP false
// --------------------- Network Related Settings ------------------------------
@ -49,6 +70,8 @@ const IPAddress kSubnetMask = IPAddress(255, 255, 255, 0);
// before we will connect.
// The unset default is 8%.
// (Uncomment to enable)
// Do you want/need mdns enabled? (https://en.wikipedia.org/wiki/Multicast_DNS)
#define MDNS_ENABLE true // `false` to disable and save ~21k of program space.
// ----------------------- HTTP Related Settings -------------------------------
#define FIRMWARE_OTA true // Allow remote update of the firmware via http.
@ -56,8 +79,9 @@ const IPAddress kSubnetMask = IPAddress(255, 255, 255, 0);
// Note: Firmware OTA is also disabled until
// a password is set.
#define HTML_PASSWORD_ENABLE false // Protect access to the HTML interface.
// Note: OTA update is always passworded.
// If you do not set a password, Firmware OTA updates will be blocked.
// Note: OTA & GPIO updates are always
// passworded.
// If you do not set a password, Firmware OTA & GPIO updates will be blocked.
// ----------------------- MQTT Related Settings -------------------------------
#if MQTT_ENABLE
@ -71,13 +95,29 @@ const uint32_t kMqttReconnectTime = 5000; // Delay(ms) between reconnect tries.
#define MQTT_CLIMATE "ac" // Sub-topic for the climate topics.
#define MQTT_CLIMATE_CMND "cmnd" // Sub-topic for the climate command topics.
#define MQTT_CLIMATE_STAT "stat" // Sub-topic for the climate stat topics.
#define MQTTbroadcastInterval 10 * 60 // Seconds between rebroadcasts
// Enable sending/receiving climate via JSON. `true` cost ~5k of program space.
#define MQTT_CLIMATE_JSON false
// Do we send an IR message when we reboot and recover the existing A/C state?
// If set to `false` you may miss requested state changes while the ESP was
// down. If set to `true`, it will resend the previous desired state sent to the
// A/C. Depending on your circumstances, you may need to change this.
#define MQTT_CLIMATE_IR_SEND_ON_RESTART false
#define MQTTbroadcastInterval 10 * 60 // Seconds between rebroadcasts.
#define QOS 1 // MQTT broker should queue up any unreceived messages for us
// #define QOS 0 // MQTT broker WON'T queue up messages for us. Fire & Forget.
// Enable(true)/Disable(false) the option to send a MQTT Discovery message for
// the AirCon/Climate system to Home Assistant. `false` saves ~1.5k.
#define MQTT_DISCOVERY_ENABLE true
#endif // MQTT_ENABLE
// ------------------------ IR Capture Settings --------------------------------
// Should we stop listening for IR messages when we send a message via IR?
// Set this to `true` if your IR demodulator is picking up self transmissions.
// Use `false` if it isn't or can't see the self-sent transmissions
// Using `true` may mean some incoming IR messages are lost or garbled.
// i.e. `false` is better if you can get away with it.
#define DISABLE_CAPTURE_WHILE_TRANSMITTING true
// Let's use a larger than normal buffer so we can handle AirCon remote codes.
const uint16_t kCaptureBufferSize = 1024;
#if DECODE_AC
@ -94,16 +134,27 @@ const uint16_t kMinUnknownSize = 2 * 10;
#define REPORT_RAW_UNKNOWNS false // Report the whole buffer, recommended:
// MQTT_MAX_PACKET_SIZE of 1024 or more
// Should we use and report individual A/C settings we capture via IR if we
// can understand the individual settings of the remote.
// e.g. Aquire the A/C settings from an actual A/C IR remote and override
// any local settings set via MQTT/HTTP etc.
#define USE_DECODED_AC_SETTINGS true // `false` to disable. `true` to enable.
// Should we allow or ignore an A/C IR remote to override the A/C protocol/model
// as set via MQTT or HTTP?
// e.g. If `true`, you can use any fully supported A/C remote to control
// another brand's or model's A/C unit. `false` means change to the new
// protocol/model if we support it via `USE_DECODED_AC_SETTINGS`.
#define IGNORE_DECODED_AC_PROTOCOL true
// Do we (re-)send the captured & decoded A/C message via the IR_LED?
// `false` if you don't want to repeat the captured message.
// e.g. Useful if the IR demodulator is located in the path between the remote
// and the A/C unit so the command isn't sent twice.
// `true` if you want it sent anyway.
// e.g. The IR demodulator is in a completely different location than than the
// actual a/c unit.
#define REPLAY_DECODED_AC_MESSAGE false
// ------------------------ Advanced Usage Only --------------------------------
// Change if you need multiple independent send gpio/topics.
const uint8_t gpioTable[] = {
IR_LED, // Default GPIO. e.g. ir_server/send or ir_server/send_0
// Uncomment the following as needed.
// NOTE: Remember to disable DEBUG if you are using one of the serial pins.
// 5, // GPIO 5 / D1 e.g. ir_server/send_1
// 14, // GPIO 14 / D5 e.g. ir_server/send_2
// 16, // GPIO 16 / D0 e.g. ir_server/send_3
};
#define KEY_PROTOCOL "protocol"
#define KEY_MODEL "model"
@ -119,10 +170,11 @@ const uint8_t gpioTable[] = {
#define KEY_BEEP "beep"
#define KEY_ECONO "econo"
#define KEY_SLEEP "sleep"
#define KEY_CLOCK "clock"
#define KEY_FILTER "filter"
#define KEY_CLEAN "clean"
#define KEY_CELSIUS "use_celsius"
#define KEY_JSON "json"
#define KEY_RESEND "resend"
// HTML arguments we will parse for IR code information.
#define KEY_TYPE "type" // KEY_PROTOCOL is also checked too.
@ -130,6 +182,10 @@ const uint8_t gpioTable[] = {
#define KEY_BITS "bits"
#define KEY_REPEAT "repeats"
// GPIO html/config keys
#define KEY_TX_GPIO "tx"
#define KEY_RX_GPIO "rx"
// Text for Last Will & Testament status messages.
const char* kLwtOnline = "Online";
const char* kLwtOffline = "Offline";
@ -140,24 +196,36 @@ const uint8_t kUsernameLength = 15;
const uint8_t kPasswordLength = 20;
// -------------------------- Debug Settings -----------------------------------
// Disable debug output if any of the IR pins are on the TX (D1) pin.
// Note: This is a crude method to catch the common use cases.
// See `isSerialGpioUsedByIr()` for the better method.
#if (IR_LED != 1 && IR_RX != 1)
// Debug output is disabled if any of the IR pins are on the TX (D1) pin.
// See `isSerialGpioUsedByIr()`.
// Note: Debug costs ~6k of program space.
#ifndef DEBUG
#define DEBUG true // Change to 'false' to disable all serial output.
#define DEBUG false // Change to 'true' for serial debug output.
#endif // DEBUG
#else // (IR_LED != 1 && IR_RX != 1)
#undef DEBUG
#define DEBUG false
#endif
// ----------------- End of User Configuration Section -------------------------
// Constants
#define _MY_VERSION_ "v1.0.0"
#define _MY_VERSION_ "v1.3.2-testing"
const uint8_t kRebootTime = 15; // Seconds
const uint8_t kQuickDisplayTime = 2; // Seconds
// Gpio related
#if defined(ESP8266)
const int8_t kTxGpios[] = {-1, 0, 1, 2, 3, 4, 5, 12, 13, 14, 15, 16};
const int8_t kRxGpios[] = {-1, 0, 1, 2, 3, 4, 5, 12, 13, 14, 15};
#endif // ESP8266
#if defined(ESP32)
// Ref: https://randomnerdtutorials.com/esp32-pinout-reference-gpios/
const int8_t kTxGpios[] = {
-1, 0, 1, 2, 3, 4, 5, 12, 13, 14, 15, 16, 17, 18, 19, 21, 22, 23,
25, 26, 27, 32, 33};
const int8_t kRxGpios[] = {
-1, 1, 2, 3, 4, 5, 12, 13, 14, 15, 16, 17, 18, 19, 21, 22, 23,
25, 26, 27, 32, 33, 34, 35, 36, 39};
#endif // ESP32
const uint8_t kSendTableSize = sizeof(gpioTable);
// JSON stuff
// Name of the json config file in SPIFFS.
const char* kConfigFile = "/config.json";
@ -169,45 +237,87 @@ const char* kMqttPrefixKey = "mqtt_prefix";
const char* kHostnameKey = "hostname";
const char* kHttpUserKey = "http_user";
const char* kHttpPassKey = "http_pass";
const char* kCommandDelimiter = ",";
// URLs
const char* kUrlRoot = "/";
const char* kUrlAdmin = "/admin";
const char* kUrlAircon = "/aircon";
const char* kUrlSendDiscovery = "/send_discovery";
const char* kUrlExamples = "/examples";
const char* kUrlGpio = "/gpio";
const char* kUrlGpioSet = "/gpio/set";
const char* kUrlInfo = "/info";
const char* kUrlReboot = "/quitquitquit";
const char* kUrlWipe = "/reset";
#if MQTT_ENABLE
const uint32_t kBroadcastPeriodMs = MQTTbroadcastInterval * 1000; // mSeconds.
const uint32_t kStatListenPeriodMs = 5 * 1000; // mSeconds
const int32_t kMaxPauseMs = 10000; // 10 Seconds.
const char* kSequenceDelimiter = ";";
const char kPauseChar = 'P';
#if defined(ESP8266)
const uint32_t kChipId = ESP.getChipId();
#endif // ESP8266
#if defined(ESP32)
const uint32_t kChipId = ESP.getEfuseMac(); // Discard the top 16 bits.
#endif // ESP32
const char* kClimateTopics =
"(" KEY_PROTOCOL "|" KEY_MODEL "|" KEY_POWER "|" KEY_MODE "|" KEY_TEMP "|"
KEY_FANSPEED "|" KEY_SWINGV "|" KEY_SWINGH "|" KEY_QUIET "|"
KEY_TURBO "|" KEY_LIGHT "|" KEY_BEEP "|" KEY_ECONO "|" KEY_SLEEP "|"
KEY_FILTER "|" KEY_CLEAN "|" KEY_CELSIUS "|" KEY_RESEND
#if MQTT_CLIMATE_JSON
"|" KEY_JSON
#endif // MQTT_CLIMATE_JSON
")<br>";
void mqttCallback(char* topic, byte* payload, unsigned int length);
String listOfCommandTopics(void);
void handleSendMqttDiscovery(void);
void subscribing(const String topic_name);
void unsubscribing(const String topic_name);
void mqttLog(const String mesg);
void mqttLog(const char* str);
bool mountSpiffs(void);
bool reconnect(void);
void receivingMQTT(String const topic_name, String const callback_str);
void callback(char* topic, byte* payload, unsigned int length);
void sendMQTTDiscovery(const char *topic);
void doBroadcast(TimerMs *timer, const uint32_t interval,
const commonAcState_t state, const bool retain,
const stdAc::state_t state, const bool retain,
const bool force);
#if MQTT_CLIMATE_JSON
stdAc::state_t jsonToState(const stdAc::state_t current, const String str);
void sendJsonState(const stdAc::state_t state, const String topic,
const bool retain = false, const bool ha_mode = true);
#endif // MQTT_CLIMATE_JSON
#endif // MQTT_ENABLE
bool isSerialGpioUsedByIr(void);
void debug(const char *str);
void saveWifiConfigCallback(void);
void saveWifiConfig(void);
void loadWifiConfigFile(void);
void doRestart(const char* str, const bool serial_only = false);
String msToHumanString(uint32_t const msecs);
String timeElapsed(uint32_t const msec);
String timeSince(uint32_t const start);
String listOfSendGpios(void);
String gpioToString(const int16_t gpio);
uint8_t getDefaultIrSendIdx(void);
IRsend* getDefaultIrSendPtr(void);
int8_t getDefaultTxGpio(void);
String listOfTxGpios(void);
bool hasUnsafeHTMLChars(String input);
String htmlHeader(const String title, const String h1_text = "");
String htmlEnd(void);
String htmlButton(const String url, const String button,
const String text = "");
String htmlMenu(void);
void handleRoot(void);
String addJsReloadUrl(const String url, const uint16_t timeout_s,
const bool notify);
void handleExamples(void);
String boolToString(const bool value);
String opmodeToString(const stdAc::opmode_t mode);
String fanspeedToString(const stdAc::fanspeed_t speed);
String swingvToString(const stdAc::swingv_t swingv);
String swinghToString(const stdAc::swingh_t swingh);
String htmlSelectBool(const String name, const bool def);
String htmlSelectProtocol(const String name, const decode_type_t def);
String htmlSelectModel(const String name, const int16_t def);
@ -221,7 +331,7 @@ void handleAdmin(void);
void handleInfo(void);
void handleReset(void);
void handleReboot(void);
bool parseStringAndSendAirCon(IRsend *irsend, const uint16_t irType,
bool parseStringAndSendAirCon(IRsend *irsend, const decode_type_t irType,
const String str);
uint16_t countValuesInStr(const String str, char sep);
uint16_t * newCodeArray(const uint16_t size);
@ -241,18 +351,21 @@ void setup_wifi(void);
void init_vars(void);
void setup(void);
void loop(void);
uint32_t maxSketchSpace(void);
uint64_t getUInt64fromHex(char const *str);
bool sendIRCode(IRsend *irsend, int const ir_type,
bool sendIRCode(IRsend *irsend, decode_type_t const ir_type,
uint64_t const code, char const * code_str, uint16_t bits,
uint16_t repeat);
bool sendInt(const String topic, const int32_t num, const bool retain);
bool sendBool(const String topic, const bool on, const bool retain);
bool sendString(const String topic, const String str, const bool retain);
bool sendFloat(const String topic, const float_t temp, const bool retain);
commonAcState_t updateClimate(commonAcState_t current, const String str,
stdAc::state_t updateClimate(stdAc::state_t current, const String str,
const String prefix, const String payload);
bool cmpClimate(const commonAcState_t a, const commonAcState_t b);
bool sendClimate(const commonAcState_t prev, const commonAcState_t next,
bool cmpClimate(const stdAc::state_t a, const stdAc::state_t b);
bool sendClimate(const stdAc::state_t prev, const stdAc::state_t next,
const String topic_prefix, const bool retain,
const bool forceMQTT, const bool forceIR);
const bool forceMQTT, const bool forceIR,
const bool enableIR = true);
bool decodeCommonAc(const decode_results *decode);
#endif // EXAMPLES_IRMQTTSERVER_IRMQTTSERVER_H_

View File

@ -0,0 +1,62 @@
[platformio]
src_dir = .
[env]
lib_extra_dirs = ../../
lib_ldf_mode = deep+
lib_ignore = examples
build_flags = -DMQTT_MAX_PACKET_SIZE=768
[common]
lib_deps_builtin =
lib_deps_external =
PubSubClient
ArduinoJson@<6.0
[common_esp8266]
lib_deps_external =
${common.lib_deps_builtin}
${common.lib_deps_external}
WifiManager@>=0.14
[common_esp32]
lib_deps_external =
${common.lib_deps_builtin}
${common.lib_deps_external}
https://github.com/tzapu/WiFiManager.git#development
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
lib_deps = ${common_esp8266.lib_deps_external}
[env:d1_mini]
platform = espressif8266
framework = arduino
board = d1_mini
lib_deps = ${common_esp8266.lib_deps_external}
[env:d1_mini_no_mqtt]
platform = espressif8266
framework = arduino
board = d1_mini
build_flags =
${env.build_flags}
-DMQTT_ENABLE=false
lib_deps = ${common_esp8266.lib_deps_external}
[env:esp32dev]
platform = espressif32
framework = arduino
board = esp32dev
lib_deps = ${common_esp32.lib_deps_external}
[env:esp01_1m]
platform = espressif8266
framework = arduino
board = esp01_1m
build_flags =
${env.build_flags}
-Wl,-Teagle.flash.1m64.ld
lib_deps = ${common_esp8266.lib_deps_external}

View File

@ -1,15 +1,17 @@
/*
* IRremoteESP8266: IRServer - demonstrates sending IR codes controlled from a webserver
* Version 0.3 May, 2019
* Version 0.2 June, 2017
* Copyright 2015 Mark Szabo
* Copyright 2019 David Conran
*
* An IR LED circuit *MUST* be connected to the ESP8266 on a pin
* An IR LED circuit *MUST* be connected to the ESP on a pin
* as specified by kIrLed below.
*
* TL;DR: The IR LED needs to be driven by a transistor for a good result.
*
* Suggested circuit:
* https://github.com/markszabo/IRremoteESP8266/wiki#ir-sending
* https://github.com/crankyoldgit/IRremoteESP8266/wiki#ir-sending
*
* Common mistakes & tips:
* * Don't just connect the IR LED directly to the pin, it won't
@ -26,12 +28,17 @@
* * ESP-01 modules are tricky. We suggest you use a module with more GPIOs
* for your first time. e.g. ESP-12 etc.
*/
#ifndef UNIT_TEST
#include <Arduino.h>
#endif
#if defined(ESP8266)
#include <ESP8266WiFi.h>
#include <ESP8266WebServer.h>
#include <ESP8266mDNS.h>
#endif // ESP8266
#if defined(ESP32)
#include <WiFi.h>
#include <WebServer.h>
#include <ESPmDNS.h>
#endif // ESP32
#include <IRremoteESP8266.h>
#include <IRsend.h>
#include <WiFiClient.h>
@ -40,18 +47,27 @@ const char* kSsid = ".....";
const char* kPassword = ".....";
MDNSResponder mdns;
#if defined(ESP8266)
ESP8266WebServer server(80);
#undef HOSTNAME
#define HOSTNAME "esp8266"
#endif // ESP8266
#if defined(ESP32)
WebServer server(80);
#undef HOSTNAME
#define HOSTNAME "esp32"
#endif // ESP32
const uint16_t kIrLed = 4; // ESP8266 GPIO pin to use. Recommended: 4 (D2).
const uint16_t kIrLed = 4; // ESP GPIO pin to use. Recommended: 4 (D2).
IRsend irsend(kIrLed); // Set the GPIO to be used to sending the message.
void handleRoot() {
server.send(200, "text/html",
"<html>" \
"<head><title>ESP8266 Demo</title></head>" \
"<head><title>" HOSTNAME " Demo</title></head>" \
"<body>" \
"<h1>Hello from ESP8266, you can send NEC encoded IR" \
"<h1>Hello from " HOSTNAME ", you can send NEC encoded IR" \
"signals from here!</h1>" \
"<p><a href=\"ir?code=16769055\">Send 0xFFE01F</a></p>" \
"<p><a href=\"ir?code=16429347\">Send 0xFAB123</a></p>" \
@ -104,7 +120,11 @@ void setup(void) {
Serial.print("IP address: ");
Serial.println(WiFi.localIP().toString());
if (mdns.begin("esp8266", WiFi.localIP())) {
#if defined(ESP8266)
if (mdns.begin(HOSTNAME, WiFi.localIP())) {
#else // ESP8266
if (mdns.begin(HOSTNAME)) {
#endif // ESP8266
Serial.println("MDNS responder started");
}

View File

@ -0,0 +1,18 @@
[platformio]
src_dir = .
[env]
lib_extra_dirs = ../../
lib_ldf_mode = deep+
lib_ignore = examples
build_flags =
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
[env:esp32dev]
platform = espressif32
framework = arduino
board = esp32dev

View File

@ -6,7 +6,7 @@
* An IR detector/demodulator must be connected to the input kRecvPin.
* Copyright 2009 Ken Shirriff, http://arcfn.com
* Example circuit diagram:
* https://github.com/markszabo/IRremoteESP8266/wiki#ir-receiving
* https://github.com/crankyoldgit/IRremoteESP8266/wiki#ir-receiving
* Changes:
* Version 0.2 June, 2017
* Changed GPIO pin to the same as other examples.
@ -16,9 +16,7 @@
* Based on Ken Shirriff's IrsendDemo Version 0.1 July, 2009
*/
#ifndef UNIT_TEST
#include <Arduino.h>
#endif
#include <IRremoteESP8266.h>
#include <IRrecv.h>
#include <IRutils.h>

View File

@ -0,0 +1,18 @@
[platformio]
src_dir = .
[env]
lib_extra_dirs = ../../
lib_ldf_mode = deep+
lib_ignore = examples
build_flags =
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
[env:esp32dev]
platform = espressif32
framework = arduino
board = esp32dev

View File

@ -22,9 +22,7 @@
* LG added by Darryl Smith (based on the JVC protocol)
*/
#ifndef UNIT_TEST
#include <Arduino.h>
#endif
#include <IRremoteESP8266.h>
#include <IRrecv.h>
#include <IRutils.h>

View File

@ -0,0 +1,18 @@
[platformio]
src_dir = .
[env]
lib_extra_dirs = ../../
lib_ldf_mode = deep+
lib_ignore = examples
build_flags =
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
[env:esp32dev]
platform = espressif32
framework = arduino
board = esp32dev

View File

@ -3,12 +3,14 @@
* An IR detector/demodulator must be connected to the input kRecvPin.
*
* Copyright 2009 Ken Shirriff, http://arcfn.com
* Copyright 2017 David Conran
* Copyright 2017-2019 David Conran
*
* Example circuit diagram:
* https://github.com/markszabo/IRremoteESP8266/wiki#ir-receiving
* https://github.com/crankyoldgit/IRremoteESP8266/wiki#ir-receiving
*
* Changes:
* Version 0.5 June, 2019
* - Move A/C description to IRac.cpp.
* Version 0.4 July, 2018
* - Minor improvements and more A/C unit support.
* Version 0.3 November, 2017
@ -19,31 +21,11 @@
* Based on Ken Shirriff's IrsendDemo Version 0.1 July, 2009,
*/
#ifndef UNIT_TEST
#include <Arduino.h>
#endif
#include <IRrecv.h>
#include <IRremoteESP8266.h>
#include <IRac.h>
#include <IRutils.h>
// The following are only needed for extended decoding of A/C Messages
#include <ir_Coolix.h>
#include <ir_Daikin.h>
#include <ir_Fujitsu.h>
#include <ir_Gree.h>
#include <ir_Haier.h>
#include <ir_Hitachi.h>
#include <ir_Kelvinator.h>
#include <ir_Midea.h>
#include <ir_Mitsubishi.h>
#include <ir_MitsubishiHeavy.h>
#include <ir_Panasonic.h>
#include <ir_Samsung.h>
#include <ir_Tcl.h>
#include <ir_Teco.h>
#include <ir_Toshiba.h>
#include <ir_Vestel.h>
#include <ir_Whirlpool.h>
// ==================== start of TUNEABLE PARAMETERS ====================
// An IR detector/demodulator is connected to GPIO pin 14
@ -114,171 +96,19 @@ const uint16_t kMinUnknownSize = 12;
// Use turn on the save buffer feature for more complete capture coverage.
IRrecv irrecv(kRecvPin, kCaptureBufferSize, kTimeout, true);
decode_results results; // Somewhere to store the results
// Display the human readable state of an A/C message if we can.
void dumpACInfo(decode_results *results) {
String description = "";
#if DECODE_DAIKIN
if (results->decode_type == DAIKIN) {
IRDaikinESP ac(0);
ac.setRaw(results->state);
description = ac.toString();
}
#endif // DECODE_DAIKIN
#if DECODE_DAIKIN2
if (results->decode_type == DAIKIN2) {
IRDaikin2 ac(0);
ac.setRaw(results->state);
description = ac.toString();
}
#endif // DECODE_DAIKIN2
#if DECODE_DAIKIN216
if (results->decode_type == DAIKIN216) {
IRDaikin216 ac(0);
ac.setRaw(results->state);
description = ac.toString();
}
#endif // DECODE_DAIKIN216
#if DECODE_FUJITSU_AC
if (results->decode_type == FUJITSU_AC) {
IRFujitsuAC ac(0);
ac.setRaw(results->state, results->bits / 8);
description = ac.toString();
}
#endif // DECODE_FUJITSU_AC
#if DECODE_KELVINATOR
if (results->decode_type == KELVINATOR) {
IRKelvinatorAC ac(0);
ac.setRaw(results->state);
description = ac.toString();
}
#endif // DECODE_KELVINATOR
#if DECODE_MITSUBISHI_AC
if (results->decode_type == MITSUBISHI_AC) {
IRMitsubishiAC ac(0);
ac.setRaw(results->state);
description = ac.toString();
}
#endif // DECODE_MITSUBISHI_AC
#if DECODE_MITSUBISHIHEAVY
if (results->decode_type == MITSUBISHI_HEAVY_88) {
IRMitsubishiHeavy88Ac ac(0);
ac.setRaw(results->state);
description = ac.toString();
}
if (results->decode_type == MITSUBISHI_HEAVY_152) {
IRMitsubishiHeavy152Ac ac(0);
ac.setRaw(results->state);
description = ac.toString();
}
#endif // DECODE_MITSUBISHIHEAVY
#if DECODE_TOSHIBA_AC
if (results->decode_type == TOSHIBA_AC) {
IRToshibaAC ac(0);
ac.setRaw(results->state);
description = ac.toString();
}
#endif // DECODE_TOSHIBA_AC
#if DECODE_GREE
if (results->decode_type == GREE) {
IRGreeAC ac(0);
ac.setRaw(results->state);
description = ac.toString();
}
#endif // DECODE_GREE
#if DECODE_MIDEA
if (results->decode_type == MIDEA) {
IRMideaAC ac(0);
ac.setRaw(results->value); // Midea uses value instead of state.
description = ac.toString();
}
#endif // DECODE_MIDEA
#if DECODE_HAIER_AC
if (results->decode_type == HAIER_AC) {
IRHaierAC ac(0);
ac.setRaw(results->state);
description = ac.toString();
}
#endif // DECODE_HAIER_AC
#if DECODE_HAIER_AC_YRW02
if (results->decode_type == HAIER_AC_YRW02) {
IRHaierACYRW02 ac(0);
ac.setRaw(results->state);
description = ac.toString();
}
#endif // DECODE_HAIER_AC_YRW02
#if DECODE_SAMSUNG_AC
if (results->decode_type == SAMSUNG_AC) {
IRSamsungAc ac(0);
ac.setRaw(results->state, results->bits / 8);
description = ac.toString();
}
#endif // DECODE_SAMSUNG_AC
#if DECODE_COOLIX
if (results->decode_type == COOLIX) {
IRCoolixAC ac(0);
ac.setRaw(results->value); // Coolix uses value instead of state.
description = ac.toString();
}
#endif // DECODE_COOLIX
#if DECODE_PANASONIC_AC
if (results->decode_type == PANASONIC_AC &&
results->bits > kPanasonicAcShortBits) {
IRPanasonicAc ac(0);
ac.setRaw(results->state);
description = ac.toString();
}
#endif // DECODE_PANASONIC_AC
#if DECODE_HITACHI_AC
if (results->decode_type == HITACHI_AC) {
IRHitachiAc ac(0);
ac.setRaw(results->state);
description = ac.toString();
}
#endif // DECODE_HITACHI_AC
#if DECODE_WHIRLPOOL_AC
if (results->decode_type == WHIRLPOOL_AC) {
IRWhirlpoolAc ac(0);
ac.setRaw(results->state);
description = ac.toString();
}
#endif // DECODE_WHIRLPOOL_AC
#if DECODE_VESTEL_AC
if (results->decode_type == VESTEL_AC) {
IRVestelAc ac(0);
ac.setRaw(results->value); // Like Coolix, use value instead of state.
description = ac.toString();
}
#endif // DECODE_VESTEL_AC
#if DECODE_TECO
if (results->decode_type == TECO) {
IRTecoAc ac(0);
ac.setRaw(results->value); // Like Coolix, use value instead of state.
description = ac.toString();
}
#endif // DECODE_TECO
#if DECODE_TCL112AC
if (results->decode_type == TCL112AC) {
IRTcl112Ac ac(0);
ac.setRaw(results->state);
description = ac.toString();
}
#endif // DECODE_TCL112AC
// If we got a human-readable description of the message, display it.
if (description != "") Serial.println("Mesg Desc.: " + description);
}
// The section of code run only once at start-up.
// This section of code runs only once at start-up.
void setup() {
#if defined(ESP8266)
Serial.begin(kBaudRate, SERIAL_8N1, SERIAL_TX_ONLY);
#else // ESP8266
Serial.begin(kBaudRate, SERIAL_8N1);
#endif // ESP8266
while (!Serial) // Wait for the serial connection to be establised.
delay(50);
Serial.println();
Serial.print("IRrecvDumpV2 is now running and waiting for IR input on Pin ");
Serial.println(kRecvPin);
Serial.printf("\nIRrecvDumpV2 is now running and waiting for IR input on Pin "
"%d\n", kRecvPin);
#if DECODE_HASH
// Ignore messages with less than minimum on or off pulses.
irrecv.setUnknownThreshold(kMinUnknownSize);
@ -287,36 +117,33 @@ void setup() {
}
// The repeating section of the code
//
void loop() {
// Check if the IR code has been received.
if (irrecv.decode(&results)) {
// Display a crude timestamp.
uint32_t now = millis();
Serial.printf("Timestamp : %06u.%03u\n", now / 1000, now % 1000);
// Check if we got an IR message tha was to big for our capture buffer.
if (results.overflow)
Serial.printf(
"WARNING: IR code is too big for buffer (>= %d). "
"This result shouldn't be trusted until this is resolved. "
"Edit & increase kCaptureBufferSize.\n",
kCaptureBufferSize);
// Display the library version the message was captured with.
Serial.println("Library : v" _IRREMOTEESP8266_VERSION_ "\n");
// Display the basic output of what we found.
Serial.print(resultToHumanReadableBasic(&results));
dumpACInfo(&results); // Display any extra A/C info if we have it.
// Display any extra A/C info if we have it.
String description = IRAcUtils::resultAcToString(&results);
if (description.length()) Serial.println("Mesg Desc.: " + description);
yield(); // Feed the WDT as the text output can take a while to print.
// Display the library version the message was captured with.
Serial.print("Library : v");
Serial.println(_IRREMOTEESP8266_VERSION_);
Serial.println();
// Output RAW timing info of the result.
Serial.println(resultToTimingInfo(&results));
yield(); // Feed the WDT (again)
// Output the results as source code
Serial.println(resultToSourceCode(&results));
Serial.println(""); // Blank line between entries
Serial.println(); // Blank line between entries
yield(); // Feed the WDT (again)
}
}

View File

@ -0,0 +1,18 @@
[platformio]
src_dir = .
[env]
lib_extra_dirs = ../../
lib_ldf_mode = deep+
lib_ignore = examples
build_flags =
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
[env:esp32dev]
platform = espressif32
framework = arduino
board = esp32dev

View File

@ -10,7 +10,7 @@
* TL;DR: The IR LED needs to be driven by a transistor for a good result.
*
* Suggested circuit:
* https://github.com/markszabo/IRremoteESP8266/wiki#ir-sending
* https://github.com/crankyoldgit/IRremoteESP8266/wiki#ir-sending
*
* Common mistakes & tips:
* * Don't just connect the IR LED directly to the pin, it won't
@ -28,9 +28,7 @@
* for your first time. e.g. ESP-12 etc.
*/
#ifndef UNIT_TEST
#include <Arduino.h>
#endif
#include <IRremoteESP8266.h>
#include <IRsend.h>
@ -53,7 +51,11 @@ uint8_t samsungState[kSamsungAcStateLength] = {
void setup() {
irsend.begin();
#if ESP8266
Serial.begin(115200, SERIAL_8N1, SERIAL_TX_ONLY);
#else // ESP8266
Serial.begin(115200, SERIAL_8N1);
#endif // ESP8266
}
void loop() {

View File

@ -0,0 +1,18 @@
[platformio]
src_dir = .
[env]
lib_extra_dirs = ../../
lib_ldf_mode = deep+
lib_ignore = examples
build_flags =
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
[env:esp32dev]
platform = espressif32
framework = arduino
board = esp32dev

View File

@ -11,7 +11,7 @@
* TL;DR: The IR LED needs to be driven by a transistor for a good result.
*
* Suggested circuit:
* https://github.com/markszabo/IRremoteESP8266/wiki#ir-sending
* https://github.com/crankyoldgit/IRremoteESP8266/wiki#ir-sending
*
* Common mistakes & tips:
* * Don't just connect the IR LED directly to the pin, it won't
@ -29,9 +29,7 @@
* for your first time. e.g. ESP-12 etc.
*/
#ifndef UNIT_TEST
#include <Arduino.h>
#endif
#include <IRremoteESP8266.h>
#include <IRsend.h>

View File

@ -0,0 +1,18 @@
[platformio]
src_dir = .
[env]
lib_extra_dirs = ../../
lib_ldf_mode = deep+
lib_ignore = examples
build_flags =
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
[env:esp32dev]
platform = espressif32
framework = arduino
board = esp32dev

View File

@ -10,7 +10,7 @@
* TL;DR: The IR LED needs to be driven by a transistor for a good result.
*
* Suggested circuit:
* https://github.com/markszabo/IRremoteESP8266/wiki#ir-sending
* https://github.com/crankyoldgit/IRremoteESP8266/wiki#ir-sending
*
* Common mistakes & tips:
* * Don't just connect the IR LED directly to the pin, it won't
@ -28,9 +28,7 @@
* for your first time. e.g. ESP-12 etc.
*/
#ifndef UNIT_TEST
#include <Arduino.h>
#endif
#include <IRremoteESP8266.h>
#include <IRsend.h>

View File

@ -0,0 +1,18 @@
[platformio]
src_dir = .
[env]
lib_extra_dirs = ../../
lib_ldf_mode = deep+
lib_ignore = examples
build_flags =
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
[env:esp32dev]
platform = espressif32
framework = arduino
board = esp32dev

View File

@ -0,0 +1,18 @@
[platformio]
src_dir = .
[env]
lib_extra_dirs = ../../
lib_ldf_mode = deep+
lib_ignore = examples
build_flags =
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
[env:esp32dev]
platform = espressif32
framework = arduino
board = esp32dev

View File

@ -0,0 +1,143 @@
/*
* IRremoteESP8266: SmartIRRepeater.ino - Record and playback IR codes.
* Copyright 2019 David Conran (crankyoldgit)
*
* This program will try to capture incoming IR messages and tries to
* intelligently replay them back.
* It uses the advanced detection features of the library, and the custom
* sending routines. Thus it will try to use the correct frequencies,
* duty cycles, and repeats as it thinks is required.
* Anything it doesn't understand, it will try to replay back as best it can,
* but at 38kHz.
* Note:
* That might NOT be the frequency of the incoming message, so some not
* recogised messages that are replayed may not work. The frequency & duty
* cycle of unknown incoming messages is lost at the point of the Hardware IR
* demodulator. The ESP can't see it.
*
* W A R N I N G
* This code is just for educational/example use only. No help will be given
* to you to make it do something else, or to make it work with some
* weird device or circuit, or to make it more usable or practical.
* If it works for you. Great. If not, Congratulations on changing/fixing it.
*
* An IR detector/demodulator must be connected to the input, kRecvPin.
* An IR LED circuit must be connected to the output, kIrLedPin.
*
* Example circuit diagrams (both are needed):
* https://github.com/crankyoldgit/IRremoteESP8266/wiki#ir-receiving
* https://github.com/crankyoldgit/IRremoteESP8266/wiki#ir-sending
*
* Common mistakes & tips:
* * Don't just connect the IR LED directly to the pin, it won't
* have enough current to drive the IR LED effectively.
* * Make sure you have the IR LED polarity correct.
* See: https://learn.sparkfun.com/tutorials/polarity/diode-and-led-polarity
* * Some digital camera/phones can be used to see if the IR LED is flashed.
* Replace the IR LED with a normal LED if you don't have a digital camera
* when debugging.
* * Avoid using the following pins unless you really know what you are doing:
* * Pin 0/D3: Can interfere with the boot/program mode & support circuits.
* * Pin 1/TX/TXD0: Any serial transmissions from the ESP will interfere.
* * Pin 3/RX/RXD0: Any serial transmissions to the ESP will interfere.
* * ESP-01 modules are tricky. We suggest you use a module with more GPIOs
* for your first time. e.g. ESP-12 etc.
*
* Changes:
* Version 1.0: June, 2019
* - Initial version.
*/
#include <Arduino.h>
#include <IRsend.h>
#include <IRrecv.h>
#include <IRremoteESP8266.h>
#include <IRutils.h>
// ==================== start of TUNEABLE PARAMETERS ====================
// The GPIO an IR detector/demodulator is connected to. Recommended: 14 (D5)
const uint16_t kRecvPin = 14;
// GPIO to use to control the IR LED circuit. Recommended: 4 (D2).
const uint16_t kIrLedPin = 4;
// The Serial connection baud rate.
// NOTE: Make sure you set your Serial Monitor to the same speed.
const uint32_t kBaudRate = 115200;
// As this program is a special purpose capture/resender, let's use a larger
// than expected buffer so we can handle very large IR messages.
const uint16_t kCaptureBufferSize = 1024; // 1024 == ~511 bits
// kTimeout is the Nr. of milli-Seconds of no-more-data before we consider a
// message ended.
const uint8_t kTimeout = 50; // Milli-Seconds
// kFrequency is the modulation frequency all UNKNOWN messages will be sent at.
const uint16_t kFrequency = 38000; // in Hz. e.g. 38kHz.
// ==================== end of TUNEABLE PARAMETERS ====================
// The IR transmitter.
IRsend irsend(kIrLedPin);
// The IR receiver.
IRrecv irrecv(kRecvPin, kCaptureBufferSize, kTimeout, false);
// Somewhere to store the captured message.
decode_results results;
// This section of code runs only once at start-up.
void setup() {
irrecv.enableIRIn(); // Start up the IR receiver.
irsend.begin(); // Start up the IR sender.
Serial.begin(kBaudRate, SERIAL_8N1);
while (!Serial) // Wait for the serial connection to be establised.
delay(50);
Serial.println();
Serial.print("SmartIRRepeater is now running and waiting for IR input "
"on Pin ");
Serial.println(kRecvPin);
Serial.print("and will retransmit it on Pin ");
Serial.println(kIrLedPin);
}
// The repeating section of the code
void loop() {
// Check if an IR message has been received.
if (irrecv.decode(&results)) { // We have captured something.
// The capture has stopped at this point.
decode_type_t protocol = results.decode_type;
uint16_t size = results.bits;
bool success = true;
// Is it a protocol we don't understand?
if (protocol == decode_type_t::UNKNOWN) { // Yes.
// Convert the results into an array suitable for sendRaw().
// resultToRawArray() allocates the memory we need for the array.
uint16_t *raw_array = resultToRawArray(&results);
// Find out how many elements are in the array.
size = getCorrectedRawLength(&results);
// Send it out via the IR LED circuit.
irsend.sendRaw(raw_array, size, kFrequency);
// Deallocate the memory allocated by resultToRawArray().
delete [] raw_array;
} else if (hasACState(protocol)) { // Does the message require a state[]?
// It does, so send with bytes instead.
success = irsend.send(protocol, results.state, size / 8);
} else { // Anything else must be a simple message protocol. ie. <= 64 bits
success = irsend.send(protocol, results.value, size);
}
// Resume capturing IR messages. It was not restarted until after we sent
// the message so we didn't capture our own message.
irrecv.resume();
// Display a crude timestamp & notification.
uint32_t now = millis();
Serial.printf(
"%06u.%03u: A %d-bit %s message was %ssuccessfully retransmitted.\n",
now / 1000, now % 1000, size, typeToString(protocol).c_str(),
success ? "" : "un");
}
yield(); // Or delay(milliseconds); This ensures the ESP doesn't WDT reset.
}

View File

@ -0,0 +1,18 @@
[platformio]
src_dir = .
[env]
lib_extra_dirs = ../../
lib_ldf_mode = deep+
lib_ignore = examples
build_flags =
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
[env:esp32dev]
platform = espressif32
framework = arduino
board = esp32dev

View File

@ -5,7 +5,7 @@
* TL;DR: The IR LED needs to be driven by a transistor for a good result.
*
* Suggested circuit:
* https://github.com/markszabo/IRremoteESP8266/wiki#ir-sending
* https://github.com/crankyoldgit/IRremoteESP8266/wiki#ir-sending
*
* Common mistakes & tips:
* * Don't just connect the IR LED directly to the pin, it won't
@ -23,9 +23,7 @@
* for your first time. e.g. ESP-12 etc.
*/
#ifndef UNIT_TEST
#include <Arduino.h>
#endif
#include <IRremoteESP8266.h>
#include <IRsend.h>
#include <ir_Argo.h>
@ -44,7 +42,7 @@ void loop() {
// Set up what we want to send. See ir_Argo.cpp for all the options.
ac.setPower(true);
ac.setFan(kArgoFan1);
ac.setCoolMode(kArgoCoolAuto);
ac.setMode(kArgoAuto);
ac.setTemp(25);
#if SEND_ARGO

View File

@ -0,0 +1,18 @@
[platformio]
src_dir = .
[env]
lib_extra_dirs = ../../
lib_ldf_mode = deep+
lib_ignore = examples
build_flags =
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
[env:esp32dev]
platform = espressif32
framework = arduino
board = esp32dev

View File

@ -6,7 +6,7 @@
* TL;DR: The IR LED needs to be driven by a transistor for a good result.
*
* Suggested circuit:
* https://github.com/markszabo/IRremoteESP8266/wiki#ir-sending
* https://github.com/crankyoldgit/IRremoteESP8266/wiki#ir-sending
*
* Common mistakes & tips:
* * Don't just connect the IR LED directly to the pin, it won't
@ -24,9 +24,7 @@
* for your first time. e.g. ESP-12 etc.
*/
#ifndef UNIT_TEST
#include <Arduino.h>
#endif
#include <IRremoteESP8266.h>
#include <IRsend.h>
#include <ir_Daikin.h>

View File

@ -0,0 +1,18 @@
[platformio]
src_dir = .
[env]
lib_extra_dirs = ../../
lib_ldf_mode = deep+
lib_ignore = examples
build_flags =
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
[env:esp32dev]
platform = espressif32
framework = arduino
board = esp32dev

View File

@ -1,7 +1,5 @@
// Copyright 2017 Jonny Graham, 2018 David Conran
#ifndef UNIT_TEST
#include <Arduino.h>
#endif
#include <IRremoteESP8266.h>
#include <IRsend.h>
#include <ir_Fujitsu.h>
@ -30,11 +28,13 @@ void setup() {
Serial.println("Default state of the remote.");
printState();
Serial.println("Setting desired state for A/C.");
ac.setCmd(kFujitsuAcCmdTurnOn);
ac.setSwing(kFujitsuAcSwingBoth);
// See `fujitsu_ac_remote_model_t` in `ir_Fujitsu.h` for a list of models.
ac.setModel(ARRAH2E);
ac.setSwing(kFujitsuAcSwingOff);
ac.setMode(kFujitsuAcModeCool);
ac.setFanSpeed(kFujitsuAcFanHigh);
ac.setTemp(24); // 24C
ac.setCmd(kFujitsuAcCmdTurnOn);
}
void loop() {

View File

@ -0,0 +1,18 @@
[platformio]
src_dir = .
[env]
lib_extra_dirs = ../../
lib_ldf_mode = deep+
lib_ignore = examples
build_flags =
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
[env:esp32dev]
platform = espressif32
framework = arduino
board = esp32dev

View File

@ -6,7 +6,7 @@
* TL;DR: The IR LED needs to be driven by a transistor for a good result.
*
* Suggested circuit:
* https://github.com/markszabo/IRremoteESP8266/wiki#ir-sending
* https://github.com/crankyoldgit/IRremoteESP8266/wiki#ir-sending
*
* Common mistakes & tips:
* * Don't just connect the IR LED directly to the pin, it won't
@ -23,9 +23,7 @@
* * ESP-01 modules are tricky. We suggest you use a module with more GPIOs
* for your first time. e.g. ESP-12 etc.
*/
#ifndef UNIT_TEST
#include <Arduino.h>
#endif
#include <IRremoteESP8266.h>
#include <IRsend.h>
#include <ir_Kelvinator.h>

View File

@ -0,0 +1,18 @@
[platformio]
src_dir = .
[env]
lib_extra_dirs = ../../
lib_ldf_mode = deep+
lib_ignore = examples
build_flags =
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
[env:esp32dev]
platform = espressif32
framework = arduino
board = esp32dev

View File

@ -6,7 +6,7 @@
* TL;DR: The IR LED needs to be driven by a transistor for a good result.
*
* Suggested circuit:
* https://github.com/markszabo/IRremoteESP8266/wiki#ir-sending
* https://github.com/crankyoldgit/IRremoteESP8266/wiki#ir-sending
*
* Common mistakes & tips:
* * Don't just connect the IR LED directly to the pin, it won't
@ -23,9 +23,7 @@
* * ESP-01 modules are tricky. We suggest you use a module with more GPIOs
* for your first time. e.g. ESP-12 etc.
*/
#ifndef UNIT_TEST
#include <Arduino.h>
#endif
#include <IRremoteESP8266.h>
#include <IRsend.h>
#include <ir_Mitsubishi.h>

View File

@ -0,0 +1,18 @@
[platformio]
src_dir = .
[env]
lib_extra_dirs = ../../
lib_ldf_mode = deep+
lib_ignore = examples
build_flags =
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
[env:esp32dev]
platform = espressif32
framework = arduino
board = esp32dev

View File

@ -6,7 +6,7 @@
* TL;DR: The IR LED needs to be driven by a transistor for a good result.
*
* Suggested circuit:
* https://github.com/markszabo/IRremoteESP8266/wiki#ir-sending
* https://github.com/crankyoldgit/IRremoteESP8266/wiki#ir-sending
*
* Common mistakes & tips:
* * Don't just connect the IR LED directly to the pin, it won't
@ -23,9 +23,7 @@
* * ESP-01 modules are tricky. We suggest you use a module with more GPIOs
* for your first time. e.g. ESP-12 etc.
*/
#ifndef UNIT_TEST
#include <Arduino.h>
#endif
#include <IRremoteESP8266.h>
#include <IRsend.h>
#include <ir_MitsubishiHeavy.h>

View File

@ -0,0 +1,18 @@
[platformio]
src_dir = .
[env]
lib_extra_dirs = ../../
lib_ldf_mode = deep+
lib_ignore = examples
build_flags =
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
[env:esp32dev]
platform = espressif32
framework = arduino
board = esp32dev

View File

@ -6,7 +6,7 @@
* TL;DR: The IR LED needs to be driven by a transistor for a good result.
*
* Suggested circuit:
* https://github.com/markszabo/IRremoteESP8266/wiki#ir-sending
* https://github.com/crankyoldgit/IRremoteESP8266/wiki#ir-sending
*
* Common mistakes & tips:
* * Don't just connect the IR LED directly to the pin, it won't
@ -23,9 +23,7 @@
* * ESP-01 modules are tricky. We suggest you use a module with more GPIOs
* for your first time. e.g. ESP-12 etc.
*/
#ifndef UNIT_TEST
#include <Arduino.h>
#endif
#include <IRremoteESP8266.h>
#include <IRsend.h>
#include <ir_Panasonic.h>

View File

@ -0,0 +1,18 @@
[platformio]
src_dir = .
[env]
lib_extra_dirs = ../../
lib_ldf_mode = deep+
lib_ignore = examples
build_flags =
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
[env:esp32dev]
platform = espressif32
framework = arduino
board = esp32dev

View File

@ -6,7 +6,7 @@
* TL;DR: The IR LED needs to be driven by a transistor for a good result.
*
* Suggested circuit:
* https://github.com/markszabo/IRremoteESP8266/wiki#ir-sending
* https://github.com/crankyoldgit/IRremoteESP8266/wiki#ir-sending
*
* Common mistakes & tips:
* * Don't just connect the IR LED directly to the pin, it won't
@ -23,9 +23,7 @@
* * ESP-01 modules are tricky. We suggest you use a module with more GPIOs
* for your first time. e.g. ESP-12 etc.
*/
#ifndef UNIT_TEST
#include <Arduino.h>
#endif
#include <IRremoteESP8266.h>
#include <IRsend.h>
#include <ir_Toshiba.h>

View File

@ -0,0 +1,18 @@
[platformio]
src_dir = .
[env]
lib_extra_dirs = ../../
lib_ldf_mode = deep+
lib_ignore = examples
build_flags =
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
[env:esp32dev]
platform = espressif32
framework = arduino
board = esp32dev

View File

@ -5,7 +5,7 @@
* TL;DR: The IR LED needs to be driven by a transistor for a good result.
*
* Suggested circuit:
* https://github.com/markszabo/IRremoteESP8266/wiki#ir-sending
* https://github.com/crankyoldgit/IRremoteESP8266/wiki#ir-sending
*
* Common mistakes & tips:
* * Don't just connect the IR LED directly to the pin, it won't
@ -23,9 +23,7 @@
* for your first time. e.g. ESP-12 etc.
*/
#ifndef UNIT_TEST
#include <Arduino.h>
#endif
#include <IRremoteESP8266.h>
#include <IRsend.h>
#include <ir_Trotec.h>

View File

@ -0,0 +1,18 @@
[platformio]
src_dir = .
[env]
lib_extra_dirs = ../../
lib_ldf_mode = deep+
lib_ignore = examples
build_flags =
[env:nodemcuv2]
platform = espressif8266
framework = arduino
board = nodemcuv2
[env:esp32dev]
platform = espressif32
framework = arduino
board = esp32dev

View File

@ -22,10 +22,13 @@
IRArgoAC KEYWORD1
IRCoolixAC KEYWORD1
IRDaikin160 KEYWORD1
IRDaikin2 KEYWORD1
IRDaikin216 KEYWORD1
IRDaikinESP KEYWORD1
IRElectraAc KEYWORD1
IRFujitsuAC KEYWORD1
IRGoodweatherAc KEYWORD1
IRGreeAC KEYWORD1
IRHaierAC KEYWORD1
IRHaierACYRW02 KEYWORD1
@ -35,8 +38,10 @@ IRMideaAC KEYWORD1
IRMitsubishiAC KEYWORD1
IRMitsubishiHeavy152Ac KEYWORD1
IRMitsubishiHeavy88Ac KEYWORD1
IRNeoclimaAc KEYWORD1
IRPanasonicAc KEYWORD1
IRSamsungAc KEYWORD1
IRSharpAc KEYWORD1
IRTcl112Ac KEYWORD1
IRTecoAc KEYWORD1
IRToshibaAC KEYWORD1
@ -49,19 +54,32 @@ IRsend KEYWORD1
IRtimer KEYWORD1
TimerMs KEYWORD1
decode_results KEYWORD1
ir_params_t KEYWORD1
decode_type_t KEYWORD1
fanspeed_t KEYWORD1
fujitsu_ac_remote_model_t KEYWORD1
irparams_t KEYWORD1
match_result_t KEYWORD1
opmode_t KEYWORD1
panasonic_ac_remote_model_t KEYWORD1
state_t KEYWORD1
swingh_t KEYWORD1
swingv_t KEYWORD1
whirlpool_ac_remote_model_t KEYWORD1
#######################################
# Methods and Functions (KEYWORD2)
#######################################
_delayMicroseconds KEYWORD2
_matchGeneric KEYWORD2
_setMode KEYWORD2
_setTemp KEYWORD2
acBoolToString KEYWORD2
acModeToString KEYWORD2
add KEYWORD2
argo KEYWORD2
begin KEYWORD2
boolToString KEYWORD2
buildFromState KEYWORD2
buildState KEYWORD2
calcBlockChecksum KEYWORD2
@ -73,36 +91,47 @@ calibrate KEYWORD2
cancelOffTimer KEYWORD2
cancelOnTimer KEYWORD2
cancelTimers KEYWORD2
celsiusToFahrenheit KEYWORD2
checkZjsSig KEYWORD2
checkZmsSig KEYWORD2
checksum KEYWORD2
clearOnTimerFlag KEYWORD2
clearSensorTemp KEYWORD2
clearSleepTimerFlag KEYWORD2
cmpStates KEYWORD2
compare KEYWORD2
convertFan KEYWORD2
convertMode KEYWORD2
convertSwingH KEYWORD2
convertSwingV KEYWORD2
coolix KEYWORD2
copyIrParams KEYWORD2
countBits KEYWORD2
daikin KEYWORD2
daikin160 KEYWORD2
daikin2 KEYWORD2
daikin216 KEYWORD2
decode KEYWORD2
decodeAiwaRCT501 KEYWORD2
decodeArgo KEYWORD2
decodeCOOLIX KEYWORD2
decodeCarrierAC KEYWORD2
decodeDISH KEYWORD2
decodeDaikin KEYWORD2
decodeDaikin160 KEYWORD2
decodeDaikin2 KEYWORD2
decodeDaikin216 KEYWORD2
decodeDenon KEYWORD2
decodeElectraAC KEYWORD2
decodeFujitsuAC KEYWORD2
decodeGICable KEYWORD2
decodeGoodweather KEYWORD2
decodeGree KEYWORD2
decodeHaierAC KEYWORD2
decodeHaierACYRW02 KEYWORD2
decodeHash KEYWORD2
decodeHitachiAC KEYWORD2
decodeInax KEYWORD2
decodeJVC KEYWORD2
decodeKelvinator KEYWORD2
decodeLG KEYWORD2
@ -117,6 +146,7 @@ decodeMitsubishi2 KEYWORD2
decodeMitsubishiAC KEYWORD2
decodeMitsubishiHeavy KEYWORD2
decodeNEC KEYWORD2
decodeNeoclima KEYWORD2
decodeNikai KEYWORD2
decodePanasonic KEYWORD2
decodePanasonicAC KEYWORD2
@ -130,18 +160,23 @@ decodeSamsungAC KEYWORD2
decodeSanyo KEYWORD2
decodeSanyoLC7461 KEYWORD2
decodeSharp KEYWORD2
decodeSharpAc KEYWORD2
decodeSony KEYWORD2
decodeTcl112Ac KEYWORD2
decodeTeco KEYWORD2
decodeToState KEYWORD2
decodeToshibaAC KEYWORD2
decodeTrotec KEYWORD2
decodeVestelAc KEYWORD2
decodeWhirlpoolAC KEYWORD2
decodeWhynter KEYWORD2
defaultBits KEYWORD2
disableIRIn KEYWORD2
disableOffTimer KEYWORD2
disableOnTimer KEYWORD2
disableSleepTimer KEYWORD2
elapsed KEYWORD2
electra KEYWORD2
enableIRIn KEYWORD2
enableIROut KEYWORD2
enableOffTimer KEYWORD2
@ -162,11 +197,13 @@ encodeSanyoLC7461 KEYWORD2
encodeSharp KEYWORD2
encodeSony KEYWORD2
encodeTime KEYWORD2
fanspeed_t KEYWORD2
fahrenheitToCelsius KEYWORD2
fanspeedToString KEYWORD2
fixChecksum KEYWORD2
fixup KEYWORD2
fujitsu KEYWORD2
get3D KEYWORD2
get8CHeat KEYWORD2
getBeep KEYWORD2
getBufSize KEYWORD2
getButton KEYWORD2
@ -175,9 +212,9 @@ getClock KEYWORD2
getCmd KEYWORD2
getComfort KEYWORD2
getCommand KEYWORD2
getCoolMode KEYWORD2
getCorrectedRawLength KEYWORD2
getCurrTime KEYWORD2
getCurrentDay KEYWORD2
getCurrentTime KEYWORD2
getEcono KEYWORD2
getEye KEYWORD2
@ -186,10 +223,13 @@ getFan KEYWORD2
getFanSpeed KEYWORD2
getFilter KEYWORD2
getFlap KEYWORD2
getFollow KEYWORD2
getFresh KEYWORD2
getFreshAir KEYWORD2
getFreshAirHigh KEYWORD2
getHealth KEYWORD2
getHeatMode KEYWORD2
getHold KEYWORD2
getIFeel KEYWORD2
getIon KEYWORD2
getIonFilter KEYWORD2
getLed KEYWORD2
@ -205,6 +245,7 @@ getOffTimerEnabled KEYWORD2
getOnTime KEYWORD2
getOnTimer KEYWORD2
getOnTimerEnabled KEYWORD2
getOutsideQuiet KEYWORD2
getPower KEYWORD2
getPowerToggle KEYWORD2
getPowerful KEYWORD2
@ -212,6 +253,7 @@ getPurify KEYWORD2
getQuiet KEYWORD2
getRClevel KEYWORD2
getRaw KEYWORD2
getRoomTemp KEYWORD2
getSensor KEYWORD2
getSensorTemp KEYWORD2
getSilent KEYWORD2
@ -224,7 +266,9 @@ getStateLength KEYWORD2
getStopClock KEYWORD2
getSuper KEYWORD2
getSwing KEYWORD2
getSwingH KEYWORD2
getSwingHorizontal KEYWORD2
getSwingV KEYWORD2
getSwingVertical KEYWORD2
getSwingVerticalAuto KEYWORD2
getSwingVerticalPosition KEYWORD2
@ -235,9 +279,12 @@ getTime KEYWORD2
getTimer KEYWORD2
getTurbo KEYWORD2
getVane KEYWORD2
getWeeklyTimerEnable KEYWORD2
getWiFi KEYWORD2
getXFan KEYWORD2
getZoneFollow KEYWORD2
getiFeel KEYWORD2
goodweather KEYWORD2
gree KEYWORD2
haier KEYWORD2
haierYrwo2 KEYWORD2
@ -260,24 +307,28 @@ ledOn KEYWORD2
mark KEYWORD2
match KEYWORD2
matchAtLeast KEYWORD2
matchBytes KEYWORD2
matchData KEYWORD2
matchGeneric KEYWORD2
matchMark KEYWORD2
matchSpace KEYWORD2
midea KEYWORD2
minRepeats KEYWORD2
mitsubishi KEYWORD2
mitsubishiHeavy152 KEYWORD2
mitsubishiHeavy88 KEYWORD2
mode) KEYWORD2
neoclima KEYWORD2
off KEYWORD2
on KEYWORD2
opmode_t KEYWORD2
opmodeToString KEYWORD2
panasonic KEYWORD2
position) KEYWORD2
recoverSavedState KEYWORD2
renderTime KEYWORD2
reset KEYWORD2
resultAcToString KEYWORD2
resultToHexidecimal KEYWORD2
resultToHumanReadableBasic KEYWORD2
resultToRawArray KEYWORD2
resultToSourceCode KEYWORD2
resultToTimingInfo KEYWORD2
resume KEYWORD2
@ -291,6 +342,7 @@ sendCOOLIX KEYWORD2
sendCarrierAC KEYWORD2
sendDISH KEYWORD2
sendDaikin KEYWORD2
sendDaikin160 KEYWORD2
sendDaikin2 KEYWORD2
sendDaikin216 KEYWORD2
sendData KEYWORD2
@ -301,12 +353,14 @@ sendFujitsuAC KEYWORD2
sendGC KEYWORD2
sendGICable KEYWORD2
sendGeneric KEYWORD2
sendGoodweather KEYWORD2
sendGree KEYWORD2
sendHaierAC KEYWORD2
sendHaierACYRW02 KEYWORD2
sendHitachiAC KEYWORD2
sendHitachiAC1 KEYWORD2
sendHitachiAC2 KEYWORD2
sendInax KEYWORD2
sendJVC KEYWORD2
sendKelvinator KEYWORD2
sendLG KEYWORD2
@ -323,6 +377,7 @@ sendMitsubishiAC KEYWORD2
sendMitsubishiHeavy152 KEYWORD2
sendMitsubishiHeavy88 KEYWORD2
sendNEC KEYWORD2
sendNeoclima KEYWORD2
sendNikai KEYWORD2
sendOff KEYWORD2
sendOn KEYWORD2
@ -340,6 +395,7 @@ sendSamsung36 KEYWORD2
sendSamsungAC KEYWORD2
sendSanyoLC7461 KEYWORD2
sendSharp KEYWORD2
sendSharpAc KEYWORD2
sendSharpRaw KEYWORD2
sendSherwood KEYWORD2
sendSony KEYWORD2
@ -352,6 +408,7 @@ sendWhirlpoolAC KEYWORD2
sendWhynter KEYWORD2
serialPrintUint64 KEYWORD2
set3D KEYWORD2
set8CHeat KEYWORD2
setAuto KEYWORD2
setBeep KEYWORD2
setButton KEYWORD2
@ -360,8 +417,8 @@ setClock KEYWORD2
setCmd KEYWORD2
setComfort KEYWORD2
setCommand KEYWORD2
setCoolMode KEYWORD2
setCurrTime KEYWORD2
setCurrentDay KEYWORD2
setCurrentTime KEYWORD2
setEcono KEYWORD2
setEye KEYWORD2
@ -370,10 +427,13 @@ setFan KEYWORD2
setFanSpeed KEYWORD2
setFilter KEYWORD2
setFlap KEYWORD2
setFollow KEYWORD2
setFresh KEYWORD2
setFreshAir KEYWORD2
setFreshAirHigh KEYWORD2
setHealth KEYWORD2
setHeatMode KEYWORD2
setHold KEYWORD2
setIFeel KEYWORD2
setIon KEYWORD2
setIonFilter KEYWORD2
setLed KEYWORD2
@ -387,6 +447,7 @@ setOffTimer KEYWORD2
setOffTimerActive KEYWORD2
setOnTimer KEYWORD2
setOnTimerActive KEYWORD2
setOutsideQuiet KEYWORD2
setPower KEYWORD2
setPowerToggle KEYWORD2
setPowerful KEYWORD2
@ -404,7 +465,9 @@ setStartClock KEYWORD2
setStopClock KEYWORD2
setSuper KEYWORD2
setSwing KEYWORD2
setSwingH KEYWORD2
setSwingHorizontal KEYWORD2
setSwingV KEYWORD2
setSwingVertical KEYWORD2
setTemp KEYWORD2
setTempRaw KEYWORD2
@ -414,20 +477,22 @@ setTimerActive KEYWORD2
setTurbo KEYWORD2
setUnknownThreshold KEYWORD2
setVane KEYWORD2
setWeeklyTimerEnable KEYWORD2
setWiFi KEYWORD2
setXFan KEYWORD2
setZoneFollow KEYWORD2
setiFeel KEYWORD2
sharp KEYWORD2
space KEYWORD2
speed) KEYWORD2
stateReset KEYWORD2
stepHoriz KEYWORD2
stepVert KEYWORD2
strToBool KEYWORD2
strToDecodeType KEYWORD2
strToModel KEYWORD2
sumBytes KEYWORD2
swingh_t KEYWORD2
swingv) KEYWORD2
swingv_t KEYWORD2
swinghToString KEYWORD2
swingvToString KEYWORD2
tcl112 KEYWORD2
teco KEYWORD2
ticksHigh KEYWORD2
@ -436,6 +501,8 @@ timeToString KEYWORD2
toString KEYWORD2
toggleRC5 KEYWORD2
toggleRC6 KEYWORD2
toggleSwingHoriz KEYWORD2
toggleSwingVert KEYWORD2
toshiba KEYWORD2
trotec KEYWORD2
typeToString KEYWORD2
@ -450,6 +517,7 @@ xorBytes KEYWORD2
# Constants (LITERAL1)
#######################################
// LITERAL1
AIWA_RC_T501 LITERAL1
AIWA_RC_T501_BITS LITERAL1
ALLOW_DELAY_CALLS LITERAL1
@ -477,12 +545,15 @@ ARGO_HEAT_BLINK LITERAL1
ARGO_HEAT_ON LITERAL1
ARGO_MAX_TEMP LITERAL1
ARGO_MIN_TEMP LITERAL1
ARJW2 LITERAL1
ARRAH2E LITERAL1
ARREB1E LITERAL1
CARRIER_AC LITERAL1
CARRIER_AC_BITS LITERAL1
COOLIX LITERAL1
COOLIX_BITS LITERAL1
DAIKIN LITERAL1
DAIKIN160 LITERAL1
DAIKIN2 LITERAL1
DAIKIN216 LITERAL1
DAIKIN_AUTO LITERAL1
@ -503,6 +574,7 @@ DECODE_ARGO LITERAL1
DECODE_CARRIER_AC LITERAL1
DECODE_COOLIX LITERAL1
DECODE_DAIKIN LITERAL1
DECODE_DAIKIN160 LITERAL1
DECODE_DAIKIN2 LITERAL1
DECODE_DAIKIN216 LITERAL1
DECODE_DENON LITERAL1
@ -511,6 +583,7 @@ DECODE_ELECTRA_AC LITERAL1
DECODE_FUJITSU_AC LITERAL1
DECODE_GICABLE LITERAL1
DECODE_GLOBALCACHE LITERAL1
DECODE_GOODWEATHER LITERAL1
DECODE_GREE LITERAL1
DECODE_HAIER_AC LITERAL1
DECODE_HAIER_AC_YRW02 LITERAL1
@ -518,6 +591,7 @@ DECODE_HASH LITERAL1
DECODE_HITACHI_AC LITERAL1
DECODE_HITACHI_AC1 LITERAL1
DECODE_HITACHI_AC2 LITERAL1
DECODE_INAX LITERAL1
DECODE_JVC LITERAL1
DECODE_KELVINATOR LITERAL1
DECODE_LASERTAG LITERAL1
@ -532,6 +606,7 @@ DECODE_MITSUBISHIHEAVY LITERAL1
DECODE_MITSUBISHI_AC LITERAL1
DECODE_MWM LITERAL1
DECODE_NEC LITERAL1
DECODE_NEOCLIMA LITERAL1
DECODE_NIKAI LITERAL1
DECODE_PANASONIC LITERAL1
DECODE_PANASONIC_AC LITERAL1
@ -545,6 +620,7 @@ DECODE_SAMSUNG36 LITERAL1
DECODE_SAMSUNG_AC LITERAL1
DECODE_SANYO LITERAL1
DECODE_SHARP LITERAL1
DECODE_SHARP_AC LITERAL1
DECODE_SHERWOOD LITERAL1
DECODE_SONY LITERAL1
DECODE_TCL112AC LITERAL1
@ -593,6 +669,7 @@ FUJITSU_AC_SWING_VERT LITERAL1
GICABLE LITERAL1
GICABLE_BITS LITERAL1
GLOBALCACHE LITERAL1
GOODWEATHER LITERAL1
GREE LITERAL1
GREE_AUTO LITERAL1
GREE_COOL LITERAL1
@ -682,6 +759,7 @@ HITACHI_AC2_STATE_LENGTH LITERAL1
HITACHI_AC_BITS LITERAL1
HITACHI_AC_STATE_LENGTH LITERAL1
ICACHE_RAM_ATTR LITERAL1
INAX LITERAL1
JVC LITERAL1
JVC_BITS LITERAL1
KELVINATOR LITERAL1
@ -749,6 +827,7 @@ MWM LITERAL1
NEC LITERAL1
NEC_BITS LITERAL1
NEC_LIKE LITERAL1
NEOCLIMA LITERAL1
NIKAI LITERAL1
NIKAI_BITS LITERAL1
ONCE LITERAL1
@ -781,6 +860,7 @@ SEND_ARGO LITERAL1
SEND_CARRIER_AC LITERAL1
SEND_COOLIX LITERAL1
SEND_DAIKIN LITERAL1
SEND_DAIKIN160 LITERAL1
SEND_DAIKIN2 LITERAL1
SEND_DAIKIN216 LITERAL1
SEND_DENON LITERAL1
@ -789,12 +869,14 @@ SEND_ELECTRA_AC LITERAL1
SEND_FUJITSU_AC LITERAL1
SEND_GICABLE LITERAL1
SEND_GLOBALCACHE LITERAL1
SEND_GOODWEATHER LITERAL1
SEND_GREE LITERAL1
SEND_HAIER_AC LITERAL1
SEND_HAIER_AC_YRW02 LITERAL1
SEND_HITACHI_AC LITERAL1
SEND_HITACHI_AC1 LITERAL1
SEND_HITACHI_AC2 LITERAL1
SEND_INAX LITERAL1
SEND_JVC LITERAL1
SEND_KELVINATOR LITERAL1
SEND_LASERTAG LITERAL1
@ -809,6 +891,7 @@ SEND_MITSUBISHIHEAVY LITERAL1
SEND_MITSUBISHI_AC LITERAL1
SEND_MWM LITERAL1
SEND_NEC LITERAL1
SEND_NEOCLIMA LITERAL1
SEND_NIKAI LITERAL1
SEND_PANASONIC LITERAL1
SEND_PANASONIC_AC LITERAL1
@ -823,6 +906,7 @@ SEND_SAMSUNG36 LITERAL1
SEND_SAMSUNG_AC LITERAL1
SEND_SANYO LITERAL1
SEND_SHARP LITERAL1
SEND_SHARP_AC LITERAL1
SEND_SHERWOOD LITERAL1
SEND_SONY LITERAL1
SEND_TCL112AC LITERAL1
@ -833,6 +917,7 @@ SEND_VESTEL_AC LITERAL1
SEND_WHIRLPOOL_AC LITERAL1
SEND_WHYNTER LITERAL1
SHARP LITERAL1
SHARP_AC LITERAL1
SHARP_BITS LITERAL1
SHERWOOD LITERAL1
SHERWOOD_BITS LITERAL1
@ -868,6 +953,7 @@ TROTEC_MAX_TIMER LITERAL1
TROTEC_MIN_TEMP LITERAL1
UNKNOWN LITERAL1
UNUSED LITERAL1
USE_IRAM_ATTR LITERAL1
VESTEL_AC LITERAL1
WHIRLPOOL_AC LITERAL1
WHYNTER LITERAL1
@ -878,16 +964,17 @@ kAiwaRcT501PostBits LITERAL1
kAiwaRcT501PostData LITERAL1
kAiwaRcT501PreBits LITERAL1
kAiwaRcT501PreData LITERAL1
kArgoAuto LITERAL1
kArgoBitMark LITERAL1
kArgoCoolAuto LITERAL1
kArgoCoolHum LITERAL1
kArgoCoolOff LITERAL1
kArgoCoolOn LITERAL1
kArgoBits LITERAL1
kArgoCool LITERAL1
kArgoDefaultRepeat LITERAL1
kArgoDry LITERAL1
kArgoFan1 LITERAL1
kArgoFan2 LITERAL1
kArgoFan3 LITERAL1
kArgoFanAuto LITERAL1
kArgoFanMask LITERAL1
kArgoFlap1 LITERAL1
kArgoFlap2 LITERAL1
kArgoFlap3 LITERAL1
@ -896,15 +983,29 @@ kArgoFlap5 LITERAL1
kArgoFlap6 LITERAL1
kArgoFlapAuto LITERAL1
kArgoFlapFull LITERAL1
kArgoGap LITERAL1
kArgoHdrMark LITERAL1
kArgoHdrSpace LITERAL1
kArgoHeat LITERAL1
kArgoHeatAuto LITERAL1
kArgoHeatBit LITERAL1
kArgoHeatBlink LITERAL1
kArgoHeatOn LITERAL1
kArgoIFeelBit LITERAL1
kArgoMaxBit LITERAL1
kArgoMaxRoomTemp LITERAL1
kArgoMaxTemp LITERAL1
kArgoMinTemp LITERAL1
kArgoModeMask LITERAL1
kArgoNightBit LITERAL1
kArgoOff LITERAL1
kArgoOneSpace LITERAL1
kArgoPowerBit LITERAL1
kArgoRoomTempHighMask LITERAL1
kArgoRoomTempLowMask LITERAL1
kArgoStateLength LITERAL1
kArgoTempHighMask LITERAL1
kArgoTempLowMask LITERAL1
kArgoTempOffset LITERAL1
kArgoZeroSpace LITERAL1
kAuto LITERAL1
kCarrierAcBitMark LITERAL1
@ -965,11 +1066,40 @@ kCoolixUnknown LITERAL1
kCoolixZeroSpace LITERAL1
kCoolixZeroSpaceTicks LITERAL1
kCoolixZoneFollowMask LITERAL1
kDaikin160BitMark LITERAL1
kDaikin160Bits LITERAL1
kDaikin160ByteFan LITERAL1
kDaikin160ByteMode LITERAL1
kDaikin160BytePower LITERAL1
kDaikin160ByteSwingV LITERAL1
kDaikin160ByteTemp LITERAL1
kDaikin160DefaultRepeat LITERAL1
kDaikin160Freq LITERAL1
kDaikin160Gap LITERAL1
kDaikin160HdrMark LITERAL1
kDaikin160HdrSpace LITERAL1
kDaikin160MaskFan LITERAL1
kDaikin160MaskMode LITERAL1
kDaikin160MaskSwingV LITERAL1
kDaikin160MaskTemp LITERAL1
kDaikin160OneSpace LITERAL1
kDaikin160Section1Length LITERAL1
kDaikin160Section2Length LITERAL1
kDaikin160Sections LITERAL1
kDaikin160StateLength LITERAL1
kDaikin160SwingVAuto LITERAL1
kDaikin160SwingVHigh LITERAL1
kDaikin160SwingVHighest LITERAL1
kDaikin160SwingVLow LITERAL1
kDaikin160SwingVLowest LITERAL1
kDaikin160SwingVMiddle LITERAL1
kDaikin160ZeroSpace LITERAL1
kDaikin216BitMark LITERAL1
kDaikin216Bits LITERAL1
kDaikin216ByteFan LITERAL1
kDaikin216ByteMode LITERAL1
kDaikin216BytePower LITERAL1
kDaikin216BytePowerful LITERAL1
kDaikin216ByteSwingH LITERAL1
kDaikin216ByteSwingV LITERAL1
kDaikin216ByteTemp LITERAL1
@ -1039,6 +1169,7 @@ kDaikinBitPower LITERAL1
kDaikinBitPowerful LITERAL1
kDaikinBitSensor LITERAL1
kDaikinBitSilent LITERAL1
kDaikinBitWeeklyTimer LITERAL1
kDaikinBits LITERAL1
kDaikinBitsShort LITERAL1
kDaikinByteChecksum1 LITERAL1
@ -1063,6 +1194,7 @@ kDaikinByteSensor LITERAL1
kDaikinByteSilent LITERAL1
kDaikinByteSwingH LITERAL1
kDaikinByteTemp LITERAL1
kDaikinByteWeeklyTimer LITERAL1
kDaikinCool LITERAL1
kDaikinCurBit LITERAL1
kDaikinCurIndex LITERAL1
@ -1095,7 +1227,9 @@ kDaikinStateLengthShort LITERAL1
kDaikinTolerance LITERAL1
kDaikinUnusedTime LITERAL1
kDaikinZeroSpace LITERAL1
kDefaultESP32Timer LITERAL1
kDefaultMessageGap LITERAL1
kDenon48Bits LITERAL1
kDenonBitMark LITERAL1
kDenonBitMarkTicks LITERAL1
kDenonBits LITERAL1
@ -1131,13 +1265,32 @@ kDishZeroSpaceTicks LITERAL1
kDry LITERAL1
kDutyDefault LITERAL1
kDutyMax LITERAL1
kElectraAcAuto LITERAL1
kElectraAcBitMark LITERAL1
kElectraAcBits LITERAL1
kElectraAcCool LITERAL1
kElectraAcDry LITERAL1
kElectraAcFan LITERAL1
kElectraAcFanAuto LITERAL1
kElectraAcFanHigh LITERAL1
kElectraAcFanLow LITERAL1
kElectraAcFanMask LITERAL1
kElectraAcFanMed LITERAL1
kElectraAcHdrMark LITERAL1
kElectraAcHdrSpace LITERAL1
kElectraAcHeat LITERAL1
kElectraAcMaxTemp LITERAL1
kElectraAcMessageGap LITERAL1
kElectraAcMinRepeat LITERAL1
kElectraAcMinTemp LITERAL1
kElectraAcModeMask LITERAL1
kElectraAcOffsetTemp LITERAL1
kElectraAcOneSpace LITERAL1
kElectraAcPowerMask LITERAL1
kElectraAcStateLength LITERAL1
kElectraAcSwingHMask LITERAL1
kElectraAcSwingVMask LITERAL1
kElectraAcTempMask LITERAL1
kElectraAcZeroSpace LITERAL1
kFan LITERAL1
kFnvBasis32 LITERAL1
@ -1145,9 +1298,13 @@ kFnvPrime32 LITERAL1
kFooter LITERAL1
kFujitsuAcBitMark LITERAL1
kFujitsuAcBits LITERAL1
kFujitsuAcCmdEcono LITERAL1
kFujitsuAcCmdPowerful LITERAL1
kFujitsuAcCmdStayOn LITERAL1
kFujitsuAcCmdStepHoriz LITERAL1
kFujitsuAcCmdStepVert LITERAL1
kFujitsuAcCmdToggleSwingHoriz LITERAL1
kFujitsuAcCmdToggleSwingVert LITERAL1
kFujitsuAcCmdTurnOff LITERAL1
kFujitsuAcCmdTurnOn LITERAL1
kFujitsuAcFanAuto LITERAL1
@ -1191,6 +1348,58 @@ kGlobalCacheMinUsec LITERAL1
kGlobalCacheRptIndex LITERAL1
kGlobalCacheRptStartIndex LITERAL1
kGlobalCacheStartIndex LITERAL1
kGoodweatherAuto LITERAL1
kGoodweatherBitCommand LITERAL1
kGoodweatherBitFan LITERAL1
kGoodweatherBitLight LITERAL1
kGoodweatherBitMark LITERAL1
kGoodweatherBitMode LITERAL1
kGoodweatherBitPower LITERAL1
kGoodweatherBitSleep LITERAL1
kGoodweatherBitSwing LITERAL1
kGoodweatherBitTemp LITERAL1
kGoodweatherBitTurbo LITERAL1
kGoodweatherBits LITERAL1
kGoodweatherCmdAirFlow LITERAL1
kGoodweatherCmdDownTemp LITERAL1
kGoodweatherCmdFan LITERAL1
kGoodweatherCmdHold LITERAL1
kGoodweatherCmdLight LITERAL1
kGoodweatherCmdMode LITERAL1
kGoodweatherCmdPower LITERAL1
kGoodweatherCmdSleep LITERAL1
kGoodweatherCmdSwing LITERAL1
kGoodweatherCmdTimer LITERAL1
kGoodweatherCmdTurbo LITERAL1
kGoodweatherCmdUpTemp LITERAL1
kGoodweatherCommandMask LITERAL1
kGoodweatherCool LITERAL1
kGoodweatherDry LITERAL1
kGoodweatherFan LITERAL1
kGoodweatherFanAuto LITERAL1
kGoodweatherFanHigh LITERAL1
kGoodweatherFanLow LITERAL1
kGoodweatherFanMask LITERAL1
kGoodweatherFanMed LITERAL1
kGoodweatherHdrMark LITERAL1
kGoodweatherHdrSpace LITERAL1
kGoodweatherHeat LITERAL1
kGoodweatherLightMask LITERAL1
kGoodweatherMinRepeat LITERAL1
kGoodweatherModeMask LITERAL1
kGoodweatherOneSpace LITERAL1
kGoodweatherPowerMask LITERAL1
kGoodweatherSleepMask LITERAL1
kGoodweatherSwingFast LITERAL1
kGoodweatherSwingMask LITERAL1
kGoodweatherSwingOff LITERAL1
kGoodweatherSwingSlow LITERAL1
kGoodweatherTempMask LITERAL1
kGoodweatherTempMax LITERAL1
kGoodweatherTempMin LITERAL1
kGoodweatherTurboMask LITERAL1
kGoodweatherZeroSpace LITERAL1
kGpioUnused LITERAL1
kGreeAuto LITERAL1
kGreeBitMark LITERAL1
kGreeBits LITERAL1
@ -1207,6 +1416,7 @@ kGreeFanMin LITERAL1
kGreeHdrMark LITERAL1
kGreeHdrSpace LITERAL1
kGreeHeat LITERAL1
kGreeIFeelMask LITERAL1
kGreeLightMask LITERAL1
kGreeMaxTemp LITERAL1
kGreeMinTemp LITERAL1
@ -1230,6 +1440,7 @@ kGreeSwingPosMask LITERAL1
kGreeSwingUp LITERAL1
kGreeSwingUpAuto LITERAL1
kGreeTurboMask LITERAL1
kGreeWiFiMask LITERAL1
kGreeXfanMask LITERAL1
kGreeZeroSpace LITERAL1
kHaierACBits LITERAL1
@ -1265,8 +1476,10 @@ kHaierAcMaxTemp LITERAL1
kHaierAcMaxTime LITERAL1
kHaierAcMinGap LITERAL1
kHaierAcMinTemp LITERAL1
kHaierAcModeMask LITERAL1
kHaierAcOneSpace LITERAL1
kHaierAcPrefix LITERAL1
kHaierAcSleepBit LITERAL1
kHaierAcSwingChg LITERAL1
kHaierAcSwingDown LITERAL1
kHaierAcSwingOff LITERAL1
@ -1334,6 +1547,15 @@ kHitachiAcOneSpace LITERAL1
kHitachiAcStateLength LITERAL1
kHitachiAcZeroSpace LITERAL1
kIdleState LITERAL1
kInaxBitMark LITERAL1
kInaxBits LITERAL1
kInaxHdrMark LITERAL1
kInaxHdrSpace LITERAL1
kInaxMinGap LITERAL1
kInaxMinRepeat LITERAL1
kInaxOneSpace LITERAL1
kInaxTick LITERAL1
kInaxZeroSpace LITERAL1
kJvcBitMark LITERAL1
kJvcBitMarkTicks LITERAL1
kJvcBits LITERAL1
@ -1666,6 +1888,60 @@ kNecRptSpaceTicks LITERAL1
kNecTick LITERAL1
kNecZeroSpace LITERAL1
kNecZeroSpaceTicks LITERAL1
kNeoclima8CHeatMask LITERAL1
kNeoclimaAuto LITERAL1
kNeoclimaBitMark LITERAL1
kNeoclimaBits LITERAL1
kNeoclimaButton8CHeat LITERAL1
kNeoclimaButtonAirFlow LITERAL1
kNeoclimaButtonEye LITERAL1
kNeoclimaButtonFanSpeed LITERAL1
kNeoclimaButtonFollow LITERAL1
kNeoclimaButtonFresh LITERAL1
kNeoclimaButtonHold LITERAL1
kNeoclimaButtonIon LITERAL1
kNeoclimaButtonLight LITERAL1
kNeoclimaButtonMask LITERAL1
kNeoclimaButtonMode LITERAL1
kNeoclimaButtonPower LITERAL1
kNeoclimaButtonSleep LITERAL1
kNeoclimaButtonSwing LITERAL1
kNeoclimaButtonTempDown LITERAL1
kNeoclimaButtonTempUp LITERAL1
kNeoclimaButtonTurbo LITERAL1
kNeoclimaCool LITERAL1
kNeoclimaDry LITERAL1
kNeoclimaEyeMask LITERAL1
kNeoclimaFan LITERAL1
kNeoclimaFanAuto LITERAL1
kNeoclimaFanHigh LITERAL1
kNeoclimaFanLow LITERAL1
kNeoclimaFanMask LITERAL1
kNeoclimaFanMed LITERAL1
kNeoclimaFollowMe LITERAL1
kNeoclimaFreshMask LITERAL1
kNeoclimaHdrMark LITERAL1
kNeoclimaHdrSpace LITERAL1
kNeoclimaHeat LITERAL1
kNeoclimaHoldMask LITERAL1
kNeoclimaIonMask LITERAL1
kNeoclimaLightMask LITERAL1
kNeoclimaMaxTemp LITERAL1
kNeoclimaMinGap LITERAL1
kNeoclimaMinRepeat LITERAL1
kNeoclimaMinTemp LITERAL1
kNeoclimaModeMask LITERAL1
kNeoclimaOneSpace LITERAL1
kNeoclimaPowerMask LITERAL1
kNeoclimaSleepMask LITERAL1
kNeoclimaStateLength LITERAL1
kNeoclimaSwingHMask LITERAL1
kNeoclimaSwingVMask LITERAL1
kNeoclimaSwingVOff LITERAL1
kNeoclimaSwingVOn LITERAL1
kNeoclimaTempMask LITERAL1
kNeoclimaTurboMask LITERAL1
kNeoclimaZeroSpace LITERAL1
kNikaiBitMark LITERAL1
kNikaiBitMarkTicks LITERAL1
kNikaiBits LITERAL1
@ -1835,9 +2111,12 @@ kSamsungAcMinTemp LITERAL1
kSamsungAcModeMask LITERAL1
kSamsungAcOneSpace LITERAL1
kSamsungAcPowerMask1 LITERAL1
kSamsungAcPowerMask2 LITERAL1
kSamsungAcPowerMask6 LITERAL1
kSamsungAcPowerSection LITERAL1
kSamsungAcQuietMask11 LITERAL1
kSamsungAcPowerfulMask10 LITERAL1
kSamsungAcPowerfulMask8 LITERAL1
kSamsungAcQuietMask1 LITERAL1
kSamsungAcQuietMask5 LITERAL1
kSamsungAcSectionGap LITERAL1
kSamsungAcSectionMark LITERAL1
kSamsungAcSectionSpace LITERAL1
@ -1885,6 +2164,37 @@ kSanyoSa8650bHdrSpace LITERAL1
kSanyoSa8650bOneMark LITERAL1
kSanyoSa8650bRptLength LITERAL1
kSanyoSa8650bZeroMark LITERAL1
kSharpAcAuto LITERAL1
kSharpAcBitFanManual LITERAL1
kSharpAcBitMark LITERAL1
kSharpAcBitPower LITERAL1
kSharpAcBitTempManual LITERAL1
kSharpAcBits LITERAL1
kSharpAcByteFan LITERAL1
kSharpAcByteManual LITERAL1
kSharpAcByteMode LITERAL1
kSharpAcBytePower LITERAL1
kSharpAcByteTemp LITERAL1
kSharpAcCool LITERAL1
kSharpAcDefaultRepeat LITERAL1
kSharpAcDry LITERAL1
kSharpAcFanAuto LITERAL1
kSharpAcFanHigh LITERAL1
kSharpAcFanMax LITERAL1
kSharpAcFanMed LITERAL1
kSharpAcFanMin LITERAL1
kSharpAcGap LITERAL1
kSharpAcHdrMark LITERAL1
kSharpAcHdrSpace LITERAL1
kSharpAcHeat LITERAL1
kSharpAcMaskFan LITERAL1
kSharpAcMaskMode LITERAL1
kSharpAcMaskTemp LITERAL1
kSharpAcMaxTemp LITERAL1
kSharpAcMinTemp LITERAL1
kSharpAcOneSpace LITERAL1
kSharpAcStateLength LITERAL1
kSharpAcZeroSpace LITERAL1
kSharpAddressBits LITERAL1
kSharpAddressMask LITERAL1
kSharpBitMark LITERAL1
@ -1954,6 +2264,7 @@ kTcl112AcPowerMask LITERAL1
kTcl112AcStateLength LITERAL1
kTcl112AcTempMax LITERAL1
kTcl112AcTempMin LITERAL1
kTcl112AcTolerance LITERAL1
kTcl112AcZeroSpace LITERAL1
kTecoAuto LITERAL1
kTecoBitMark LITERAL1
@ -2006,6 +2317,8 @@ kToshibaAcOneSpace LITERAL1
kToshibaAcPower LITERAL1
kToshibaAcZeroSpace LITERAL1
kTrotecAuto LITERAL1
kTrotecBitMark LITERAL1
kTrotecBits LITERAL1
kTrotecCool LITERAL1
kTrotecDefTemp LITERAL1
kTrotecDefaultRepeat LITERAL1
@ -2023,13 +2336,11 @@ kTrotecIntro2 LITERAL1
kTrotecMaxTemp LITERAL1
kTrotecMaxTimer LITERAL1
kTrotecMinTemp LITERAL1
kTrotecOneMark LITERAL1
kTrotecOneSpace LITERAL1
kTrotecPowerBit LITERAL1
kTrotecSleepBit LITERAL1
kTrotecStateLength LITERAL1
kTrotecTimerBit LITERAL1
kTrotecZeroMark LITERAL1
kTrotecZeroSpace LITERAL1
kUnknownThreshold LITERAL1
kVestelAcAuto LITERAL1

View File

@ -1,17 +1,18 @@
{
"name": "IRremoteESP8266",
"version": "2.6.0",
"keywords": "infrared, ir, remote, esp8266",
"description": "Send and receive infrared signals with multiple protocols (ESP8266)",
"version": "2.6.3",
"keywords": "infrared, ir, remote, esp8266, esp32",
"description": "Send and receive infrared signals with multiple protocols (ESP8266/ESP32)",
"repository":
{
"type": "git",
"url": "https://github.com/markszabo/IRremoteESP8266.git"
"url": "https://github.com/crankyoldgit/IRremoteESP8266.git"
},
"authors": [
{
"name": "Ken Shirriff",
"email": "zetoslab@gmail.com"
"name": "David Conran",
"url": "https://plus.google.com/+davidconran",
"maintainer": true
},
{
"name": "Mark Szabo",
@ -24,9 +25,8 @@
"maintainer": true
},
{
"name": "David Conran",
"url": "https://plus.google.com/+davidconran",
"maintainer": true
"name": "Ken Shirriff",
"email": "zetoslab@gmail.com"
},
{
"name": "Roi Dayan",
@ -40,5 +40,5 @@
}
],
"frameworks": "arduino",
"platforms": "espressif8266"
"platforms": ["espressif8266", "espressif32"]
}

View File

@ -1,9 +1,9 @@
name=IRremoteESP8266
version=2.6.0
author=Sebastien Warin, Mark Szabo, Ken Shirriff, David Conran
version=2.6.3
author=David Conran, Sebastien Warin, Mark Szabo, Ken Shirriff
maintainer=Mark Szabo, David Conran, Sebastien Warin, Roi Dayan, Massimiliano Pinto
sentence=Send and receive infrared signals with multiple protocols (ESP8266)
paragraph=This library enables you to send and receive infra-red signals on an ESP8266.
sentence=Send and receive infrared signals with multiple protocols (ESP8266/ESP32)
paragraph=This library enables you to send and receive infra-red signals on an ESP8266 or an ESP32.
category=Device Control
url=https://github.com/markszabo/IRremoteESP8266
architectures=esp8266
url=https://github.com/crankyoldgit/IRremoteESP8266
architectures=esp8266,esp32

View File

@ -6,14 +6,13 @@
#ifndef UNIT_TEST
#include <Arduino.h>
#endif
#ifndef ARDUINO
#include <string>
#endif
#include "IRremoteESP8266.h"
#include "ir_Argo.h"
#include "ir_Coolix.h"
#include "ir_Daikin.h"
#include "ir_Fujitsu.h"
#include "ir_Electra.h"
#include "ir_Goodweather.h"
#include "ir_Gree.h"
#include "ir_Haier.h"
#include "ir_Hitachi.h"
@ -21,8 +20,10 @@
#include "ir_Midea.h"
#include "ir_Mitsubishi.h"
#include "ir_MitsubishiHeavy.h"
#include "ir_Neoclima.h"
#include "ir_Panasonic.h"
#include "ir_Samsung.h"
#include "ir_Sharp.h"
#include "ir_Tcl.h"
#include "ir_Teco.h"
#include "ir_Toshiba.h"
@ -30,9 +31,14 @@
#include "ir_Vestel.h"
#include "ir_Whirlpool.h"
// Constants
const int8_t kGpioUnused = -1;
// Class
class IRac {
public:
explicit IRac(uint8_t pin);
explicit IRac(const uint16_t pin, const bool inverted = false,
const bool use_modulation = true);
static bool isProtocolSupported(const decode_type_t protocol);
bool sendAc(const decode_type_t vendor, const int16_t model,
const bool power, const stdAc::opmode_t mode, const float degrees,
@ -42,23 +48,31 @@ class IRac {
const bool light, const bool filter, const bool clean,
const bool beep, const int16_t sleep = -1,
const int16_t clock = -1);
bool sendAc(const stdAc::state_t desired, const stdAc::state_t *prev = NULL);
static bool cmpStates(const stdAc::state_t a, const stdAc::state_t b);
static bool strToBool(const char *str, const bool def = false);
static int16_t strToModel(const char *str, const int16_t def = -1);
static stdAc::opmode_t strToOpmode(
const char *str, const stdAc::opmode_t def = stdAc::opmode_t::kAuto);
const char *str, const stdAc::opmode_t def = stdAc::opmode_t::kAuto);
static stdAc::fanspeed_t strToFanspeed(
const char *str,
const stdAc::fanspeed_t def = stdAc::fanspeed_t::kAuto);
const char *str,
const stdAc::fanspeed_t def = stdAc::fanspeed_t::kAuto);
static stdAc::swingv_t strToSwingV(
const char *str, const stdAc::swingv_t def = stdAc::swingv_t::kOff);
const char *str, const stdAc::swingv_t def = stdAc::swingv_t::kOff);
static stdAc::swingh_t strToSwingH(
const char *str, const stdAc::swingh_t def = stdAc::swingh_t::kOff);
const char *str, const stdAc::swingh_t def = stdAc::swingh_t::kOff);
static String boolToString(const bool value);
static String opmodeToString(const stdAc::opmode_t mode);
static String fanspeedToString(const stdAc::fanspeed_t speed);
static String swingvToString(const stdAc::swingv_t swingv);
static String swinghToString(const stdAc::swingh_t swingh);
#ifndef UNIT_TEST
private:
#endif
uint8_t _pin;
uint16_t _pin;
bool _inverted;
bool _modulation;
#if SEND_ARGO
void argo(IRArgoAC *ac,
const bool on, const stdAc::opmode_t mode, const float degrees,
@ -81,6 +95,18 @@ class IRac {
const bool quiet, const bool turbo, const bool econo,
const bool clean);
#endif // SEND_DAIKIN
#if SEND_DAIKIN160
void daikin160(IRDaikin160 *ac,
const bool on, const stdAc::opmode_t mode,
const float degrees, const stdAc::fanspeed_t fan,
const stdAc::swingv_t swingv);
#endif // SEND_DAIKIN160
#if SEND_DAIKIN176
void daikin176(IRDaikin176 *ac,
const bool on, const stdAc::opmode_t mode,
const float degrees, const stdAc::fanspeed_t fan,
const stdAc::swingh_t swingh);
#endif // SEND_DAIKIN176
#if SEND_DAIKIN2
void daikin2(IRDaikin2 *ac,
const bool on, const stdAc::opmode_t mode,
@ -96,15 +122,31 @@ void daikin216(IRDaikin216 *ac,
const bool on, const stdAc::opmode_t mode,
const float degrees, const stdAc::fanspeed_t fan,
const stdAc::swingv_t swingv, const stdAc::swingh_t swingh,
const bool quiet);
const bool quiet, const bool turbo);
#endif // SEND_DAIKIN216
#if SEND_ELECTRA_AC
void electra(IRElectraAc *ac,
const bool on, const stdAc::opmode_t mode,
const float degrees, const stdAc::fanspeed_t fan,
const stdAc::swingv_t swingv,
const stdAc::swingh_t swingh);
#endif // SEND_ELECTRA_AC
#if SEND_FUJITSU_AC
void fujitsu(IRFujitsuAC *ac, const fujitsu_ac_remote_model_t model,
const bool on, const stdAc::opmode_t mode, const float degrees,
const stdAc::fanspeed_t fan,
const stdAc::swingv_t swingv, const stdAc::swingh_t swingh,
const bool quiet);
const bool quiet, const bool turbo, const bool econo);
#endif // SEND_FUJITSU_AC
#if SEND_GOODWEATHER
void goodweather(IRGoodweatherAc *ac,
const bool on, const stdAc::opmode_t mode,
const float degrees,
const stdAc::fanspeed_t fan,
const stdAc::swingv_t swingv,
const bool turbo, const bool light,
const int16_t sleep = -1);
#endif // SEND_GOODWEATHER
#if SEND_GREE
void gree(IRGreeAC *ac,
const bool on, const stdAc::opmode_t mode, const float degrees,
@ -169,6 +211,13 @@ void daikin216(IRDaikin216 *ac,
const bool filter, const bool clean,
const int16_t sleep = -1);
#endif // SEND_MITSUBISHIHEAVY
#if SEND_NEOCLIMA
void neoclima(IRNeoclimaAc *ac, const bool on, const stdAc::opmode_t mode,
const float degrees, const stdAc::fanspeed_t fan,
const stdAc::swingv_t swingv, const stdAc::swingh_t swingh,
const bool turbo, const bool light, const bool filter,
const int16_t sleep = -1);
#endif // SEND_NEOCLIMA
#if SEND_PANASONIC_AC
void panasonic(IRPanasonicAc *ac, const panasonic_ac_remote_model_t model,
const bool on, const stdAc::opmode_t mode, const float degrees,
@ -181,8 +230,13 @@ void daikin216(IRDaikin216 *ac,
const bool on, const stdAc::opmode_t mode, const float degrees,
const stdAc::fanspeed_t fan, const stdAc::swingv_t swingv,
const bool quiet, const bool turbo, const bool clean,
const bool beep, const bool sendOnOffHack = true);
const bool beep, const bool dopower = true);
#endif // SEND_SAMSUNG_AC
#if SEND_SHARP_AC
void sharp(IRSharpAc *ac,
const bool on, const stdAc::opmode_t mode,
const float degrees, const stdAc::fanspeed_t fan);
#endif // SEND_SHARP_AC
#if SEND_TCL112AC
void tcl112(IRTcl112Ac *ac,
const bool on, const stdAc::opmode_t mode, const float degrees,
@ -222,27 +276,13 @@ void daikin216(IRDaikin216 *ac,
const bool turbo, const bool light,
const int16_t sleep = -1, const int16_t clock = -1);
#endif // SEND_WHIRLPOOL_AC
static stdAc::state_t handleToggles(const stdAc::state_t desired,
const stdAc::state_t *prev = NULL);
}; // IRac class
// Structure to hold a common A/C state.
typedef struct {
decode_type_t protocol;
int16_t model;
bool power;
stdAc::opmode_t mode;
float degrees;
bool celsius;
stdAc::fanspeed_t fanspeed;
stdAc::swingv_t swingv;
stdAc::swingh_t swingh;
bool quiet;
bool turbo;
bool econo;
bool light;
bool filter;
bool clean;
bool beep;
int16_t sleep;
int16_t clock;
} commonAcState_t;
namespace IRAcUtils {
String resultAcToString(const decode_results * const results);
bool decodeToState(const decode_results *decode, stdAc::state_t *result,
const stdAc::state_t *prev = NULL);
} // namespace IRAcUtils
#endif // IRAC_H_

View File

@ -1,18 +1,23 @@
// Copyright 2009 Ken Shirriff
// Copyright 2015 Mark Szabo
// Copyright 2015 Sebastien Warin
// Copyright 2017 David Conran
// Copyright 2017, 2019 David Conran
#include "IRrecv.h"
#include <stddef.h>
#ifndef UNIT_TEST
#if defined(ESP8266)
extern "C" {
#include <gpio.h>
#include <user_interface.h>
}
#endif // ESP8266
#include <Arduino.h>
#endif
#include <algorithm>
#ifdef UNIT_TEST
#include <cassert>
#endif // UNIT_TEST
#include "IRremoteESP8266.h"
#include "IRutils.h"
@ -20,32 +25,68 @@ extern "C" {
#undef ICACHE_RAM_ATTR
#define ICACHE_RAM_ATTR
#endif
#ifndef USE_IRAM_ATTR
#if defined(ESP8266)
#define USE_IRAM_ATTR ICACHE_RAM_ATTR
#endif // ESP8266
#if defined(ESP32)
#define USE_IRAM_ATTR IRAM_ATTR
#endif // ESP32
#endif // USE_IRAM_ATTR
#define ONCE 0
// Updated by David Conran (https://github.com/crankyoldgit) for receiving IR
// code on ESP32
// Updated by Sebastien Warin (http://sebastien.warin.fr) for receiving IR code
// on ESP8266
// Updated by markszabo (https://github.com/markszabo/IRremoteESP8266) for
// Updated by markszabo (https://github.com/crankyoldgit/IRremoteESP8266) for
// sending IR code on ESP8266
// Globals
#ifndef UNIT_TEST
#if defined(ESP8266)
static ETSTimer timer;
#endif
#endif // ESP8266
#if defined(ESP32)
static hw_timer_t * timer = NULL;
#endif // ESP32
#endif // UNIT_TEST
#if defined(ESP32)
portMUX_TYPE irremote_mux = portMUX_INITIALIZER_UNLOCKED;
#endif // ESP32
volatile irparams_t irparams;
irparams_t *irparams_save; // A copy of the interrupt state while decoding.
#ifndef UNIT_TEST
static void ICACHE_RAM_ATTR read_timeout(void *arg __attribute__((unused))) {
#if defined(ESP8266)
static void USE_IRAM_ATTR read_timeout(void *arg __attribute__((unused))) {
os_intr_lock();
#endif // ESP8266
#if defined(ESP32)
static void USE_IRAM_ATTR read_timeout(void) {
portENTER_CRITICAL(&irremote_mux);
#endif // ESP32
if (irparams.rawlen) irparams.rcvstate = kStopState;
#if defined(ESP8266)
os_intr_unlock();
#endif // ESP8266
#if defined(ESP32)
portEXIT_CRITICAL(&irremote_mux);
#endif // ESP32
}
static void ICACHE_RAM_ATTR gpio_intr() {
uint32_t now = system_get_time();
uint32_t gpio_status = GPIO_REG_READ(GPIO_STATUS_ADDRESS);
static void USE_IRAM_ATTR gpio_intr() {
uint32_t now = micros();
static uint32_t start = 0;
#if defined(ESP8266)
uint32_t gpio_status = GPIO_REG_READ(GPIO_STATUS_ADDRESS);
os_timer_disarm(&timer);
GPIO_REG_WRITE(GPIO_STATUS_W1TC_ADDRESS, gpio_status);
#endif // ESP8266
// Grab a local copy of rawlen to reduce instructions used in IRAM.
// This is an ugly premature optimisation code-wise, but we do everything we
@ -74,8 +115,14 @@ static void ICACHE_RAM_ATTR gpio_intr() {
irparams.rawlen++;
start = now;
#define ONCE 0
#if defined(ESP8266)
os_timer_arm(&timer, irparams.timeout, ONCE);
#endif // ESP8266
#if defined(ESP32)
timerWrite(timer, 0); // Reset the timeout.
timerAlarmEnable(timer);
#endif // ESP32
}
#endif // UNIT_TEST
@ -87,11 +134,21 @@ static void ICACHE_RAM_ATTR gpio_intr() {
// bufsize: Nr. of entries to have in the capture buffer. (Default: kRawBuf)
// timeout: Nr. of milli-Seconds of no signal before we stop capturing data.
// (Default: kTimeoutMs)
// save_buffer: Use a second (save) buffer to decode from. (Def: false)
// save_buffer: Use a second (save) buffer to decode from. (Default: false)
// timer_num: Which ESP32 timer number to use? ESP32 only, otherwise unused.
// (Range: 0-3. Default: kDefaultESP32Timer)
// Returns:
// An IRrecv class object.
IRrecv::IRrecv(uint16_t recvpin, uint16_t bufsize, uint8_t timeout,
bool save_buffer) {
#if defined(ESP32)
IRrecv::IRrecv(const uint16_t recvpin, const uint16_t bufsize,
const uint8_t timeout, const bool save_buffer,
const uint8_t timer_num) {
// There are only 4 timers. 0 to 3.
_timer_num = std::min(timer_num, (uint8_t)3);
#else // ESP32
IRrecv::IRrecv(const uint16_t recvpin, const uint16_t bufsize,
const uint8_t timeout, const bool save_buffer) {
#endif // ESP32
irparams.recvpin = recvpin;
irparams.bufsize = bufsize;
// Ensure we are going to be able to store all possible values in the
@ -123,7 +180,7 @@ IRrecv::IRrecv(uint16_t recvpin, uint16_t bufsize, uint8_t timeout,
irparams_save = NULL;
}
#if DECODE_HASH
unknown_threshold = kUnknownThreshold;
_unknown_threshold = kUnknownThreshold;
#endif // DECODE_HASH
}
@ -134,35 +191,70 @@ IRrecv::~IRrecv(void) {
delete[] irparams_save->rawbuf;
delete irparams_save;
}
disableIRIn();
#if defined(ESP32)
if (timer != NULL) timerEnd(timer); // Cleanup the ESP32 timeout timer.
#endif // ESP32
}
// initialization
void IRrecv::enableIRIn() {
// initialize state machine variables
// Set up and (re)start the IR capture mechanism.
//
// Args:
// pullup: A flag indicating should the GPIO use the internal pullup resistor.
// (Default: `false`. i.e. No.)
void IRrecv::enableIRIn(const bool pullup) {
// ESP32's seem to require explicitly setting the GPIO to INPUT etc.
// This wasn't required on the ESP8266s, but it shouldn't hurt to make sure.
if (pullup) {
#ifndef UNIT_TEST
pinMode(irparams.recvpin, INPUT_PULLUP);
} else {
pinMode(irparams.recvpin, INPUT);
#endif // UNIT_TEST
}
#if defined(ESP32)
// Initialize the ESP32 timer.
timer = timerBegin(_timer_num, 80, true); // 80MHz / 80 = 1 uSec granularity.
// Set the timer so it only fires once, and set it's trigger in uSeconds.
timerAlarmWrite(timer, MS_TO_USEC(irparams.timeout), ONCE);
// Note: Interrupt needs to be attached before it can be enabled or disabled.
timerAttachInterrupt(timer, &read_timeout, true);
#endif // ESP32
// Initialize state machine variables
resume();
#ifndef UNIT_TEST
// Initialize timer
#if defined(ESP8266)
// Initialize ESP8266 timer.
os_timer_disarm(&timer);
os_timer_setfn(&timer, reinterpret_cast<os_timer_func_t *>(read_timeout),
NULL);
#endif // ESP8266
// Attach Interrupt
attachInterrupt(irparams.recvpin, gpio_intr, CHANGE);
#endif
#endif // UNIT_TEST
}
void IRrecv::disableIRIn() {
void IRrecv::disableIRIn(void) {
#ifndef UNIT_TEST
#if defined(ESP8266)
os_timer_disarm(&timer);
#endif // ESP8266
#if defined(ESP32)
timerAlarmDisable(timer);
#endif // ESP32
detachInterrupt(irparams.recvpin);
#endif
#endif // UNIT_TEST
}
void IRrecv::resume() {
void IRrecv::resume(void) {
irparams.rcvstate = kIdleState;
irparams.rawlen = 0;
irparams.overflow = false;
#if defined(ESP32)
timerAlarmDisable(timer);
#endif // ESP32
}
// Make a copy of the interrupt state & buffer data.
@ -196,12 +288,12 @@ void IRrecv::copyIrParams(volatile irparams_t *src, irparams_t *dst) {
// Obtain the maximum number of entries possible in the capture buffer.
// i.e. It's size.
uint16_t IRrecv::getBufSize() { return irparams.bufsize; }
uint16_t IRrecv::getBufSize(void) { return irparams.bufsize; }
#if DECODE_HASH
// Set the minimum length we will consider for reporting UNKNOWN message types.
void IRrecv::setUnknownThreshold(uint16_t length) {
unknown_threshold = length;
void IRrecv::setUnknownThreshold(const uint16_t length) {
_unknown_threshold = length;
}
#endif // DECODE_HASH
@ -335,7 +427,7 @@ bool IRrecv::decode(decode_results *results, irparams_t *save) {
#if DECODE_DENON
// Denon needs to precede Panasonic as it is a special case of Panasonic.
DPRINTLN("Attempting Denon decode");
if (decodeDenon(results, DENON_48_BITS) || decodeDenon(results, DENON_BITS) ||
if (decodeDenon(results, kDenon48Bits) || decodeDenon(results, kDenonBits) ||
decodeDenon(results, kDenonLegacyBits))
return true;
#endif
@ -523,6 +615,38 @@ bool IRrecv::decode(decode_results *results, irparams_t *save) {
DPRINTLN("Attempting MITSUBISHIHEAVY (88 bit) decode");
if (decodeMitsubishiHeavy(results, kMitsubishiHeavy88Bits)) return true;
#endif
#if DECODE_ARGO
DPRINTLN("Attempting Argo decode");
if (decodeArgo(results)) return true;
#endif // DECODE_ARGO
#if DECODE_SHARP_AC
DPRINTLN("Attempting SHARP_AC decode");
if (decodeSharpAc(results)) return true;
#endif
#if DECODE_GOODWEATHER
DPRINTLN("Attempting GOODWEATHER decode");
if (decodeGoodweather(results)) return true;
#endif // DECODE_GOODWEATHER
#if DECODE_INAX
DPRINTLN("Attempting Inax decode");
if (decodeInax(results)) return true;
#endif // DECODE_INAX
#if DECODE_TROTEC
DPRINTLN("Attempting Trotec decode");
if (decodeTrotec(results)) return true;
#endif // DECODE_TROTEC
#if DECODE_DAIKIN160
DPRINTLN("Attempting Daikin160 decode");
if (decodeDaikin160(results)) return true;
#endif // DECODE_DAIKIN160
#if DECODE_NEOCLIMA
DPRINTLN("Attempting Neoclima decode");
if (decodeNeoclima(results)) return true;
#endif // DECODE_NEOCLIMA
#if DECODE_DAIKIN176
DPRINTLN("Attempting Daikin176 decode");
if (decodeDaikin176(results)) return true;
#endif // DECODE_DAIKIN176
#if DECODE_HASH
// decodeHash returns a hash on any input.
// Thus, it needs to be last in the list.
@ -583,6 +707,17 @@ bool IRrecv::match(uint32_t measured, uint32_t desired, uint8_t tolerance,
DPRINT(measured);
DPRINT(" <= ");
DPRINTLN(ticksHigh(desired, tolerance, delta));
#ifdef UNIT_TEST
// Sanity checks that we don't have values that cause integer over/underflow.
// Only performed during testing so there is no performance hit in normal
// operation.
assert(ticksLow(desired, tolerance, delta) <= desired);
// Check if we overflowed. (UINT32_MAX >> 3 is approx 9 minutes!)
assert(ticksHigh(desired, tolerance, delta) < UINT32_MAX >> 3);
// Check if our high mark is below where we started. This could happen.
// If there is a legit case, then this should be removed.
assert(ticksHigh(desired, tolerance, delta) >= desired);
#endif // UNIT_TEST
return (measured >= ticksLow(desired, tolerance, delta) &&
measured <= ticksHigh(desired, tolerance, delta));
}
@ -616,6 +751,17 @@ bool IRrecv::matchAtLeast(uint32_t measured, uint32_t desired,
DPRINT(", ");
DPRINT(ticksLow(MS_TO_USEC(irparams.timeout), tolerance, delta));
DPRINTLN(")]");
#ifdef UNIT_TEST
// Sanity checks that we don't have values that cause integer over/underflow.
// Only performed during testing so there is no performance hit in normal
// operation.
assert(ticksLow(desired, tolerance, delta) <= desired);
// Check if we overflowed. (UINT32_MAX >> 3 is approx 9 minutes!)
assert(ticksHigh(desired, tolerance, delta) < UINT32_MAX >> 3);
// Check if our high mark is below where we started. This could happen.
// If there is a legit case, then this should be removed.
assert(ticksHigh(desired, tolerance, delta) >= desired);
#endif // UNIT_TEST
// We really should never get a value of 0, except as the last value
// in the buffer. If that is the case, then assume infinity and return true.
if (measured == 0) return true;
@ -702,7 +848,7 @@ int16_t IRrecv::compare(uint16_t oldval, uint16_t newval) {
*/
bool IRrecv::decodeHash(decode_results *results) {
// Require at least some samples to prevent triggering on noise
if (results->rawlen < unknown_threshold) return false;
if (results->rawlen < _unknown_threshold) return false;
int32_t hash = kFnvBasis32;
// 'rawlen - 2' to avoid the look ahead from going out of bounds.
// Should probably be -3 to avoid comparing the trailing space entry,
@ -765,4 +911,236 @@ match_result_t IRrecv::matchData(
return result;
}
// Match & decode the typical data section of an IR message.
// The bytes are stored at result_ptr. The first byte in the result equates to
// the first byte encountered, and so on.
//
// Args:
// data_ptr: A pointer to where we are at in the capture buffer.
// result_ptr: A pointer to where to start storing the bytes we decoded.
// remaining: The size of the capture buffer are remaining.
// nbytes: Nr. of data bytes we expect.
// onemark: Nr. of uSeconds in an expected mark signal for a '1' bit.
// onespace: Nr. of uSeconds in an expected space signal for a '1' bit.
// zeromark: Nr. of uSeconds in an expected mark signal for a '0' bit.
// zerospace: Nr. of uSeconds in an expected space signal for a '0' bit.
// tolerance: Percentage error margin to allow. (Def: kTolerance)
// excess: Nr. of useconds. (Def: kMarkExcess)
// MSBfirst: Bit order to save the data in. (Def: true)
// Returns:
// A uint16_t: If successful, how many buffer entries were used. Otherwise 0.
uint16_t IRrecv::matchBytes(volatile uint16_t *data_ptr, uint8_t *result_ptr,
const uint16_t remaining, const uint16_t nbytes,
const uint16_t onemark, const uint32_t onespace,
const uint16_t zeromark, const uint32_t zerospace,
const uint8_t tolerance, const int16_t excess,
const bool MSBfirst) {
// Check if there is enough capture buffer to possibly have the desired bytes.
if (remaining < nbytes * 8 * 2) return 0; // Nope, so abort.
uint16_t offset = 0;
for (uint16_t byte_pos = 0; byte_pos < nbytes; byte_pos++) {
match_result_t result = matchData(data_ptr + offset, 8, onemark, onespace,
zeromark, zerospace, tolerance, excess,
MSBfirst);
if (result.success == false) return 0; // Fail
result_ptr[byte_pos] = (uint8_t)result.data;
offset += result.used;
}
return offset;
}
// Match & decode a generic/typical IR message.
// The data is stored in result_bits_ptr or result_bytes_ptr depending on flag
// `use_bits`.
// Values of 0 for hdrmark, hdrspace, footermark, or footerspace mean skip
// that requirement.
//
// Args:
// data_ptr: A pointer to where we are at in the capture buffer.
// result_bits_ptr: A pointer to where to start storing the bits we decoded.
// result_bytes_ptr: A pointer to where to start storing the bytes we decoded.
// use_bits: A flag indicating if we are to decode bits or bytes.
// remaining: The size of the capture buffer are remaining.
// nbits: Nr. of data bits we expect.
// hdrmark: Nr. of uSeconds for the expected header mark signal.
// hdrspace: Nr. of uSeconds for the expected header space signal.
// onemark: Nr. of uSeconds in an expected mark signal for a '1' bit.
// onespace: Nr. of uSeconds in an expected space signal for a '1' bit.
// zeromark: Nr. of uSeconds in an expected mark signal for a '0' bit.
// zerospace: Nr. of uSeconds in an expected space signal for a '0' bit.
// footermark: Nr. of uSeconds for the expected footer mark signal.
// footerspace: Nr. of uSeconds for the expected footer space/gap signal.
// atleast: Is the match on the footerspace a matchAtLeast or matchSpace?
// tolerance: Percentage error margin to allow. (Def: kTolerance)
// excess: Nr. of useconds. (Def: kMarkExcess)
// MSBfirst: Bit order to save the data in. (Def: true)
// Returns:
// A uint16_t: If successful, how many buffer entries were used. Otherwise 0.
uint16_t IRrecv::_matchGeneric(volatile uint16_t *data_ptr,
uint64_t *result_bits_ptr,
uint8_t *result_bytes_ptr,
const bool use_bits,
const uint16_t remaining,
const uint16_t nbits,
const uint16_t hdrmark,
const uint32_t hdrspace,
const uint16_t onemark,
const uint32_t onespace,
const uint16_t zeromark,
const uint32_t zerospace,
const uint16_t footermark,
const uint32_t footerspace,
const bool atleast,
const uint8_t tolerance,
const int16_t excess,
const bool MSBfirst) {
// If we are expecting byte sizes, check it's a factor of 8 or fail.
if (!use_bits && nbits % 8 != 0) return 0;
// Calculate how much remaining buffer is required.
uint16_t min_remaining = nbits * 2;
if (hdrmark) min_remaining++;
if (hdrspace) min_remaining++;
if (footermark) min_remaining++;
// Don't need to extend for footerspace because it could be the end of message
// Check if there is enough capture buffer to possibly have the message.
if (remaining < min_remaining) return 0; // Nope, so abort.
uint16_t offset = 0;
// Header
if (hdrmark && !matchMark(*(data_ptr + offset++), hdrmark, tolerance, excess))
return 0;
if (hdrspace && !matchSpace(*(data_ptr + offset++), hdrspace, tolerance,
excess))
return 0;
// Data
if (use_bits) { // Bits.
match_result_t result = IRrecv::matchData(data_ptr + offset, nbits,
onemark, onespace,
zeromark, zerospace, tolerance,
excess, MSBfirst);
if (!result.success) return 0;
*result_bits_ptr = result.data;
offset += result.used;
} else { // bytes
uint16_t data_used = IRrecv::matchBytes(data_ptr + offset, result_bytes_ptr,
remaining - offset, nbits / 8,
onemark, onespace,
zeromark, zerospace, tolerance,
excess, MSBfirst);
if (!data_used) return 0;
offset += data_used;
}
// Footer
if (footermark && !matchMark(*(data_ptr + offset++), footermark, tolerance,
excess))
return 0;
// If we have something still to match & haven't reached the end of the buffer
if (footerspace && offset < remaining) {
if (atleast) {
if (!matchAtLeast(*(data_ptr + offset), footerspace, tolerance, excess))
return 0;
} else {
if (!matchSpace(*(data_ptr + offset), footerspace, tolerance, excess))
return 0;
}
offset++;
}
return offset;
}
// Match & decode a generic/typical <= 64bit IR message.
// The data is stored at result_ptr.
// Values of 0 for hdrmark, hdrspace, footermark, or footerspace mean skip
// that requirement.
//
// Args:
// data_ptr: A pointer to where we are at in the capture buffer.
// result_ptr: A pointer to where to start storing the bits we decoded.
// remaining: The size of the capture buffer are remaining.
// nbits: Nr. of data bits we expect.
// hdrmark: Nr. of uSeconds for the expected header mark signal.
// hdrspace: Nr. of uSeconds for the expected header space signal.
// onemark: Nr. of uSeconds in an expected mark signal for a '1' bit.
// onespace: Nr. of uSeconds in an expected space signal for a '1' bit.
// zeromark: Nr. of uSeconds in an expected mark signal for a '0' bit.
// zerospace: Nr. of uSeconds in an expected space signal for a '0' bit.
// footermark: Nr. of uSeconds for the expected footer mark signal.
// footerspace: Nr. of uSeconds for the expected footer space/gap signal.
// atleast: Is the match on the footerspace a matchAtLeast or matchSpace?
// tolerance: Percentage error margin to allow. (Def: kTolerance)
// excess: Nr. of useconds. (Def: kMarkExcess)
// MSBfirst: Bit order to save the data in. (Def: true)
// Returns:
// A uint16_t: If successful, how many buffer entries were used. Otherwise 0.
uint16_t IRrecv::matchGeneric(volatile uint16_t *data_ptr,
uint64_t *result_ptr,
const uint16_t remaining,
const uint16_t nbits,
const uint16_t hdrmark,
const uint32_t hdrspace,
const uint16_t onemark,
const uint32_t onespace,
const uint16_t zeromark,
const uint32_t zerospace,
const uint16_t footermark,
const uint32_t footerspace,
const bool atleast,
const uint8_t tolerance,
const int16_t excess,
const bool MSBfirst) {
return _matchGeneric(data_ptr, result_ptr, NULL, true, remaining, nbits,
hdrmark, hdrspace, onemark, onespace,
zeromark, zerospace, footermark, footerspace, atleast,
tolerance, excess, MSBfirst);
}
// Match & decode a generic/typical > 64bit IR message.
// The bytes are stored at result_ptr. The first byte in the result equates to
// the first byte encountered, and so on.
// Values of 0 for hdrmark, hdrspace, footermark, or footerspace mean skip
// that requirement.
//
// Args:
// data_ptr: A pointer to where we are at in the capture buffer.
// result_ptr: A pointer to where to start storing the bytes we decoded.
// remaining: The size of the capture buffer are remaining.
// nbits: Nr. of data bits we expect.
// hdrmark: Nr. of uSeconds for the expected header mark signal.
// hdrspace: Nr. of uSeconds for the expected header space signal.
// onemark: Nr. of uSeconds in an expected mark signal for a '1' bit.
// onespace: Nr. of uSeconds in an expected space signal for a '1' bit.
// zeromark: Nr. of uSeconds in an expected mark signal for a '0' bit.
// zerospace: Nr. of uSeconds in an expected space signal for a '0' bit.
// footermark: Nr. of uSeconds for the expected footer mark signal.
// footerspace: Nr. of uSeconds for the expected footer space/gap signal.
// atleast: Is the match on the footerspace a matchAtLeast or matchSpace?
// tolerance: Percentage error margin to allow. (Def: kTolerance)
// excess: Nr. of useconds. (Def: kMarkExcess)
// MSBfirst: Bit order to save the data in. (Def: true)
// Returns:
// A uint16_t: If successful, how many buffer entries were used. Otherwise 0.
uint16_t IRrecv::matchGeneric(volatile uint16_t *data_ptr,
uint8_t *result_ptr,
const uint16_t remaining,
const uint16_t nbits,
const uint16_t hdrmark,
const uint32_t hdrspace,
const uint16_t onemark,
const uint32_t onespace,
const uint16_t zeromark,
const uint32_t zerospace,
const uint16_t footermark,
const uint32_t footerspace,
const bool atleast,
const uint8_t tolerance,
const int16_t excess,
const bool MSBfirst) {
return _matchGeneric(data_ptr, NULL, result_ptr, false, remaining, nbits,
hdrmark, hdrspace, onemark, onespace,
zeromark, zerospace, footermark, footerspace, atleast,
tolerance, excess, MSBfirst);
}
// End of IRrecv class -------------------

Some files were not shown because too many files have changed in this diff Show More