В последнее время огромной популярностью пользуются беспроводные модули работающие на частоте 433МГц. Они дешевы, работают на разрешенных частотах и хотя я их недолюбливаю, но обойти стороной никак немогу.
Итак сегодня будем передавать температуру и влажность с датчика DHT22 посредствам беспроводной связи.
Нам понадобятся
Для передатчика:
1. Датчик температуры и влажности DHT22
2. Arduino Pro mini
3. Передатчик 433МГц
Для приемника:
1. Приемник 433МГц
Arduino Uno
Дисплей 1602 с интерфейсом I2C
Собираем схему:
Передатчик
Записываем в передатчик
//Подключаем библиотеки #include <VirtualWire.h> #include "DHT.h" //Определяем пин светодиода const int led_pin = 13; //Определяем пин передатчика const int transmit_pin = 12; //Пин и тип датчика температуры #define DHTPIN 6 #define DHTTYPE DHT22 DHT dht(DHTPIN, DHTTYPE); // объявляем массив char dataString [12]; //---------------------------------------------------------------- void setup() { vw_set_tx_pin(transmit_pin); vw_set_ptt_inverted(true); // скорость передачи бит в секунду vw_setup(2000); pinMode(led_pin, OUTPUT); //запуск датчика температуры dht.begin(); } //--------------------------------------------------------------- void loop() { // опрашиваем датчик температуры и влажности float h = dht.readHumidity(); float t = dht.readTemperature(); int h1 = (h-(int)h)*100; int t1 = (t-(int)t)*100; //Формируем буфер sprintf(dataString, "/%1d.%1d/%1d.%1d",int(t),t1,int(h),h1); // Включаем светодиод digitalWrite(led_pin, HIGH); // Передаем данные vw_send((uint8_t *)dataString, 12); //Ждем окончания отправки vw_wait_tx(); // Выключаем светодиод digitalWrite(led_pin, LOW); //отдыхаем 10 сек. delay(10000); }
Приемник
Внимание обязательно подключаем к модулям антенны(отрезки провода длиной 15-17 см) без них дальность связи будет несколько сантиметров.
Записываем в приемник
// Подключаем библиотеки #include <VirtualWire.h> #include <Wire.h> #include <LiquidCrystal_I2C.h> // Пин светодиода const int led_pin = 13; //Пин приемника const int receive_pin = 11; uint8_t buf[VW_MAX_MESSAGE_LEN]; uint8_t buflen = VW_MAX_MESSAGE_LEN; // Определяем диспелй LiquidCrystal_I2C lcd(0x27,16,2); //--------------------------------------------------------- void setup() { // Инициализация дисплея lcd.init(); lcd.begin(16, 2); lcd.backlight(); vw_set_ptt_inverted(true); // Required for DR3100 //Скорость приема бит в секунду vw_setup(2000); // запускаем приемник vw_rx_start(); // Start the receiver PLL running pinMode(led_pin, OUTPUT); } //-------------------------------------------------------- void loop() { //Принимаем данные в буфер if (vw_get_message(buf, &buflen)) { // Зажигаем светодиод digitalWrite(led_pin, HIGH); // разбираем буфер и выводим данные на дисплей printbuf(); // Гасим светодиод digitalWrite(led_pin, LOW); } } //---------------------------------------------------------- void printbuf(){ int i; int a=0; //Пока не кончилась длина буфера повторяем цикл for (i = 0; i < buflen; i++) { //Если встретили первую / значит сейчас пойдет температура if ((char) buf[i]=='/'){ if (a==0){ lcd.setCursor(0, 0); lcd.print("Temperature "); a++; } // Иначе влажность else { lcd.setCursor(0, 1); lcd.print("Humidity "); } } else { // Если / нет выводим данные lcd.print((char)buf[i]); } } }
Библиотеки
для датчиков DHT 22 b DHT11 здесь
для приемника и передатчика здесь
для дисплея здесь
Результат
А реально ли прикрутить к данному проекту измерение напряжения питания. Планирую данное устройство запитывать от акб..
Вполне реально, про вольтметр я писал чуть раньше, просто подать на аналоговый вход нужное напряжение и с необходимой периодичностью его проверять
Подскажите, почему
//Ждем окончания отправки
vw_wait_tx();
занимает порядка минуты? Или так только у меня?
Спасибо за статью. Как раз задался вопросом беспроводной передачи данных. Будем пробовать.
Ваш комментарий ожидает проверки.
int h1 = (h-(int)h)*100;
int t1 = (t-(int)t)*100;
//Формируем буфер
sprintf(dataString, «/%1d.%1d/%1d.%1d»,int(t),t1,int(h),h1);
Тут есть проблема. При переходе на отрицательную температуру показывает: -1.-23
И при отрицательной температуре ниже ноля показывает: 0.-16
Тут еще косяк есть кроме этого, в приемной части и выводе на LCD 20×4 постоянно вылазят доп знаки левые. Вопрос можно решить конечно можно решить, но,
в передатчике тоже косяк, а именно, время от времени выдача неправильной влажности.
Вписал дебажные строки, ошибка появляется именно образуя буффер перед отсылкой.
sprintf(dataString, «/%1d.%1d/%1d.%1d»,int(t),t1,int(h),h1);
Походу остатки предыдущего буфера проявляются в новом сформированном.
Переправил применительно к этому варианту приемника на это:
float t = dht.readTemperature();
float h = dht.readHumidity();
SendData((«/»+ ((String)t))+(«/»+ ((String)h)));
}
void SendData(String Data)
{
const char* rawdata = Data.c_str();
digitalWrite(13, true);
vw_send((uint8_t *)rawdata, strlen(rawdata));
vw_wait_tx();
digitalWrite(13, false);
}