4 Relay Module

Um relé é um interruptor eletromecânico composto por uma bobina e um conjunto de contatos. Ao ser energizado, uma corrente percorre a bobina fazendo com que os seus contatos abram ou fechem.

O módulo apresentado aqui é um dispositivo com  quatro canais independentes e é ativado com nível lógico baixo. Uma grande vantagem deste módulo é que cada canal utiliza um acoplador ótico, garantindo que não exista nenhum contato elétrico entre o pino da placa Arduino com o circuito de acionamento do relé.

 

Quando o pino de entrada do canal (IN1 a IN4)  vai ao nível lógico baixo (LOW) , o acoplador ótico (U1 a U4) conduz e aciona o transistor (Q1 a Q4) que por sua vez energiza a bobina do relé (K1 a K4) fechando os contatos 2 e 3. Parece confuso com muitos elementos 😀 , porém veja o esquema a seguir.

 

Teste do módulo

Monte o circuito abaixo observando os pinos de ligação.

 

pino módulo Relé pino Arduino
IN1 D7
IN2 D8
IN3 D9
IN4 D10
VCC 5V
GND GND

 

 

 

Aqui vamos criar dois arquivos: o rele.ino que é o código principal e o Rele.h (atente para o primeiro caractere maiúsculo) com a declaração das macros (#define) e a função de tratamento do módulo. A separação, na prática, não é necessária. Estamos sugerindo a separação para que o código seja o mais reutilizável possível. Deste modo você poderá utilizar um mesmo módulo em diversos projetos e ser poupado de escrever tudo novamente 😎 .

Obs.:  toda diretiva de pré-processamento começa com o símbolo #. As diretivas não são comandos da linguagem C ou Arduino. São instruções que antes da compilação efetiva, são tratadas (processadas) no código fonte (sketch) e posteriormente entregues ao compilador.  Ah, a sintaxe também difere dos comandos/declarações C/Arduino. Não temos o ponto e virgula (;) ao termino de uma diretiva. Por convenção, o nome das constantes da diretiva #define são escritas em maiúsculas.

Copie e cole no IDE do Arduino e salve como rele.ino

#include "Rele.h"

void setup() {
  byte arrPinos[] = {RELECH1, RELECH2, RELECH3, RELECH4};

  for ( byte indice = 0; indice < sizeof(arrPinos); indice++ ) {
    pinMode( arrPinos[indice], OUTPUT );
   acionaRele( arrPinos[indice], RELEOFF );
  }

  for ( byte indice = 0; indice < sizeof(arrPinos); indice++ ) {
    acionaRele( arrPinos[indice], RELEON );
    delay(1000);
    acionaRele( arrPinos[indice], RELEOFF );
    delay(1000);
  }
}

void loop() {
}

 

Copie e cole no IDE do Arduino e salve como Rele.h

#define RELEON LOW
#define RELEOFF (! RELEON)
#define RELECH1 7
#define RELECH2 8
#define RELECH3 9
#define RELECH4 10

void acionaRele( byte canal, boolean estado ) {
  digitalWrite( canal, estado );
}

 

Módulos RTC – DS1307/DS3231

conteúdo revisto e atualizado – publicado originalmente em 2015

Estes módulos permitem adicionar um relógio em tempo real (RTC – Real Time Clock) aos seus projetos de uma forma bem simples e barata. Mesmo que falte energia ao seu Arduino, o relógio continua a contar pois é alimentado com uma bateria que pode durar muitos e muitos anos!

A maioria dos módulos RTC  são equipados com os circuitos integrados DS1307 e DS3231 ambos da empresa californiana Maxim Integrated e utilizam o barramento de comunicação I2C.

 

DS1307 e DS3231
DS1307 e DS3231

I2C

I2C (IIC – Inter Integrated Circuit) é um barramento de comunicação desenvolvido pela Philips, hoje NXP Semiconductors, para permitir troca de dados entre os componentes que residem na mesma placa de circuito impresso. Este barramento também é conhecido por TWI (Two Wire Interface) implementado pela ATMEL, hoje Microchip Technology.

A vantagem de usar este tipo de barramento é que precisamos de apenas dois pinos para comunicação, além do pino de alimentação (5V) e o pino terra (GND).

Os módulos I2C possuem um endereço único para cada módulo. A seleção do endereço é feita pela combinação dos pads A0, A1 e A2, para o DS3231 .

Mas como saber o endereço do módulo se não tenho a documentação disponível? 🙁

A biblioteca Wire.h (necessária para utilizar o I2C), contém um exemplo que faz uma varredura em módulos I2C acoplados a placa Arduino.  Esta biblioteca é nativa no software Arduino, ou seja, não é preciso instalar.

Na comunicação  I2C temos dois terminais conhecidos por SDA (Serial Data Line) e SCL (Serial Clock Line).

Nas placas Arduino Uno e compatíveis, o

SDA é o pino analógico  4 (A4)

e o

SCL é o pino analógico 5 (A5).

No Arduino Mega o SDA é o pino digital 20 e o SCL é o pino digital 21.

Conectando o módulo DS1307 (Tiny RTC)

Primeiro verifique se você vai usar um módulo com um dos dois chips indicados no começo do artigo. Após, verifique se tem instalado a biblioteca RTClib.h (esta biblioteca serve para os dois modelos).

Vá até o gerenciador de bibliotecas (atalho CTRL-SHIFT-i), digite rtclib. Caso não encontre, acesse o site  Arduino Library List e faça o download em https://www.arduinolibraries.info/libraries/rt-clib

 

Monte o circuito orientando-se pela tabela a seguir:

 

pino Tiny RTC pino Arduino
GND (jumper preto) GND
VCC (jumper vermelho) 5V
SDA (jumper amarelo) A4
SCL (jumper azul) A5

 

 

Agora iremos verificar o endereço do módulo. Carregue o IDE Arduino e acesse:  menu File (Arquivo)  e navegue até Examples (Exemplos), Wire e i2c_scanner. Execute o sketch e veja qual o endereço retornado no monitor serial.

Você deve ter visto esta informação:

Scanning…
I2C device found at address 0x50 !
I2C device found at address 0x68 !
done

Foram exibidos dois endereços. Um é do chip DS1307 (0x68) e o outro da memória EEPROM (0x50). Este sketch é muito útil para identificar outros módulos que usam I2C.

Exemplos

É quase certo que o seu módulo novo está com a data e hora incorretas. Vamos fazer o ajuste e será necessário apenas uma vez, visto que o módulo contém uma bateria para mantê-lo funcionando.

O ajuste será feito utilizando duas macros da linguagem C: __DATE__ e __TIME__, que retornam respectivamente a data e hora do seu sistema operacional. Note que este recurso é válido somente em tempo de compilação do sketch. Não dá para colocar estas macros em um laço de repetição, por exemplo, e exibir valores atualizados. Sempre conterá o valor no momento da compilação.

Aqui temos os métodos:

begin() – retorna false caso não seja detectado um módulo RTC ou o seu endereço é inválido.

adjust() – grava data e hora no seguinte formato ano (AAAA), mês (MM), dia (DD), hora (HH), minuto (MM) e segundo (SS). A classe DateTime formata os valores das macros __DATE__ e __TIME__  corretamente para este método.

now() – retorna data e hora corrente. Novamente usamos a classe DateTime que monta uma estrutura com os seguintes métodos: day(), month(), year(), hour(), minute() e second().

#include <Wire.h>;
#include <RTClib.h>;

RTC_DS1307 rtc;

void setup() {
  Serial.begin(9600);
  delay(1000);

  if (rtc.begin()) {
    rtc.adjust(DateTime((__DATE__), (__TIME__)));

    DateTime now = rtc.now();
    int dia     = now.day();
    int mes     = now.month();
    int ano     = now.year();
    int hora    = now.hour();
    int minuto  = now.minute();
    int segundo = now.second();
    Serial.print(dia);
    Serial.print("/");
    Serial.print(mes);
    Serial.print("/");
    Serial.print(ano);
    Serial.print("\t");
    Serial.print(hora);
    Serial.print(":");
    Serial.print(minuto);
    Serial.print(":");
    Serial.print(segundo);
  }
  else {
    Serial.println("Modulo RTC nao encontrado!");
  }
}

void loop() {

}

No próximo exemplo vamos formatar os dados retornados pelo módulo .

Foram inicializados três vetores: um para armazenar o texto formatado, um contendo os dias da semana e o último contendo os meses do ano.

Os dados foram formatados com a função sprintf() da linguagem C.  Aliás, temos um mini curso de linguagem C que acreditamos seja útil para um melhor entendimento da linguagem Arduino. Não deixe de fazê-lo 😉

Mais um método utilizado:

dayOfTheWeek() – retorna um inteiro (0 a 6) que representa o dia da semana começando em 0 (domingo).

#include <Wire.h>
#include <RTClib.h>


RTC_DS1307 rtc;

void setup() {
  char texto[255];

  char diasDaSemana[7][10] = {
    "Domingo",
    "Segunda",
    "Terca",
    "Quarta",
    "Quinta",
    "Sexta",
    "Sabado"
  };

  char mesDoAno[13][10] = {
    "",
    "Janeiro",
    "Fevereiro",
    "Marco",
    "Abril",
    "Maio",
    "Junho",
    "Julho",
    "Agosto",
    "Setembro",
    "Outubro",
    "Novembro",
    "Dezembro"
  };

  Serial.begin(9600);
  delay(1000);

  if (rtc.begin()) {
    DateTime now = rtc.now();
    int dia     = now.day();
    int mes     = now.month();
    int ano     = now.year();
    int hora    = now.hour();
    int minuto  = now.minute();
    int segundo = now.second();

    sprintf(texto, "Hoje: %s, %02d/%02d/%04d Hora: %02d:%02d:%02d",
            diasDaSemana[now.dayOfTheWeek()], dia, mes, ano, hora, minuto, segundo);
    Serial.println(texto);

    sprintf(texto, "Hoje: %s, %02d/%s/%04d Hora: %02d:%02d:%02d",
            diasDaSemana[now.dayOfTheWeek()], dia, mesDoAno[mes], ano, hora, minuto, segundo);
    Serial.println(texto);
  }
  else {
    Serial.println("Modulo RTC nao encontrado!");
  }
}

void loop() {
}

A saída no monitor serial será a data e hora do dia que você executou este sketch:

Hoje: Sexta, 21/08/2020 Hora: 17:31:42
Hoje: Sexta, 21/Agosto/2020 Hora: 17:31:42

 


Links úteis:


 

Sensor de Presença – HC-SR501

Sensores de presença ou movimento, conhecidos como sensores IR (infravermelho) ou PIR (Passive Infrared Sensor ou Pyroelectric Infrared Sensor), são sensores que detectam radiação emitida pelo corpo humano, por exemplo.

PIR01

O elemento sensor é vedado e oferece grande imunidade a umidade e temperatura e sua área exposta deixa passar somente radiação infravermelha. O circuito ao redor dá suporte a leitura do sensor e posterior conversão em um sinal digital. Portanto, na saída deste sensor teremos um nível alto, quando da detecção do movimento e um nível baixo em estado de repouso.

PIR - ElecFreaks
sensor piroelétrico – fonte http://www.elecfreaks.com

A lente (que cobre o elemento sensor) é do tipo Fresnel, feita de plástico, cuja função é ampliar o ângulo de detecção e concentração dos raios infravermelhos.

fonte http://www.fresnelfactory.com
fonte http://www.fresnelfactory.com

Pinos e Ajustes

Não é crítico mas requer um pouco de tempo para ajustar as suas necessidades.

Pinos:

  • 5V = ligar no pino 5V da placa Arduino
  • sinal = ligar em qualquer pino digital da placa Arduino
  • GND = ligar no pino GND da placa Arduino

Ajustes:

      • tempo (trimpot) = no sentido horário, aumenta o delay (tempo que o sinal ficará em nível alto) para aproximadamente 5 minutos e no sentido anti-horário para aproximadamente 5 segundos.
      • sensibilidade (trimpot) = no sentido horário, aumenta a distância de detecção para aproximadamente 7 metros e no sentido contrário para aproximadamente 3 metros.
      • trigger (jumper)
        low – não repetitivo:  quando alguém é detectado, um nível alto ficará presente no pino digital até que o tempo se esgote, daí o nível muda para baixo por aproximadamente 3 segundos, não aceitando novas detecções neste período.
        high – repetitivo: quando em nível alto, ficará neste estado enquanto o sensor detectar alguém no ambiente (dentro do tempo ajustado, porém o tempo será renovado a cada detecção) até que não haja movimento, daí alterando o nível para baixo por aproximadamente 3 segundos, não aceitando novas detecções neste período.

Um pouco confuso, não? 🙂 A melhor forma de entender estes ajustes é fazer experiências com a montagem sugerida mais adiante.

Montagem do circuito

Nos testes/experiências com este sensor, deixamos os trimpots posicionados no sentido máximo anti-horário e o jumper do modo trigger em high. A nossa sugestão é deixar inicialmente desta forma e ir ajustando conforme a sua necessidade.  O LED, neste período de ajuste, terá grande importância para nos orientar quando sensor estiver em nível alto. O pino de sinal do PIR está conectado ao pino digital 2 do Arduino e o LED está conectado ao pino 13 digital do Arduino através de um resistor de 220Ω.

PIR_protoboard PIR_esquematico   PIR_montagem

Exemplo

#define LED 13
#define PIR 2

void setup() {
   pinMode(LED, OUTPUT);
   pinMode(PIR, INPUT);
   delay(5000);
}

void loop() {
   byte leitura = digitalRead(PIR);
   digitalWrite(LED, leitura);
}