Метеостанция на Raspberry Pi своими руками
Для воссоздания этой метеостанции понадобится:
Схема подключения датчика изображена на рисунке.
Дисплей WH1602 подключается как показано на рисунке. Наличие дисплея не обязательно:
Подробнее о дисплеи WH1602 читайте тут: http://www.avislab.com/blog/raspberry-pi-wh1602/
Настройка I2C
Для включения I2C шины на Raspberry Pi нужно выполнить операции, описанные ниже.
Вариант #1:
Запустить настройки командой raspi-config
Зайти в меню Advanced Options->I2C
Включить I2C, позволить загрузку модуля для I2C
Вариант #2:
Редактируем файл: /etc/modprobe.d/raspi-blacklist.conf:
nano /etc/modprobe.d/raspi-blacklist.conf
Закомментируйте строку blacklist i2c-bcm2708. Пример содержимого файла:
#blacklist i2c-bcm2708
Редактируем файл: /etc/modules:
sudo nano /etc/modules
Добавляем строки:
i2c-bcm2708
i2c-dev
Редактируем файл: /boot/config.txt:
sudo nano /boot/config.txt
Добавляем строку:
dtparam=i2c_arm=on
Устанавливаем i2c-tools утилиты
sudo apt-get install python-smbus i2c-tools
Перезагружаем Raspberry Pi:
reboot
После перезагрузки можем пересмотреть устройства подключенные к шине I2C:
sudo i2cdetect -y 1
0 1 2 3 4 5 6 7 8 9 a b c d e f 00: — — — — — — — — — — — — — 10: — — — — — — — — — — — — — — — — 20: — — — — — — — — — — — — — — — — 30: — — — — — — — — — — — — — — — — 40: — — — — — — — — — — — — — — — — 50: — — — — — — — — — — — — — — — — 60: — — — — — — — — — — — — — — — —
70: — — — — — — 76 —
В данном случае на шине 1 только одно устройство по адресу 0x76
Подробнее о I2C читайте здесь: http://www.avislab.com/blog/raspberry-pi-i2c/
Установка программного обеспечения
apt-get install sqlite3
apt-get install apache2
Запускаем apache:
service apache2 start
Устанавливаем скрипт weather.py
Качаем скрипты (у /home/pi/ будет создана директория weather и в нее закачаны необходимые файлы):
cd /home/pi
git clone https://github.com/avislab/weather.git
cd /home/pi/weather
Создаем базу данных:
python ./install.py
Настройка скрипта
Откройте скрипт:
nano /home/pi/weather/weather.py
Проверяем параметры:
home_dir – папка где лежит скрипт.
www_dir – папка www – сервера в которую будет записываться html файл с графиками.
Пример:
home_dir = “/home/pi/scripts/weather/”
www_dir = “/var/www/weather/”
Тестовый запуск:
python /home/pi/weather/weather.py
Скрипт должен отработать без ошибок и сформировать файл index.htm с графиками в директории www_dir
Зайдите браузером для просмотра:
http://IP-address/weather/
IP-address – ip-адрес вашего Raspberry Pi
Устанавливаем запуск скрипта каждые 15 минут
sudo echo “*/15 * * * * root /home/pi/weather/weather.py” >> /etc/crontab
Как работает скрипт
сrontab запускает скрипт каждые 15 минут (смотри файл /etc/crontab). Этот параметр можно изменить по желанию.
Далее комментарии к некоторым строкам кода.
Скрипт опрашивает датчик:
#Read data from Sensor
ps = BME280()
ps_data = ps.get_data()
Выводит текущие данные в консоль и на дисплей:
print “Temperature:”, convert(ps_data['t'], units[temperature_field]), “°”+units[temperature_field], “Pressure:”, convert(ps_data['p'], units[pressure_field]), units[pressure_field], “Humidity:”, ps_data['h'], units[humidity_field] #LCD
lcd = Adafruit_CharLCD()
lcd.clear()
lcd.home()
lcd.message('T=%s  P=%s
' % (convert(ps_data['t'], units[temperature_field]), convert(ps_data['p'], units[pressure_field])))
lcd.message('H=%s%%' % (ps_data['h']))
Если хотите чтобы температура произносилась голосом установите програму espeak и разкоментируйте следующие строки:
#speak_str = “Тем пе ратура ”
#if ps_data['t'] < 0:
# speak_str += "минус"
#speak_str += str(int(round(abs(ps_data['t']))))
#os.system('espeak "' + speak_str + '" -vru -s50 -a100 2> /dev/null')
Подключается к базе данных и записывает текущие данные:
#Connect to database
con = sqlite3.connect(home_dir + database_name)
cur = con.cursor() #Insert new reccord
SQL=”INSERT INTO weather VALUES({0}, '{1}', {2}, {3})”.format(time.time(), ps_data['t'], ps_data['p'], ps_data['h'])
cur.execute(SQL)
con.commit()
Удаляет старые записи:
#Delete data older than 30 days
start_time = time.time() – 86400 * delete_data_older_than_days
SQL = “DELETE FROM weather WHERE (id < {0})".format(start_time)
cur.execute(SQL)
con.commit()
Где delete_data_older_than_days – период в днях, за который данные сохраняются в базе. Все что старше удаляется.
Читает шаблон:
#Read template &amp;amp;amp; make index.htm
f = open(home_dir+'templates/index.tpl', 'r')
txt = f.read()
f.close()
Формирует HTML с графиками:
#Prepare html
date_time = datetime.datetime.fromtimestamp(time.time()).strftime('%Y-%m-%d %H:%M') #Units
txt = re.sub('{temperature_unit}', units[temperature_field], txt)
txt = re.sub('{pressure_unit}', units[pressure_field], txt)
txt = re.sub('{humidity_unit}', units[humidity_field], txt) #Current data
txt = re.sub('{time}', date_time, txt)
txt = re.sub('{temperature}', str(convert(ps_data['t'], units[temperature_field])), txt)
txt = re.sub('{pressure}', str(convert(ps_data['p'], units[pressure_field])), txt)
txt = re.sub('{humidity}', str(ps_data['h']), txt) #Day ago
txt = re.sub('{temperature24h}', get_chart_data(temperature_field, 1), txt)
txt = re.sub('{pressure24h}', get_chart_data(pressure_field, 1), txt)
txt = re.sub('{humidity24h}', get_chart_data(humidity_field, 1), txt) #Last week
txt = re.sub('{temperature7d}', get_chart_data(temperature_field, 7), txt)
txt = re.sub('{pressure7d}', get_chart_data(pressure_field, 7), txt)
txt = re.sub('{humidity7d}', get_chart_data(humidity_field, 7), txt)
Записывает HTML файл:
#Writing file index.htm
f = open(www_dir+'index.htm','w')
f.write(txt)
f.close()
Закрывает базу данных:
#Database connection close
con.close()
Отправляет данные на сайт:
#Send data to my site
s=”{0}:{1}:0:{2}:”.format(int(ps_data['p']), int(ps_data['t']), int(ps_data['h']))
response = urllib2.urlopen(“http://mysite.com.ua/getdata.php?data=”+s)
Пример скрипта на PHP для приема данных и записи в файл:
SimpleHTTP.py
Если Вы по каким-то причинам не хотите использовать Apache в качестве web-сервера, достаточно запустить скрипт SimpleHTTP.py:
#!/usr/bin/env python
# -*- coding: utf-8 -*- import SimpleHTTPServer
import SocketServer
import os PORT = 80
DocumentRoot = “/home/pi/weather/http” os.chdir(DocumentRoot)
Handler = SimpleHTTPServer.SimpleHTTPRequestHandler
httpd = SocketServer.TCPServer((“”, PORT), Handler)
print “serving at port”, PORT
httpd.serve_forever()
Перед запуском следует проверить указанную директорий DocumentRoot. Она должна существовать и совпадать с www_dir указанной в скрипте weather.py
Успехов.
Смотри также:
Brushless Motors
ESP8266
STM32
Raspberry Pi
Источник: http://www.avislab.com/blog/raspberry-pi-meteo_ru/
Собираем умный дом на Raspberry Pi собственноручно – Техсад
Сложно игнорировать технологичные новинки, которые уже давно стали частью повседневной жизни.
Среди таких привычных вещей, как интернет или смартфоны, особенно выделяется умный дом, помогающий объединить используемые гаджеты и бытовую технику в единую сеть для более комфортного и простого управления.
Умный дом легко настроить под собственные потребности, вводы в состав сети новые модули и программируя их на выполнение заданных сценариев. Сенсоры, используемые в процессе управления домом, срабатывают:
- На звук;
- На движение;
- На тепловую энергию.
Простые сенсоры представлены даже в ТРЦ, где они следят за автоматическим открытием дверей и выполняют другие задачи.
В то, что умный дом может стать неотъемлемым элементом жизни человека может и сложно поверить, но это действительно так.
Чтобы снизить свои трудозатраты и обучить приборы выполнять простые функции самостоятельно, потребуется лишь реализовать проект умный дом, способствующий всему этому.
Принцип работы умного дома
Для автоматизированной техники используется ПО, позволяющее выполнять различные задачи с ее помощью. Программы применяются и в умном доме, расширяя функционал его возможностей.
Чтобы запрограммировать работу прибора, следует обладать определенными навыками.
Поэтому для начинающих владельцев лучшим выбором станет использование приложений, уже адаптированных под требования обычных пользователей.
Разрабатывая умный дом, можно выбрать один из нескольких вариантов. В первом случае будет использоваться готовое решение, которое останется установить на объекте.
Такой вариант требует минимум усилий, но его стоимость значительная. Позволить реализовать такой проект может не каждый.
Другим решением остается понимание самой концепции, что позволит в дальнейшем создать и собрать умный дом собственноручно.
Процесс работы зависит от правильности расчётов, выполненных владельцем, что приводит к снижению расходов. Самостоятельно собрать умный дом не сложно, если подойти к делу со всей осторожностью и пониманием. В итоге это сэкономит средства, и позволит получить некоторые навыки обращения с модулями.
Процесс автоматизации умного дома
Заставить приборы, используемыми повседневно, работать по заданному сценарию легко, если использовать для этого соответствующий блок управления. Компанией Raspberry Pi был разработан миникомпьютер, который подходит для решения поставленной задачи.
Устройство отличается компактностью и производительностью, а также делает автоматизацию проекта простым и понятным делом. Raspberry отличается невысокой стоимостью, особенно при сравнении с другими производителями, представившими свою продукцию на рынке.
Но это не помешало компании предложить действительно качественное оснащение, ставшее популярным. Первоначально компанией разрабатывалось две вариации миникомпьютера:
Визуальное оформление и комплектация
Данные устройства находятся под управлением чипсета ARM11 с производительностью в 700 МГц. Различия между вариациями заключаются в объеме памяти на борту. Так изделие B оснащается планкой ОЗУ на 512 Мб, что двукратно превосходит показатели модели А с 256 Мб.
В итоге компания пришла к решению выпускать обе вариации одновременно, тем более, что миникомпьютер А имел дополнительные достоинства. Он оснащался портом Ethernet, позволяющим подключиться к сети.
Компания продолжила работу над модернизацией своих продуктов, переосмыслив вторую версию компьютера. Это привело к появлению улучшенного варианта В, ставшего еще более компактным, а также получившего стильный дизайн.
Из конструктивных наработок стоит отметить наличие 4 разъемов USB, что в 2 раза превышает число портов данного типа для предыдущей версии.
Источник: https://techsad.com/umnyjdom/sobiraem-umnyj-dom-na-raspberry-pi-sobstvennoruchno/
Arduino + Raspberry Pi = термометр + гигрометр с отправкой данных на сервер (часть 1)
Часть 2: http://blog.edtex.ru/2015/10/arduino-raspberry-pi-2.htmlТолько недавно начал знакомится с Arduino, и возникла идея сделать что-то не очень сложное, и, собственно, выбор упал на метеостанцию.
- Arduino Uno (осуществляет сбор данных с датчиков, отправляет данные на Raspberry Pi и отображает данные на дисплее)
- Raspberry Pi Model B+ (отправка данных на веб-сайт, ftp-сервер и на OpenWeatherMap, а так же сохранение данных на флешку)
- датчик температуры DS18B20+ и датчик температуры/влажности DHT11
- LCD дисплей 16×2
- макетная плата под пайку (для замены беспаечной макетки)
- 1 пищевой контейнер
- провода для соединения экрана и макетки с arduino
- несколько метров витой пары и разъемы на 3 провода (такие же, как на корпусных вентиляторах для пк)
- канистра из-под питьевой воды (для защиты датчиков от дождя)
- несколько саморезов и прочей мелочи
Как это все собрано
Сразу скажу, что в 1-й части я решил описать все, что связано непосредственно с самим arduino и датчиками, об остальном я подробно расскажу в следующей части.
Итак, начнем. Для удобства сделал схему в Fritzing. Желательно ее скачать.
Теперь по-порядку, что здесь к чему.
Начнем с того, почему здесь нет беспаечной макетки. Все просто – она не удобна, когда нужно поместить устройство в корпус, и еще не удобней, когда нужно подключать длинные провода, идущие к датчикам.
Макетка тут выполняет роль своеобразного коммутатора, то есть у нас подходит один провод +5V от arduino и питает линию контактов (красные провода – +5V, черные – GND, остальные – данные), от которой питаются датчики и экран, аналогично для GND.
И у нас есть 2 линии для датчиков, на этой схеме каждому датчику отведена целиком каждая, но если у вас будет макетка другого формата, то это можно будет оптимизировать.
Так же у нас есть 2 подтягивающих резистора по 5 КОм (на схеме 4.7К, потому что нарисовать на 5К не удалось :-/ ), для ds18b20 резистор обязателен, а иначе ничего не будет работать, для dht11 рекомендуется его поставить при длине провода до 20 метров, если нужно длиннее – то нужно подбирать меньшее значение опытным путем.
Как подключить экран читаем здесь. ВАЖНО! Внимательно следите за нумерацией контактов на дисплее, на схеме они идут по-порядку от 1 до 16 справа налево. В экране от амперки порядок отличается. Поэтому скачиваем проект и внимательно смотрим номера контактов.
Датчики у меня подключены с помощью двух витых пар, длиной примерно метра 4-5 каждая, никаких проблем с ними не наблюдалось.
А теперь немного фото. Вот так выглядят внутренности:
Цвета проводов со схемой не совпадают, потому что делал все из того, что было))
Моя макетка отличается от той, что на схеме и разводка сделана очень паршиво, поэтому копировать ее не стоит, делайте сразу как положено.
Штекера на витой паре:
Плату arduino и макетку закрепил саморезами из старых китайский игрушек, дополнительно сделал подкладки из мягкого шланга (резал его вдоль на куски, из-за чего они немного пружинят и нет необходимости сильно притягивать плату саморезами), подобные подкладки сделаны и для дисплея, там лучше подошел разрезанный поперек шланг (около 0.5 см):
Целиком все выглядит вот так (тут датчики подключены без витых пар):
В закрытом виде:
А так выглядят датчики на улице:
Предварительно стоит сказать, что скетч я старался написать не так, чтобы “лишь бы работало”, а старался сделать обработку ошибок, чтобы можно было хотя бы узнать, а почему же вдруг исчезли показания с одного из датчиков. Теперь про отсылку данных – все данные отправляются в формате CSV с интервалом 5 минут, причем опрос датчиков происходит каждые 30 секунд, а отправляемые показания усредняются (на дисплее отображаются текущие показания). А теперь переходим к коду.#include
#include
#include #define DS18B20_ID 0x28
#define DHT11_PIN 2
#define LED 13
#define DS18B20_TRYOUT 5
#define DS18B20_PIN 3 enum DS18_ERR{NOT_FOUND = 1, CRC_ADDR_FAIL, NOT_DS18B20_DEV, CRC_SCRATCH_FAIL}; dht DHT;
LiquidCrystal lcd(4, 5, 9, 10, 11, 12);
OneWire ds(DS18B20_PIN);
char tempS[16], humS[16], ds18_tempS[16];
float ds18_temp;
byte ds18_err;
byte addr[8];
// интервал опроса датчиков
unsigned long sensors_interval = 30000;
// интервал отображения информации с датчиков (поочередно DS18B20+ и DHT11)
unsigned long lcd_interval = 15000;
// интервал отсылки данных на Raspberry Pi (каждые 5 минут)
unsigned long sending_interval = (unsigned long) 5*60*1000;
/* в этих переменных будем хранить значения таймера в момент выполнения действия
Я постарался избежать использования функции delay(), потому что планирую сделать управление через меню или кнопки, а эта функция не позволит этого сделать, подробнее см. ниже
*/
unsigned long prevMillis_sensors = sensors_interval, prevMillis_lcd = lcd_interval, prevMillis_sending = sending_interval;
// с какого датчика будем отображать данные на дисплее (0 – с DHT, 1 – с DS18B20)
byte temp12 = 0;
/* переменные для подсчета средних значений
Подсчитывать будем крайне просто: суммируем значения на каждом считывании, увеличиваем счетчик (сколько раз мы уже считали), а при отправке отправляем сумма_значений/счетчик
*/
float ds18_temp_mid = 0, DHT_temp_mid = 0, humid_mid = 0;
// сколько раз считали данные (так же для подсчета средних значений)
byte ds18_data_read_count = 0;
byte dht_data_read_count = 0; void setup()
{ // выводим строку приветствия lcd.begin(16, 2); lcd.print(“MStation v0.1.1”); lcd.setCursor(0, 1); lcd.print(“Init…”); // настраиваем 13-й пин на вывод (это встроенный светодиод) pinMode(LED, OUTPUT); // настраиваем передачу данных Serial.begin(115200); // отправляем строку инициализации Serial.println(“MStationV0.1_Init”); // ищем датчик DS18B20+ if (!getAddrDS18B20()) { Serial.print(“ERR:DS18B20_FATAL_ERROR_”); Serial.println(ds18_err); }
} void loop()
{ int chk; unsigned long currMillis = millis(); // здесь у нас хранится текущее значение таймера // ЧИТАЕМ ДАННЫЕ С ДАТЧИКОВ if (currMillis – prevMillis_sensors > sensors_interval) { prevMillis_sensors = currMillis; // ВКЛЮЧАЕМ СВЕТОДИОД digitalWrite(LED, HIGH); // ЧИТАЕМ С DS18B20+ if (getTempDS18B20()) { // прибавляем ds18_temp_mid += ds18_temp; // увеличиваем счетчик ds18_data_read_count++; } else { Serial.print(“ERR:DS18B20_ERROR_”); Serial.println(ds18_err); } // ЧИТАЕМ С DHT11 chk = DHT.read11(DHT11_PIN); switch (chk) { case DHTLIB_OK: // увеличиваем счетчик и суммируем dht_data_read_count++; DHT_temp_mid += DHT.temperature; humid_mid += DHT.humidity; break; case DHTLIB_ERROR_CHECKSUM: Serial.println(“Checksum_error”); break; case DHTLIB_ERROR_TIMEOUT: Serial.println(“Time_out_error”); break; default: Serial.println(“Unknown_error”); break; } // ВЫКЛЮЧАЕМ СВЕТОДИОД digitalWrite(LED, LOW); } // ОТПРАВЛЯЕМ ДАННЫЕ if (currMillis – prevMillis_sending > sending_interval) { prevMillis_sending = currMillis; /* Оставил на всякий случай, если вдруг нужно будет отказаться от отсылки средних значений Serial.print(ds18_temp, 2); Serial.print(','); Serial.print((int) DHT.temperature); Serial.print(','); Serial.println((int) DHT.humidity); */ // Отправляем Serial.print((float) ds18_temp_mid/ds18_data_read_count, 2); Serial.print(','); Serial.print((float) DHT_temp_mid/dht_data_read_count, 2); Serial.print(','); Serial.println((float) humid_mid/dht_data_read_count, 2); // обнуляем переменные ds18_temp_mid = 0; DHT_temp_mid = 0; humid_mid = 0; ds18_data_read_count = 0; dht_data_read_count = 0; } // ВЫВОДИМ ДАННЫЕ НА ДИСПЛЕЙ if (currMillis – prevMillis_lcd > lcd_interval) { prevMillis_lcd = currMillis; // Преобразуем из double в char dtostrf(ds18_temp, 3, 2, ds18_tempS); // Выводим температуру lcd.setCursor(0, 0); if (!temp12) { lcd.print(“Temp1: “); lcd.print((int) DHT.temperature); lcd.print(” x99″”C “); temp12 = 1; } else { lcd.print(“Temp2: “); lcd.print(ds18_tempS); lcd.print(” x99″”C”); temp12 = 0; } // и влажность lcd.setCursor(0, 1); lcd.print(“Humid: “); lcd.print((int) DHT.humidity); lcd.print(” %”); }
} boolean getTempDS18B20()
{ byte i; byte data[12]; ds.reset(); ds.select(addr); ds.write(0x44, 0); // start conversion, without parasite power delay(1000); // delay must be >750ms ds.reset(); ds.select(addr); ds.write(0xBE); //read scratchpad for (i = 0; i < 9; i++) { data[i] = ds.read(); } // check CRC if (OneWire::crc8(data, 8) != data[8]) { ds18_err = CRC_SCRATCH_FAIL; return false; } ds18_temp = ((data[1] = interv) { // делаем что-то prev = curr; // сохраняем время выполнения действия }
}Ну, пожалуй, по коду самое основное я рассказал. На этом можно и остановиться, все остальное (как обрабатываются данные на raspberry, отсылаются на севера и тд) я расскажу в следующих частях.
Написал вторую часть статьи про сбор данных с ардуины на raspberry pi: http://blog.edtex.ru/2015/10/arduino-raspberry-pi-2.htmlДля тех, кто хочет разобраться в деталях, выкладываю даташиты для датчиков и дисплея, скачиваем тут.Комплект исходников можно скачать на GitHub-е.Данные с метеостанции можно посмотреть тут: edtex.ru
Источник: https://blog.edtex.ru/2014/09/arduino-raspberry-pi-1.html
Погода в доме: беспроводной метеодатчик из Arduino Pro Mini
В прошлом рассказе про то, что можно сделать из Arduino, мне предложили делать погоду и бросать ее в сеть. Не сказать, чтобы это мне это было сильно нужно, но сама идея осталась в голове и это обстоятельство представляло хотя и смутное, но постоянное беспокойство.
Так что я решил попробовать, и закрыть этот вопрос раз и навсегда. Тем более, что тот самый рассказ стал призовым, и позволил мне купить практические все необходимое, чтобы решить задачу. В некотором смысле это спасибо MySKU и всем, кому понравились игрушки из Arduino.
ЖЕЛЕЗКИ
Arduino Pro Mini
Плата совершенно крошечная. Я даже не ожидал, что настолько. Но при этом на ней — взрослый чип ATmega328, так что по производительности она не уступает той же Uno. Это версия 5В, питается или от 5В стабилизированного по любому пину VCC или же от 5 — 12В по пину RAW (если верить Arduino.cc). По-моему, очень удобно.
Комплект передатчик-приемник ASK/OOK 433 МГц
Это уже проверенные (не в этом магазине, а вообще) простейшие приемники и передатчики с амплитудной модуляцией. У них нет никаких средств коррекции ошибок и контроля передачи, зато они крайне дешевы и без проблем работают с нужными мне устройствами (розетками, выключателями и с самими собой).
Живые фото можно посмотреть в предыдущем тексте про Arduino.
Преобразователь Serial — USB
Очень простой, недорогой и универсальный — есть питание 5В и 3.3В на выбор. Нужен, чтобы загружать код в Arduino Pro Mini, так как у платы нет своего USB. Шлейф, который вы видите на фото, входит в комплект. И хотя ничего необычного в нем нет — обычные четыре провода, все равно приятно.
Датчик влажности и температуры DHT21
Заказывал часы для жены, но DX ошибся с заказом, ошибку признал и вернул стоимость на счет в магазине. Так что вместо часов жене получился датчик температуры мне любимому.
Этот датчик выбран за разумную цену (вообще, а не в DX), широкий диапазон измерений и точность до десятых.
Кроме того, в отзывах на DX писали, что он полностью совместим с DHT22, для которого есть готовые библиотеки для Arduino.
Пара слов о продавце на eBay
С одной стороны, в магазине приятные цены, все выслали достаточно быстро, и почти все пришло в рабочем состоянии. Исключение — один приемник, который не включился. Возможно, он настроен на другую частоту и поэтому я не увидел сигнала на выходе.
С этим буду разбираться позже, но пока факт остается фактом — в текущем состоянии один приемник оказался бесполезен. Другой минус состоит в том, что бесплатная доставка — без номера для отслеживания. А так как я эти номера все же люблю, то заплатил за него, как и было предложено в письме-подтверждении заказа.
При этом продавец предлагает оплатить трек-номер на отдельный эккаунт PayPal. Итог: сначала мне больше недели номер вообще не давали. Потом, когда я пообещал диспут, выдали с интервалом в день сразу два трек-номера. Один был явно левым, поскольку дата приема посылки по нему была раньше даты заказа.
Другой казался нормальным ровно до импорта в России. Как только появился индекс места назначения стало понятно, что это посылка не моя, а какого-то счастливчика из Обнинска. Ну а потом уже пришла моя посылка — без каких-либо трек-номеров.
Поэтому поводу я еще немного поскандалил с продавцом, и в конечном итоге плату за трек-номер мне вернули. Впечатления двойственные: с одной стороны, в магазине очень приятные цены. С другой — получается какая-то лотерея.
ФИЗИЧЕСКИЙ УРОВЕНЬ
За громким заголовком суровая правда: дома на боевом дежурстве живет небольшая коробочка с Arduino Uno, подключенная к сети через Ethernet-шилд. В этой коробочке также есть копия упомянутого выше ASK/OOK приемника для получения сигналов с домашних датчиков (протечки, открытия дверей и т.п.). Это определило некое подобие клиент-серверной модели для подключения метеодатчика. То есть, метеодатчик на базе Arduino Pro Mini отправляет данные температуры и влажности коробке, а она, в свою очередь, отправляет их в интернет. Отвечаю на очевидные вопросы ) Q: Почему примитивные приемники, а не, скажем, рекомендованные ранее чудесные nRF24L01, которым не страшны помехи, которые легко объединяются в сеть и вообще идеальны для такого применения? A: Во-первых, кажется, я просто боюсь, что потрачу слишком много времени на усвоение методики работы с nRF24L01. Во-вторых, у меня (то есть, у Arduino Uno в коробке) заканчивается все — пины, память. А нужно подключить еще несколько устройств: пищалку, датчик движения. Между тем, в коробке уже есть все, что нужно для получения метеоданных — и приемник, и библиотека RC-Switch, которая вполне подходит не только для управления розетками, но для передачи нескольких символов. Почему бы не воспользоваться уже имеющимися ресурсами? Q: Почему тогда не Virtual Wire? A: Ответ, в общем, выше — еще одна библиотека, еще меньше памяти. С практической точки зрения такой радиоканал можно назвать слабым местом системы. Но, если задуматься, вся моя система — сплошное слабое место, так сказать, by design. Q: почему бы не подключить Arduino Pro Mini к сети напрямую? A: Дело в том, что для минимального количества проводов я планирую поставить датчик на окно, а рядом нет ни сетевых, ни электрических розеток. Это раз. И два: Wi-Fi-шилд для Arduino или комбинация из электрической розетки с Ethernet и обычного Ethernet-шилда Arduino стоят совершенно неразумных для решения этой задачи денег. Q: Почему не меряем атмосферное давление? A: Потому что датчик сразу не заказал, и в итоге он еще не приехал. А попробовать очень хотелось. Q: У тебя же есть метеостанция с беспроводным датчиком. Почему не используешь его, а городишь огород на пустом месте? A: Честно говоря, огород для меня проще, чем писать код для обработки сигнала. Потом, может быть, попробую. А сейчас так гораздо быстрее.
ЛОГИЧЕСКИЙ УРОВЕНЬ
Для логической основы радиоканала я решил воспользоваться возможностями библиотеки RC-Switch. Она предназначена для управления беспроводными розетками, но методика управления позволяет использовать ее и для передачи данных. Медленно, не очень надежно, но — позволяет. Суть в том, что команда розетки — всего лишь цифровой код.
При этом RC-Switch совершенно безразлично, какой именно код передавать. Главное — не больше 24 бит, то есть не больше 16777216.
В итоге мой протокол передачи метеоданных выглядит следующим образом: Первые три цифры — идентификатор датчика Четвертая цифра — тип данных (1 — влажность, 0 — температура) Пятая цифра — знак температуры (1 — отрицательная, 0 — положительная) Остальные цифры — величина Например, чтобы передать температуру 23.
5С нужно отправить через RC-Switch код 16100235. Плюсы примитивного «кодирования»: достаточно всего одного действия арифметики, чтобы выделить передаваемую величину. Минусы — один «пакет» для одного значения.
ПРАКТИЧЕСКАЯ РЕАЛИЗАЦИЯ
Arduino Pro Mini поставляется в комплекте с контактными планками. При желании их можно напаять на плату. А при необходимости сделать максимально компактную конструкцию провода можно паять прямо к контактным площадкам платы. Я выбрал первый вариант — мне так проще, да и плату, если что, легче использовать повторно. После беглого ознакомления с датчиком температуры и влажности DHT21 выяснилось, что напрямую подключать его к Arduino не очень правильно. Оказывается, правильная схема включает «подтягивающий» резистор 4.7 кОм между плюсом и линией данных. Мне повезло — нужный резистор выкусил из ненужного беспроводного звонка. Для питания прототипа я воспользовался ненужной «аварийной» зарядкой для мобильного телефона. Это такой цилиндрик: с одной стороны вставляем батарейку AA 1.5В, а с другой получаем 5.9В (без нагрузки). Для страховки я подключил выход зарядки к входу RAW Arduino Pro Mini, чтобы все компоненты (плата и датчик) получали стабилизированные 5В. По крайней мере, из описания платы можно заключить, что RAW принимает от 5В до 12В, при этом на контактах VCC — стабилизированные 5В. Дальше все просто. Подключаем передатчик, датчик и пишем простой код. В моем случае для кода потребовались три библиотеки: RC-Switch (передача данных), SimpleTimer (отсчет интервалов для передачи) и DHT22 (получение данных с датчика температуры и влажности). А вот и прототип:Схема работы: раз в пять минут опрашиваем датчик и попеременно отправляем температуру и влажность. За одну сессию можно передать только один параметр, поэтому «большая сестра» получает их по очереди, а потом скопом отправляет в Open Weather Map. В результате данные в интернете обновляются раз в десять минут. Почему такой интервал? Потому что, во-первых, каждая сессия — это занятый радиоканал (а у меня есть и другие радиодатчики, требующие внимания) и отнятое процессорное время. Так что это попытка минимизировать издержки. Во-вторых, я не такой уж и погодный маньяк, чтобы обновлять погоду каждую секунду. И третье. Интервал в пять минут, по-моему, более-менее рационален с точки зрения энергетики, так как я планирую питать метеодатчик от батареек. Для записи кода в плату соединяем Arduino Pro Mini с компьютером через преобразователь Serial — USB и не забываем «перекрестить» линии TX/RX, то есть: RX подключаем к TX, и наоборот — TX к RX. Для питания берем пин 5В, потому что эта версия Arduino — 5В.Секрет: если заливка программы не удается (ошибка типа avrdude: stk500_getsync(): not in sync: resp=0x00), помогает такая процедура: 1) Нажимаем кнопку загрузки программы в среде разработки Arduino 2) Ждем пока загорится красный светодиод на преобразователе Serial — USB 3) Нажимаем кнопку сброса на Arduino Pro Mini Если не получилось — ждем, пока погаснет красный светодиод на преобразователе и повторяем процедуру. Со стороны «большой сестры» нужно только добавить несколько фрагментов кода для получения метеоданных из радиоканала и отправки их в интернет. Для примера — готовый код по ссылке в конце текста, который подходит для использования с Arduino Uno как в монопольном режиме, так и в составе вашего кода (если, разумеется, разобрать исходник на нужные части). Если будете использовать — не забудьте подставить свои IP/MAC, ключ авторизации OpenWeatherMap и координаты метеодатчика. А вот так метеодатчик выглядит почти в финальной (ну или вообще финальной, если нет ничего более постоянного, чем временное) версии:
НА ДЕРЕВНЮ, ДЕДУШКЕ
Итак, метеоданные получили, передали и приняли. Ок. И что делать с этим счастьем? Мне советовали отправлять его в Openweathermap.org, поскольку дело хорошее и вообще. Я проникся и немного изучил вопрос, хотя такое ощущение, что Openweathermap это совершенно не нужно. Так что получилось, скорее, не благодаря, а вопреки.
Спасибо нашему чуваку, который сделал интернет-метеостанцию и рассказал о ней, Wiki за описание базовой аутентификации HTTP и чудесному сервису hurl.it, который имитирует HTTP-запросы и показывает их тело, что важно для кода. Ах да, еще большое спасибо онлайновым сервисам кодирования Base64.
Иными словами, документация на Openweathemap upload API говорит, что нужна аутентификация HTTP Basic и описывает имена и форматы полей данных, но не дает практических примеров, что нужно таким безмозглым, как я. Как все получилось. Сначала я зарегистрировался на Openweathermap.org.
Потом выяснил, что для HTTP Basic нужна строка авторизации, состоящая из имени и пароля, разделенных двоеточием и кодированных Base64. Так что взял логин и пароль, пошел в онлайновый кодер и на выходе получил нужную строчку.
Например, для имени test и пароля test она выглядит так: dGVzdDp0ZXN0Как результат, строка авторизации Openweathermap выглядит так: Authorization: Basic dGVzdDp0ZXN0 Берем ее и составляем тестовый запрос в Openweathermap и смотрим тело запроса:Обратите внимание, что если все правильно, то «тест» отправляет данные в Openweathermap.
Я эту проблему решил просто: подставлял актуальную информацию о погоде из своего региона. Полученный таким образом текст запроса можно запросто использовать в коде Arduino: строчки печатаются в HTTP-клиент. Плюсы: в целом все довольно просто. Минусы: у Openweathermap отсутствуют адекватные (с моей точки зрения, разумеется) методы визуализации данных. Доступны только запросы к БД с выдачей результатов для визуализации «на стороне».
КАК ЭТО РАБОТАЕТ
Все просто. Метеодатчик получает температуру и влажность от DHT21, и отправляет их Arduino Uno, подключенной к интернету. Оттуда данные уходят на Openweathermap (чего добру пропадать?), где их можно посмотреть в онлайне и где они, вероятно, используются для прогноза погоды.
Желающим понаблюдать за местной (Россия, Москва, СВАО, Лианозово) погодой: мой метеодатчик на Openweathermap.org.
А ТЕПЕРЬ О ПРОБЛЕМАХ
Так как руки у меня растут все-таки не совсем из правильного места, то я закономерно наступил на несколько художественным образом разложенных грабель. Во-первых, несмотря на то, что авторы библиотеки DHT22 заверяли, что они решили проблему с отрицательными температурами, мне это не помогло.
При минусе библиотека начала выдавать совершенно нереальные показания, что в обсуждениях обосновывали ошибкой переполнения. Т.е. вместо -4.5С мне показывали 32763,5. Я не стал переписывать библиотеку (см. выше про руки), а просто стал вычитать полученное значение из 32768 (максимальное значение для заданного типа переменной).
Во-вторых, практически сразу после первого включения метеодатчика выяснилась печальная особенность: на кухонном столе (около 2.5 метров до приемника) он еще работал, а вот на балконе (около 4 метров) — нет. После изучения кода и прочего стало понятно, что проблема, все-таки и не в нем, и не в батарейках. Подозрение пало на антенны, которые я сделал из простых кусочков провода.
Чтение этих ваших интернетов догадки подтвердило: диапазон 433 МГц — довольно коварная в плане распространения волн штука. Поэтому антенну лучше делать хотя бы минимально похожей на антенну, а не изгибать проводочки под причудливыми углами, лишь бы в корпус поместилось. В итоге я заменил все проводки на штыри из одножильного медного провода (просто купил пару метров (с запасом, да) 2х1.
5 электрического кабеля, и распотрошил его на жилы. Длина штырей как и раньше — около 17.3 см, т.е. четверть волны. Все ориентированы вертикально. Результат — теперь не только метеодатчик работает на балконе, но и другие беспроводные датчики в квартире работают гораздо более уверенно. Третья очевидная проблема — совершенно зверское потребление энергии.
Двух батареек 14500 по 1000 мАч хватает где-то на пару суток. Т.е., по грубым прикидкам метеодатчик кушает около 20 мА. Говорят, что одна из наиболее прожорливых частей — встроенный стабилизатор напряжения, но от него я избавиться как раз и не могу, потому что пока не вижу, как в батарейный отсек на две АА можно разместить автономный источник 5В. Поэтому рассматриваю две альтернативы.
Первая — эксперименты со «спящим» режимом. Вторая — бросить эти девичьи мечты об автономности и запитать уже от электрической сети. Ну а пока наслаждаюсь тем, что датчик вообще работает 🙂
ССЫЛКИ
Библиотека RC-Switch
Библиотека DHT22
Библиотека SimpleTimer
Сервис для тест HTTP-запросов hurl.it
Сервис кодирования Base64
Код метеодатчика
Код принимающей стороны Планирую купить +106 Добавить в избранное Обзор понравился +113 +198
Источник: https://mysku.ru/blog/ebay/16290.html
Кроссплатформенная разработка погодной станции для Raspberry Pi
23 сентября 2017 в 15:26 (МСК) | сохранено7 октября 2017 в 15:26 (МСК)<\p>
Как известно, что ни делай под Raspberry Pi, получится либо медиаплеер, либо метеостанция. Постигла эта участь и меня — когда после очередного ливня датчик метеостанции залило, настала пора или купить новую, или сделать самому.
От метеостанции нужны были следующие функции:
- отображение температуры
- отображение графика атмосферного давления
- прогноз дождя
- синхронизация времени (в случае обычной метеостанции, по DCF77, если уж на устройстве есть часы, они должны показывать точное время)
Из покупных, по сочетанию «дизайн-цена-функции» не понравилась ни одна — либо нет одного, либо другого, либо слишком громоздко и дорого. В итоге решено было задействовать Raspberry Pi с TFT-экраном, и сделать те функции, которые нужны. Получилось примерно так:Подробности реализации и готовый проект под катом.
Первое, с чем нужно было определиться — это получение данных погоды. Здесь есть 2 варианта, либо использовать свои датчики, либо брать погоду из интернета. Первое интереснее, но есть несколько «но»:
- Сделать датчик «абы как» несложно, но сделать датчик хорошо, чтобы он например год работал от одного комплекта батареек, задача уже не столь тривиальная. Есть конечно сейчас и малопотребляющие процы, и радиомодули, но потратить на это месяц было бы лень.
- Нужно заморачиваться с корпусом, влагозащитой и прочими мелочами (3д-принтера у меня нет).
- Балкон выходит на солнечную сторону, так что погрешность измерения температуры в первую половину дня была бы слишком большой.
Альтернативным вариантом была покупка готового метеомодуля с датчиками для Raspberry Pi. Увы, поиск показал что в продаже есть всего 2 варианта:
— Raspberry Pi sense hat
Плата имеет «на борту» термометр, барометр, датчик влажности, гироскоп и акселерометр — но чем думали разработчики, ставя такой «экран» 8х8 светодиодов, непонятно — ничего внятного на нем вывести нельзя. Желаю разработчикам этого модуля всю жизнь UI под матрицу 8х8 писать 🙂
— Raspberry Pi weather hat
Ничего кроме светодиодов здесь нет вообще. В общем, как ни странно, но нормального готового шилда для метеостанции с хорошим экраном и хорошим набором датчиков так никто и не сделал. Краудсорсеры, ау — рыночная ниша пропадает 🙂
В итоге, не паримся и делаем по-простому — берем погоду из Интернета и выводим на обычный TFT. Как подсказал гугл, самое развитое API сейчас у https://openweathermap.org/api, его и будем использовать.
В комментариях был вопрос про точность интернет-данных.
Как можно видеть в коде ниже, для вывода температуры и атмосферного давления используется запрос на получение текущих (current weather data), а не прогнозируемых данных.
Их точность можно считать вполне достаточной для бытовых целей, более того, скорее всего она даже выше, чем точность уличного термометра/датчика, размещенного за окном или на балконе.
Для получения данных погоды с openweathermap нужен ключ, его можно получить бесплатно, зарегистрировавшись на вышеупомянутом сайте. Ключ выглядит примерно так «dadef5765xxxxxxxxxxxxxx6dc8». Большинство функций доступны бесплатно, платные API нам не понадобятся. Для бесплатных функций есть ограничение на 60 запросов в минуту, нам этого достаточно. Чтение данных весьма просто благодаря библиотеке pyowm. Получение погоды на данный момент (Python):import pyowm owm = pyowm.OWM(apiKey)
observation = owm.weather_at_coords(lat, lon)
w = observation.get_weather()
dtRef = w.get_reference_time(timeformat='date')
t = w.get_temperature('celsius')
temperatureVal = int(t['temp']) p = w.get_pressure()
pVal = int(p['press'])
Получение прогноза погоды для отображения осадков:fc = owm.three_hours_forecast_at_coords(lat, lon)
rain = fc.will_have_rain()
snow = fc.will_have_snow()
rains = fc.when_rain()На выходе получаем массив данных со списком дождей и их интенсивностью. Несмотря на название функции three_hours_forecast_at_coords, дожди прописаны на 2-3 дня вперед.
Можно использовать GET-запросы напрямую, например так. Это может пригодиться, например при портировании кода на MicroPython под ESP.
Как можно видеть выше, для получения данных нужны широта и долгота. Получение координат также весьма просто, и делается в 3 строчки кода:import geocoder g = geocoder.ip('me')
lat = g.latlng[0]
lon = g.latlng[1]
Собственно, самая сложная часть. На Raspberry Pi используется TFT-дисплей от Adafruit, поддерживающий систему команд ILI9340.
Библиотеки под него найти несложно, однако отлаживать код на Raspberry Pi не очень удобно. В итоге было принято решение написать высокоуровневый набор контролов, которых нужно было всего 3 — изображения, текст и линии. При запуске на Raspberry Pi контрол будет рисовать себя на TFT, при запуске на десктопе будет использоваться встроенная в Python библиотека tkinter.
В итоге, код будет работать везде — и на Raspberry Pi, и на Windows, и на OSX. Код одного контрола выглядит примерно так:class UIImage: def __init__(self, image = None, x = 0, y = 0, cId = 0): self.x = x self.y = y self.width = 0 self.height = 0 self.cId = cId self.tkID = None self.tftImage = None self.tkImage = None self.useTk = utils.
isRaspberryPi() is False if image is not None: self.setImage(image) def setImage(self, image): width, height = image.size if self.useTk: self.tkImage = ImageTk.PhotoImage(image) self.tftImage = image self.width = width self.height = height def draw(self, canvas = None, tft = None): if tft != None: tft.draw_img(self.tftImage, self.x, self.y, self.width, self.
height) elif canvas != None and self.tkImage != None: if self.tkID == None or len(canvas.find_withtag(self.tkID)) == 0: self.tkID = canvas.create_image(self.x, self.y, image=self.tkImage , anchor=tkinter.NW) else: canvas.itemconfigure(self.tkID, image=self.tkImage)
Класс «FakeTFT» создает обычное окно программы:class FakeTFT: def __init__(self): self.tkRoot = tkinter.
Tk() self.tkRoot.geometry(“500×300″) self.screenFrame = tkinter.Frame(self.tkRoot, width=330, height=250, bg=”lightgray”) self.screenFrame.place(x=250 – 330 / 2, y=5) self.tkScreenCanvas = tkinter.Canvas(self.tkRoot, bg = 'white', width = 320, height = 240, highlightthickness=0) self.tkScreenCanvas.focus_set() self.tkScreenCanvas.
place(x=250 – 320 / 2, y=10) self.controls = [] def draw(self): for c in self.controls: c.draw(self.tkScreenCanvas)
Класс «LCDTFT» использует «настоящий» дисплей (фрагмент кода):class LCDTFT: def __init__(self, spidev, dc_pin, rst_pin=0, led_pin=0, spi_speed=16000000): # CE is 0 or 1 for RPI, but is actual CE pin for virtGPIO # RST pin.
0 means soft reset (but reset pin still needs holding high (3V) # LED pin, may be tied to 3V (abt 14mA) or used on a 3V logic pin (abt 7mA) # and this object needs to be told the GPIO and SPIDEV objects to talk to global GPIO self.SPI = spidev self.SPI.open(0, 0) self.SPI.max_speed_hz = spi_speed self.RST = rst_pin self.DC = dc_pin self.LED = led_pin self.
controls = [] def draw(self): for c in self.controls: c.draw(tft = self)
При инициализации автоматически выбирается нужный дисплей, в зависимости от того, где запускается программа:def lcdInit(): if utils.isRaspberryPi(): GPIO.setwarnings(False) GPIO.setmode(GPIO.BCM) DC = 25 LED = 18 RST = 0 return LCDTFT(spidev.
SpiDev(), DC, RST, LED) else: return FakeTFT()Все это позволяет полностью абстрагироваться от «железа», и писать код типа такого:self.labelPressure = libTFT.UILabel(“Pressure”, 18,126, textColor=self.tft.BLACK, backColor=self.tft.WHITE, fontS = 7)
self.tft.controls.append(self.labelPressure)
self.labelRain = libTFT.UILabel(“Rain”, 270,126, textColor=self.tft.
BLUE, backColor=self.tft.WHITE, fontS = 7)
self.tft.controls.append(self.
labelRain)Собственно UI выглядит так:На экране отображаются текущая температура, график атмосферного давления за сегодняшний день (в следующей версии будет добавлен график температуры), также в случае прогноза дождя, его время отмечается на графике вертикальной синей чертой (на данной картинке дождей нет). Также выводятся время последнего обновления данных и IP-адрес, если понадобится подключиться к устройству.
Желающие ознакомиться с исходником подробнее, могут посмотреть его на guthub.
Для тех, кто не хочет заморачиваться описанным выше, короткая инструкция по установке под спойлером.Инструкция— Скачиваем исходники с github:
git clone github.com/dmitryelj/RPi-Weather-Station.
git — Если не установлен Python3, ставим: sudo apt-get install python3 — Ставим дополнительные библиотеки (они нужны для работы с дисплеем): sudo pip3 install numpy pillow spidev — Добавляем в автозапуск (sudo nano /etc/rc.local) python3 /home/pi/Documents/RPi-Weather-Station/weather.py & — Пробуем запустить python3 weather.
py Если все работает, то перезагружаемся (sudo reboot) и пользуемся.В плане добавить еще что-нибудь полезное, например отображение карты облачности, API на openweathermap для этого есть.
Продолжение следует.
Источник: https://sohabr.net/gt/post/293303/
Погодная станция с часами (за полчаса)
Сегодня мы создадим погодную станцию, которая будет работать с двумя внешними датчиками Oregon (THGN132N – температура и относительная влажность), измерять температуру, атмосферное давление и относительную влажность внутри помещения. Дополнительно оснастим ее часами реального времени (для удобства и оставим некоторый “задел на будущее”).
Отображение температуры, влажности и состояния элемента питания датчика |
Функционирование реализуем следующее:
- На дисплее циклически будет отображаться:
- Текущее время, день недели, дата
- Атмосферное давление, температура и относительная влажность внутри помещения
- Температура, относительная влажность с внешних датчиков и информация о состоянии их батарей
- Принудительное переключение между режимами отображения с помощью кнопки.
- Для всех параметров (температура, влажность, давление) будем отслеживать тренд изменения (увеличивается, стабильно, понижается) и рядом с конкретным значением будем показывать эту информацию в виде специальных значков.
- В качестве уличных датчиков будем использовать покупные Oregon THGN132N.
- Когда приходит информация от уличного датчика – будем индицировать это кратковременным зажиганием светодиода.
Для достижения быстрого результата нам потребуется:
- Ардуино (или любой клон) с 328 “камушком” – 1 шт.,
- Датчик Oregon THGN132N – 2 шт.,
- Grove Base Shield – 1 шт.,
- Дисплей 16х2 с последовательным интерфейсом (серии Grove) – 1 шт.,
- Модуль RTC на базе DS1307 (серии Grove) – 1 шт.,
- Датчик температуры и влажности DHT11 (серии Grove) – 1 шт.,
- Модуль кнопки (серии Grove) – 1 шт.,
- Модуль светодиода (серии Grove) – 1 шт.,
- Высокоточный датчик давления BMP085 (серии Grove) – 1 шт.,
- RF-кит (приемник и передатчик) на частоту 433МГц (серии Grove) – 1 шт.
- 4-х контактный кабель (серии Grove) – 7 шт.,
Комплектующие серии Grove очень удобно соединять между собой – достаточно взять модуль, подключить к нему соответствующий кабель и дальше этот кабель подсоединить в необходимый разъем на шилде. Таким образом есть некоторая “защита от дурака” – сложно перепутать контакты питания между собой и скорость монтажа просто потрясающая – нашу “погодную станцию” можно собрать за пару минут.
Большая часть необходимых нам комплектующих входит в Grove Starter Kit.
В случае, если у вас нет комплектующих данной серии – ничего страшного, вы можете использовать их аналоги и разместить их, например, на беспаечной макетной плате (в статье мы опишем, к каким конкретно пинам будет осуществляться подключение).
Частично собранная “метеостанция” и датчик Oregon |
- Подсоединяем дисплей к разъему 5 (здесь и далее разъемы согласно нумерации на схеме шилда) – будем использовать D5 и D6, как TX и RX.
- Датчик для измерения внутренней температуры и влажности (DHT11) подключаем к разъему 4 – используем D4.
- Модуль кнопки – в разъем 3 – используем D3.
- RF-приемник на 433МГц подключаем к разъему 2 – используем D2.
- Модуль светодиода подключаем к разъему 13 – используем D13.
- Модуль RTC подключаем к разъему IIC (SDA – A4, SCL – A5).
- Модуль барометра BMP085 – тоже к разъему IIC (SDA – A4, SCL – A5).
Последние два модуля фактически получаются подключенными параллельно (это нормально).
Быстросборный “паук”. Модули (по часовой стрелке, начиная с самого верхнего): RTC, LED, Button, DHT11, Serial LCD, RF-приемник (антенна в виде спирали), BMP085. В центре виден Base-шилд. |
Датчики THGN132N так же необходимо подготовить – на одном из них выбрать (переключателем под крышкой батарейного отсека) канал 1 (это будет первый уличный датчик), а на втором, соответственно, надо выбрать 2 канал.
Переключатель каналов под крышкой батарейного отсека |
На этом наша “аппаратная платформа” полностью готова.
В качестве основы для общего кода будем использовать примеры использования конкретных датчиков (и их библиотеки, если они необходимы).
Сложность возникает с датчиками Oregon, но благодаря тому, что датчики эти доступны по цене (от 600 рублей) и обладают хорошими характеристиками, энтузиасты не прошли мимо протокола их работы и неплохо его разобрали.
Более подробно работа с датчиками описана в этой заметке на habrahabr.ru (повторяться не будем). Особенности:
- Для хранения информации о текущих значениях датчиков используется два массива t[4] и h[4] (температура и влажность, соответственно). Значения давления храним в соответствующем элементе массива вместо влажности.
- Для вычисления трендов используется массивы предыдущих значений PrevTemp[] и PrevHym[]. Сами же параметры, характеризующие рост (или спад) того или иного параметра задаются с помощью директив (можно изменить под свои личные предпочтения):
- #define DELTA_TIME 900000 // 15 минут – период расчета трендов
- #define DELTA_TEMP 0.
1 // превышение этого значения будет означать изменение температуры – 0.1 градуса
- #define DELTA_HYM 1 // порог для влажности 1 процент
- #define DELTA_BAR 1 // порог для давления 1 мм.рт.ст.
- Для определения температуры внутри помещения используем значения с датчика BMP085, как более высокоточного по сравнению с DHT11.
- Из-за того, что дисплей не поддерживает кириллицу и нельзя “создать” собственные символы, для отображения трендов и состояния элементов питания будем использовать символы из набора доступных.
- Получение параметров от датчиков Oregon происходит по мере того, как датчики передают о себе информацию (примерно 1 раз в 40 секунд).
- Остальные измерения происходят в момент обновления экрана (в автоматическом режиме 1 раз в 20 секунд или в ручном режиме при нажатии на кнопку).
Примеры отображения информации на экране:
Текущее время, день недели и дата |
Атмосферное давление и температура и влажность внутри помещения. Атмосферное давление и влажность растут (обозначено значком “^”) |
Отображение информации с датчиков Oregon (первый датчик находится на улице, второй – дома). Уличная температура – понижается (обозначено значком “_”), остальные параметры – повышаются.
Состояние элементов питания в датчиках – в норме (для обоих). |
Вот, собственно, и все – наша погодная станция готова и функционирует.
Что можно было бы еще добавить:
Архив с полным кодом скетча и необходимыми библиотеками.Если у вас возникают какие-то вопросы, замечания, пожелания – оставляйте их в комментариях к данной статье. Как это работает:
Продолжение: оснастим нашу погодную станцию web-интерфейсом.
Источник: http://devicter.blogspot.com/2013/01/blog-post.html