medir-distancia-con-arduino-y-el-sensor-gp2y0e03

Medir distancia con Arduino y el sensor GP2Y0E03

¿Qué es un GP2Y0E03?

El sensor Sharp GP2Y0E03 es un sensor de distancia infrarrojo que incorpora la electrónica para el procesado de los datos y que podemos conectarse con un procesador como Arduino.

El sensor GP2Y0E03 es similar a la familia de sensores Sharp GP2Y0A02 que vimos en esta entrada, pero dispone de un menor tamaño, mayor precisión, e incorpora comunicación digital I2C, a la vez que mantiene la salida analógica.

arduino-gp2y0e03-interior El rango de medición es de 4 a 50 cm, manteniendo un grado de precisión elevado en todo el intervalo. La tensión de alimentación es de 2.7 a 5.5V y el consumo de corriente de 26mA. El intervalo de refresco entre mediciones es de unos 40ms.

El funcionamiento y características son similares a los sensores Sharp. En particular, recordamos que este tipo de sensores son poco sensibles al color y reflectividad del objeto detectado, ni a la temperatura ambiente. El ángulo de detección es estrecho, unos 5º de abanico en frente del sensor.

También comparten sus mayores limitaciones, como la influencia con la luz ambiente, la posibilidad de interferencia al usar varios sensores, el ruido en la medición y, en especial, la imposibilidad de determinar si un objeto esta fuera del rango de medición (muy cerca o muy lejos),

El GP2Y0E03 es sencillo de conectar y usar. Sin embargo, hay que tener en cuenta que incorpora un conector JST (Japanese Solderless Terminal) para su conexión, por lo que tendremos que emplear un conector de este tipo o soldar directamente los terminales en la placa

arduino-gp2y0e03-esquema

Las aplicaciones para el GP2Y0E03 incluyen detección de distancias en robots, sistemas touchless, detección de presencia, detección de objetos en una determinada área, entre otros.

Precio

Podemos encontrar un sensor GP2Y0E03 por unos 3.80€ en vendedores internacionales de Ebay y Aliexpress. Con ese precio, es más caro que un sensor de ultrasonidos como el HC-SR04, similar al resto de sensores Sharp, y ligeramente más barato que un sensor TOF como el VL53L0X.

arduino-gp2y0e03-componente

¿Cómo funciona un GP2Y0E03?

El GP2Y0E03 funciona de forma similar a los sensores Sharp de distancia de mayor distancia. Un LED infrarrojo emite un pulso que ilumina un estrecho haz en frente del sensor.

arduino-gp2y0e03-funcionamiento

Un sensor CMOS (un array de sensores infrarrojos) detecta el reflejo del haz en el objeto ubicado frente al mismo, y la electrónica del sensor calcula la distancia al objeto en función del punto del sensor que ha detectado el haz.

El sensor GP2Y0E03 forma parte de la familia que incluye los sensores GP2Y0E02A y GP2Y0E02B. No obstante, es el único que permite tensiones de alimentación de 5V.

SensorOutputTensiónXYZ
GP2Y0E02AAnalog2,7-3,3V18.98.05.2
GP2Y0E02BDigital (I2C)2,7-3,3V18.98.05.2
GP2Y0E03Analog + Digital2,7-5.5V11.016.75.2

Esquema de montaje

El GP2Y0E03 dispone de salida analógica y por I2C, pudiendo usar cualquiera de ellas. El esquema de patillaje del GP2Y0E03 es el siguiente.

arduino-gp2y0e03-montaje

En el caso de usar conexión analógica, no es necesario que empleéis el pin SCA y SCL. En caso de emplear conexión por I2C podemos dejar sin conectar sin conectar el pin Vout.

arduino-gp2y0e03-conexion

Ejemplos de código

La lectura analógica del sensor es similar al resto de sensores infrarrojos de distancia que hemos visto. Un ejemplo de código es el siguiente.

const int sensorPin = A0;
void setup()
{
  Serial.begin(9600);
  pinMode(sensorPin, INPUT);
}

void loop()
{
  auto raw = analogRead(sensorPin);
  Serial.println(raw);  

  delay(100);
}

Y aquí tenemos un ejemplo de código por comunicación I2C.

#include <Wire.h>

 // 7 highest bits

#define ADDRESS         (0x80 >> 1)


#define SHIFT_ADDR      0x35

#define DISTANCE_ADDR   0x5E

#define RIGHT_EDGE_ADDR 0xF8 // C

#define LEFT_EDGE_ADDR  0xF9 // A

#define PEAK_EDGE_ADDR  0xFA // B

uint8_t distance_raw[2] = { 0 };
uint8_t shift = 0;
uint8_t distance_cm = 0;
char buf[100];

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

  delay(2000);

  Serial.println("Initializing");

  Wire.beginTransmission(ADDRESS);
  Wire.write(byte(SHIFT_ADDR));
  Wire.endTransmission();

  Wire.requestFrom(ADDRESS, 1);
  if (1 <= Wire.available())
  {
    shift = Wire.read();
  }

  Serial.print("Read shift bit: ");
  Serial.println(shift, HEX);
}

void loop()
{
  // Read basic measurement
  Wire.beginTransmission(ADDRESS);
  Wire.write(byte(DISTANCE_ADDR));
  Wire.endTransmission();

  Wire.requestFrom(ADDRESS, 2);

  if (2 <= Wire.available())
  {
    distance_raw[0] = Wire.read();
    distance_raw[1] = Wire.read();

    // Print distance in cm
    distance_cm = (distance_raw[0] * 16 + distance_raw[1]) / 16 / (int)pow(2, shift);
    sprintf(buf, "Distance %u cm", distance_cm);
    Serial.println(buf);
  }
  else
  {
    Serial.println("Read error");
  }
  delay(1000);
}

Descarga el código

Todo el código de esta entrada está disponible para su descarga en Github. github-full