domingo, 4 de diciembre de 2016

Sensor ultrasónico HC-SR04

El sensor ultrasónico HC-SR04 es un módulo que incorpora un par de transductores de ultrasonido que se utilizan de manera conjunta para determinar la distancia del sensor con un objeto colocado enfrente de este. 



Este sensor nos permite enviar pulsos ultrasónicos y escuchar el eco de retorno. Midiendo este tiempo, podemos calcular la distancia hasta el obstáculo.



Protocolo de comunicación del sensor ultrasónico

Esquema y funcionamiento

El esquema que vamos a utilizar es el siguiente:


El esquema consiste únicamente en proveer alimentación de 5v al módulo y asignarle 2 pines de interfaz con el Arduino UNO (echo y trigger). Este tipo de módulos para medición de distancia por ultrasonidos se divide en 2 grandes grupos:  Interfaz mediante pulso de eco e interfaz serial (I2C o UART). El HC-SR04 cae dentro del primer grupo, por lo que explicaremos su funcionamiento brevemente en las siguientes lineas.
  • Trig (D1 - GPIO5): recibe un pulso de habilitación de parte del microcontrolador, mediante el cual se le indica al módulo que comience a realizar la medición de distancia.
  • Echo (D2 - GPIO4): A través de este pin el sensor envía al microcontrolador un pulso cuyo ancho es proporcional al tiempo que tarda el sonido en viajar del transductor al obstaculo y luego de vuelta al módulo.
Mediante una sencilla formula puede estimarse entonces la distancia entre el sensor y el obstáculo si se conoce el tiempo de viaje del sonido así como la velocidad de propagación de la onda sonora. La siguiente imagen muestra los pulsos recibidos y enviados por el sensor, de acuerdo a la hoja de datos elaborada por Itead Studio.


Como se puede observar, el HC-SR04 genera un pulso en el pin marcado como “echo” cuya duración es proporcional a la distancia medida por el sensor. Para obtener la distancia en centímetros, solamente debemos dividir el tiempo en microsegundos entre 58 (mas concretamente 58,2 como veremos más adelante).

Para programarlo podemos hacerlo utilizando o no una librería externa.

Programación sin librerías

Despues de definir algunos pines e inicializar la consola serial y los pins en nuestro arduino, utilizamos un par de variables para obtener la duración del pulso y calcular la distancia.

Para dar un pulso lo que hacemos es activar el pin Trigger durante x microsegundos. Para producir un retardo entre un estado y otro de los puertos de arduino utilizamos:
delayMicroseconds(microsegundos);

Para escuchar el pulso vamos a usar la función pulseIn:
pulseIn(echoPin, HIGH)

Básicamente lo que hace es escuchar el pin que le pasamos, buscando una señal que pase de LOW a HIGH (si le pasamos HIGH como parámetro) y cuenta el tiempo que tarda en volver a bajar desde que sube.

Ahora ya sabemos el tiempo que tarda en volver el eco en µs. Como la velocidad del sonido es de 343 metros / segundo, necesitamos 1/343 = 0,00291 segundos para recorrer un metro.

Para usar una medida más cómoda podemos pasar esto  a microsegundos por centímetro:

Como nuestro eco mide el tiempo que tarda el pulso en ir y venir la distancia recorrida será la mitad:


El código completo es el siguiente:

#define trigPin 13
#define echoPin 12

void setup(){ 
  Serial.begin (9600);
  pinMode(trigPin, OUTPUT);
  pinMode(echoPin, INPUT);
}

void loop(){
  long duracion, distancia ;
  digitalWrite(trigPin, LOW); // Trigger
  delayMicroseconds(5); // Nos aseguramos Trigger esta LOW
  digitalWrite(trigPin, HIGH); // Activamos el pulso de salida
  delayMicroseconds(10); // Esperamos 10µs.
  digitalWrite(trigPin, LOW); // Cortamos el pulso
  duracion = pulseIn(echoPin, HIGH) ;
  distancia = duracion / 2 / 29.1  ;
  Serial.println(String(distancia) + " cm.") ;
  delay (500) ; // Limitamos el número de mediciones
}

El resultado es el siguiente:


Programación con librerías

Primero debemos descargar la librería desde la web del autor. Lo descomprimiremos en la carpeta libraries de Arduino y unos crea una nueva carpeta denominada NewPing


Esta librería se encarga de inicializar los pines necesarios, enviar los pulsos, escuchar el eco de retorno  y de hacer los cálculos para obtener la distancia.

Despues de incluir la librería y definir los pines de Trigger y Echo, le indicamos la distancia máxima (opcional) que en este caso es 200 cm (por defecto es 500 cm).

A continuación instanciamos un objeto de la clase NewPing y le pasamos estos parámetros
NewPing sonar(TRIGGER_PIN, ECHO_PIN, MAX_DISTANCE);

Para obtener la medida en cm utilizamos el método:
sonar.ping_cm()

Este método envía un ping (pulso) y obtiene la distancia en centímetros enteros.

El código completo es el siguiente:

#include <NewPing.h>

// Aqui se configuran los pines donde debemos conectar el sensor
#define TRIGGER_PIN 13
#define ECHO_PIN 12
#define MAX_DISTANCE 200 // Distancia máxima

//Crear el objeto de la clase NewPing
NewPing sonar(TRIGGER_PIN, ECHO_PIN, MAX_DISTANCE);

void setup() {
  Serial.begin(9600);
}

void loop() {
  delay(500); // Esperar medio segundo entre mediciones
  // Muestra la distancia medida a la consola serial
  Serial.print("Ping: ");
  // Calcular la distancia con base en una constante
  Serial.print(sonar.ping_cm());
  Serial.println("cm.");
}

El resultado es el siguiente:


Los métodos de la librería son los siguientes:
  • sonar.ping([max_cm_distance]) - Envía un ping y obtiene el tiempo que el eco en microsegundos. [max_cm_distance] es un parámetro opcional y permite definir la máxima distancia.
  • sonar.ping_in([max_cm_distance]) - Envía un ping y obtiene la distancia en pulgadas. [max_cm_distance] es un parámetro opcional y permite definir la máxima distancia.
  • sonar.ping_cm([max_cm_distance]) - Envía un ping y obtiene la distancia en centrímetros. [max_cm_distance] es un parámetro opcional y permite definir la máxima distancia.
  • sonar.ping_median(iterations [max_cm_distance]) - Hace pings múltiples (5 de forma predeterminada), descarta los pings fuera de rango y devuelve la mediana en microsegundos. [Max_cm_distance] le permite establecer opcionalmente una nueva distancia máxima.
  • sonar.convert_in(echoTime) - Convierta tiempo del eco de microsegundos a pulgadas.
  • sonar.convert_cm(echoTime) - Convierta tiempo del eco de microsegundos a centímetros.
  • sonar.ping_timer(function [max_cm_distance]) - Llama a la función de ping y comprueba si el ping está completo. [Max_cm_distance] le permite establecer opcionalmente una nueva distancia máxima.
  • sonar.check_timer() - Compruebe si el ping ha vuelto dentro del límite de distancia establecido.
  • NewPing::timer_us(frequency, function) - Llama a la función cada cierto tiempo (frequency) en microsegundos.
  • NewPing::timer_ms(frequency, function) - Llama a la función cada cierto tiempo (frecuency) en milisegundos.
  • NewPing::timer_stop() - Para el timer.
Para más información y ejemplos de esta librería consulta la página del desarrollador.

Fuentes:
Enlaces:

No hay comentarios:

Publicar un comentario

Nota: solo los miembros de este blog pueden publicar comentarios.