Оглавление:

Pool Pi Guy - управляемая искусственным интеллектом система сигнализации и мониторинг бассейна с использованием Raspberry Pi: 12 шагов (с изображениями)
Pool Pi Guy - управляемая искусственным интеллектом система сигнализации и мониторинг бассейна с использованием Raspberry Pi: 12 шагов (с изображениями)

Видео: Pool Pi Guy - управляемая искусственным интеллектом система сигнализации и мониторинг бассейна с использованием Raspberry Pi: 12 шагов (с изображениями)

Видео: Pool Pi Guy - управляемая искусственным интеллектом система сигнализации и мониторинг бассейна с использованием Raspberry Pi: 12 шагов (с изображениями)
Видео: Альманах по автоматизации и системе “умный дом” на примере элитного загородного дома от девелопера 2024, Июль
Anonim
Pool Pi Guy - управляемая искусственным интеллектом система сигнализации и мониторинг бассейна с использованием Raspberry Pi
Pool Pi Guy - управляемая искусственным интеллектом система сигнализации и мониторинг бассейна с использованием Raspberry Pi

Бассейн дома - это весело, но требует большой ответственности. Больше всего меня беспокоит отслеживание того, находится ли кто-нибудь возле бассейна без присмотра (особенно дети младшего возраста). Мое самое большое раздражение - следить за тем, чтобы линия воды в бассейне никогда не спускалась ниже входа насоса, что приведет к высыханию насоса и его разрушению, что требует ремонта в $ $$.

Недавно я понял, как использовать Raspberry Pi с OpenCV и TensorFlow, а также датчик уровня воды и соленоидный клапан для решения обеих проблем - и получайте удовольствие от этого!

Оказывается, это также отличная система сигнализации - активируемая движением, управляемая искусственным интеллектом, бесконечно настраиваемая.

Давайте погрузимся.

Шаг 1: грандиозный план

В этом руководстве мы покажем, как:

  1. Настройте Raspberry Pi с OpenCV и TensorFlow
  2. Подключите веб-камеру с помощью длинного USB-кабеля
  3. Напишите алгоритм OpenCV для обнаружения движения
  4. Используйте TensorFlow для обнаружения объектов
  5. Настройте веб-сервер на Raspberry Pi, чтобы показывать интересные изображения
  6. Интегрируйтесь с IFTTT, чтобы запускать мобильные оповещения в случае обнаружения человека
  7. Прикрепите шляпу реле к Raspberry Pi и подключите ее к соленоидному клапану, который будет добавлять воду в бассейн.
  8. Присоедините датчик уровня воды к Raspberry Pi и подключитесь к нему с помощью GPIO Pi.
  9. Напишите код, чтобы склеить все вместе

Шаг 2: список покупок

Список покупок
Список покупок

Все компоненты легко доступны на Amazon. Не стесняйтесь экспериментировать и обмениваться компонентами - это половина удовольствия!

  1. Raspberry Pi
  2. Блок питания Raspberry Pi (не экономьте здесь)
  3. Карта памяти (чем больше, тем лучше)
  4. Корпус (он достаточно большой, чтобы вместить Pi и HAT)
  5. Веб-камера USB (подойдет любая веб-камера, но вам нужна такая, которая дает хорошие изображения и хорошо балансирует освещение)
  6. Удлинительный USB-кабель (при необходимости - измерьте расстояние между Pi и местом, где вы бы разместили камеру)
  7. Плата реле HAT (у этого есть 3 реле, и нам нужно только одно, но скоро вы найдете применение другим!)
  8. Соленоид
  9. Штуцер соленоида 1 и штуцер 2 (это действительно зависит от того, на что вы устанавливаете соленоид, но они сработали для меня)
  10. Электропитание соленоида (подойдет любой 24 В переменного тока)
  11. Кабель (опять же, подойдет почти любой двухжильный кабель - ток минимальный)
  12. Поплавковый выключатель уровня воды (это всего лишь пример, проверьте, что можно легко подключить к вашему бассейну)
  13. Некоторые перемычки и соединители проводов

Шаг 3: Настройте Raspberry Pi

Настройте свой Raspberry Pi
Настройте свой Raspberry Pi

Raspberry Pi - отличный маленький компьютер. Он стоит всего 35 долларов, работает стабильно и имеет множество совместимого программного и аппаратного обеспечения. Настроить довольно просто:

  1. Отформатируйте SD-карту. Это требует особой осторожности - Raspberry Pi может загружаться только с SD-карты в формате FAT. Следуйте этим инструкциям.
  2. Подключите Raspberry Pi к USB-клавиатуре и мыши, а также к дисплею HDMI, и следуйте инструкциям в руководстве Raspberry Pi NOOBS. Обязательно настройте Wi-Fi и включите доступ по SSH. Не забудьте установить пароль для учетной записи Pi по умолчанию.
  3. В вашей домашней сети настройте статический IP-адрес для Raspberry Pi - это упростит использование SSH.
  4. Убедитесь, что на вашем настольном компьютере / ноутбуке установлен ssh-клиент. Для ПК я бы порекомендовал Putty, которую вы можете установить отсюда.
  5. Отключите USB и HDMI от Raspberry Pi, перезагрузите его и подключитесь по ssh - если все сработало, вы должны увидеть что-то вроде этого:

Linux raspberrypi 4.14.98-v7 + # 1200 SMP Вт, 12 фев, 20:27:48 GMT 2019 armv7l

Программы, входящие в состав системы Debian GNU / Linux, являются бесплатными; точные условия распространения для каждой программы описаны в отдельных файлах в / usr / share / doc / * / copyright. Debian GNU / Linux поставляется с СОВЕРШЕННО ОТСУТСТВИЕМ ГАРАНТИЙ, насколько это разрешено действующим законодательством. Последний вход: Mon May 13 10:41:40 2019 from 104.36.248.13 pi @ raspberrypi: ~ $

Шаг 4: Настройте OpenCV

Настроить OpenCV
Настроить OpenCV

OpenCV - это потрясающая коллекция функций обработки изображений для компьютерного зрения. Это позволит нам читать изображения с веб-камеры, манипулировать ими, находить области движения, сохранять их и многое другое. Настройка на Raspberry Pi несложная, но требует некоторого ухода.

Начните с установки virtaulenvwrapper: мы будем использовать python для выполнения всего нашего программирования, а virtualenv поможет нам сохранить зависимости отдельно для OpenCV и TensorFlow по сравнению с Flask или GPIO:

pi @ raspberrypi: ~ $ sudo pip install virtualenvwrapper

Теперь вы можете выполнить «mkvirtualenv», чтобы создать новую среду, «workon», чтобы поработать над ней, и многое другое.

Итак, давайте создадим среду для наших манипуляций с изображениями с Python 3 в качестве интерпретатора по умолчанию (это 2019 год, нет причин придерживаться более старого Python 2):

pi @ raspberrypi: ~ $ mkvirtualenv cv -p python3

… (Cv) pi @ raspberrypi: ~

Теперь мы готовы установить OpenCV. В основном мы будем следовать отличному руководству в Learn OpenCV. В частности, следуйте их шагам 1 и 2:

sudo apt -y updatesudo apt -y upgrade ## Установить зависимости sudo apt-get -y install build-essential checkinstall cmake pkg-config yasm sudo apt-get -y install git gfortran sudo apt-get -y install libjpeg8-dev libjasper- dev libpng12-dev sudo apt-get -y install libtiff5-dev sudo apt-get -y install libtiff-dev sudo apt-get -y install libavcodec-dev libavformat-dev libswscale-dev libdc1394-22-dev sudo apt-get - y установить libxine2-dev libv4l-dev cd / usr / include / linux sudo ln -s -f../libv4l1-videodev.h videodev.h sudo apt-get -y install libgstreamer0.10-dev libgstreamer-plugins-base0. 10-dev sudo apt-get -y install libgtk2.0-dev libtbb-dev qt5-default sudo apt-get -y install libatlas-base-dev sudo apt-get -y install libmp3lame-dev libtheora-dev sudo apt-get -y установить libvorbis-dev libxvidcore-dev libx264-dev sudo apt-get -y install libopencore-amrnb-dev libopencore-amrwb-dev sudo apt-get -y install libavresample-dev sudo apt-get -y install x264 v4l-utils sudo apt-get -y установить libprotobuf -dev protobuf-compiler sudo apt-get -y install libgoogle-glog-dev libgflags-dev sudo apt-get -y install libgphoto2-dev libeigen3-dev libhdf5-dev doxygen sudo apt-get install libqtgui4 sudo apt-get install libqt4- тестовое задание

Теперь мы можем просто установить OpenCV с привязками Python внутри cv virtualenv (вы все еще в нем, верно?), Используя

pip установить opencv-contrib-python

Вот и все! У нас установлен OpenCV на Raspberry Pi, он готов снимать фото и видео, манипулировать ими и быть крутым.

Убедитесь в этом, открыв интерпретатор python и импортировав opencv, и убедитесь, что ошибок нет:

(cv) pi @ raspberrypi: ~ $ python

Python 3.5.3 (по умолчанию, 27 сентября 2018 г., 17:25:39) [GCC 6.3.0 20170516] в Linux Введите «help», «copyright», «credits» или «license» для получения дополнительной информации. >>> импортировать cv2 >>>

Шаг 5: Настройте TensorFlow

Настроить TensorFlow
Настроить TensorFlow

TensorFlow - это фреймворк машинного обучения / искусственного интеллекта, разработанный и поддерживаемый Google. Он имеет обширную поддержку моделей глубокого обучения для различных задач, включая обнаружение объектов на изображениях, и теперь его довольно просто установить на Raspberry Pi. Производительность его легких моделей на крошечном Pi составляет около 1 кадра в секунду, что вполне достаточно для такого приложения, как наше.

В основном мы будем следовать отличному руководству от Edje Electronics, с изменениями, которые стали возможны благодаря более поздним дистрибутивам TensorFlow:

pi @ raspberrypi: ~ $ workon cv

(cv) pi @ raspberrypi: ~ $ pip install tensorflow (cv) pi @ raspberrypi: ~ $ sudo apt-get install libxml2-dev libxslt-dev (cv) pi @ raspberrypi: ~ $ pip install Pillow lxml jupyter matplotlib cython (cv) pi @ raspberrypi: ~ $ sudo apt-get install python-tk

Теперь нам нужно скомпилировать protobuf Google. Просто следуйте инструкциям на шаге 4 того же отличного руководства.

Наконец, клонируйте и настройте определения модели TensorFlow - следуйте шагу 5 в руководстве Edje Electronics.

Не стесняйтесь следовать их примеру на шаге 6, это отличное введение в обнаружение объектов на Raspberry Pi.

Шаг 6: Обнаружение движения с использованием OpenCV

Давайте начнем с тестирования того, что OpenCV может взаимодействовать с нашей веб-камерой: ssh в Raspberry Pi, перейдите к cv virtualenv (workon cv), откройте интерпретатор python (просто введите python) и введите следующие команды python:

импорт cv2

cap = cv2. VideoCapture (0) cap.set (cv2. CAP_PROP_FRAME_WIDTH, 1920) cap.set (cv2. CAP_PROP_FRAME_HEIGHT, 1080) ret, frame = cap.read () print ('Размер кадра чтения: {} x {}'.format (frame.shape [1], frame.shape [0])

Если повезет, вы увидите, что OpenCV смог прочитать кадр HD с камеры.

Вы можете использовать cv2.imwrite (путь, фрейм) для записи этого фрейма на диск и sftp его обратно, чтобы получить реальный вид.

Стратегия обнаружения движения довольно проста:

  1. Работайте с кадрами с более низким разрешением - здесь нет необходимости работать с Full HD
  2. Кроме того, размывайте изображения, чтобы обеспечить как можно меньше шума.
  3. Держите среднее значение последних N кадров. Для этого приложения, где частота кадров составляет около 1 кадра в секунду (просто потому, что TensorFlow занимает некоторое время на кадр), я обнаружил, что N = 60 дает хорошие результаты. И поскольку тщательная реализация не требует большего количества ЦП с большим количеством кадров, это нормально (требуется больше памяти, но это незначительно, когда мы работаем с кадрами с более низким разрешением)
  4. Вычтите текущее изображение из скользящего среднего (просто будьте осторожны с вводом - вам нужно разрешить положительные и отрицательные значения [-255.. 255], поэтому кадр необходимо преобразовать в int)
  5. Вы можете выполнить вычитание при преобразовании серой шкалы кадра (и среднего значения) или сделать это отдельно для каждого из каналов RGB, а затем объединить результаты (это стратегия, которую я выбрал, делая ее чувствительной к изменениям цвета)
  6. Используйте порог на дельте и удалите шум за счет эрозии и расширения.
  7. Наконец, обратите внимание на контуры областей с дельтой - в этих областях произошло движение, и текущее изображение отличается от среднего значения предыдущих изображений. При необходимости мы можем найти ограничивающие рамки для этих контуров.

Я инкапсулировал код для этого в классе Python DeltaFinder, который вы можете найти в моем github здесь

Шаг 7: обнаружение объектов с помощью TensorFlow

Если вы следовали процедуре установки TensorFlow, вы уже проверили, что у вас установлен и работает TensorFlow.

С целью обнаружения людей в общей уличной сцене модели, которые предварительно обучены на наборе данных COCO, работают достаточно хорошо - это именно та модель, которую мы загрузили в конце установки TensorFlow. Нам просто нужно использовать его для вывода!

Опять же, чтобы упростить задачу, я инкапсулировал загрузку модели и логический вывод в класс Python TFClassify, который вы можете найти здесь.

Шаг 8: Настройте веб-сервер на Raspberry Pi

Настройте веб-сервер на Raspberry Pi
Настройте веб-сервер на Raspberry Pi

Самый простой способ получить доступ к результатам обнаружения объектов - это использовать веб-браузер, поэтому давайте настроим веб-сервер на Raspberry Pi. Затем мы можем настроить его для обслуживания изображений из заданного каталога.

Существует несколько вариантов структуры веб-сервера. Я выбрал Flask. Его очень легко настраивать и легко расширять с помощью Python. Поскольку необходимый нам «масштаб» тривиален, этого было более чем достаточно.

Я предлагаю установить его в новом virtualenv, поэтому:

pi @ raspberrypi: ~ $ mkvirtualenv webserv

(webserv) pi @ raspberrypi: ~ $ pip установить Flask

Обратите внимание, что при нормальной настройке сети он будет доступен только в том случае, если ваш браузер находится в той же беспроводной локальной сети, что и ваш Raspberry Pi. Вы можете создать конфигурацию сопоставления портов / NAT на своем интернет-маршрутизаторе, чтобы разрешить внешний доступ, но я не рекомендую этого делать. Код, который я написал, не пытается обеспечить безопасность, которая вам понадобится при разрешении общего доступа в Интернет к вашему Raspberry Pi.

Проверьте свою установку, следуя руководству по быстрому запуску Flask.

Шаг 9. Мобильные уведомления от Raspberry Pi с использованием IFTTT

Мобильные уведомления от Raspberry Pi с использованием IFTTT
Мобильные уведомления от Raspberry Pi с использованием IFTTT

Я очень хочу получать мобильные уведомления о событиях. В этом случае при обнаружении человека и при низком уровне воды. Самый простой способ, который я нашел для этого, без необходимости писать собственное мобильное приложение, - это использовать IFTTT. IFTTT означает «Если это, то это» и позволяет множеству типов событий запускать многие типы действий. В нашем случае нас интересует триггер IFTTT Maker Webhook. Это позволяет нам запускать действие IFTTT, отправляя HTTP-запрос POST на сервер IFTTT со специальным ключом, назначенным нашей учетной записи, вместе с данными, которые определяют, что произошло. Действия, которые мы предпринимаем, могут быть такими же простыми, как создание уведомления на нашем мобильном устройстве с помощью мобильного приложения IFTTT, или что-то более сложное.

Вот как это сделать:

  1. Создайте учетную запись IFTTT на ifttt.com
  2. Войдя в систему, перейдите на страницу настроек службы Webhook и введите URL-адрес в своем браузере (например, https://maker.ifttt.com/use/. На этой веб-странице будет показан ваш ключ и URL-адрес, который будет использоваться для запуска действий..
  3. Создайте апплет IFTTT, который будет генерировать мобильное уведомление при срабатывании Webhook с подробной информацией о событии:

    1. Щелкните «Мои апплеты», а затем «Новый апплет».
    2. Щелкните «+ this» и выберите «webhooks». Нажмите «Получить веб-запрос», чтобы перейти к деталям.
    3. Дайте вашему мероприятию название, например «PoolEvent» и нажмите «Создать триггер».
    4. Нажмите «+ это» и выберите «уведомления». Затем выберите «Отправить подробное уведомление из приложения IFTTT».
    5. В качестве заголовка выберите что-то вроде «PoolPi».
    6. В поле «сообщение» напишите «Обнаружен пул Pi:» и нажмите «добавить ингредиент».. «Значение1».
    7. Вернитесь к URL-адресу, который вы скопировали на шаге 2. Он покажет URL-адрес, который будет использоваться для вызова вашего недавно созданного апплета. Скопируйте этот URL, заменив заполнитель {событие} именем события (в нашем примере PoolEvent)
  4. Загрузите, установите и войдите в приложение IFTTT для своего мобильного устройства.
  5. Запустите этот скрипт python на своем Raspberry Pi, чтобы убедиться, что он работает (обратите внимание, что запуск на вашем мобильном устройстве может занять несколько секунд или минут):

запросы на импорт

request.post ('https://maker.ifttt.com/trigger/PoolEvent/with/key/', json = {"value1": "Hello Notifications"})

Шаг 10: Добавьте шляпу реле к Raspberry Pi и подключите ее к соленоидному клапану

Добавьте шляпу реле к Raspberry Pi и подключите ее к соленоидному клапану
Добавьте шляпу реле к Raspberry Pi и подключите ее к соленоидному клапану
Добавьте шляпу реле к Raspberry Pi и подключите ее к соленоидному клапану
Добавьте шляпу реле к Raspberry Pi и подключите ее к соленоидному клапану
Добавьте шляпу реле к Raspberry Pi и подключите ее к соленоидному клапану
Добавьте шляпу реле к Raspberry Pi и подключите ее к соленоидному клапану

Прежде чем продолжить этот шаг, ВЫКЛЮЧИТЕ свой Raspberry Pi: ssh и введите «sudo shutdown now», затем отключите его от питания.

Наша цель - включать и выключать подачу питания на электромагнитный клапан - клапан, который может открывать или закрывать подачу воды на основе напряжения 24 В переменного тока, которое он получает от источника питания. Реле - это электрические компоненты, которые могут размыкать или замыкать цепь на основе цифрового сигнала, который может обеспечить Raspberry Pi. Что мы здесь делаем, так это подключаем реле к этим цифровым сигнальным контактам Raspberry Pi и заставляем его замкнуть цепь между источником питания 24 В переменного тока и соленоидным клапаном.

Контакты на Raspberry Pi, которые могут действовать как цифровой ввод или вывод, называются GPIO - универсальный ввод / вывод, и они представляют собой ряд из 40 выводов на стороне Pi. Выключите Pi и плотно вставьте в него шляпу реле. В выбранной мной шляпе 3 реле, и мы будем использовать только одно из них. Представьте себе все, что вы можете сделать с двумя другими:)

Теперь снова включите Raspberry Pi. Красный светодиодный индикатор питания на реле HAT должен загореться, указывая на то, что он получает питание от Pi через GPIO. Давайте проверим, можем ли мы управлять им: снова подключите ssh к Pi, введите python и введите:

импорт гпиозеро

dev = gpiozero. DigitalOutputDevice (26, начальное_значение = True) dev.off ()

Вы должны услышать слышимый щелчок, указывающий на то, что реле задействовано, и увидеть, как загорится светодиод, показывающий, что первое реле находится в подключенном положении. Теперь вы можете ввести

dev.on ()

Это переключит реле в положение «выключено» (странно, я знаю…) и выйдет () из python.

Теперь с помощью соединительных кабелей и более длинного кабеля подключите реле между источником питания 24 В и электромагнитным клапаном. См. Схему. Наконец, подключите электромагнитный клапан к водопроводному крану с помощью переходников и приготовьтесь все это проверить, повторив приведенные выше команды - они должны включать и выключать воду.

Присоедините шланг к электромагнитному клапану, а другой конец опустите глубоко в бассейн. Теперь у вас есть управляемая компьютером система доливки бассейна, и пора подключить датчик, чтобы сообщить ему, когда запускать.

Шаг 11: Подключите датчик уровня воды

Подключите датчик уровня воды
Подключите датчик уровня воды
Подключите датчик уровня воды
Подключите датчик уровня воды
Подключите датчик уровня воды
Подключите датчик уровня воды
Подключите датчик уровня воды
Подключите датчик уровня воды

Датчик уровня воды - это просто поплавок, который подключает электрическую цепь, когда поплавок опущен, и размыкает ее, когда он поднимается. Если вы вставите его в бассейн на нужной высоте, поплавок будет подниматься, когда уровень воды будет достаточным, но упадет, когда воды недостаточно.

Чтобы Raspberry Pi знал состояние датчика уровня воды, нам нужно, чтобы Pi обнаруживал открытую или замкнутую цепь. К счастью, это очень просто: те же разъемы GPIO, которые мы используем в качестве цифровых выходов для управления реле, могут действовать как входы (отсюда и I в GPIO). В частности, если мы подключим один провод датчика к + 3,3 В на разъеме GPIO, а другой провод датчика - к контакту, который мы настроим как нисходящий вход (это означает, что он обычно будет на уровне напряжения GND), этот контакт будет измерять цифровое «высокое» или «включено» напряжение только тогда, когда датчик уровня воды замыкает цепь - когда уровень воды низкий. В качестве входа я использовал вывод 16 GPIO, который отмечен на изображении выше.

Код Python для настройки пина в качестве входа и проверки его текущего состояния:

импорт гпиозеро

level_input = gpiozero. Button (16) water_low = level_input.is_pressed

Одна потенциальная проблема заключается в том, что когда датчик просто меняет состояние, он будет быстро колебаться между включенным и выключенным состояниями. Решение этой проблемы известно как «устранение неполадок», и прежде чем предпринимать какие-либо действия, требуется согласованное изменение состояния. В библиотеке GPIOZERO есть код для этого, но по какой-то причине этот код мне не подошел. Я написал простой цикл для запуска предупреждений IFTTT при обнаружении последовательного изменения состояния, который вы можете найти в моем репозитории здесь.

Шаг 12: напишите код, чтобы связать все вместе

Напишите код, чтобы связать все вместе
Напишите код, чтобы связать все вместе

Вот и все. Наша настройка завершена. Вы можете написать свой собственный код, чтобы связать все вместе в единую систему, или использовать предоставленный мной код. Для этого просто создайте структуру каталогов и клонируйте репозиторий, например:

mkdir poolpi

cd poolpi git clone

Затем отредактируйте файлы с именем ifttt_url.txt в каталогах motion_alert и water_level, чтобы получить URL-адрес вашего собственного веб-хука IFTTT с вашим секретным ключом. Вы можете использовать два разных веб-хука для разных действий.

Наконец, мы хотим, чтобы этот код запускался автоматически. Самый простой способ сделать это - использовать службу Linux crontab. Мы можем добавить несколько строк crontab для двух основных задач:

  1. Запускаем наши три программы: детектор объектов, датчик уровня воды и веб-сервер при каждой перезагрузке.
  2. Очистите выходной каталог, удалив старые изображения и старые видеофайлы (я решил удалить файлы старше 1 дня и изображения старше 7 дней - не стесняйтесь экспериментировать)

Для этого введите crontab -e, который откроет ваш текстовый редактор nano. Добавьте следующие строки в конец файла:

0 1 * * * find / home / pi / poolpi / output -type f -name "*.avi" -mtime +1 -delete

0 2 * * * find / home / pi / poolpi / output -type f -name "*.jpg" -mtime +7 -delete @reboot python3 /home/pi/poolpi/motion_alert/webserv/webserv.py @reboot python3 /home/pi/poolpi/motion_alert/motion_obj_alert.py @reboot python3 /home/pi/poolpi/water_level/test_water_level.py

Наконец, перезагрузите Raspberry Pi. Теперь он готов, чтобы ваш бассейн был наполнен и оставался в безопасности.

Повозитесь с настройкой, кодом и не забудьте пометить мой репозиторий на github и прокомментировать инструкции, если вы сочтете их полезными. Я всегда хочу узнать больше.

Удачи!

IoT Challenge
IoT Challenge
IoT Challenge
IoT Challenge

Второе место в конкурсе IoT Challenge

Рекомендуемые: