Introduction: Smart Piscina Com IoT - Ionic, Dweet E DragonBoard

Picture of Smart Piscina Com IoT - Ionic, Dweet E DragonBoard

Introdução

Apresento aqui uma solução para monitoramento e tratamento de piscinas de maneira remota, que poderia ser usado tanto pelo proprietário de um imóvel, como por algum piscineiro que poderia verificar remotamente diversas piscinas as quais ele atende.

O hardware utilizado é baseado na placa DragonBoard da Qualcom e na placa Linker Mezanine da 96boards. Também serão utilizados sensores da Arrow para a placa Linker Mezanine.

Esta não é uma implementação final! Mas sim um desenvolvimento para mostrar como realizar a programação do Hardware, a comunicação com um serviço repositório na nuvem e a criação de um app para acesso e controle do sistema. As funções criadas são:

-Controle do PH da Piscina

-Acionamento da Bomba e monitoramento

-Monitoramento do nível do reservatório de produto para tratamento


Arquitetura IoT

A automação e o controle do tratamento da piscina são realizados pela Dragonboard, com interface do usuário via app Web. Para que isto seja possível, é utilizada a arquitetura demonstrada na imagem, e consiste em:

  1. Os dados são lidos e processados pela Dragonboard
  2. A DragonBoard escreve em um repositório na Web, neste caso o Dweet.io
  3. O Dweet.io disponibiliza as informações lidas para que sejam disponíveis para outras aplicações
  4. Um aplicativo Web desenvolvido no Ionic e Acessa os dados do Dweet.io e apresenta em uma interface HTML para o usuário

Step 1: Configuração Do Hardware

Picture of Configuração Do Hardware

Como dito, foi utilizada a DragonBoard 410c para realizar a automação e controle local da piscina. Junto com a Dragonboard foi instalada um shield da 96boards chamado Linker Mezanine, que facilita o acesso aos IOs da DragonBoard. Este shield tb possui dois conversores A/D para leitura de dados analógicos. Nas imagens existe a configuração utilizada para conexão dos IOs deste exemplo.

  1. Foi considerado o uso de um PHmetro que forneça uma saída proporcional de 0 a 5V para que seja compatível com a entrada do A/D. Caso seja utilizado um com sinal maior, será necessário um divisor resistivo para compatibilizar o sinal com a entrada
  2. No exemplo, ao invés de um PHmetro foi utilizado um potênciometro para simulação do sinal
  3. Para simular o acionamento da bomba foi utilizado um led, que em um projeto real poderia ser um acoplador ótico acionando um TRIAC ou relé
  4. O sensor de rotação da bomba foi simulado com um sensor de toque. Em uma aplicação real poderia ser um sensor no eixo da bomba ou um contado auxiliar do contator que aciona a bomba. Neste caso, em caso de defeito da bomba ou queda do disjuntor, seria possível verificar que a bomba foi acionada e não está girando
  5. O sensor para nível do reservatório é um do tipo "tilt" que deverá ser instalado em uma bóia
  6. Por fim, a doseagem de produto é feita por uma eletroválvula acionada por um relé

Step 2: Preparação Da DragonBoard

Atualização da Placa e instalação das bibliotecas p/ 96boards

A placa DragonBoard vem de fábrica com uma distribuiçaõ Linux chamada Linaro, ela é suficiente em recursos para executar esta aplicação, bastando atualizar a placa e realizar a instalação das bibliotecas da 96boards para interface com a Linker Mezanine.

Uma vez que estamos trabalhando em Linux, podemos acessar o Terminal para realizar os comandos de atualização e instalação de bibliotecas:

Os seguintes comandos realizam a atualização da placa:

sudo apt-get update
sudo apt-get upgrade sudo apt-get dist-upgrade

Para trabalhar com o Python, também realize a instalação de um editor de textos e do interpretador

sudo apt-get install gedit
sudo apt-get install python-pip

Na sequeência serão instaladas as Bibliotecas necessárias. Os comandos devem ser apresentados na ordem a seguir e são críticos para a instalação correta:

sudo apt-get install build-essential autoconf
automake libtool-bin pkg-config python-dev sudo reboot

LIBSOC (Acesso a Linker Mezanine)

git clone  https://github.com/jackmitch/
libsoc.git cd libsoc sudo autoreconf -i sudo ./configure --enable-python=2 --enableboard= dragonboard410c --with-board-configs sudo make sudo make install sudo ldconfig /usr/local/lib sudo reboot

96boards:

git clone  https://github.
com/96boards/96BoardsGPIO.git
cd 96BoardsGPIO/ 
sudo ./autogen.sh
sudo ./configure
sudo make
sudo make install
sudo ldconfig

Quase no fim... mas aproveitamos para instalar tb a biblioteca para acesso a parte analógica da Linker Mezanine:

git clone  https://github.com/doceme/pyspidev.git
cd py-spidev
sudo python setup.py install
sudo ldconfig
sudo reboot

É importante lebrar que na LIBSOC estão as referências de endereçamento da Linker Mezanine, e serve de referência caso precise acessar diretamente um endereço de IO

sudo gedit /usr/local/etc/libsoc.conf

Step 3: Criação Do Objeto No Dweet.io

Picture of Criação Do Objeto No Dweet.io

Como o próprio slogan diz, o dweet.io funciona como um Twitter para IoT, onde as coisas podem enviar e receber dados pela internet de maneira facilitada

Uma característica importante é que o Dweet não necessita de uma autenticação complexa para acessar os dados, o que o torna interessante para início dos testes com IoT.

Para criar o objeto no Dweet basta seguir os seguintes passos:

  1. Acessar o Dweet.io e clicar em "Play"
  2. Na guia POST crie um nom para o obejto no campo "thing"
  3. No campo "content" adicione os dados que serão lidos e enviados. Os dados devem estar no formato "json"
  4. Clique em "Try it out!" e observe o resultado em "Response Body"
  5. Caso queira confirmar o uncionamento da "coisa", vá até o campo "Get Lattest Dweet", insira o nome do obje criado e clique em "Try it out" para verificar a resposta do Dweet.

Para esta aplicação foi criado o objeto "smart_piscina" que tem o seguinte conteúdo:

{
"status_tratamento": 0, "ligadesliga_bomba": 0, "status_bomba":0, "status_reservatorio":0, "PH_setpoint":6, "PH_valor": 4 }

Nele estão todos os dados necessários para comunicação entre a DragonBoard e a aplicação Web.

É importante ressaltar que o nome do objeto deve ser alterado no Dweet e no código fonte das aplicações para evitar que outros dispositivos acessem simultaneamente a coisa gerando resultados indesejados

Step 4: Programação Em Python

Lógica de Funcionamento

O software de Controle da Piscina foi desenvolvido em Python, que é uma linguagem simples e interpretada, ou seja não necessita de compiladores para obter a execução da aplicação.

As funções realizadas pelo software piscina_final.py, que roda na DragonBoard são as seguintes:

  1. Controla o PH, monitorando o valor medido na piscina e comparando com o "Setpoint" definido pelo usuário no Web app. A correção será feita dosando produto através do acionamento da eletroválvula.
  2. O acionamento da eletroválvula é temporizado, ou seja, uma certa quantidade de produto é dosada e a lógica aguarda um determinado período para realizar uma nova dosagem
  3. O controle só é realizado se a bomba da piscina estiver em funcionamento e se o nível do tanque de produto para dosagem estiver ok!
  4. Quando o PH atinge um valor superior ao desejado, a dosagem para automaticamente
  5. Controla a bomba, ligando e desligando a mesma através do Web app, conforme solicitação do usuário
  6. Monitora e informa ao usuário o nível do reservatório do produto de Dosagem
  7. Informa anomalia na bomba, caso seja ligada e não rode.

Antes de apresentar o código, devemos realizar alguns ajustes na Dragonboard para que ela se comunique adequadamente com o Dweet.io

Componentes adicionais

Instalar a biblioteca REQUESTS para realizar funções de POST e GET em HTTP

sudo pip install requests

Copiar o arquivo dweet.py para a mesma pasta onde está a aplicação smart_piscina.py


Código Fonte em Python

A seguir apresentamos o código por partes, nesta primeira são lidas as bibliotecas necessárias, configurados os IOs e realizada a leitura analógica do valor de PH.

import spidev
import time from dweet import Dweet from libsoc import gpio from gpio_96boards import GPIO

COMANDO_BBA = 36 #Comando Bomba NIVEL_PROD = 13 #Chave de nivel DOSAGEM_VVL = 115 #Valvula Dosagem BBA_LIGADA = 24 #Retorno de Bomba ligada GPIO_CS = 18 #Sensor PH (Analogico) pins = ( (GPIO_CS, 'out'),(COMANDO_BBA, 'out'),(DOSAGEM_VVL, 'out'),(NIVEL_PROD, 'in'),(BBA_LIGADA, 'in') )

dweet = Dweet()

spi = spidev.SpiDev() spi.open(0,0) spi.max_speed_hz=10000 spi.mode = 0b00 spi.bits_per_word = 8def readPH(gpio): gpio.digital_write(GPIO_CS, GPIO.HIGH) time.sleep(0.0002) gpio.digital_write(GPIO_CS, GPIO.LOW) r = spi.xfer2([0x01, 0x80, 0x00]) gpio.digital_write(GPIO_CS, GPIO.HIGH) adcout = (r[1] << 8) & 0b1100000000 adcout = adcout | (r[2] & 0xff) adcout = (adcout * 0.014) #converte para PH 0 a 14 return adcout

Na segunda parte, é realizada a leitura do Dweet e os dados armazenados em variáveis globais para as logicas do software:

def le_dweet():                                 #Le qual setpoint para tratamento
global ld_bomba, st_bomba, st_trat, st_res, PH_valor, PH_SP resposta = dweet.latest_dweet(name="smart_piscina") ld_bomba = resposta['with'][0]['content']['ligadesliga_bomba'] st_bomba = resposta['with'][0]['content']['status_bomba'] st_trat = resposta['with'][0]['content']['status_tratamento'] st_res = resposta['with'][0]['content']['status_reservatorio'] PH_valor = resposta['with'][0]['content']['PH_valor'] PH_SP = resposta['with'][0]['content']['PH_setpoint'] return ld_bomba, st_bomba, st_trat, st_res, PH_valor, PH_SP

A terceira parte é a função que realiza o tratamento da piscina, com a lógica para acionamento baseada no PH, nível do reservatório e bomba ligada. Note que as variáveis de monitoramento são as mesmas lidas pelo Dweet, desta forma conseguimos atualizar os valores na lógica para que despois sejam novamente enviados ao serviço.

def tratamento():
global st_trat, st_res, st_bomba st_res = gpio.digital_read(NIVEL_PROD) st_bomba = gpio.digital_read(BBA_LIGADA) if (PH_valor < PH_SP) and ( st_res == 1) and ( st_bomba == 1): gpio.digital_write(DOSAGEM_VVL, GPIO.HIGH) time.sleep(2) #tempo da dosagem do produto gpio.digital_write(DOSAGEM_VVL, GPIO.LOW) time.sleep(1) #espera entre dosagens st_trat = 1 print("TRATAMENTO lIGADO") else: gpio.digital_write(DOSAGEM_VVL, GPIO.LOW) st_trat = 0 print("TRATAMENTO DESlIGADO") return st_trat, st_res

A quarta e última parte é o looping de execução da lógica. A ordem onde as subrotinas são chamadas é importante para que os dados lidos pelo Dweet sejam atualizados e depois enviados para a correta visualização no Web app.

if __name__=='__main__':
with GPIO(pins) as gpio: while True: le_dweet() tratamento() PH_valor = round(readPH(gpio), 2) if ld_bomba == 1: gpio.digital_write(COMANDO_BBA, GPIO.HIGH) print("Bomba Ligada") else: gpio.digital_write(COMANDO_BBA, GPIO.LOW) print("Bomba Desligada") print("Valor do PH = %d" % PH_valor) print("Valor do SP PH = %d" % PH_SP) print("") dweet.dweet_by_name(name="smart_piscina", data={"ligadesliga_bomba":ld_bomba, "status_bomba":st_bomba, "status_tratamento":st_trat, "status_reservatorio":st_res, "PH_valor":PH_valor, "PH_setpoint":PH_SP}) time.sleep(10)

Step 5: Desenvolvimento Do APP - Ambiente Hídrido

Plataforma híbrida Ionic

O aplicativo para controle da piscina será desenvolvido utilizando uma plataforma híbrida, ou seja, fazemos a abstração do hardware que o app será utilizado e desenvolvemos um projeto utilizando HTML, CSS e Javascript que posteriormente pode ser convertido em um app para uma plataforma específica como Android ou IOS.

Neste caso utilizamos o IONIC, que funciona baseado na plataforma Cordova, que permite visualizar e testar a aplicação através da renderização na mesma na tela de um Web Browser.

Para o Desenvolvimento do app, utilizaremos a linguagem HTML e Typescript. o IONIC também permite a utilização do framework Angular para trabalhar ocs componentes como Models e Controllers.

Instalação do Ambiente de Desenvolvimento

O desenvolvimento do app será realizado em um computador pessoal, e não na placa DragonBoard. Iniciaremos com a instalçaão do node.js, necessário apra o funcionamento do Ionic

Acessar o site https://nodejs.org/en/ e fazer o Download da última versão do node.js

Após concluída a instalação, o gerencador de pacotes NPM deve ter sido instalado durante a instalação do node.js. Ele permitirá realizar a instalação do Ionic.

No prompt de comando do Windows realize a instalação com os seguintes comandos:

npm install –g cordova ionic
npm install –g cordova

Para testar o ionic, o seguinte comando pode ser executado e se estiver tudo ok retornará a versão instalada:

ionic –v

Criação da aplicação no Ionic

Não, não tem uma interface gráfica bonita. Tem que criar o app utilizando a linha de comandos. Mas depois a facilidade de uso compensa.

Para criar uma nova aplicação, neste caso a smart_piscina, digitamos o seguinte comando:

ionic start smart_piscina blank

Será criada uma nova aplicação em branco que estará salva no diretório:

C:\Usuários\Nome do usuário\smart_piscina

Para testar o código:

cd smart_piscina 
ionic serve

Será aberta uma tela no navegador padrão mostrando a aplicação em branco

Step 6: Desenvolvimento Do APP - Edição Da Aplicação

Picture of Desenvolvimento Do APP - Edição Da Aplicação

A edição da aplicação em branco gerada pelo Ionic será realizada no Visual Studio Code, aplicativo gratuito de programação desenvolvido pela Microsoft e que pode ser baixado no site: https://code.visualstudio.com/download

Os códigos alterados são apresentados a seguir, mas também estão disponíveis para download.

Interface

A interface com o usuário será editada no arquivo home.html. Note que as tags utilizadas são próprias do Ionic e contém alguns parâmetros inseridos utilizando os recursos do framework Angular. Os recursos do Angular são utilizados no botão de acionamento da bomba e na entrada do valor de Setpoint do PH. Não é possível apresentar o código aqui por uma limitação do Instructables, que apaga as tags. De qualquer forma está disponível no arquivo compactado para download.

Processamento

As fuções referentes a leitura e escrita de dados no Dweet e lógicas em geral para o correto funcionamento da interface estão no arquivo home.ts desenvolvido em Typescript, liguagem muito semelhante ao Javascript

import { Component } from '@angular/core';
import { NavController } from 'ionic-angular';

//É preciso importar o provideer. import { DweetProvider } from '../../providers/dweet/dweet';

@Component({ selector: 'page-home', templateUrl: 'home.html' })

export class HomePage {

constructor(public navCtrl: NavController, private DweetProvider: DweetProvider) { }

//Declarações de Variáveis public respostaDweet: string=""; public status_tratamento: string="danger"; public st_trat = 0; public status_bomba: string="danger"; public st_bba = 0; public status_reservatorio: string="danger"; public st_res = 0; public locais = Array(); public PH_val = 0; public SP_PH = 0;

//Model do botão de ligar bomba public bomba_model = { checked: false, name: "Ligar Bomba" }

ionViewDidLoad () { //buscando os dados no Dweet e salvando nas variáies locais this.DweetProvider.getLastestDweet("smart_piscina").subscribe( data=>{ const response = (data as any); const objeto_retorno = JSON.parse(response._body); this.locais = objeto_retorno.with[0].content; this.bomba_model.checked = objeto_retorno.with[0].content.ligadesliga_bomba; this.st_bba = objeto_retorno.with[0].content.status_bomba; this.st_trat = objeto_retorno.with[0].content.status_tratamento; this.st_res = objeto_retorno.with[0].content.status_reservatorio; this.PH_val = objeto_retorno.with[0].content.PH_valor; this.SP_PH = objeto_retorno.with[0].content.PH_setpoint; console.log(this.locais); }, error => { console.log(error); } ) //Atualiza icones de Status this.status_bomba = ((this.st_bba == 1) ? "secondary" : "danger"); this.status_tratamento = ((this.st_trat == 1) ? "secondary" : "danger"); this.status_reservatorio = ((this.st_res == 1) ? "secondary" : "danger"); }

//Botão Atualizar update() { this.ionViewDidLoad(); }

//Liga Desliga Bomba liga_des_bomba(){ this.dweetPost() }

atualiza_sp(){ this.dweetPost() }

dweetPost(){ //Converte dados do botão de Boolean para inteiro const ld_bba = ((this.bomba_model.checked == true) ? 1 : 0);

//Envia dados para o Dweet.io const json_dweet = {"ligadesliga_bomba": ld_bba, "status_bomba": this.st_bba, "status_tratamento": this.st_trat, "status_reservatorio": this.st_res, "PH_valor": this.PH_val, "PH_setpoint": this.SP_PH}; this.DweetProvider.setDweet("smart_piscina",json_dweet).subscribe( data=>{ console.log(data); }, error=> { console.log(error); } ) } }

Dweet provider

É necessário criar um provider para realizar a comunicação HTTP com o Dweet. Isto é feito através do Ionic com o seguinte comando no prompt de comando:

ionic generate provider dweet

Neste momento é gerado o arquivo dweet.ts que deverá ter os comandos referentes a conexão com o Dweet e realização das funções de GET e POST. O código necessário é exibido a seguir:

import { Http } from '@angular/http';
import { Injectable } from '@angular/core'; import 'rxjs/add/operator/map';

/* Generated class for the DweetProvider provider.

See https://angular.io/guide/dependency-injection for more info on providers and Angular DI. */ @Injectable() export class DweetProvider {

private baseUrl = "https://dweet.io:443/"

constructor(public http: Http) { console.log('Hello DweetProvider Provider'); }

//Método responsável por buscar as informações no Dweet. getLastestDweet(thing: string) { const url_get = this.baseUrl + "get/latest/dweet/for/" + thing; console.log(url_get); return this.http.get(url_get); }

//Método resposnsável por modificar os dados no Dweet. setDweet(thing, body) { return this.http.post(this.baseUrl + "dweet/for/"+ thing, body); }

}

Por fim, é necessário realizar uma modificação no arquivo app.module.ts para que carregue adequadamente os componentes HTTP para o funcionamento do Dweet Provider:

import { BrowserModule } from '@angular/platform-browser';
import { ErrorHandler, NgModule } from '@angular/core'; import { IonicApp, IonicErrorHandler, IonicModule } from 'ionic-angular'; import { SplashScreen } from '@ionic-native/splash-screen'; import { StatusBar } from '@ionic-native/status-bar';

import { HttpModule } from '@angular/http'; import { MyApp } from './app.component'; import { HomePage } from '../pages/home/home'; import { DweetProvider } from '../providers/dweet/dweet';

@NgModule({ declarations: [ MyApp, HomePage ], imports: [ BrowserModule, IonicModule.forRoot(MyApp), //Importar o modulo HTTP usado pelo Dweet. HttpModule ], bootstrap: [IonicApp], entryComponents: [ MyApp, HomePage ], providers: [ StatusBar, SplashScreen, {provide: ErrorHandler, useClass: IonicErrorHandler}, DweetProvider ] }) export class AppModule {}

Ufa!

Salve tudo e teste a aplicação através do comando:

ionic serve

Step 7: Colocando Tudo Para Funcionar!!

1.Iniciando o Dweet:

No site Dweet.io, crie o objeto conform descrito no passo 3

2.Iniciando a aplicação na DragonBoard:

Abra o Terminal no Linaro, acesse a pasta onde está a aplicação smart_home.py e digite o comando:

sudo python smarthome.py

3.Iniciando a aplicação no Ionic:

Abra o prompt de comando, acesse a pasta onde está o aplicativo criado no Ionic e digite o comando

ionic serve

Step 8:

Comments

About This Instructable

24views

0favorites

License:

More by rxidieh:Smart Piscina Com IoT - Ionic, Dweet E DragonBoard
Add instructable to: