В настоящее время в связи с текущим ухудшением экологической обстановки во всем мире повышается актуальность использования различных анализаторов качества воздуха. В связи с этим в данной статье мы рассмотрим создание анализатора качества воздуха с определением частиц PM2.5, PM10 и CO на основе модуля ESP32 и датчиков Nova PM SDS011, MQ-7 и DHT11. Вывод измеряемых значений мы будем производить на экран OLED дисплея.
В современном мире основными загрязнителями воздуха, влияющим на здоровье человека, являются ультрадисперсные взвешенные частицы PM2.5 и PM10, а также окись углерода (CO). На основе этих трех показателей мы и будем определять индекс качества воздуха. Все измеряемые значения мы будем передавать на онлайн сервис Adafruit IO, что позволит иметь доступ к ним из любой точки земного шара где есть подключение к сети интернет.
Ранее на нашем сайте мы рассматривали подобный анализатор качества воздуха с определением частиц PM2.5 и PM10 на основе платы Arduino. Также на нашем сайте вы можете посмотреть и другие проекты анализаторов качества воздуха:
- измерение концентрации углекислого газа (CO2) с помощью Arduino и датчика MQ-135;
- измерение TVOC и CO2 с помощью Arduino и датчика качества воздуха CCS811;
- измерение уровня аммиака в воздухе с помощью датчика газа MQ-137 и Arduino;
- система мониторинга загрязнения воздуха на основе Arduino.
Необходимые компоненты
- Модуль ESP32 (купить на AliExpress).
- Nova PM Sensor SDS011 (датчик SDS011 от компании Nova) (купить на AliExpress).
- 0.96’ SPI OLED Display Module – модуль OLED дисплея с диагональю 0.96’ и поддержкой интерфейса SPI (купить на AliExpress — если будете покупать по приведенной ссылке, то выбирайте модель OLED дисплея с 7 контактами).
- Датчик температуры и влажности DHT11 (купить на AliExpress).
- Датчик газа MQ-7.
- Соединительные провода.
Nova PM Sensor SDS011
Датчик SDS011 – недавно появившийся на рынке анализатор качества воздуха, разработанный компанией Nova Fitness. Принцип его работы основан на активной лазерной спектроскопии (анализ рассеяния луча лазера). Данный датчик способен обнаруживать в воздухе частицы с размерами от 0.3 до 10μm (микрометров). Датчик состоит из небольшого вентилятора, клапана впуска воздуха, лазерного диода и фотодиода. Воздух в датчик поступает через клапан впуска (air inlet). Внутри датчика работает лазерный диод, который освещает поступивший внутрь датчика воздух и частицы, содержащиеся в нем. Получившийся рассеянный свет преобразуется в электрический сигнал с помощью фотодетектора. Этот сигнал затем усиливается и обрабатывается. В результате обработки вычисляется концентрация частиц PM2.5 и PM10.
Технические характеристик датчика SDS011:
- обнаружение частиц: PM2.5, PM10;
- диапазон измерений: 0.0-999.9μg/m3;
- входное напряжение: от 4.7V до 5.3V;
- максимальный ток: 100mA;
- ток покоя (в «спящем» состоянии): 2mA;
- время отклика: 1 секунда;
- разрешающая способность при обнаружении частиц: ≤ 0.3μm;
- относительная ошибка: 10% ;
- диапазон рабочих температур: -20~50°C.
Модуль OLED дисплея (0.96’ OLED Display Module)
OLED (Organic Light-Emitting Diodes, органический светоизлучающий диод) – это светоизлучающая технология, которая применяется в большинстве современных телевизоров. В OLED дисплеях используется тот же принцип формирования изображения, что и в современных телевизорах, только количество пикселей в них значительно меньше.
Для нашего проекта мы использовали монохромный 7-ми контактный OLED дисплей SSD1306 с диагональю 0.96”. Он может использовать 3 различных коммуникационных протокола: 3-х проводный SPI, 4-х проводный SPI и I2C.
Назначение его контактов (распиновка) приведены в следующей таблице.
Номер контакта | Название контакта | Альтернативное название контакта | Назначение контакта |
1 | Gnd | Ground | земля |
2 | Vdd | Vcc, 5V | напряжение питания (в диапазоне 3-5 В) |
3 | SCK | D0, SCL, CLK | используется как контакт часов (clock pin). Применяется в интерфейсах I2C и SPI |
4 | SDA | D1, MOSI | контакт данных. Применяется в интерфейсах I2C и SPI |
5 | RES | RST, RESET | контакт сброса модуля. Применяется в интерфейсе SPI |
6 | DC | A0 | контакт команд (Data Command pin). Применяется в интерфейсе SPI |
7 | CS | Chip Select (выбор чипа) | используется когда несколько устройств взаимодействуют по интерфейсу SPI |
Все проекты с использованием данного дисплея на нашем сайте вы можете посмотреть по следующей ссылке.
Технические характеристики OLED дисплея SSD1306:
- драйвер микросхемы OLED: SSD1306;
- разрешение: 128 x 64;
- угол зрения: >160°;
- входное напряжение: 3.3V ~ 6V;
- цвет пикселов: синий;
- диапазон рабочих температур: -30°C ~ 70°C.
Подготовка датчика MQ-7 для измерения окиси углерода (CO)
Датчик MQ-7 (CO Carbon Monoxide Gas Sensor Module) способен определять концентрацию окиси углерода/угарного газа (CO) в окружающем воздухе. Он способен измерять концентрации данного газа от 10 до 10,000 ppm (part(s) per million – число частиц на миллион). MQ-7 можно купить либо в виде модуле, либо в виде отдельного датчика. Ранее на нашем сайте мы уже рассматривали проекты с использованием различных датчиков газа, посмотреть их вы можете по этой ссылке. В этом проекте мы будем использовать датчик MQ-7 для измерения концентрации окиси углерода в PPM. Принципиальная схема датчика MQ-7 представлена на следующем рисунке.
Важную роль в работе данного датчика играет нагрузочный резистор RL. Его сопротивление изменяется в зависимости от концентрации газа. По умолчанию датчик MQ-7 поставляется с резистором RL сопротивлением 1 кОм, которое практически бесполезно в нашем проекте, поэтому нам необходимо заменить его на резистор сопротивлением 10 кОм.
Индекс качества воздуха (ИКВ)
Индекс качества воздуха (ИКВ) в различных странах рассчитывается исходя из средней концентрации определенных загрязнителей, измеряемых в течение стандартного интервала времени (24 часа для большинства загрязнителей, 8 часов для окиси углерода и озона). Для частиц PM2.5 и PM10 также используется 24-часовой интервал измерения. Суммарный индекс качества воздуха включает 8 загрязнителей: PM10, PM2.5, двуокись азота (NO2), диоксид серы/сернистый газ (SO2), окись углерода (CO), озон в околоземном пространстве (O3), аммиак (NH3) и свинец (Pb). Но не в каждой локации измеряются все эти 8 загрязнителей.
Поэтому часто вместо полного индекса качества воздуха измеряется субиндекс, который представляет собой линейную функцию концентрации частиц PM2.5 и PM10, например, субиндекс для частиц PM2.5 при их концентрации 31 µg/m3 будет равен 51, при их концентрации 60 µg/m3 он будет равен 100, а при концентрации 45 µg/m3 – 75. Самый худший субиндекс (по максимуму всех параметров) будет определять суммарный индекс качества воздуха.
Схема проекта
Схема анализатора качества воздуха с определением частиц PM2.5, PM10 и CO на основе модуля ESP32 представлена на следующем рисунке.
№ п/п | OLED дисплей | Модуль ESP32 |
1 | GND | Ground |
2 | VCC | 5V |
3 | D0 | 18 |
4 | D1 | 23 |
5 | RES | 2 |
6 | DC | 4 |
7 | CS | 5 |
№ п/п | Датчик SDS011 | Модуль ESP32 |
1 | 5V | 5V |
2 | GND | GND |
3 | RX | 17 |
4 | TX | 16 |
№ п/п | Датчик DHT11 | Модуль ESP32 |
1 | Vcc | 5V |
2 | GND | GND |
3 | Data | 27 |
№ п/п | Датчик MQ-7 | Модуль ESP32 |
1 | Vcc | 5V |
2 | GND | GND |
3 | A0 | 25 |
Корпус нашего проекта мы напечатаем на 3D принтере, поэтому схему нашего проекта мы спаяли на перфорированной плате. Учтите, что соединительные провода должны иметь достаточную длину для подключения датчиков и OLED дисплее. Внешний вид собранной на перфорированной плате конструкции проекта приведен на следующем рисунке.
Настройка сервиса Adafruit IO
Adafruit IO – это открытая облачная платформа, которая позволяет агрегировать, визуализировать и анализировать данные реального времени. Используя Adafruit IO вы можете загружать, отображать и производить мониторинг данных через сеть интернет, что делает ее чрезвычайно удобной для применения в различных проекта интернета вещей (IoT).
Для использования Adafruit IO вам сначала необходимо зарегистрироваться в данной платформе. Для этого перейдите на веб-сайт Adafruit IO и нажмите на ‘Get started for Free’ в правом верхнем углу экрана.
После окончания регистрации зайдите в свой аккаунт и нажмите на ‘View AIO Key’ в правом верхнем углу экрана чтобы получить имя пользователя (username) и AIO key (ключ).
Когда вы нажмете на ‘AIO Key’, откроется всплывающее окно с данными AIO Key и username. Скопируйте и сохраните этот ключ и имя пользователя, в дальнейшем они нам понадобятся при написании программы.
Теперь, после получения AIO ключа, создайте фид (feed) для хранения данных датчика DHT. Для создания фида нажмите на ‘Feed’. Затем нажмите на ‘Actions’ (действия), после этого выберите ‘Create a New Feed’ из доступных пунктов.
После этого откроется новое окно, в котором вам необходимо ввести имя (Name) и описание (Description) фида. Описание можно не указывать.
Затем нажмите на кнопку ‘Create’, после этого вы будете перенаправлены на новый созданный фид. Для данного проекта мы создадим 6 фидов – для PM10, PM2.5, CO, температуры, влажности и индекса качества воздуха (AQI).
После создания фидов создадим панель инструментов (dashboard) Adafruit IO, на которой мы будем визуализировать данные от наших датчиков. Для этого создайте панель инструментов и добавьте на нее все наши фиды.
Для создания панели инструментов нажмите на Dashboard, затем на ‘Action’, и после этого на ‘Create a New Dashboard’ (создать новую панель инструментов).
В следующем открывшемся окне введите имя панели инструментов и нажмите на ‘Create’.
После того как панель инструментов будет создана, вы можете использовать блоки Adafruit IO типа Gauge и Slider для визуализации данных. Для добавления блоков нажмите на иконку ‘+’ в правом верхнем углу экрана.
Далее выберите блок ‘Gauge’.
В следующем окне выберите данные фида, которые вы хотите визуализировать.
И, наконец, измените настройки блока в соответствии со своими предпочтениями.
Аналогичным образом добавьте блоки визуализации для остальных фидов. После этого панель инструментов Adafruit IO должна у вас выглядеть примерно следующим образом:
Объяснение программы для модуля ESP32
Полный код программы приведен в конце статьи, здесь же мы кратко рассмотрим его основные фрагменты.
В коде нашей программы будут использоваться библиотеки SDS011, Adafruit_GFX, Adafruit_SSD1306, Adafruit_MQTT и DHT.h. При этом библиотеки SDS011, Adafruit_GFX и Adafruit_SSD1306 можно скачать и установить с помощью менеджера библиотек (Library Manager) Arduino IDE. Для этого откройте Arduino IDE и выберите в ней пункт меню Sketch < Include Library < Manage Libraries. После этого выполните поиск библиотеки SDS011 и в открывшихся результатах поиска установите библиотеку от R. Zschiegner.
Аналогичным образом установите библиотеки Adafruit GFX и Adafruit SSD1306 от компании Adafruit. Библиотеки Adafruit_MQTT.h и DHT11.h можно скачать с репозитория Github.
После скачивания и установки всех необходимых библиотек подключим их использование в программе.
1 2 3 4 5 6 7 8 |
#include <SDS011.h> #include <SPI.h> #include <WiFi.h> #include "Adafruit_MQTT.h" #include "Adafruit_MQTT_Client.h" #include "DHT.h" #include <Adafruit_GFX.h> #include <Adafruit_SSD1306.h> |
Затем зададим ширину и высоту экрана OLED дисплея в пикселах.
1 2 |
#define SCREEN_WIDTH 128 #define SCREEN_HEIGHT 64 |
Затем укажем контакты для связи по интерфейсу SPI с OLED дисплеем.
1 2 3 4 5 |
#define OLED_MOSI 23 #define OLED_CLK 18 #define OLED_DC 4 #define OLED_CS 5 #define OLED_RESET 2 |
Далее создадим объект для работы с OLED дисплеем.
1 2 |
Adafruit_SSD1306 display(SCREEN_WIDTH, SCREEN_HEIGHT, OLED_MOSI, OLED_CLK, OLED_DC, OLED_RESET, OLED_CS); |
После этого укажем параметры доступа к сети WiFi (имя пользователя и пароль) и параметры для работы с платформой Adafruit IO, которые будут включать MQTT сервер, номер порта, имя пользователя и ключ AIO (AIO Key).
1 2 3 4 5 6 |
const char *ssid = "Galaxy-M20"; const char *pass = "ac312124"; #define MQTT_SERV "io.adafruit.com" #define MQTT_PORT 1883 #define MQTT_NAME "choudharyas" #define MQTT_PASS "988c4e045ef64c1b9bc8b5bb7ef5f2d9" |
Затем укажем фиды Adafruit IO для хранения данных от датчиков. В нашем случае мы использовали 6 фидов с именами AirQuality, Temperature, Humidity, PM10, PM25 и CO.
1 2 3 4 5 6 7 |
Adafruit_MQTT_Client mqtt(&client, MQTT_SERV, MQTT_PORT, MQTT_NAME, MQTT_PASS); Adafruit_MQTT_Publish AirQuality = Adafruit_MQTT_Publish(&mqtt,MQTT_NAME "/f/AirQuality"); Adafruit_MQTT_Publish Temperature = Adafruit_MQTT_Publish(&mqtt,MQTT_NAME "/f/Temperature"); Adafruit_MQTT_Publish Humidity = Adafruit_MQTT_Publish(&mqtt,MQTT_NAME "/f/Humidity"); Adafruit_MQTT_Publish PM10 = Adafruit_MQTT_Publish(&mqtt,MQTT_NAME "/f/PM10"); Adafruit_MQTT_Publish PM25 = Adafruit_MQTT_Publish(&mqtt,MQTT_NAME "/f/PM25"); Adafruit_MQTT_Publish CO = Adafruit_MQTT_Publish(&mqtt,MQTT_NAME "/f/CO"); |
После этого внутри функции void setup() инициализируем последовательную связь со скоростью 9600 бод для целей отладки. Также инициализируем OLED дисплей, датчики DHT и SDS011 с помощью функций begin().
1 2 3 4 5 6 |
void setup() { my_sds.begin(16,17); Serial.begin(9600); dht.begin(); display.begin(SSD1306_SWITCHCAPVCC); |
Далее цикл for внутри функции setup используется для сбора значений с определенного номера и затем установки счетчика в 0.
1 2 3 |
for (int thisReading1 = 0; thisReading1 < numReadingsPM10; thisReading1++) { readingsPM10[thisReading1] = 0; } |
После этого мы будем считывать данные с датчиков. Для этого внутри функции loop мы будем использовать функцию millis() чтобы считывать данные с датчиков каждый час. После считывания данных c аналогового выхода датчика MQ-7 мы получаем значения на выходе АЦП в диапазоне от 0 до 4095. Для преобразования этого значения в аналоговое значение напряжения используем формулу:
RvRo = MQ7Raw * (3.3 / 4095)
где MQ7Raw – значение с выхода АЦП аналогового контакта, к которому подключен датчик MQ-7.
Также считаем данные о концентрации частиц PM2.5 и PM10 с датчика SDS011.
1 2 3 4 5 6 7 8 9 10 11 |
if ((unsigned long)(currentMillis - previousMillis) >= interval) { MQ7Raw = analogRead( iMQ7 ); RvRo = MQ7Raw * (3.3 / 4095); MQ7ppm = 3.027*exp(1.0698*( RvRo )); Serial.println(MQ7ppm); error = my_sds.read(&p25,&p10); if (! error) { Serial.println("P2.5: "+String(p25)); Serial.println("P10: "+String(p10)); } } |
Мы считываем значения PM2.5 и PM10 с датчика SDS011 в µg/m3, а значения окиси углерода (Carbon Monoxide) – в PPM (частиц на миллион). Нам их необходимо преобразовать в mg/m3, для этого используем формулу:
1 |
Concentration (mg/m3) = Concentration (PPM) × (Molecular Mass (g/mol) / Molar Volume (L)) |
в которой молекулярная масса (Molecular Mass) CO равна 28.06 g/mol, а ее молярный объем (Molar Volume) равен 24.45L при 25 градусах Цельсия.
1 2 |
ConcentrationINmgm3 = MQ7ppm* (28.06/24.45); Serial.println(ConcentrationINmgm3); |
Расчет средних значений за 24 часа
В следующем фрагменте кода рассчитаем средние за 24 часа значения частиц PM10, PM2.5 и средние за 8 часов значения окиси углерода. В первой строке этого фрагмента кода из общей суммы значений вычтем первый элемент массива. Затем получим текущее значение и прибавим его к общему, и увеличим номер индекса. Если значение индекса равно или больше чем numReadings, сбросим значение индекса снова в 0.
1 2 3 4 5 6 7 |
totalPM10 = totalPM10 - readingsPM10[readIndexPM10]; readingsPM10[readIndexPM10] = p10; totalPM10 = totalPM10 + readingsPM10[readIndexPM10]; readIndexPM10 = readIndexPM10 + 1; if (readIndexPM10 >= numReadingsPM10) { readIndexPM10 = 0; } |
И, наконец, опубликуем эти данные на платформе Adafruit IO.
1 2 3 4 5 6 7 8 9 |
if (! Temperature.publish(temperature)) { delay(30000); } if (! Humidity.publish(humidity)) { delay(30000); ………………………………………………………. ………………………………………………………. |
Изготовление корпуса для нашего проекта
Далее мы измерили размеры всех компонентов нашего проекта и на основе их значений спроектировали модель корпуса, показанную на следующем рисунке.
После этого мы экспортировали эту модель в STL и закачали его на сервис Thingiverse — вы ее можете скачать и использовать для изготовления корпуса проекта. Также этот STL файл мы использовали для печати данной модели корпуса на 3D принтере. После этого мы разместили в нее все компоненты нашего проекта. Внешний вид собранной в корпусе конструкции нашего проекта показан на следующем рисунке.
Тестирование работы проекта
После того как аппаратная часть проекта будет готова можно приступить к тестированию его работы. Мы использовали адаптер 12V 1A для подачи питания на устройство. Как вы видите из представленного ниже рисунка, на экране OLED дисплея отображаются значения концентрации частиц PM10 и PM2.5 (в µg/m3), а также концентрация окиси углерода (в mg/m3).
Эти же значения публикуются и в нашей панели инструментов Adafruit IO. Максимальное значение из всех этих трех параметров (PM10, PM2.5 & CO) и будет значением индекса качества воздуха (AQI).
Также значения индекса качества воздуха (AQI) за последние 30 дней будут выводиться на графике.
Более подробно работу проекта вы можете посмотреть на видео, приведенном в конце статьи.
Исходный код программы (скетча)
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 |
#include <SDS011.h> #include <SPI.h> #include <WiFi.h> #include "Adafruit_MQTT.h" #include "Adafruit_MQTT_Client.h" #include "DHT.h" #include <Adafruit_GFX.h> #include <Adafruit_SSD1306.h> #include "esp32-hal-adc.h" // needed for adc pin reset #include "soc/sens_reg.h" // needed for adc pin reset uint64_t reg_b; // Used to store Pin registers #define SCREEN_WIDTH 128 // ширина OLED дисплея, в пикселах #define SCREEN_HEIGHT 64 // высота OLED дисплея, в пикселах // Declaration for SSD1306 display connected using software SPI (default case): #define OLED_MOSI 23 #define OLED_CLK 18 #define OLED_DC 4 #define OLED_CS 5 #define OLED_RESET 2 Adafruit_SSD1306 display(SCREEN_WIDTH, SCREEN_HEIGHT, OLED_MOSI, OLED_CLK, OLED_DC, OLED_RESET, OLED_CS); const int numReadingsPM10 = 24; const int numReadingsPM25 = 24; const int numReadingsCO = 8; WiFiClient client; SDS011 my_sds; const char *ssid = "Galaxy-M20"; // Enter your WiFi Name (имя WiFi сети) const char *pass = "ac312124"; // Enter your WiFi Password (пароль для доступа к WiFi сети) #define MQTT_SERV "io.adafruit.com" #define MQTT_PORT 1883 #define MQTT_NAME "choudharyas" // Your Adafruit IO Username #define MQTT_PASS "988c4e045ef64c1b9bc8b5bb7ef5f2d9" // Adafruit IO AIO key #define DHTTYPE DHT11 // DHT 11 uint8_t DHTPin = 27; DHT dht(DHTPin, DHTTYPE); int error; unsigned long interval = 3600000; unsigned long previousMillis = 0; int temperature, humidity, AQI; float p10,p25; int iMQ7 = 25; int MQ7Raw = 0; int MQ7ppm = 0; double RvRo; int ConcentrationINmgm3; int readingsPM10[numReadingsPM10]; // значения, считываемые с аналогового входа int readIndexPM10 = 0; // the index of the current reading int totalPM10 = 0; // the running total int averagePM10 = 0; // the average (среднее) int readingsPM25[numReadingsPM25]; // значения, считываемые с аналогового входа int readIndexPM25 = 0; // the index of the current reading int totalPM25 = 0; // the running total int averagePM25 = 0; // the average (среднее) int readingsCO[numReadingsCO]; // значения, считываемые с аналогового входа int readIndexCO = 0; // the index of the current reading int totalCO = 0; // the running total int averageCO = 0; // the average (среднее) Adafruit_MQTT_Client mqtt(&client, MQTT_SERV, MQTT_PORT, MQTT_NAME, MQTT_PASS); Adafruit_MQTT_Publish AirQuality = Adafruit_MQTT_Publish(&mqtt,MQTT_NAME "/f/AirQuality"); Adafruit_MQTT_Publish Temperature = Adafruit_MQTT_Publish(&mqtt,MQTT_NAME "/f/Temperature"); Adafruit_MQTT_Publish Humidity = Adafruit_MQTT_Publish(&mqtt,MQTT_NAME "/f/Humidity"); Adafruit_MQTT_Publish PM10 = Adafruit_MQTT_Publish(&mqtt,MQTT_NAME "/f/PM10"); Adafruit_MQTT_Publish PM25 = Adafruit_MQTT_Publish(&mqtt,MQTT_NAME "/f/PM25"); Adafruit_MQTT_Publish CO = Adafruit_MQTT_Publish(&mqtt,MQTT_NAME "/f/CO"); //Adafruit_MQTT_Publish NH3 = Adafruit_MQTT_Publish(&mqtt,MQTT_NAME "/f/NH3"); void setup() { my_sds.begin(16,17); Serial.begin(9600); dht.begin(); display.begin(SSD1306_SWITCHCAPVCC); delay(10); pinMode(DHTPin, INPUT); pinMode(iMQ7, INPUT); Serial.println("Connecting to "); Serial.println(ssid); reg_b = READ_PERI_REG(SENS_SAR_READ_CTRL2_REG); WiFi.begin(ssid, pass); while (WiFi.status() != WL_CONNECTED) { delay(550); Serial.print("."); } Serial.println(""); Serial.println("WiFi connected"); for (int thisReading1 = 0; thisReading1 < numReadingsPM10; thisReading1++) { readingsPM10[thisReading1] = 0; } for (int thisReading2 = 0; thisReading2 < numReadingsPM25; thisReading2++) { readingsPM25[thisReading2] = 0; } for (int thisReading3 = 0; thisReading3 < numReadingsCO; thisReading3++) { readingsCO[thisReading3] = 0; } display.clearDisplay(); display.display(); } void loop() { unsigned long currentMillis = millis(); MQTT_connect(); if ((unsigned long)(currentMillis - previousMillis) >= interval) { WRITE_PERI_REG(SENS_SAR_READ_CTRL2_REG, reg_b); MQ7Raw = analogRead( iMQ7 ); Serial.print("MQ Raw: "); Serial.println(MQ7Raw); RvRo = MQ7Raw * (3.3 / 4095); MQ7ppm = 3.027*exp(1.0698*( RvRo )); Serial.print("CO: "); Serial.println(MQ7ppm); //Serial.println(); error = my_sds.read(&p25,&p10); if (! error) { Serial.println("P2.5: "+String(p25)); Serial.println("P10: "+String(p10)); } } temperature = dht.readTemperature(); humidity = dht.readHumidity(); Serial.print("Temperature: "); Serial.print(temperature); Serial.println(); Serial.print("Humidity: "); Serial.print(humidity); Serial.println(); ConcentrationINmgm3 = MQ7ppm* (28.06/24.45); //преобразование PPM в mg/m3. 28.06 молекулярная масса CO, а 24.45 – его молярный объем Serial.print("mg/m3: "); // for more inforation on this follow: https://www.markes.com/Resources/Frequently-asked-questions/How-do-I-convert-units.aspx Serial.println(ConcentrationINmgm3); totalPM10 = totalPM10 - readingsPM10[readIndexPM10]; readingsPM10[readIndexPM10] = p10; totalPM10 = totalPM10 + readingsPM10[readIndexPM10]; readIndexPM10 = readIndexPM10 + 1; if (readIndexPM10 >= numReadingsPM10) { readIndexPM10 = 0; } averagePM10 = totalPM10 / numReadingsPM10; Serial.print("PM10 Average: "); Serial.println(averagePM10); totalPM25 = totalPM25 - readingsPM25[readIndexPM25]; readingsPM25[readIndexPM25] = p25; totalPM25 = totalPM25 + readingsPM25[readIndexPM25]; readIndexPM25 = readIndexPM25 + 1; if (readIndexPM25 >= numReadingsPM25) { readIndexPM25 = 0; } averagePM25 = totalPM25 / numReadingsPM25; Serial.print("PM2.5 Average: "); Serial.println(averagePM25); totalCO = totalCO - readingsCO[readIndexCO]; readingsCO[readIndexCO] = ConcentrationINmgm3; totalCO = totalCO + readingsCO[readIndexCO]; readIndexCO = readIndexCO + 1; if (readIndexCO >= numReadingsCO) { readIndexCO = 0; } averageCO = totalCO / numReadingsCO; Serial.print("CO Average: "); Serial.println(averageCO); if (averagePM10 > averagePM25){ AQI = averagePM10; } else { AQI = averagePM25; } if (! Temperature.publish(temperature)) { delay(30000); } if (! Humidity.publish(humidity)) { delay(30000); } if (! PM10.publish(averagePM10)) { delay(30000); } if (! PM25.publish(averagePM25)) { delay(30000); } if (! CO.publish(MQ7ppm)) { delay(30000); } if (! AirQuality.publish(AQI)) { delay(30000); } displayvalues(); delay(10000); //delay(3000); } void displayvalues() { display.clearDisplay(); display.setTextSize(2); display.setCursor(0,15); display.println("CO: "); display.setCursor(40,15); display.println(averageCO); display.setTextSize(1); display.setCursor(68,35); display.println("mg/m3"); display.display(); delay(2000); display.clearDisplay(); display.setTextSize(2); display.setCursor(0,5); display.println("Temp:"); display.setCursor(75,5); display.println(temperature); display.setCursor(101,5); display.println("C"); display.setCursor(0,28); display.println("Humid:"); display.setCursor(75,28); display.println(humidity); display.setCursor(101,28); display.println("%"); display.display(); display.clearDisplay(); delay(2000); display.setTextSize(2); display.setTextColor(WHITE); display.setCursor(0,5); display.println("PM2.5: "); display.setCursor(75,5); display.println(averagePM25); display.setCursor(0,28); display.println("PM10: "); display.setCursor(75,28); display.println(averagePM10); display.setTextSize(1); display.setCursor(90,49); display.println("ug/m3"); display.display(); delay(2000); } void MQTT_connect() { int8_t ret; // Stop if already connected. if (mqtt.connected()) { return; } uint8_t retries = 3; while ((ret = mqtt.connect()) != 0) // connect will return 0 for connected { mqtt.disconnect(); delay(5000); // ждем 5 секунд retries--; if (retries == 0) { // basically die and wait for WDT to reset me while (1); } } } |
4 ответа к “Анализатор качества воздуха с определением частиц PM2.5, PM10 и CO на ESP32”
Можете прислать проект с использованием многофункциональной платы 9 в 1 желательно с кодом программы? Спасибо за раннее.
Так что вы за плату 9 в 1 имеете ввиду, никак не могу понять
Плата DHT11 LM35
Нет, с этой многофункциональной платой у нас, к сожалению, нет проектов на нашем сайте