В данном проекте мы рассмотрим создание системы автоматизации дома (подобные системы также известны под названием "умный дом") на основе платы Arduino. Управление домашними устройствами в нем будет осуществляться с помощью голоса, преобразование голоса в текст будет осуществляться с помощью Android приложения. Прием данных от смартфона будет осуществляться с помощью Bluetooth модуля HC-05.
Принцип работы нашего проекта будет достаточно прост. Голосовые команды будет распознаваться и преобразовываться в текст с помощью Android приложения на смартфоне, после этого данный текст будет передаваться плате Arduino по протоколу Bluetooth. Для приема этих данных мы будем использовать хорошо зарекомендовавший себя во многих проектах Bluetooth модуль HC-05, который будет передавать эти данные плате Arduino через последовательный порт (UART). Мы будем использовать штатный последовательный порт платы Arduino Nano, однако вы при желании можете его организовать на любых двух цифровых контактах данной платы с помощью библиотеки software serial.
Ранее на нашем сайте мы уже рассматривали достаточно много различных проектов автоматизации дома на основе различных микроконтроллеров (плат), наиболее популярными среди которых являются следующие:
- автоматизация дома на Raspberry Pi с управлением с веб-страницы;
- управление светом в доме с помощью сенсорного датчика и Arduino;
- автоматическая регулировка температуры в доме с помощью терморезистора и Arduino;
- автоматизация дома на Arduino под управлением смартфона.
Необходимые компоненты
- Плата Arduino Nano (купить на AliExpress).
- Bluetooth модуль HC-05 (купить на AliExpress).
- Модуль источника питания Hi-link 5V 3W.
- Инфракрасный датчик VS1838.
- Инфракрасный светодиод 5MM.
- NPN транзистор S8050 – 4 шт.
- Реле 5V – 4 шт.
- Диод 1N4007 (купить на AliExpress).
- Светодиоды – 4 шт. (купить на AliExpress).
- Резисторы 1 кОм (5 шт.), 470 Ом (4 шт.) (купить на AliExpress).
- Двухпиновые терминалы на 10A – 5 шт.
- Перфорированная плата, соединительные провода.
Реклама: ООО "АЛИБАБА.КОМ (РУ)" ИНН: 7703380158
Схема проекта
Схема проекта автоматизации дома на основе платы Arduino с голосовым управлением представлена на следующем рисунке.
Модуль Hi-Link 5V AC-DC используется в качестве источника питания для схемы. В схеме присутствуют 4 отдельных реле со схемами их управления (драйверами реле), которые построены на основе транзисторов S8050. Контакты катушек реле подключены к линии 5V. Когда на базу транзистора будет подаваться импульс высокого уровня, он будет подавать на второй контакт катушки землю. Диод 1N4007 используется для защиты схемы от скачков напряжения. Светодиод в схеме каждого реле будет индицировать статус каждого реле (вкл/выкл).
Внешний вид платы проекта с обеих сторон показан на следующем рисунке.
Bluetooth модуль подключен к плате Arduino с использованием последовательного порта, ему никакая дополнительная настройка не требуется, он будет взаимодействовать с платой Arduino на скорости по умолчанию. Можно использовать любой другой аналогичный Bluetooth модуль с поддержкой профиля SPP. Но в этом случае удостоверьтесь в том, что вы установили скорость 9600 бод.
Инфракрасный датчик VS1838 подключен к контакту D2 платы Arduino. Лучше использовать именно этот контакт поскольку обработку информации от инфракрасного датчика мы будем производить с использованием аппаратного прерывания. В режиме обучения при обнаружении инфракрасного сигнала мы будем использовать подпрограмму обработки прерывания для декодирования инфракрасных сигналов. Передающий инфракрасный светодиод будет управляться с помощью транзистора S8050, база которого подключена к контакту D3 платы. Этот контакт также желательно не менять поскольку от него зависит используемая нами библиотека. На выходе данного контакт мы будем формировать ШИМ сигнал (широтно-импульсная модуляция) чтобы управлять передающим инфракрасным светодиодом. Цветная RGB лента neopixel со светодиодами подключена к контакту D12 платы. Измените в коде программы количество светодиодов соответственно используемой вами светодиодной ленте. Если число светодиодов в ленте достаточно большое лучше ее запитать от отдельного источника.
Внешний вид собранной конструкции проекта представлен на следующем рисунке.
Объяснение программы для Arduino
Полный код программы приведен в конце статьи, здесь же мы кратко рассмотрим его основные фрагменты.
Первым делом в коде программы установим все необходимые библиотеки и зададим настройки для библиотек IRMP (прием инфракрасных сигналов) и FastLED (для управления RGB светодиодной лентой). Вы можете установить эти библиотеки с помощью менеджера библиотек Arduino или скачать их с репозитория GitHub и установить вручную. Также задействуем все известные протоколы инфракрасной связи, их около 40. Если вы уверены что часть этих протоколов вам точно не понадобится, вы можете просто закомментарить их в приведенном коде – этим вы снизите объем используемой памяти. Также создадим с помощью библиотеки FastLED два объекта для работы с инфракрасными датчиками – один для приема сигналов, а другой для передачи. Затем объявим все необходимые нам глобальные переменные.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 |
#include <Arduino.h> #include <FastLED.h> #include <EEPROM.h> #define DATA_PIN 12 //Define led data pin in #define LED_TYPE NEOPIXEL //define type of led #define NUM_LEDS 16 //num of leds in strip #define IRMP_INPUT_PIN 2 // To be compatible with interrupt example, pin 2 is chosen here. #define IRSND_OUTPUT_PIN 3 #define TONE_PIN 4 #define IRSND_IR_FREQUENCY 38000 #define IRMP_PROTOCOL_NAMES 1 // Enable protocol number mapping to protocol strings - needs some program memory ~ 420 bytes here #define IRMP_USE_COMPLETE_CALLBACK 1 // Enable callback functionality // Decode protocol list!disable unwanted Enable Remarks F_INTERRUPTS program memory #define IRMP_SUPPORT_SIRCS_PROTOCOL 1 // Sony SIRCS >= 10000 ~150 bytes #define IRMP_SUPPORT_NEC_PROTOCOL 1 // NEC + APPLE + ONKYO >= 10000 ~300 bytes #define IRMP_SUPPORT_SAMSUNG_PROTOCOL 1 // Samsung + Samsg32 >= 10000 ~300 bytes #define IRMP_SUPPORT_KASEIKYO_PROTOCOL 1 // Kaseikyo >= 10000 ~250 bytes #define IRMP_SUPPORT_JVC_PROTOCOL 1 // JVC >= 10000 ~150 bytes #define IRMP_SUPPORT_NEC16_PROTOCOL 1 // NEC16 >= 10000 ~100 bytes #define IRMP_SUPPORT_NEC42_PROTOCOL 1 // NEC42 >= 10000 ~300 bytes #define IRMP_SUPPORT_MATSUSHITA_PROTOCOL 1 // Matsushita >= 10000 ~50 bytes #define IRMP_SUPPORT_DENON_PROTOCOL 1 // DENON, Sharp >= 10000 ~250 bytes #define IRMP_SUPPORT_RC5_PROTOCOL 1 // RC5 >= 10000 ~250 bytes #define IRMP_SUPPORT_RC6_PROTOCOL 1 // RC6 & RC6A >= 10000 ~250 bytes #define IRMP_SUPPORT_IR60_PROTOCOL 1 // IR60 (SDA2008) >= 10000 ~300 bytes #define IRMP_SUPPORT_GRUNDIG_PROTOCOL 1 // Grundig >= 10000 ~300 bytes #define IRMP_SUPPORT_SIEMENS_PROTOCOL 1 // Siemens Gigaset >= 15000 ~550 bytes #define IRMP_SUPPORT_NOKIA_PROTOCOL 1 // Nokia >= 10000 ~300 bytes #define IRMP_SUPPORT_BOSE_PROTOCOL 1 // BOSE >= 10000 ~150 bytes #define IRMP_SUPPORT_KATHREIN_PROTOCOL 1 // Kathrein >= 10000 ~200 bytes #define IRMP_SUPPORT_NUBERT_PROTOCOL 1 // NUBERT >= 10000 ~50 bytes #define IRMP_SUPPORT_FAN_PROTOCOL 0 // FAN (ventilator) >= 10000 ~50 bytes conflicts with NUBERT #define IRMP_SUPPORT_SPEAKER_PROTOCOL 1 // SPEAKER (~NUBERT) >= 10000 ~50 bytes #define IRMP_SUPPORT_BANG_OLUFSEN_PROTOCOL 1 // Bang & Olufsen >= 10000 ~200 bytes #define IRMP_SUPPORT_RECS80_PROTOCOL 1 // RECS80 (SAA3004) >= 15000 ~50 bytes #define IRMP_SUPPORT_RECS80EXT_PROTOCOL 1 // RECS80EXT (SAA3008) >= 15000 ~50 bytes #define IRMP_SUPPORT_THOMSON_PROTOCOL 1 // Thomson >= 10000 ~250 bytes #define IRMP_SUPPORT_NIKON_PROTOCOL 1 // NIKON camera >= 10000 ~250 bytes #define IRMP_SUPPORT_NETBOX_PROTOCOL 1 // Netbox keyboard >= 10000 ~400 bytes (PROTOTYPE!) #define IRMP_SUPPORT_ORTEK_PROTOCOL 0 // ORTEK (Hama) >= 10000 ~150 bytes conflicts with FDC and NETBOX #define IRMP_SUPPORT_TELEFUNKEN_PROTOCOL 1 // Telefunken 1560 >= 10000 ~150 bytes #define IRMP_SUPPORT_FDC_PROTOCOL 1 // FDC3402 keyboard >= 10000 (better 15000) ~150 bytes (~400 in combination with RC5) #define IRMP_SUPPORT_RCCAR_PROTOCOL 1 // RC Car >= 10000 (better 15000) ~150 bytes (~500 in combination with RC5) #define IRMP_SUPPORT_ROOMBA_PROTOCOL 0 // iRobot Roomba >= 10000 ~150 bytes conflicts with RC6 #define IRMP_SUPPORT_RUWIDO_PROTOCOL 0 // RUWIDO, T-Home >= 15000 ~550 bytes conflicts with DENON #define IRMP_SUPPORT_A1TVBOX_PROTOCOL 1 // A1 TV BOX >= 15000 (better 20000) ~300 bytes #define IRMP_SUPPORT_LEGO_PROTOCOL 1 // LEGO Power RC >= 20000 ~150 bytes #define IRMP_SUPPORT_RCMM_PROTOCOL 1 // RCMM 12,24, or 32 >= 20000 ~150 bytes #define IRMP_SUPPORT_LGAIR_PROTOCOL 1 // LG Air Condition >= 10000 ~300 bytes #define IRMP_SUPPORT_SAMSUNG48_PROTOCOL 1 // Samsung48 >= 10000 ~100 bytes (SAMSUNG must be enabled!) #define IRMP_SUPPORT_MERLIN_PROTOCOL 1 // Merlin >= 15000 (better 20000) ~300 bytes (requires IRMP_32_BIT=1) #define IRMP_SUPPORT_PENTAX_PROTOCOL 1 // Pentax >= 10000 <=17000 ~150 bytes (<= 17000 due to 8 bit timing overflow issue) #define IRMP_SUPPORT_S100_PROTOCOL 0 // S100 >= 10000 ~250 bytes conflicts with RC5 #define IRMP_SUPPORT_ACP24_PROTOCOL 0 // ACP24 >= 10000 ~250 bytes conflicts with DENON #define IRMP_SUPPORT_TECHNICS_PROTOCOL 1 // TECHNICS >= 10000 ~250 bytes #define IRMP_SUPPORT_PANASONIC_PROTOCOL 0 // PANASONIC Beamer >= 10000 ~250 bytes conflicts with KASEIKYO #define IRMP_SUPPORT_MITSU_HEAVY_PROTOCOL 0 // Mitsubishi Aircond >= 10000 ~250 bytes conflicts with KASEIKYO #define IRMP_SUPPORT_VINCENT_PROTOCOL 1 // VINCENT >= 10000 ~250 bytes #define IRMP_SUPPORT_SAMSUNGAH_PROTOCOL 1 // SAMSUNG AH >= 10000 ~250 bytes #define IRMP_SUPPORT_IRMP16_PROTOCOL 0 // IRMP specific >= 15000 ~250 bytes #define IRMP_SUPPORT_GREE_PROTOCOL 1 // GREE CLIMATE >= 10000 <=17000 ~250 bytes #define IRMP_SUPPORT_RCII_PROTOCOL 0 // RCII T+A >= 15000 ~250 bytes conflicts with GRUNDIG and NOKIA #define IRMP_SUPPORT_METZ_PROTOCOL 1 #define IRMP_SUPPORT_MELINERA_PROTOCOL 1 // MELINERA (Lidl) >= 10000 // Encode protocol list!disable unwanted Enable Remarks F_INTERRUPTS program memory #define IRSND_SUPPORT_SIRCS_PROTOCOL 1 // Sony SIRCS >= 10000 ~200 bytes #define IRSND_SUPPORT_NEC_PROTOCOL 1 // NEC + APPLE >= 10000 ~100 bytes #define IRSND_SUPPORT_SAMSUNG_PROTOCOL 1 // Samsung + Samsung32 >= 10000 ~300 bytes #define IRSND_SUPPORT_KASEIKYO_PROTOCOL 1 // Kaseikyo >= 10000 ~300 bytes #define IRSND_SUPPORT_JVC_PROTOCOL 1 // JVC >= 10000 ~150 bytes #define IRSND_SUPPORT_NEC16_PROTOCOL 1 // NEC16 >= 10000 ~150 bytes #define IRSND_SUPPORT_NEC42_PROTOCOL 1 // NEC42 >= 10000 ~150 bytes #define IRSND_SUPPORT_MATSUSHITA_PROTOCOL 1 // Matsushita >= 10000 ~200 bytes #define IRSND_SUPPORT_DENON_PROTOCOL 1 // DENON, Sharp >= 10000 ~200 bytes #define IRSND_SUPPORT_RC5_PROTOCOL 1 // RC5 >= 10000 ~150 bytes #define IRSND_SUPPORT_RC6_PROTOCOL 1 // RC6 >= 10000 ~250 bytes #define IRSND_SUPPORT_RC6A_PROTOCOL 1 // RC6A >= 10000 ~250 bytes #define IRSND_SUPPORT_GRUNDIG_PROTOCOL 1 // Grundig >= 10000 ~300 bytes #define IRSND_SUPPORT_SIEMENS_PROTOCOL 1 // Siemens, Gigaset >= 15000 ~150 bytes #define IRSND_SUPPORT_NOKIA_PROTOCOL 1 // Nokia >= 10000 ~400 bytes #define IRSND_SUPPORT_IR60_PROTOCOL 0 // IR60 (SDA2008) >= 10000 ~250 bytes // IR frequency 30 kHz #define IRSND_SUPPORT_BOSE_PROTOCOL 1 // BOSE >= 10000 ~100 bytes #define IRSND_SUPPORT_KATHREIN_PROTOCOL 0 // Kathrein >= 10000 DON'T CHANGE, NOT SUPPORTED YET! #define IRSND_SUPPORT_NUBERT_PROTOCOL 1 // NUBERT >= 10000 ~100 bytes #define IRSND_SUPPORT_FAN_PROTOCOL 1 // FAN (ventilator) >= 10000 ~100 bytes #define IRSND_SUPPORT_SPEAKER_PROTOCOL 1 // SPEAKER >= 10000 ~100 bytes #define IRSND_SUPPORT_BANG_OLUFSEN_PROTOCOL 0 // Bang&Olufsen >= 10000 ~250 bytes // IR frequency 455 kHz #define IRSND_SUPPORT_RECS80_PROTOCOL 1 // RECS80 >= 15000 ~100 bytes #define IRSND_SUPPORT_RECS80EXT_PROTOCOL 1 // RECS80EXT >= 15000 ~100 bytes #define IRSND_SUPPORT_THOMSON_PROTOCOL 1 // Thomson >= 10000 ~250 bytes #define IRSND_SUPPORT_NIKON_PROTOCOL 1 // NIKON >= 10000 ~150 bytes #define IRSND_SUPPORT_NETBOX_PROTOCOL 0 // Netbox keyboard >= 10000 DON'T CHANGE, NOT SUPPORTED YET! #define IRSND_SUPPORT_ORTEK_PROTOCOL 0 // ORTEK (Hama) >= 10000 DON'T CHANGE, NOT SUPPORTED YET! #define IRSND_SUPPORT_TELEFUNKEN_PROTOCOL 1 // Telefunken 1560 >= 10000 ~150 bytes #define IRSND_SUPPORT_FDC_PROTOCOL 1 // FDC IR keyboard >= 10000 (better 15000) ~150 bytes #define IRSND_SUPPORT_RCCAR_PROTOCOL 1 // RC CAR >= 10000 (better 15000) ~150 bytes #define IRSND_SUPPORT_ROOMBA_PROTOCOL 1 // iRobot Roomba >= 10000 ~150 bytes #define IRSND_SUPPORT_RUWIDO_PROTOCOL 1 // RUWIDO, T-Home >= 15000 ~250 bytes #define IRSND_SUPPORT_A1TVBOX_PROTOCOL 1 // A1 TV BOX >= 15000 (better 20000) ~200 bytes #define IRSND_SUPPORT_LEGO_PROTOCOL 1 // LEGO Power RC >= 20000 ~150 bytes #define IRSND_SUPPORT_RCMM_PROTOCOL 0 // RCMM 12,24, or 32 >= 20000 DON'T CHANGE, NOT SUPPORTED YET! #define IRSND_SUPPORT_LGAIR_PROTOCOL 1 // LG Air Condition >= 10000 ~150 bytes. #define IRSND_SUPPORT_SAMSUNG48_PROTOCOL 1 // Samsung48 >= 10000 ~100 bytes #define IRSND_SUPPORT_PENTAX_PROTOCOL 1 // Pentax >= 10000 ~150 bytes #define IRSND_SUPPORT_S100_PROTOCOL 1 // S100 >= 10000 ~150 bytes #define IRSND_SUPPORT_ACP24_PROTOCOL 1 // ACP24 >= 10000 ~150 bytes #define IRSND_SUPPORT_TECHNICS_PROTOCOL 1 // TECHNICS >= 10000 ~200 bytes #define IRSND_SUPPORT_PANASONIC_PROTOCOL 1 // PANASONIC Beamer >= 10000 ~150 bytes #define IRSND_SUPPORT_MITSU_HEAVY_PROTOCOL 1 // Mitsubishi-Heavy Aircondition, similar Timing to Panasonic beamer #define IRSND_SUPPORT_IRMP16_PROTOCOL 0 // IRMP specific >= 15000 ~250 bytes #define USE_ONE_TIMER_FOR_IRMP_AND_IRSND #include <irmp.hpp> #include <irsnd.hpp> IRMP_DATA irmp_data; IRMP_DATA irsnd_data; int Prortocol_Index[58] = { IRMP_UNKNOWN_PROTOCOL, IRMP_SIRCS_PROTOCOL, IRMP_NEC_PROTOCOL, IRMP_SAMSUNG_PROTOCOL, IRMP_MATSUSHITA_PROTOCOL, IRMP_KASEIKYO_PROTOCOL, IRMP_RECS80_PROTOCOL, IRMP_RC5_PROTOCOL, IRMP_DENON_PROTOCOL, IRMP_RC6_PROTOCOL, IRMP_SAMSUNG32_PROTOCOL, IRMP_APPLE_PROTOCOL, IRMP_RECS80EXT_PROTOCOL, IRMP_NUBERT_PROTOCOL, IRMP_BANG_OLUFSEN_PROTOCOL, IRMP_GRUNDIG_PROTOCOL, IRMP_NOKIA_PROTOCOL, IRMP_SIEMENS_PROTOCOL, IRMP_FDC_PROTOCOL, IRMP_RCCAR_PROTOCOL, IRMP_JVC_PROTOCOL, IRMP_RC6A_PROTOCOL, IRMP_NIKON_PROTOCOL, IRMP_RUWIDO_PROTOCOL, IRMP_IR60_PROTOCOL, IRMP_KATHREIN_PROTOCOL, IRMP_NETBOX_PROTOCOL, IRMP_NEC16_PROTOCOL, IRMP_NEC42_PROTOCOL, IRMP_LEGO_PROTOCOL, IRMP_THOMSON_PROTOCOL, IRMP_BOSE_PROTOCOL, IRMP_A1TVBOX_PROTOCOL, IRMP_ORTEK_PROTOCOL, IRMP_TELEFUNKEN_PROTOCOL, IRMP_ROOMBA_PROTOCOL, IRMP_RCMM32_PROTOCOL, IRMP_RCMM24_PROTOCOL, IRMP_RCMM12_PROTOCOL, IRMP_SPEAKER_PROTOCOL, IRMP_LGAIR_PROTOCOL, IRMP_SAMSUNG48_PROTOCOL, IRMP_MERLIN_PROTOCOL, IRMP_PENTAX_PROTOCOL, IRMP_FAN_PROTOCOL, IRMP_S100_PROTOCOL, IRMP_ACP24_PROTOCOL, IRMP_TECHNICS_PROTOCOL, IRMP_PANASONIC_PROTOCOL, IRMP_MITSU_HEAVY_PROTOCOL, IRMP_VINCENT_PROTOCOL, IRMP_SAMSUNGAH_PROTOCOL, IRMP_IRMP16_PROTOCOL, IRMP_GREE_PROTOCOL, IRMP_RCII_PROTOCOL, IRMP_METZ_PROTOCOL, IRMP_ONKYO_PROTOCOL }; struct CRGB leds[NUM_LEDS]; // Initialize LED array const int Relay1 = 5; // Relay pin 1 (IN1) const int Relay2 = 4; // Relay pin 2 (IN2) const int Relay3 = 6; // Relay pin 3 (IN3) const int Relay4 = 7; // Relay pin 4 (IN4) int irrec = 0; String data; //Variable for storing received data int proto; uint16_t addr, cmd, temp; int eeadr; void handleReceivedIRData(); void IRDecoder(); void SerialDecoder(); bool volatile sIRMPDataAvailable = false; |
В функции void setup() мы инициализируем последовательную связь на скорости 9600 бод – это скорость по умолчанию для модуля HC-05. Если вы в настройках модуля HC-05 измените эту скорость не забудьте изменить ее и здесь, в программе. Также мы инициализируем библиотеку FastLED и установим режимы работы используемых контактов.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 |
void setup() { Serial.begin(9600); //Sets the baud for serial data transmission FastLED.addLeds<LED_TYPE, DATA_PIN>(leds, NUM_LEDS); // Set Relay pins as OUTPUT pinMode(Relay1, OUTPUT); pinMode(Relay2, OUTPUT); pinMode(Relay3, OUTPUT); pinMode(Relay4, OUTPUT); // Init all relays to off digitalWrite(Relay1, LOW); digitalWrite(Relay2, LOW); digitalWrite(Relay3, LOW); digitalWrite(Relay4, LOW); irmp_init(); irmp_irsnd_LEDFeedback(true); // Enable receive signal feedback at LED_BUILTIN irmp_register_complete_callback_function(&handleReceivedIRData); irsnd_init(); } |
В функции void loop() мы создадим два дополнительных цикла. В них плата Arduino будет проверять присутствуют ли какие либо данные в буфере последовательного порта (UART). Если данные присутствуют, мы будем считывать их в переменную и завершать досрочно (break) цикл как только обнаружим конечный символ. После выхода из цикла мы будем вызывать функцию SerialDecoder для декодирования сообщения. После этого мы будем переходить в предыдущий цикл. Если поступила команда записать инфракрасный сигнал мы будем искать (прослушивать) новый инфракрасный сигнал с помощью вызова функции RDecoder.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 |
void loop() { // Read data from Bluetooth Module char ch = 0; data = ""; while (1) { // When there is no command received the MCU will be in this loop. while (Serial.available() <= 0) { if (irrec > 0) { IRDecoder();// Call IR decoder function when a valid command is detected } digitalWrite(13, irrec); }; ch = Serial.read(); if (ch == '#') break; // break the loop when a command is received data += ch; } SerialDecoder();// call serial Decoder function } |
В функции SerialDecoder мы будем осуществлять декодирование всех голосовых сообщений (преобразованных в текст) и исполнять содержащиеся в них команды. Для этого мы будем сравнивать приходящие сообщения с заранее определенными образцами сообщений и при обнаружении соответствия исполнять необходимую команду. Вы можете модифицировать эту функцию если хотите обрабатывать дополнительные голосовые команды.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 |
void SerialDecoder() { // Print Bluetooth Module data on serial monitor Serial.print(data); Serial.print("\n"); // Control the devices using voice command if (data.startsWith("*turn on light")) // turn on Device1 { digitalWrite(Relay1, HIGH); Serial.println(" : light on"); delay(200); } else if (data.startsWith("*turn off light")) // turn off Device1 { digitalWrite(Relay1, LOW); Serial.println(" : light off"); delay(2000); } else if (data.startsWith("*turn on TV")) // turn on Device2 { digitalWrite(Relay2, HIGH); Serial.println(" : TV on"); delay(200); } else if (data.startsWith("*turn off TV")) // turn off Device2 { digitalWrite(Relay2, LOW); Serial.println(" : TV off"); delay(200); } else if (data.startsWith("*turn on fan")) // turn on Device3 { digitalWrite(Relay3, HIGH); Serial.println(" : fan on"); delay(200); } else if (data.startsWith("*turn off fan")) // turn off Device3 { digitalWrite(Relay3, LOW); Serial.println(" : fan off"); delay(200); } else if (data.startsWith("*turn on music")) // turn on Device4 { digitalWrite(Relay4, HIGH); Serial.println(" : music on"); delay(200); } else if (data.startsWith("*turn off music")) // turn off Device4 { digitalWrite(Relay4, LOW); Serial.println(" : music off"); delay(200); } else if (data.startsWith("*turn on all")) // turn on all Device { digitalWrite(Relay1, HIGH); digitalWrite(Relay2, HIGH); digitalWrite(Relay3, HIGH); digitalWrite(Relay4, HIGH); Serial.println(" : All Relays on"); delay(200); } else if (data.startsWith("*turn off all")) // turn off all Device { digitalWrite(Relay1, LOW); digitalWrite(Relay2, LOW); digitalWrite(Relay3, LOW); digitalWrite(Relay4, LOW); Serial.println(" : All Relays off"); delay(200); } else if (data.startsWith("*RGB red")) // set the RGB leds to red { for (int i = 0; i < NUM_LEDS; i++) { leds[i] = CRGB::Red; //set the RGB leds to red } FastLED.show(); delay(200); } else if (data.startsWith("*RGB green")) //set the RGB leds to green { for (int i = 0; i < NUM_LEDS; i++) { leds[i] = CRGB::Green; //set the RGB leds to green } FastLED.show(); delay(200); } else if (data.startsWith("*RGB blue")) // set the RGB leds to blue { for (int i = 0; i < NUM_LEDS; i++) { leds[i] = CRGB::Blue; //set the RGB leds to blue } FastLED.show(); delay(200); } else if (data.startsWith("*RGB yellow")) // set the RGB leds to yellow { for (int i = 0; i < NUM_LEDS; i++) { leds[i] = CRGB::Yellow; //set the RGB leds to yellow } FastLED.show(); delay(200); } else if (data.startsWith("*RGB white")) // // set the RGB leds to white { for (int i = 0; i < NUM_LEDS; i++) { leds[i] = CRGB::White; //set the RGB leds to white } FastLED.show(); delay(200); } else if (data.startsWith("*turn off RGB")) // turn off all RGB LEDS { for (int i = 0; i < NUM_LEDS; i++) { leds[i] = CRGB::Black; //turn off all RGB LEDS } FastLED.show(); delay(200); } else if (data.startsWith("*record power")) // record and save remote power button { irrec = 12; IRDecoder(); irrec = 1; delay(200); } else if (data.startsWith("*record volume up")) // record and save remote volume up button { irrec = 12; IRDecoder(); irrec = 2; delay(200); } else if (data.startsWith("*record volume down")) // record and save remote volume down button { irrec = 12; IRDecoder(); irrec = 3; delay(200); } else if (data.startsWith("*record next")) // record and save remote next button { irrec = 12; IRDecoder(); irrec = 4; Serial.print("irrec :"); Serial.println(irrec); delay(200); } else if (data.startsWith("*record previous")) /// record and save remote previous button { irrec = 12; IRDecoder(); irrec = 5; delay(200); } else if (data.startsWith("*remote power")) // Recall and send remote power button signal { eeadr = 10; irsnd_data.protocol = EEPROM.read(eeadr); temp = (EEPROM.read(eeadr + 2) << 8); temp |= EEPROM.read(eeadr + 1); irsnd_data.address = temp; temp = (EEPROM.read(eeadr + 4) << 8); temp |= EEPROM.read(eeadr + 3); irsnd_data.command = temp; irsnd_data.flags = 0; // repeat frame 1 time Serial.print(F("Sending data ")); Serial.println(proto); if (!irsnd_send_data(&irsnd_data, true)) { Serial.println(F("Protocol not found")); } irsnd_data_print(&Serial, &irsnd_data); } else if (data.startsWith("*remote volume up")) // Recall and send remote volume up button signal { eeadr = 20; irsnd_data.protocol = EEPROM.read(eeadr); temp = (EEPROM.read(eeadr + 2) << 8); temp |= EEPROM.read(eeadr + 1); irsnd_data.address = temp; temp = (EEPROM.read(eeadr + 4) << 8); temp |= EEPROM.read(eeadr + 3); irsnd_data.command = temp; irsnd_data.flags = 0; // repeat frame 1 time Serial.print(F("Sending data ")); Serial.println(proto); if (!irsnd_send_data(&irsnd_data, true)) { Serial.println(F("Protocol not found")); } irsnd_data_print(&Serial, &irsnd_data); } else if (data.startsWith("*remote volume down")) // Recall and send remote volume down button signal { eeadr = 30; irsnd_data.protocol = EEPROM.read(eeadr); temp = (EEPROM.read(eeadr + 2) << 8); temp |= EEPROM.read(eeadr + 1); irsnd_data.address = temp; temp = (EEPROM.read(eeadr + 4) << 8); temp |= EEPROM.read(eeadr + 3); irsnd_data.command = temp; irsnd_data.flags = 0; // repeat frame 1 time Serial.print(F("Sending data ")); Serial.println(proto); if (!irsnd_send_data(&irsnd_data, true)) { Serial.println(F("Protocol not found")); } irsnd_data_print(&Serial, &irsnd_data); } else if (data.startsWith("*remote next")) // Recall and send remote next button signal { eeadr = 40; irsnd_data.protocol = EEPROM.read(eeadr); temp = (EEPROM.read(eeadr + 2) << 8); temp |= EEPROM.read(eeadr + 1); irsnd_data.address = temp; temp = (EEPROM.read(eeadr + 4) << 8); temp |= EEPROM.read(eeadr + 3); irsnd_data.command = temp; irsnd_data.flags = 0; // repeat frame 1 time Serial.print(F("Sending data ")); Serial.println(proto); if (!irsnd_send_data(&irsnd_data, true)) { Serial.println(F("Protocol not found")); } irsnd_data_print(&Serial, &irsnd_data); } else if (data.startsWith("*remote previous")) // Recall and send remote previous button signal { eeadr = 50; irsnd_data.protocol = EEPROM.read(eeadr); temp = (EEPROM.read(eeadr + 2) << 8); temp |= EEPROM.read(eeadr + 1); irsnd_data.address = temp; temp = (EEPROM.read(eeadr + 4) << 8); temp |= EEPROM.read(eeadr + 3); irsnd_data.command = temp; irsnd_data.flags = 0; // repeat frame 1 time Serial.print(F("Sending data ")); Serial.println(proto); if (!irsnd_send_data(&irsnd_data, true)) { Serial.println(F("Protocol not found")); } irsnd_data_print(&Serial, &irsnd_data); } } |
Функция Rotary будет вызываться на исполнение при срабатывании прерывания на контакте D3, к которому подключен контакт CLK инкрементального энкодера. В данной функции будет устанавливаться в соответствующее положение флаг rotationdirection, показывающий направление вращения. Также будет устанавливаться флаг TurnDetected, который будет свидетельствовать о том, что обнаружено вращение ручки инкрементального энкодера.
1 2 3 4 5 6 7 8 9 |
void Rotary() { delay(75); if (digitalRead(PinCLK)) rotationdirection = digitalRead(PinDT); else rotationdirection = !digitalRead(PinDT); TurnDetected = true; delay(75); } |
Функция IRDecoder() будет обнаруживать новые инфракрасные сигналы и когда она обнаружит корректный сигнал она будет извлекать из него название протокола, адрес и команду. Затем она будет сохранять эти данные в EEPROM.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 |
void IRDecoder() { if (sIRMPDataAvailable) { int eepaddr = irrec; irrec = 0; int rpt; sIRMPDataAvailable = false; irmp_result_print(&irmp_data); proto = irmp_data.protocol; addr = irmp_data.address; cmd = irmp_data.command; // save signal data to EEPROM if (eepaddr < 10) { if (proto == 0) { EEPROM.write(eepaddr * 10, 0x0); } else { EEPROM.write(eepaddr * 10, proto); } if (addr == 0) { EEPROM.write((eepaddr * 10) + 1, 0); EEPROM.write((eepaddr * 10) + 2, 0); } else { EEPROM.write((eepaddr * 10) + 1, addr); EEPROM.write((eepaddr * 10) + 2, addr >> 8); } if (cmd == 0) { EEPROM.write((eepaddr * 10) + 3, 0x0); EEPROM.write((eepaddr * 10) + 4, 0x0); } else { EEPROM.write((eepaddr * 10) + 3, cmd); EEPROM.write((eepaddr * 10) + 4, cmd >> 8); } } } } |
Функция handleReceivedIRData является функцией-обработчиком прерывания и отвечает за обнаружение инфракрасных сигналов. Функция работает в фоновом режиме и сохраняет принимаемый сигнал в буфере для его последующей обработки.
1 2 3 4 |
void handleReceivedIRData() { irmp_get_data(&irmp_data); sIRMPDataAvailable = true; } |
Обработка голосовых команд
Для данного проекта вам необходимо установить на свой смартфон приложение BT Voice Control for Arduino (AMR_voice). Вы можете установить его самостоятельно из Play Store или скачать с репозитория GitHub по ссылке, приведенной ниже. После установки данного приложения включите Bluetooth и установите связь (Pair) с модулем, после чего откройте приложение. В приложении в меню выберите опцию Connect Robot чтобы увидеть список всех подключенных Bluetooth устройств. Из этого списка выберите модуль HC-05 и приложение установит связь с данным модулем.
После этого вы можете нажать кнопку микрофона и произнести необходимую команду. В нашем проекте мы будем использовать команды, приведенные на следующем рисунке. При желании вы можете изменить эти команды и/или добавить новые.
Исходный код программы (скетча)
Все необходимые файлы для этого проекта вы можете скачать по следующей ссылке.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 344 345 346 347 348 349 350 351 352 353 354 355 356 357 358 359 360 361 362 363 364 365 366 367 368 369 370 371 372 373 374 375 376 377 378 379 380 381 382 383 384 385 386 387 388 389 390 391 392 393 394 395 396 397 398 399 400 401 402 403 404 405 406 407 408 409 410 411 412 413 414 415 416 417 418 419 420 421 422 423 424 425 426 427 428 429 430 431 432 433 434 435 436 437 438 439 440 441 442 443 444 445 |
#include <Arduino.h> #include <FastLED.h> #include <EEPROM.h> #define DATA_PIN 12 //Define led data pin in #define LED_TYPE NEOPIXEL //define type of led #define NUM_LEDS 16 //num of leds in strip #define IRMP_INPUT_PIN 2 // To be compatible with interrupt example, pin 2 is chosen here. #define IRSND_OUTPUT_PIN 3 #define TONE_PIN 4 #define IRSND_IR_FREQUENCY 38000 #define IRMP_PROTOCOL_NAMES 1 // Enable protocol number mapping to protocol strings - needs some program memory ~ 420 bytes here #define IRMP_USE_COMPLETE_CALLBACK 1 // Enable callback functionality // Decode protocol list!disable unwanted Enable Remarks F_INTERRUPTS program memory #define IRMP_SUPPORT_SIRCS_PROTOCOL 1 // Sony SIRCS >= 10000 ~150 bytes #define IRMP_SUPPORT_NEC_PROTOCOL 1 // NEC + APPLE + ONKYO >= 10000 ~300 bytes #define IRMP_SUPPORT_SAMSUNG_PROTOCOL 1 // Samsung + Samsg32 >= 10000 ~300 bytes #define IRMP_SUPPORT_KASEIKYO_PROTOCOL 1 // Kaseikyo >= 10000 ~250 bytes #define IRMP_SUPPORT_JVC_PROTOCOL 1 // JVC >= 10000 ~150 bytes #define IRMP_SUPPORT_NEC16_PROTOCOL 1 // NEC16 >= 10000 ~100 bytes #define IRMP_SUPPORT_NEC42_PROTOCOL 1 // NEC42 >= 10000 ~300 bytes #define IRMP_SUPPORT_MATSUSHITA_PROTOCOL 1 // Matsushita >= 10000 ~50 bytes #define IRMP_SUPPORT_DENON_PROTOCOL 1 // DENON, Sharp >= 10000 ~250 bytes #define IRMP_SUPPORT_RC5_PROTOCOL 1 // RC5 >= 10000 ~250 bytes #define IRMP_SUPPORT_RC6_PROTOCOL 1 // RC6 & RC6A >= 10000 ~250 bytes #define IRMP_SUPPORT_IR60_PROTOCOL 1 // IR60 (SDA2008) >= 10000 ~300 bytes #define IRMP_SUPPORT_GRUNDIG_PROTOCOL 1 // Grundig >= 10000 ~300 bytes #define IRMP_SUPPORT_SIEMENS_PROTOCOL 1 // Siemens Gigaset >= 15000 ~550 bytes #define IRMP_SUPPORT_NOKIA_PROTOCOL 1 // Nokia >= 10000 ~300 bytes #define IRMP_SUPPORT_BOSE_PROTOCOL 1 // BOSE >= 10000 ~150 bytes #define IRMP_SUPPORT_KATHREIN_PROTOCOL 1 // Kathrein >= 10000 ~200 bytes #define IRMP_SUPPORT_NUBERT_PROTOCOL 1 // NUBERT >= 10000 ~50 bytes #define IRMP_SUPPORT_FAN_PROTOCOL 0 // FAN (ventilator) >= 10000 ~50 bytes conflicts with NUBERT #define IRMP_SUPPORT_SPEAKER_PROTOCOL 1 // SPEAKER (~NUBERT) >= 10000 ~50 bytes #define IRMP_SUPPORT_BANG_OLUFSEN_PROTOCOL 1 // Bang & Olufsen >= 10000 ~200 bytes #define IRMP_SUPPORT_RECS80_PROTOCOL 1 // RECS80 (SAA3004) >= 15000 ~50 bytes #define IRMP_SUPPORT_RECS80EXT_PROTOCOL 1 // RECS80EXT (SAA3008) >= 15000 ~50 bytes #define IRMP_SUPPORT_THOMSON_PROTOCOL 1 // Thomson >= 10000 ~250 bytes #define IRMP_SUPPORT_NIKON_PROTOCOL 1 // NIKON camera >= 10000 ~250 bytes #define IRMP_SUPPORT_NETBOX_PROTOCOL 1 // Netbox keyboard >= 10000 ~400 bytes (PROTOTYPE!) #define IRMP_SUPPORT_ORTEK_PROTOCOL 0 // ORTEK (Hama) >= 10000 ~150 bytes conflicts with FDC and NETBOX #define IRMP_SUPPORT_TELEFUNKEN_PROTOCOL 1 // Telefunken 1560 >= 10000 ~150 bytes #define IRMP_SUPPORT_FDC_PROTOCOL 1 // FDC3402 keyboard >= 10000 (better 15000) ~150 bytes (~400 in combination with RC5) #define IRMP_SUPPORT_RCCAR_PROTOCOL 1 // RC Car >= 10000 (better 15000) ~150 bytes (~500 in combination with RC5) #define IRMP_SUPPORT_ROOMBA_PROTOCOL 0 // iRobot Roomba >= 10000 ~150 bytes conflicts with RC6 #define IRMP_SUPPORT_RUWIDO_PROTOCOL 0 // RUWIDO, T-Home >= 15000 ~550 bytes conflicts with DENON #define IRMP_SUPPORT_A1TVBOX_PROTOCOL 1 // A1 TV BOX >= 15000 (better 20000) ~300 bytes #define IRMP_SUPPORT_LEGO_PROTOCOL 1 // LEGO Power RC >= 20000 ~150 bytes #define IRMP_SUPPORT_RCMM_PROTOCOL 1 // RCMM 12,24, or 32 >= 20000 ~150 bytes #define IRMP_SUPPORT_LGAIR_PROTOCOL 1 // LG Air Condition >= 10000 ~300 bytes #define IRMP_SUPPORT_SAMSUNG48_PROTOCOL 1 // Samsung48 >= 10000 ~100 bytes (SAMSUNG must be enabled!) #define IRMP_SUPPORT_MERLIN_PROTOCOL 1 // Merlin >= 15000 (better 20000) ~300 bytes (requires IRMP_32_BIT=1) #define IRMP_SUPPORT_PENTAX_PROTOCOL 1 // Pentax >= 10000 <=17000 ~150 bytes (<= 17000 due to 8 bit timing overflow issue) #define IRMP_SUPPORT_S100_PROTOCOL 0 // S100 >= 10000 ~250 bytes conflicts with RC5 #define IRMP_SUPPORT_ACP24_PROTOCOL 0 // ACP24 >= 10000 ~250 bytes conflicts with DENON #define IRMP_SUPPORT_TECHNICS_PROTOCOL 1 // TECHNICS >= 10000 ~250 bytes #define IRMP_SUPPORT_PANASONIC_PROTOCOL 0 // PANASONIC Beamer >= 10000 ~250 bytes conflicts with KASEIKYO #define IRMP_SUPPORT_MITSU_HEAVY_PROTOCOL 0 // Mitsubishi Aircond >= 10000 ~250 bytes conflicts with KASEIKYO #define IRMP_SUPPORT_VINCENT_PROTOCOL 1 // VINCENT >= 10000 ~250 bytes #define IRMP_SUPPORT_SAMSUNGAH_PROTOCOL 1 // SAMSUNG AH >= 10000 ~250 bytes #define IRMP_SUPPORT_IRMP16_PROTOCOL 0 // IRMP specific >= 15000 ~250 bytes #define IRMP_SUPPORT_GREE_PROTOCOL 1 // GREE CLIMATE >= 10000 <=17000 ~250 bytes #define IRMP_SUPPORT_RCII_PROTOCOL 0 // RCII T+A >= 15000 ~250 bytes conflicts with GRUNDIG and NOKIA #define IRMP_SUPPORT_METZ_PROTOCOL 1 #define IRMP_SUPPORT_MELINERA_PROTOCOL 1 // MELINERA (Lidl) >= 10000 // Encode protocol list!disable unwanted Enable Remarks F_INTERRUPTS program memory #define IRSND_SUPPORT_SIRCS_PROTOCOL 1 // Sony SIRCS >= 10000 ~200 bytes #define IRSND_SUPPORT_NEC_PROTOCOL 1 // NEC + APPLE >= 10000 ~100 bytes #define IRSND_SUPPORT_SAMSUNG_PROTOCOL 1 // Samsung + Samsung32 >= 10000 ~300 bytes #define IRSND_SUPPORT_KASEIKYO_PROTOCOL 1 // Kaseikyo >= 10000 ~300 bytes #define IRSND_SUPPORT_JVC_PROTOCOL 1 // JVC >= 10000 ~150 bytes #define IRSND_SUPPORT_NEC16_PROTOCOL 1 // NEC16 >= 10000 ~150 bytes #define IRSND_SUPPORT_NEC42_PROTOCOL 1 // NEC42 >= 10000 ~150 bytes #define IRSND_SUPPORT_MATSUSHITA_PROTOCOL 1 // Matsushita >= 10000 ~200 bytes #define IRSND_SUPPORT_DENON_PROTOCOL 1 // DENON, Sharp >= 10000 ~200 bytes #define IRSND_SUPPORT_RC5_PROTOCOL 1 // RC5 >= 10000 ~150 bytes #define IRSND_SUPPORT_RC6_PROTOCOL 1 // RC6 >= 10000 ~250 bytes #define IRSND_SUPPORT_RC6A_PROTOCOL 1 // RC6A >= 10000 ~250 bytes #define IRSND_SUPPORT_GRUNDIG_PROTOCOL 1 // Grundig >= 10000 ~300 bytes #define IRSND_SUPPORT_SIEMENS_PROTOCOL 1 // Siemens, Gigaset >= 15000 ~150 bytes #define IRSND_SUPPORT_NOKIA_PROTOCOL 1 // Nokia >= 10000 ~400 bytes #define IRSND_SUPPORT_IR60_PROTOCOL 0 // IR60 (SDA2008) >= 10000 ~250 bytes // IR frequency 30 kHz #define IRSND_SUPPORT_BOSE_PROTOCOL 1 // BOSE >= 10000 ~100 bytes #define IRSND_SUPPORT_KATHREIN_PROTOCOL 0 // Kathrein >= 10000 DON'T CHANGE, NOT SUPPORTED YET! #define IRSND_SUPPORT_NUBERT_PROTOCOL 1 // NUBERT >= 10000 ~100 bytes #define IRSND_SUPPORT_FAN_PROTOCOL 1 // FAN (ventilator) >= 10000 ~100 bytes #define IRSND_SUPPORT_SPEAKER_PROTOCOL 1 // SPEAKER >= 10000 ~100 bytes #define IRSND_SUPPORT_BANG_OLUFSEN_PROTOCOL 0 // Bang&Olufsen >= 10000 ~250 bytes // IR frequency 455 kHz #define IRSND_SUPPORT_RECS80_PROTOCOL 1 // RECS80 >= 15000 ~100 bytes #define IRSND_SUPPORT_RECS80EXT_PROTOCOL 1 // RECS80EXT >= 15000 ~100 bytes #define IRSND_SUPPORT_THOMSON_PROTOCOL 1 // Thomson >= 10000 ~250 bytes #define IRSND_SUPPORT_NIKON_PROTOCOL 1 // NIKON >= 10000 ~150 bytes #define IRSND_SUPPORT_NETBOX_PROTOCOL 0 // Netbox keyboard >= 10000 DON'T CHANGE, NOT SUPPORTED YET! #define IRSND_SUPPORT_ORTEK_PROTOCOL 0 // ORTEK (Hama) >= 10000 DON'T CHANGE, NOT SUPPORTED YET! #define IRSND_SUPPORT_TELEFUNKEN_PROTOCOL 1 // Telefunken 1560 >= 10000 ~150 bytes #define IRSND_SUPPORT_FDC_PROTOCOL 1 // FDC IR keyboard >= 10000 (better 15000) ~150 bytes #define IRSND_SUPPORT_RCCAR_PROTOCOL 1 // RC CAR >= 10000 (better 15000) ~150 bytes #define IRSND_SUPPORT_ROOMBA_PROTOCOL 1 // iRobot Roomba >= 10000 ~150 bytes #define IRSND_SUPPORT_RUWIDO_PROTOCOL 1 // RUWIDO, T-Home >= 15000 ~250 bytes #define IRSND_SUPPORT_A1TVBOX_PROTOCOL 1 // A1 TV BOX >= 15000 (better 20000) ~200 bytes #define IRSND_SUPPORT_LEGO_PROTOCOL 1 // LEGO Power RC >= 20000 ~150 bytes #define IRSND_SUPPORT_RCMM_PROTOCOL 0 // RCMM 12,24, or 32 >= 20000 DON'T CHANGE, NOT SUPPORTED YET! #define IRSND_SUPPORT_LGAIR_PROTOCOL 1 // LG Air Condition >= 10000 ~150 bytes. #define IRSND_SUPPORT_SAMSUNG48_PROTOCOL 1 // Samsung48 >= 10000 ~100 bytes #define IRSND_SUPPORT_PENTAX_PROTOCOL 1 // Pentax >= 10000 ~150 bytes #define IRSND_SUPPORT_S100_PROTOCOL 1 // S100 >= 10000 ~150 bytes #define IRSND_SUPPORT_ACP24_PROTOCOL 1 // ACP24 >= 10000 ~150 bytes #define IRSND_SUPPORT_TECHNICS_PROTOCOL 1 // TECHNICS >= 10000 ~200 bytes #define IRSND_SUPPORT_PANASONIC_PROTOCOL 1 // PANASONIC Beamer >= 10000 ~150 bytes #define IRSND_SUPPORT_MITSU_HEAVY_PROTOCOL 1 // Mitsubishi-Heavy Aircondition, similar Timing to Panasonic beamer #define IRSND_SUPPORT_IRMP16_PROTOCOL 0 // IRMP specific >= 15000 ~250 bytes #define USE_ONE_TIMER_FOR_IRMP_AND_IRSND #include <irmp.hpp> #include <irsnd.hpp> IRMP_DATA irmp_data; IRMP_DATA irsnd_data; int Prortocol_Index[58] = { IRMP_UNKNOWN_PROTOCOL, IRMP_SIRCS_PROTOCOL, IRMP_NEC_PROTOCOL, IRMP_SAMSUNG_PROTOCOL, IRMP_MATSUSHITA_PROTOCOL, IRMP_KASEIKYO_PROTOCOL, IRMP_RECS80_PROTOCOL, IRMP_RC5_PROTOCOL, IRMP_DENON_PROTOCOL, IRMP_RC6_PROTOCOL, IRMP_SAMSUNG32_PROTOCOL, IRMP_APPLE_PROTOCOL, IRMP_RECS80EXT_PROTOCOL, IRMP_NUBERT_PROTOCOL, IRMP_BANG_OLUFSEN_PROTOCOL, IRMP_GRUNDIG_PROTOCOL, IRMP_NOKIA_PROTOCOL, IRMP_SIEMENS_PROTOCOL, IRMP_FDC_PROTOCOL, IRMP_RCCAR_PROTOCOL, IRMP_JVC_PROTOCOL, IRMP_RC6A_PROTOCOL, IRMP_NIKON_PROTOCOL, IRMP_RUWIDO_PROTOCOL, IRMP_IR60_PROTOCOL, IRMP_KATHREIN_PROTOCOL, IRMP_NETBOX_PROTOCOL, IRMP_NEC16_PROTOCOL, IRMP_NEC42_PROTOCOL, IRMP_LEGO_PROTOCOL, IRMP_THOMSON_PROTOCOL, IRMP_BOSE_PROTOCOL, IRMP_A1TVBOX_PROTOCOL, IRMP_ORTEK_PROTOCOL, IRMP_TELEFUNKEN_PROTOCOL, IRMP_ROOMBA_PROTOCOL, IRMP_RCMM32_PROTOCOL, IRMP_RCMM24_PROTOCOL, IRMP_RCMM12_PROTOCOL, IRMP_SPEAKER_PROTOCOL, IRMP_LGAIR_PROTOCOL, IRMP_SAMSUNG48_PROTOCOL, IRMP_MERLIN_PROTOCOL, IRMP_PENTAX_PROTOCOL, IRMP_FAN_PROTOCOL, IRMP_S100_PROTOCOL, IRMP_ACP24_PROTOCOL, IRMP_TECHNICS_PROTOCOL, IRMP_PANASONIC_PROTOCOL, IRMP_MITSU_HEAVY_PROTOCOL, IRMP_VINCENT_PROTOCOL, IRMP_SAMSUNGAH_PROTOCOL, IRMP_IRMP16_PROTOCOL, IRMP_GREE_PROTOCOL, IRMP_RCII_PROTOCOL, IRMP_METZ_PROTOCOL, IRMP_ONKYO_PROTOCOL }; struct CRGB leds[NUM_LEDS]; // Initialize LED array const int Relay1 = 5; // Relay pin 1 (IN1) const int Relay2 = 4; // Relay pin 2 (IN2) const int Relay3 = 6; // Relay pin 3 (IN3) const int Relay4 = 7; // Relay pin 4 (IN4) int irrec = 0; String data; //Variable for storing received data int proto; uint16_t addr, cmd, temp; int eeadr; void handleReceivedIRData(); void IRDecoder(); void SerialDecoder(); bool volatile sIRMPDataAvailable = false; void setup() { Serial.begin(9600); //Sets the baud for serial data transmission FastLED.addLeds<LED_TYPE, DATA_PIN>(leds, NUM_LEDS); // Set Relay pins as OUTPUT pinMode(Relay1, OUTPUT); pinMode(Relay2, OUTPUT); pinMode(Relay3, OUTPUT); pinMode(Relay4, OUTPUT); // Init all relays to off digitalWrite(Relay1, LOW); digitalWrite(Relay2, LOW); digitalWrite(Relay3, LOW); digitalWrite(Relay4, LOW); irmp_init(); irmp_irsnd_LEDFeedback(true); // Enable receive signal feedback at LED_BUILTIN irmp_register_complete_callback_function(&handleReceivedIRData); irsnd_init(); } void loop() { // Read data from Bluetooth Module char ch = 0; data = ""; while (1) { // When there is no command received the MCU will be in this loop. while (Serial.available() <= 0) { if (irrec > 0) { IRDecoder();// Call IR decoder function when a valid command is detected } digitalWrite(13, irrec); }; ch = Serial.read(); if (ch == '#') break; // break the loop when a command is received data += ch; } SerialDecoder();// call serial Decoder function } //Decode received serial command void SerialDecoder() { // Print Bluetooth Module data on serial monitor Serial.print(data); Serial.print("\n"); // Control the devices using voice command if (data.startsWith("*turn on light")) // turn on Device1 { digitalWrite(Relay1, HIGH); Serial.println(" : light on"); delay(200); } else if (data.startsWith("*turn off light")) // turn off Device1 { digitalWrite(Relay1, LOW); Serial.println(" : light off"); delay(2000); } else if (data.startsWith("*turn on TV")) // turn on Device2 { digitalWrite(Relay2, HIGH); Serial.println(" : TV on"); delay(200); } else if (data.startsWith("*turn off TV")) // turn off Device2 { digitalWrite(Relay2, LOW); Serial.println(" : TV off"); delay(200); } else if (data.startsWith("*turn on fan")) // turn on Device3 { digitalWrite(Relay3, HIGH); Serial.println(" : fan on"); delay(200); } else if (data.startsWith("*turn off fan")) // turn off Device3 { digitalWrite(Relay3, LOW); Serial.println(" : fan off"); delay(200); } else if (data.startsWith("*turn on music")) // turn on Device4 { digitalWrite(Relay4, HIGH); Serial.println(" : music on"); delay(200); } else if (data.startsWith("*turn off music")) // turn off Device4 { digitalWrite(Relay4, LOW); Serial.println(" : music off"); delay(200); } else if (data.startsWith("*turn on all")) // turn on all Device { digitalWrite(Relay1, HIGH); digitalWrite(Relay2, HIGH); digitalWrite(Relay3, HIGH); digitalWrite(Relay4, HIGH); Serial.println(" : All Relays on"); delay(200); } else if (data.startsWith("*turn off all")) // turn off all Device { digitalWrite(Relay1, LOW); digitalWrite(Relay2, LOW); digitalWrite(Relay3, LOW); digitalWrite(Relay4, LOW); Serial.println(" : All Relays off"); delay(200); } else if (data.startsWith("*RGB red")) // set the RGB leds to red { for (int i = 0; i < NUM_LEDS; i++) { leds[i] = CRGB::Red; //set the RGB leds to red } FastLED.show(); delay(200); } else if (data.startsWith("*RGB green")) //set the RGB leds to green { for (int i = 0; i < NUM_LEDS; i++) { leds[i] = CRGB::Green; //set the RGB leds to green } FastLED.show(); delay(200); } else if (data.startsWith("*RGB blue")) // set the RGB leds to blue { for (int i = 0; i < NUM_LEDS; i++) { leds[i] = CRGB::Blue; //set the RGB leds to blue } FastLED.show(); delay(200); } else if (data.startsWith("*RGB yellow")) // set the RGB leds to yellow { for (int i = 0; i < NUM_LEDS; i++) { leds[i] = CRGB::Yellow; //set the RGB leds to yellow } FastLED.show(); delay(200); } else if (data.startsWith("*RGB white")) // // set the RGB leds to white { for (int i = 0; i < NUM_LEDS; i++) { leds[i] = CRGB::White; //set the RGB leds to white } FastLED.show(); delay(200); } else if (data.startsWith("*turn off RGB")) // turn off all RGB LEDS { for (int i = 0; i < NUM_LEDS; i++) { leds[i] = CRGB::Black; //turn off all RGB LEDS } FastLED.show(); delay(200); } else if (data.startsWith("*record power")) // record and save remote power button { irrec = 12; IRDecoder(); irrec = 1; delay(200); } else if (data.startsWith("*record volume up")) // record and save remote volume up button { irrec = 12; IRDecoder(); irrec = 2; delay(200); } else if (data.startsWith("*record volume down")) // record and save remote volume down button { irrec = 12; IRDecoder(); irrec = 3; delay(200); } else if (data.startsWith("*record next")) // record and save remote next button { irrec = 12; IRDecoder(); irrec = 4; Serial.print("irrec :"); Serial.println(irrec); delay(200); } else if (data.startsWith("*record previous")) /// record and save remote previous button { irrec = 12; IRDecoder(); irrec = 5; delay(200); } else if (data.startsWith("*remote power")) // Recall and send remote power button signal { eeadr = 10; irsnd_data.protocol = EEPROM.read(eeadr); temp = (EEPROM.read(eeadr + 2) << 8); temp |= EEPROM.read(eeadr + 1); irsnd_data.address = temp; temp = (EEPROM.read(eeadr + 4) << 8); temp |= EEPROM.read(eeadr + 3); irsnd_data.command = temp; irsnd_data.flags = 0; // repeat frame 1 time Serial.print(F("Sending data ")); Serial.println(proto); if (!irsnd_send_data(&irsnd_data, true)) { Serial.println(F("Protocol not found")); } irsnd_data_print(&Serial, &irsnd_data); } else if (data.startsWith("*remote volume up")) // Recall and send remote volume up button signal { eeadr = 20; irsnd_data.protocol = EEPROM.read(eeadr); temp = (EEPROM.read(eeadr + 2) << 8); temp |= EEPROM.read(eeadr + 1); irsnd_data.address = temp; temp = (EEPROM.read(eeadr + 4) << 8); temp |= EEPROM.read(eeadr + 3); irsnd_data.command = temp; irsnd_data.flags = 0; // repeat frame 1 time Serial.print(F("Sending data ")); Serial.println(proto); if (!irsnd_send_data(&irsnd_data, true)) { Serial.println(F("Protocol not found")); } irsnd_data_print(&Serial, &irsnd_data); } else if (data.startsWith("*remote volume down")) // Recall and send remote volume down button signal { eeadr = 30; irsnd_data.protocol = EEPROM.read(eeadr); temp = (EEPROM.read(eeadr + 2) << 8); temp |= EEPROM.read(eeadr + 1); irsnd_data.address = temp; temp = (EEPROM.read(eeadr + 4) << 8); temp |= EEPROM.read(eeadr + 3); irsnd_data.command = temp; irsnd_data.flags = 0; // repeat frame 1 time Serial.print(F("Sending data ")); Serial.println(proto); if (!irsnd_send_data(&irsnd_data, true)) { Serial.println(F("Protocol not found")); } irsnd_data_print(&Serial, &irsnd_data); } else if (data.startsWith("*remote next")) // Recall and send remote next button signal { eeadr = 40; irsnd_data.protocol = EEPROM.read(eeadr); temp = (EEPROM.read(eeadr + 2) << 8); temp |= EEPROM.read(eeadr + 1); irsnd_data.address = temp; temp = (EEPROM.read(eeadr + 4) << 8); temp |= EEPROM.read(eeadr + 3); irsnd_data.command = temp; irsnd_data.flags = 0; // repeat frame 1 time Serial.print(F("Sending data ")); Serial.println(proto); if (!irsnd_send_data(&irsnd_data, true)) { Serial.println(F("Protocol not found")); } irsnd_data_print(&Serial, &irsnd_data); } else if (data.startsWith("*remote previous")) // Recall and send remote previous button signal { eeadr = 50; irsnd_data.protocol = EEPROM.read(eeadr); temp = (EEPROM.read(eeadr + 2) << 8); temp |= EEPROM.read(eeadr + 1); irsnd_data.address = temp; temp = (EEPROM.read(eeadr + 4) << 8); temp |= EEPROM.read(eeadr + 3); irsnd_data.command = temp; irsnd_data.flags = 0; // repeat frame 1 time Serial.print(F("Sending data ")); Serial.println(proto); if (!irsnd_send_data(&irsnd_data, true)) { Serial.println(F("Protocol not found")); } irsnd_data_print(&Serial, &irsnd_data); } } //Decode and save IR signals void IRDecoder() { if (sIRMPDataAvailable) { int eepaddr = irrec; irrec = 0; int rpt; sIRMPDataAvailable = false; irmp_result_print(&irmp_data); proto = irmp_data.protocol; addr = irmp_data.address; cmd = irmp_data.command; // save signal data to EEPROM if (eepaddr < 10) { if (proto == 0) { EEPROM.write(eepaddr * 10, 0x0); } else { EEPROM.write(eepaddr * 10, proto); } if (addr == 0) { EEPROM.write((eepaddr * 10) + 1, 0); EEPROM.write((eepaddr * 10) + 2, 0); } else { EEPROM.write((eepaddr * 10) + 1, addr); EEPROM.write((eepaddr * 10) + 2, addr >> 8); } if (cmd == 0) { EEPROM.write((eepaddr * 10) + 3, 0x0); EEPROM.write((eepaddr * 10) + 4, 0x0); } else { EEPROM.write((eepaddr * 10) + 3, cmd); EEPROM.write((eepaddr * 10) + 4, cmd >> 8); } } } } //IR interrupt handle routine void handleReceivedIRData() { irmp_get_data(&irmp_data); sIRMPDataAvailable = true; } |
А русский язык приложение распознает?
Ну если верить вот этой странице
amr-voice.en.softonic.com/android?ex=RAMP-2046.0
то это приложение можно скачать и на русском языке