quarta-feira, 7 de fevereiro de 2018

NODEMCU+MQTT+ANDROID = IOT (PARTE2)


        Olá, pessoal que acompanha o blog lhes trago uma versão melhorada do ultimo exemplo postado, para isto organizei os componentes na protoboard e coloquei um botão, e um sensor LM35 para medir temperatura.Veja abaixo como ficou o novo protótipo.
//colocar foto
         Apesar do LM35 funcionar 4 a 30V(segundo o datasheet) com 3,3V funcionou bem(pelo menos pra medir temperatura ambiente,assim não precisou de nenhum circuito externo além do sensor.
         Usei um botão do tipo NA de forma que a entrada selecionada ficasse o tempo todo em nível alto indo para nível baixo quando pressionado.
        Adicionei mais um led(led amarelo) para indicar que o programa está rodando.Note que é possível monitorar pela porta serial tudo que acontece(caso queira).

O Código fonte :
//Autor: Aguivone    -  microcontroladores-C
//Descricao: Placa para acionar 4 reles usado um servidor MQTT.
//Data: 18/01/18
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////

#include <ESP8266WiFi.h>
#include <PubSubClient.h> // essa lib deve ser adicionada em seu programa do arduino
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
//variaveis usadas na inicialização da wifi
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
const char* ssid = "nome da wifi"; //Aqui o nome da sua rede local wifi
const char* password =  "senha"; // Aqui a senha da sua rede local wifi
const char* mqttServer = "algumacoisa.cloudmqtt.com"; // Aqui o endereço do seu servidor fornecido pelo site 
const int mqttPort =16000; // Aqui mude para sua porta fornecida pelo site
const char* mqttUser = "xxxxxx"; //  Aqui o nome de usuario fornecido pelo site
const char* mqttPassword = "hfjuytsgeh"; //  Aqui sua senha fornecida pelo site
unsigned long  tempo_rot = 1000;// aprox 1s
unsigned int est_ant_bot = 0;//guarda estado do botão pra não enviar a todo momento uma nova informação
WiFiClient espClient;
PubSubClient client(espClient);
/*
Equivalencia das saidas Digitais entre nodeMCU e ESP8266 (na IDE do Arduino)
-------------------------------------------------
NodeMCU / ESP8266  |  NodeMCU / ESP8266  |
D0 = 16            |  D6 = 12            |
D1 = 5             |  D7 = 13            |
D2 = 4             |  D8 = 15            |
D3 = 0             |  D9 = 3             |
D4 = 2             |  D10 = 1            |
D5 = 14            |                     |
-------------------------------------------------
*/
///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
//Definindo o nome dos pinos
///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
const int  LED_STATUS = 12; // led de status 
const int TEMP_LM35 = A0; // porta analogica
//////////////configura os pinos dos reles/////////////////////////////
const int RELE1 = 0; 
const int RELE2 = 4;
const int LED1 = 5;
const int LED2 = 14;
const int BOT  = 13;//botão
///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
//variaveis globais
//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////

void mqtt_callback(char* topic, byte* dados_tcp, unsigned int length);///dados_tcp = payload


void setup() { 
  pinMode(RELE1, OUTPUT);
  pinMode(RELE2, OUTPUT);
  pinMode(LED1, OUTPUT);
  pinMode(LED2, OUTPUT);
  pinMode(LED_STATUS, OUTPUT);
  pinMode(BOT, INPUT);
  digitalWrite(RELE1,LOW);//desliga todos os reles
  digitalWrite(RELE2,LOW);
  digitalWrite(LED1,LOW);
  digitalWrite(LED2,LOW);
 
  Serial.begin(115200);
 
  WiFi.begin(ssid, password);
 
  while (WiFi.status() != WL_CONNECTED) 
  {    //inicialmente pisca o led da placa do nodemcu(é a mesma do ESP8266).
     delay(100);
    Serial.println("Conectando a WiFi..");
  }
  Serial.println("Conectado!"); 
  client.setServer(mqttServer, mqttPort);//configura servidor com as informações passadas
  client.setCallback(callback);
 
  while (!client.connected()) {
    Serial.println("Conectando ao servidor MQTT...");
    
    if (client.connect("Placa_leds", mqttUser, mqttPassword ))//colocar aqui o nome do dispositivo cliente("Placa_leds")
    {
 
      Serial.println("Conectado ao servidor MQTT!");  
      digitalWrite(LED_STATUS,HIGH); 
 
    } else {
 
      Serial.print("Falha ao conectar ");
      digitalWrite(LED_STATUS,LOW);
      Serial.print(client.state());
      delay(2000);
 
    }
  }
  
  client.publish("Status - placa_rele","Reiniciado!");
  client.publish("Placa_reles","Em funcionamento!");
  client.subscribe("RELE"); ///envia autorização para trabalhar com os topicos abaixo
  client.subscribe("LED"); 
  client.subscribe("TEMP"); 
  client.subscribe("BOT"); 
}
 //////////////////
void callback(char* topic, byte* dados_tcp, unsigned int length) 
{
   String msg ; // cria variavel que será responsavel pelo tratamento das informações
   for(int i = 0; i < length; i++) //converte array de bytes em string
    {  char c = (char)dados_tcp[i];
       msg += c;
    } 
   digitalWrite(LED_STATUS,LOW);
   delay(100);   
   digitalWrite(LED_STATUS,HIGH); //só pra indicar que houve recepção 
   Serial.print("\n\r topico:");//sempre será o escolhido no subscribe
   Serial.print(topic);   
   Serial.print("\n\r Pacote recebido:");
   Serial.print(msg);
   if (strcmp(topic, "RELE") == 0)//recebeu comando para trabalhar com o dispositivo relé
   {
    for (int i = 0; i < length; i++) // Varre o vetor(array) inteiro do pacote recebido 
        {         
          //toma ação dependendo da string recebida:      
      
          if (msg.equals("L1"))
          {
              digitalWrite(RELE1, HIGH);
              
          }
          if (msg.equals("D1"))
          {
              digitalWrite(RELE1, LOW);
            
          }
          if (msg.equals("L2"))
          {
              digitalWrite(RELE2, HIGH);
             
          }
          if (msg.equals("D2"))
          {
              digitalWrite(RELE2, LOW);
              
          }
        }
   }
   if (strcmp(topic, "LED") == 0)//recebeu comando para trabalhar com o dispositivo led
   {
       for (int i = 0; i < length; i++) // Varre o vetor(array) inteiro do pacote recebido 
        {         
          //toma ação dependendo da string recebida:      
      
          if (msg.equals("L1"))
          {
              digitalWrite(LED1, HIGH);
             
          }
          if (msg.equals("D1"))
          {
              digitalWrite(LED1, LOW);
              
          }
          if (msg.equals("L2"))
          {
              digitalWrite(LED2, HIGH);
             
          }
          if (msg.equals("D2"))
          {
              digitalWrite(LED2, LOW);
             
          }
        }
   }
 
}
 
void loop() {        
     client.loop();
     if(tempo_rot==500)
     {
      digitalWrite(LED_STATUS,LOW);
     }
     if(tempo_rot<1)
     {      
     tempo_rot = 1000;//reinicia contagem
     digitalWrite(LED_STATUS, HIGH);
     float Temperatura = analogRead(TEMP_LM35);    
     Temperatura = (Temperatura/1024.0) * 330;//converte para graus celsius
     Serial.print("\n\r temperatura :");     
     Serial.println(Temperatura);
     char data[6];
     char *valor = dtostrf(Temperatura,5,2,data);//float,tamanho da string,numero de casas decimais,variavel temporaria a ser usada
     client.publish("TEMP",valor);  
     if(digitalRead(BOT) == LOW)//botão pressionado?
        {
           if(est_ant_bot == 1)//botão não estava pressionado
           {
             client.publish("BOT","ON");
           }
          est_ant_bot = 0;
        }
        else
        {
          if(est_ant_bot == 0)//botão já estava pressionado
           {
             client.publish("BOT","OFF");
           }
          est_ant_bot = 1;
        }
     }
     delay(1);
     tempo_rot--;
     
}

          Quanto ao aplicativo do android esqueci de mencionar que é possível trocar os ícones ,então para este vídeo troquei eles e acrescentei mais um ícone para mostrar o status do botão.No vídeo e demonstrado o uso de um outro app do android(MQTTDASHBOAD) para plotar o gráfico da temperatura.Então vamos ao vídeo abaixo:

Vídeo de demonstração:




Até a próxima pessoal!

2 comentários :

  1. Boa tarde!
    Dando uma olhada na net encontrei este site, que por sinal é muito bom.
    Estou tentando montar um sistema de comunicação via WIFI, do tipo uma placa com um PIC16F877A com TX e RX conectado em um módulo ESP8266 - Esp-01 e um aplicativo em Delphi rodando em um PC ou um aplicativo Android.
    A comunicação seria assim: O aplicativo envia uma sequência de caracteres ASCII parecida com esta: READ_MEM e os dados chegariam a placa com o 16F877A que retornaria os dados que solicitei. Sabendo que o equipamento esta em uma cidade, e eu poderia estar outra e tudo seria feito pela internet.
    Estou tentando dar uma mudada de ramo no trabalho e toda ajuda é bem vida. Se for livro, apostila ou uma aula via internet, se não for uma forca, pois sei que é uma área com conhecimento bem valorizado, posso pagar uma contribuição pelo empenho em me ajudar!
    Grato, Odair

    ResponderExcluir
  2. Boa Noite!

    Gostei muito deste site, porém tenho uma dúvida relacionada ao envio de dados para o broker, gostaria de saber como corrigir um erro. O erro ocorre quando o módulo(Esp32 no meu caso) lê a porta analógica(lm35) e joga para a variável temperatura . Quando rodo a programação o único número que e enviado e que e mostrado no monitor serial e 1316.6 e não sai disso, porém se eu rodo a programação sem a parte do envio para o broker somente mostrando no serial as variáveis temperatura e valor o programa roda direitinho.

    Agradeceria se me ajudasse a resolver este bug, obrigado desde já!

    ResponderExcluir

olá,digite aqui seu comentário!