Arduino en español
Circuitos con Arduino - Juan Antonio Villalpando
-- Tutorial de iniciación a Arduino --
Volver al índice del tutorial
____________________________
49BM.- Teclado 4x4, bus I2C. Pantalla LCD. Sensor de humedad y temperatura. Infrarojo. RadioFrecuencia. Reloj. Lluvia. I2C. INT_Hall. ArduinoI2C-Humo. LDR-PWM. Motores y Bluetooth. Servo RF.
- Nuestro proyecto va así:
- Teclado 4x4 con módulo I2C.
- Pantalla LCD.
- Sensor de Temperatura y Humedad.
- Infrarojo.
- Radio Frecuencia. Emisor y Receptor.
- Sensor de ultrasonido.
- Sensor de lluvia.
- Módulo I2C con sensores de inclinación, magnetismo y movimiento.
- Sensor de efecto Hall con Interrupción.
- Sensor de Humo con envío de información mediante I2C
- LDR para PWM.
- Bluetooth, motores y Android.
- Ahora le pondremos un servo dirigido desde RF.
- Vamos a añadir a nuestro proyecto un servo al terminal 9 del primer Arduino.
- Convendría echarle un vistazo al tutorial del Servo:
28.- Servomotor.
- Cuando pulsemos el pulsadorA o el pulsadorB del segundo Arduino, éste enviará una señal por Radio Frecuencia al primer Arduino y éste provocará el movimiento del servo.
- En el código del primer Arduino modificaremos de manera que además de encender los LED5 y LED6, se deberá enviar la señal para mover el servo.
_______________________
- Teclados y LED.
'A' - 'B' |
Modifica la temperatura máxima para encender el LED13 |
LED13 |
'B' |
Visualiza la Humedad en LCD. |
LED13 |
'C' |
Visualiza la Temperatura en LCD. |
LED13 |
'#' |
Fin de entrada de datos para la opción 'A' |
|
Mando de infrarojo |
Teclas '1' y '2' del mando de infrarojo. |
LED7 |
'D' |
Distancia ultrasonido por Radio Frecuencia en LCD. |
|
PulsadorA
PulsadorB |
|
LED5
LED6
Mover Servo |
'*' |
Visualiza la hora en LCD. |
|
'A' - 'C' |
Modifica la lluvia máxima para encender el LED4 |
LED4 |
'0' |
Visualiza la lluvia en LCD. |
|
|
Sensor de inclinación, el magnético o el de movimiento. (I2C) |
LED12 |
|
Sensor de efecto Hall (Interrupción) |
LED17 (es el terminal A3 funcionando como Digital) |
'1' |
Visualiza humo en LCD. (I2C) |
|
'2' |
Visualiza valor LDR-PWM |
LED10 PWM |
______________________________________________________
- Conexionado.
- Conectamos el servo al terminal 9 del Arduino.
______________________________________________________
- Código.
- He cambiado la parte de los LED5 y LED6, además de la parte del servo.
- Para el servo no utilizaré librería, lo controlaré directamente desde el código con su función el_servo().
Teclado_LCD_humedad_ir_rfr_reloj_lluvia_i2c_int_humo_ldr_servo.ino |
// Juan A. Villalpando.
// Abril 2018. KIO4.COM
#include <Wire.h>
// Teclado.
#include <Keypad_I2C.h>
#include <Keypad.h>
// Pantalla LCD
#include <LiquidCrystal_I2C.h>
LiquidCrystal_I2C lcd(0x27, 2, 1, 0, 4, 5, 6, 7, 3, POSITIVE);
// LiquidCrystal_I2C lcd(0x3F, 2, 1, 0, 4, 5, 6, 7, 3, POSITIVE);
#define LED13 13
#define LED7 7
// Sensor humedad-temperatura.
#include <DHT.h>
#define DHTPIN 2
#define DHTTYPE DHT11
DHT dht(DHTPIN, DHTTYPE);
// Infrarojo.
#include <IRremote.h>
// Radio Frecuencia.
#include <VirtualWire.h>
const int pin_de_recepcion = 8; // RF
#define LED5 5
#define LED6 6
int distancia;
int distancia_old;
boolean radiofrecuen = false;
// Reloj RTC
#include <RTClib.h>
RTC_DS1307 RTC;
boolean reloj = false;
// Lluvia
#define LED4 4
int sensorA = A0;
int valorA_lluvia = 0;
int valorA_lluvia_2 = 0;
int valorA_lluvia_old = 1.5;
String maximo_lluvia = "5";
boolean lluvia = false;
// Humo
char c;
String humostring ="";
String humostring_old ="";
boolean humo = false;
// LDR PWM
#define LED10 10
int pin_ldr = A1;
int leer_ldr;
int leer_ldr_2;
int leer_ldr_old;
boolean ldr = false;
// Sensores: inclinacion, magnetico, movimiento.
#define LED9 9
// Interrupciones.
#define INT3 3 // Se llama interrupcion 1
volatile byte cambia = LOW;
#define LED17 17 // El terminal A3 funcionando como Digital.
// Servo
int inc = 200;
int pos = 0;
int servoPin = 13;
// Teclado
const byte ROWS = 4;
const byte COLS = 4;
String maximo = "40";
char key = ' ';
// Humedad Temperatura.
float humedad = 0.0;
float temperatura = 0.0;
float temperatura_old = 0.1;
boolean temperatu = false;
// Infrarojo.
int RECV_PIN = 11;
IRrecv irrecv(RECV_PIN);
decode_results results;
int tecla;
char keys[ROWS][COLS] = {
{'1','2','3','A'},
{'4','5','6','B'},
{'7','8','9','C'},
{'*','0','#','D'}
};
byte rowPins[ROWS] = {0,1,2,3};
byte colPins[COLS] = {4,5,6,7};
int i2caddress = 0x38; // Direccion I2C teclado.
#define direccion_PFC8574 0x39 // Direccion I2C módulo de sensores.
Keypad_I2C kpd = Keypad_I2C( makeKeymap(keys), rowPins, colPins, ROWS, COLS, i2caddress );
void setup(){
Serial.begin(9600);
kpd.begin();
lcd.begin(16,2);// Columnas y filas de LCD
pinMode(LED13, OUTPUT);
// Humedad Temperatura.
dht.begin();
// Infrarojo.
pinMode(LED7, OUTPUT);
irrecv.enableIRIn();
// Radio Frecuencia.
// Inicializa IO y ISR
pinMode(LED5, OUTPUT);
pinMode(LED6, OUTPUT);
////pinMode(LED3, OUTPUT);
Serial.println("Recepcion");
vw_set_rx_pin(pin_de_recepcion);
vw_setup(2000); // Bits por segundo
vw_rx_start(); // Comienzo de recepción
// Reloj RTC
Wire.begin();
RTC.begin();
RTC.adjust(DateTime(__DATE__, __TIME__));
// Lluvia.
pinMode (LED4,OUTPUT);
// Sensores: inclinacion, magnetico, movimiento.
pinMode(LED9, OUTPUT);
// Establecimiento de la INTerrupcion.
pinMode(INT3, INPUT_PULLUP);
attachInterrupt(digitalPinToInterrupt(INT3), cambiaLED, FALLING);
pinMode(LED17,OUTPUT); // Es el pin A3 funcionando como Digital.
// LDR PWM LED
pinMode(LED10,OUTPUT);
// Servo
pinMode(servoPin, OUTPUT);
}
void loop(){
digitalWrite(LED17, cambia); // Interrupcion.
infrarojo();
radiofrecuencia();
valorA_lluvia = analogRead(sensorA);
valorA_lluvia_2 = map(valorA_lluvia, 160, 1020, 10, 0); // Entre 0 y 10.
leer_ldr = analogRead(pin_ldr);
//////////////////////////////////////////////////////////
byte cual; // Sensores: inclinacion, magnetico, movimiento.
cual = Leer(direccion_PFC8574);
if(bitRead(cual,0)){
digitalWrite(LED9, LOW);
}else{
digitalWrite(LED9, HIGH);}
if(bitRead(cual,1)){
digitalWrite(LED9, LOW);
}else{
digitalWrite(LED9, HIGH);}
if(bitRead(cual,2)){
digitalWrite(LED9, LOW);
}else{
digitalWrite(LED9, HIGH);}
/////////////////////////////////////////////////////////
key = kpd.getKey();
if (key){
if (key == 'A'){ // Cambiar maximo.
introduce_maximo();
}
if (key == 'B'){ // Ver humedad.
ver_humedad();
}
if (key == 'C'){ // Ver temperatura.
temperatu = !temperatu;
temperatura_old = 999999;
reloj = false;
lluvia = false;
radiofrecuen = false;
humo = false;
}
if (key == 'D'){ // Ver RadioFrecuencia-Ultrasonido.
radiofrecuen = !radiofrecuen;
distancia_old = 999999;
reloj = false;
temperatu = false;
lluvia = false;
humo = false;
}
if (key == '*'){ // Ver Reloj RTC.
reloj = !reloj;
lluvia = false;
temperatu = false;
radiofrecuen = false;
humo = false;
}
if (key == '0'){ // Ver lluvia
lluvia = !lluvia;
valorA_lluvia_old = 999999;
reloj = false;
temperatu = false;
radiofrecuen = false;
humo = false;
}
if (key == '1'){ // Ver Humo por Conexion I2C.
humo = !humo;
humostring_old = 999999;
reloj = false;
temperatu = false;
lluvia = false;
radiofrecuen = false;
}
if (key == '2'){ // Ver LDR-PWM.
ldr = !ldr;
leer_ldr_old = 999999;
reloj = false;
temperatu = false;
lluvia = false;
radiofrecuen = false;
}
}
if (temperatu){ver_temperatura();}
if (reloj){ver_reloj();}
if (lluvia){ver_lluvia();}
if (humo){ver_humo();}
if (ldr){ver_ldr();}
if (radiofrecuen){ver_radiofrecuencia();}
if (String(temperatura) >= maximo) {
digitalWrite(LED13, HIGH);
} else {
digitalWrite(LED13, LOW);
}
if (String(valorA_lluvia_2) >= maximo_lluvia) {
digitalWrite(LED4, HIGH);
} else {
digitalWrite(LED4, LOW);
}
} // FIN loop.
///////////// FUNCIONES ///////////////////////////
///////////////////////////////////////////////////
///// Introduccion de datos de maximo. ///////////
void introduce_maximo() {
// maximo = "";
lcd.setCursor(0,0); // Inicio del cursor
lcd.print("Pulsa B o C");
lcd.setCursor(0,1); // Siguiente renglón.
lcd.print(maximo);
maximo = "";
maximo_lluvia = "";
// Dos teclas.
while (key != 'B' && key != 'C' && key != '#') { // '#' para salir
Serial.println("Introduce otra tecla.");
delay(50);
key = kpd.getKey();
Serial.print(key);
}
if (key == 'B'){ // Establecer temperatura.
while (key != '#' )
{
key = kpd.getKey();
if (key){
maximo = maximo + key;
lcd.clear(); // Borra pantalla
lcd.setCursor(0,0); // Inicio del cursor
lcd.print("Temperat. maxima");
lcd.setCursor(0,1); // Siguiente renglón.
lcd.print(maximo);
delay(100);
}
}
}
if (key == 'C'){ // Establecer lluvia.
while (key != '#' )
{
key = kpd.getKey();
if (key){
maximo_lluvia = maximo_lluvia + key;
lcd.clear(); // Borra pantalla
lcd.setCursor(0,0); // Inicio del cursor
lcd.print("Lluvia maxima");
lcd.setCursor(0,1); // Siguiente renglón.
lcd.print(maximo_lluvia);
delay(100);
}
}
}
}
///////////////////////////////////////////////////
///// Ver informacion humedad ///////////////////
void ver_humedad() {
lcd.clear(); // Borra pantalla
humedad = dht.readHumidity();
lcd.setCursor(0,0); // Inicio del cursor
lcd.print("Humedad");
lcd.setCursor(0,1); // Siguiente renglón.
lcd.print(humedad);
delay(50);
}
///////////////////////////////////////////////////
///// Ver informacion temperatura ////////////////
void ver_temperatura() {
temperatura = dht.readTemperature();
if (temperatura != temperatura_old) { // Para que no parpadee.
temperatura_old = temperatura;
lcd.clear(); // Borra pantalla
lcd.setCursor(0,0); // Inicio del cursor
lcd.print("Temperatura");
lcd.setCursor(0,1); // Siguiente renglón.
lcd.print(temperatura);
delay(50);
}
}
///////////////////////////////////////////////////
///// Leer infrarojo ////////////////////////////
void infrarojo() {
if (irrecv.decode(&results)) {
Serial.println(results.value, DEC);
tecla=results.value; // Obtenemos el valor decimal de la tecla pulsada
//Serial.println(tecla);
if (tecla==12495){ // Código de la tecla 1
digitalWrite(LED7, HIGH);
}
if (tecla==6375){ // Código de la tecla 2
digitalWrite(LED7, LOW);
}
irrecv.resume(); // Receive the next value
}
delay(100);
}
///////////////////////////////////////////////////
///// Leer Radio Frecuencia //////////////////////
void radiofrecuencia() {
uint8_t buf[VW_MAX_MESSAGE_LEN];
uint8_t buflen = VW_MAX_MESSAGE_LEN;
if (vw_get_message(buf, &buflen))
{
int i;
// Mensaje en el Monitor Serial
for (i = 0; i < buflen; i++)
{
Serial.print((char) buf[i]); // Salen los 6 caracteres
Serial.print(' ');
}
Serial.println();
//////////////// Los LED
// LED5
if(buf[0] == '0'){
digitalWrite(LED5,HIGH);
pos += inc;
if (pos>=3600){pos=3600;}
el_servo();
} else {
digitalWrite(LED5,LOW);
}
// LED6
if(buf[1] == '0'){
digitalWrite(LED6,HIGH);
pos -= inc;
if (pos<=0){pos=0;}
el_servo();
} else {
digitalWrite(LED6,LOW);
}
// Obtiene el valor del potenciómetro
int a, b, c, d;
a = 1000 * (buf[2] - 48);
b = 100 * (buf[3] - 48);
c = 10 * (buf[4] - 48);
d = 1 * (buf[5] - 48);
distancia = a + b + c + d;
Serial.print("Distancia ultrasonido = ");
Serial.println(distancia);
}
}
///////////////////////////////////////////////////
///// Ver radiofrecuencia en LCD ////////////////
void ver_radiofrecuencia() {
if (distancia != distancia_old) { // Para que no parpadee.
distancia_old = distancia;
lcd.clear(); // Borra pantalla
lcd.setCursor(0,0); // Inicio del cursor
lcd.print("Distancia (RF)");
lcd.setCursor(0,1); // Siguiente renglón.
lcd.print(distancia);
delay(50);
}
}
///////////////////////////////////////////////////
///// Ver Reloj RTC en LCD ///////////////////////
void ver_reloj() {
DateTime now = RTC.now();
lcd.clear(); // Borra pantalla
lcd.setCursor(0,0); // Inicio del cursor
lcd.print(now.day(), DEC);
lcd.print("/");
lcd.print(now.month(), DEC);
lcd.print("/");
lcd.print(now.year(), DEC);
lcd.setCursor(0,1); // Siguiente renglón.;
lcd.print(now.hour(), DEC);
lcd.print("/");
lcd.print(now.minute(), DEC);
lcd.print("/");
lcd.print(now.second(), DEC);
delay(200);
}
//////////////////////////////////////////////////
/////// Ver lluvia en LCD ///////////////////////
void ver_lluvia() {
valorA_lluvia = analogRead(sensorA);
valorA_lluvia_2 = map(valorA_lluvia, 160, 1020, 10, 0);
if (valorA_lluvia_2 != valorA_lluvia_old) { // Para que no parpadee.
valorA_lluvia_old = valorA_lluvia_2;
lcd.clear(); // Borra pantalla
lcd.setCursor(0,0); // Inicio del cursor
lcd.print("Lluvia");
lcd.setCursor(0,1); // Siguiente renglón.
valorA_lluvia_2 = map(valorA_lluvia, 160, 1020, 10, 0);
lcd.print(valorA_lluvia_2);
delay(50);
}
}
//////////////////////////////////////////////////
// Sensores: inclinacion, magnetico, movimiento. /
byte Leer(int direccion) {
byte LeeDato = 0xff;
Wire.requestFrom(direccion,1);
if(Wire.available()){
LeeDato = Wire.read();
}
return LeeDato;
}
///////////////////////////////////////////////
///// Interrupcion ///////////////////////////
void cambiaLED() {
cambia = !cambia;
}
///////////////////////////////////////////
///// Leer HUMO I2C //////////////////////
void ver_humo() {
// Dos Arduinos I2C
Wire.requestFrom(2, 3); // Le pide 3 bytes al Esclavo 2
humostring ="";
while(Wire.available())
{
c = Wire.read(); // Recibe byte a byte
// Serial.print(String(c));
humostring = humostring + String(c);
}
if (humostring != humostring_old) { // Para que no parpadee.
humostring_old = humostring;
lcd.clear(); // Borra pantalla
lcd.setCursor(0,0); // Inicio del cursor
lcd.print("Humo (I2C)");
lcd.setCursor(0,1); // Siguiente renglón.
lcd.print(humostring);
delay(50);
}
}
//////////////////////////////////////////////////
/////// Ver LDR PWM LED ///////////////////////
void ver_ldr() {
String ver;
leer_ldr = analogRead(pin_ldr);
leer_ldr_2 = map(leer_ldr, 0, 1023, 0, 255);
//analogWrite(LED10, leer_ldr_2); // Enviamos a LED10 un Duty Cycle del 0 al 255.
analogWrite(LED10, 200); // Enviamos a LED10 un Duty Cycle del 0 al 255.
if (leer_ldr_2 != leer_ldr_old) { // Para que no parpadee.
leer_ldr_old = leer_ldr_2;
lcd.clear(); // Borra pantalla
lcd.setCursor(0,0); // Inicio del cursor
lcd.print("LDR -> PWM");
lcd.setCursor(0,1); // Siguiente renglón.
ver = String(leer_ldr) + " -> " + String(leer_ldr_2);
lcd.print(ver);
delay(50);
}
}
///////////////////////////////////////////////////
//////////////// Servo ///////////////////////////
void el_servo() {
int k=1;
// Serial.println(pos);
while(k<=40){
k=k+1;
digitalWrite(servoPin, HIGH);
delayMicroseconds(pos);
digitalWrite(servoPin, LOW);
delayMicroseconds(3600-pos);
delay (5);
}
}
|
______________________________________________________
- Código para el Arduino Emisor.
- Es igual que el del tutorial anterior.
Teclado_LCD_humedad_ir_rfe_BT.ino |
// Juan Antonio Villalpando
// juana1991@yahoo.com
// kio4.com
#include <VirtualWire.h>
#include <Wire.h>
// Bluetooth
#include <SoftwareSerial.h>
SoftwareSerial I2CBT(2,3);
// El TX del módulo BT va al pin 2 del Arduino
// El RX del módulo BT va al pin 3 del Arduino
// Ultrasonido.
int Trigger = 11;
int Echo = 10;
long microsegundos;
long duracion;
#define pulsadorA 4
#define pulsadorB 5
int valorA, valorB;
char A, B;
int distancia;
String str="";
// Humo
const int pin_humo = A2;
String humo;
String enviar_humo;
// RF
const int pin_de_transmision = 7; // RF
/// Bluetooth
char val;
// Conexiones del Motor A
int enA = 6; //9; // El terminal 9 da problemas en enA y enB
int in1 = 13;
int in2 = 12;
// Conexiones del Motor B
// NO CONECTAR ESTOS TERMINALES
int enB = 6;
int in3 = 0; //5;
int in4 = 1; //4;
void setup()
{
// Bluetooth interrupcion.
I2CBT.begin(9600);
attachInterrupt(0, int_bluetooth, CHANGE); // 0 es la interrupción 0, es decir el terminal 2
// Inicializa IO y ISR
vw_set_tx_pin(pin_de_transmision);
vw_setup(2000); // Bits por segundo
pinMode(pulsadorA, INPUT);
pinMode(pulsadorB, INPUT);
pinMode(Trigger, OUTPUT);
pinMode(Echo, INPUT);
Serial.begin(9600);
// Bus I2C otro Arduino.
Wire.begin(2); // Este Esclavo es el número 2
Wire.onRequest(requestEvent); // Cuando el Maestro le hace una petición,
// realiza el requestEvent
//// Bluetooth
pinMode(enA, OUTPUT);
pinMode(enB, OUTPUT);
pinMode(in1, OUTPUT);
pinMode(in2, OUTPUT);
pinMode(in3, OUTPUT);
pinMode(in4, OUTPUT);
analogWrite(enA, 90);
analogWrite(enB, 90);
}
void loop()
{
bluetooth_comprueba();
ultrasonido();
sensor_humo();
delay(20);
valorA = digitalRead(pulsadorA);
valorB = digitalRead(pulsadorB);
// A y B son los valores de los botones.
if (valorA == HIGH) {
A='0';
} else {
A='1';
}
if (valorB == HIGH) {
B='0';
} else {
B='1';
}
// str es el valor de la distancia con 4 caracteres.
// String str="";
str = "0000" + String(distancia); // Pasa el entero a String
str = str.substring(str.length()-4); // Siempre 4 caracteres
char msg[6] = {A, B, str[0], str[1],str[2], str[3]};
vw_send((uint8_t *)msg, 6); // Send: Aquí envía 6 elementos.
// Si está A y B en alto y la distancia en 546, enviará:
// 1 1 0 5 4 6
vw_wait_tx(); // Espera que termine el mensaje
delay(100);
}
/////////////////////////////////////////////
///////////FUNCION ULTRASONIDO //////////////
void ultrasonido(){
digitalWrite(Trigger, LOW);
delayMicroseconds(2);
digitalWrite(Trigger, HIGH);
delayMicroseconds(10);
digitalWrite(Trigger, LOW);
delayMicroseconds(2);
duracion = pulseIn(Echo, HIGH);
distancia = duracion / 29 / 2;
//Serial.println(String(distancia));
delay(20);
}
/////////////////////////////////////////////
///////////////// HUMO ///////////
void sensor_humo(){
int lee_humo = analogRead(pin_humo);
enviar_humo = "000" + String(map(lee_humo, 100, 500, 0, 10));
//// Funcion enviar datos por I2C al otro Arduino.
// Esto es lo que envía cuando le hace la petición.
}
void requestEvent()
{
// Wire.write(str.substring(str.length()-3).c_str()); // Envía 3 bytes
Wire.write(enviar_humo.substring(enviar_humo.length()-3).c_str()); // Envía 3 bytes
}
/////////////////////////////////////////////
///// Interrupcion Bluetooth
void int_bluetooth() {
val=I2CBT.read();
}
|
- bluetooth_comprueba.ino
bluetooth_comprueba.ino |
void bluetooth_comprueba() {
//if( Serial.available() ) {
//val = Serial.read();
// Avanza Motor A
if( val == '1' )
{
digitalWrite(in1, HIGH);
digitalWrite(in2, LOW);
}
// Avanza Motor A y B
if( val == '2' )
{
digitalWrite(in1, HIGH);
digitalWrite(in2, LOW);
digitalWrite(in3, HIGH);
digitalWrite(in4, LOW);
}
// Avanza Motor B
if( val == '3' )
{
digitalWrite(in3, HIGH);
digitalWrite(in4, LOW);
}
// Parar A
if( val == '4' )
{
digitalWrite(in1, LOW);
digitalWrite(in2, LOW);
}
// Parar A y B
if( val == '5' )
{
digitalWrite(in1, LOW);
digitalWrite(in2, LOW);
digitalWrite(in3, LOW);
digitalWrite(in4, LOW);
}
// Parar B
if( val == '6' )
{
digitalWrite(in3, LOW);
digitalWrite(in4, LOW);
}
// Retrocede A
if( val == '7' )
{
digitalWrite(in1, LOW);
digitalWrite(in2, HIGH);
}
// Retrocede A y B
if( val == '8' )
{
digitalWrite(in1, LOW);
digitalWrite(in2, HIGH);
digitalWrite(in3, LOW);
digitalWrite(in4, HIGH);
}
// Retrocede B
if( val == '9' )
{
digitalWrite(in3, LOW);
digitalWrite(in4, HIGH);
}
if( val == 'A' )
{
analogWrite(enA, 100);
analogWrite(enB, 100);
}
if( val == 'B' )
{
analogWrite(enA, 110);
analogWrite(enB, 110);
}
if( val == 'C' )
{
analogWrite(enA, 150);
analogWrite(enB, 150);
}
if( val == 'D' )
{
analogWrite(enA, 200);
analogWrite(enB, 200);
}
if( val == 'E' )
{
analogWrite(enA, 250);
analogWrite(enB, 250);
}
//}
}
|
______________________________________________________
- Comentarios.
______________________________________________________
________________________________
|