Manufactura industrial
Internet industrial de las cosas | Materiales industriales | Mantenimiento y reparación de equipos | Programación industrial |
home  MfgRobots >> Manufactura industrial >  >> Manufacturing Technology >> Proceso de manufactura

WiDC: Robot FPV Wi‑Fi – Control Remoto con Video en Vivo

Componentes y suministros

Componente Cantidad
Arduino UNO 1
Espressif ESP8266 ESP-01 1
Arduino Proto Shield 1
Motor DC con rueda 1
Puente H (H-bridge) 1

Aplicaciones y servicios en línea

Sobre este proyecto

¿Qué tal usar un robot controlado remotamente para explorar tu entorno, alcanzar lugares inaccesibles, vigilancia, tomar fotos, grabar videos o transmitir video en vivo? Este tutorial te muestra cómo construir uno de forma económica para todos esos propósitos.

Este tutorial es una mejora de mi anterior proyecto (Robot Rover FPV Controlado por Wi-Fi con Arduino y ESP8266), presentando un robot casero más rápido. Se explica cómo diseñar y construir un robot de dos ruedas controlado remotamente a través de una red Wi-Fi, usando dos motores DC, un Arduino Uno y un módulo Wi-Fi ESP8266.

El robot se controla desde un navegador web ordinario mediante una interfaz HTML. Un smartphone Android puede usarse para transmitir video y audio desde el robot hacia la interfaz de control.

Al igual que en el tutorial anterior, se muestra cómo diseñar y construir una estructura de bajo costo para un proyecto robótico, usando solo herramientas comunes (sin necesidad de impresora 3D, cortadora láser o router CNC).

Los componentes usados pueden no ser los óptimos para este propósito. Por ejemplo, un NodeMCU podría reemplazar la combinación Arduino + ESP8266. Una Raspberry Pi con cámara sustituiría al smartphone y controlaría los motores. Incluso es posible usar un smartphone Android como "cerebro" del robot.

Este tutorial deriva de otro proyecto en el que participo: Joy Robot (Hackaday / Hackster), y se usa el mismo hardware por simplicidad. Se eligió Arduino Uno por su accesibilidad y facilidad de uso, y se diseñó un shield simple. En el proyecto original también se controlaban servos y matrices de LEDs, y se interfazaba con el ESP. El smartphone es reemplazado por una tablet que ejecuta otras aplicaciones. Otros tutoriales relacionados:

Esta guía puede adaptarse y modificarse en su forma o interfaz de control según tus necesidades.

Paso 1: Herramientas

Las siguientes herramientas se usaron para la construcción del prototipo:

Estas herramientas se usaron para la estructura mecánica, ensamblaje y conexiones electrónicas. Algunas no son necesarias si compras la estructura en lugar de construirla. También podrías usar otros equipos (impresora 3D, cortadora láser) según lo disponible en tu makerspace.

Paso 2: Estructura mecánica y materiales

Materiales mecánicos:

Paso 3: Componentes electrónicos

Todos los componentes se encuentran fácilmente en tiendas en línea. La elección de componentes proviene de otro proyecto y puede optimizarse usando otro microcontrolador.

Paso 4: Diseño de la estructura

Primero diseñé la estructura mecánica en Fusion 360. También puedes comprar un kit robótico completo si no quieres construir tu propia estructura (en ese caso, salta al Paso 6). Se diseñó un bastidor de acrílico de bajo costo para montar motores y componentes, construido con herramientas ordinarias.

Se modelaron en 3D los componentes principales para definir su disposición. Algunos modelos se descargaron de GrabCAD:

Los componentes electrónicos se dispusieron en un plano para calcular la huella del robot. Luego se eligió la posición de motores y ruedas para una estructura estable. El diseño final consta de tres placas (base y dos laterales) unidas con soportes.

base.pdf base.svg

Paso 5: Construcción y ensamblaje de la estructura

1. Cortar la base de acrílico según el plano 2D: Puede hacerse con cortadora láser o, como en mi caso, con herramientas comunes. Transfiere las dimensiones imprimiendo el plano en papel adhesivo, pégalo al acrílico, marca con cúter y regla, rompe la lámina aplicando presión, y lija los bordes.

2. Taladrar los agujeros según el plano: Usa taladro o, si no tienes, un punzón o cúter para hacer y agrandar los orificios. Retira la plantilla adhesiva.

3. Montar componentes con tornillos y tuercas según el modelo 3D: Tornillos M3 para soportes y motores DC; M2 para electrónica; 5/32" para rueda delantera y clip del smartphone.

base.pdf

Paso 6: Ensamblaje de la electrónica

El circuito usa Arduino Uno como controlador principal, interfazando con ESP8266 para comunicación Wi-Fi. Arduino controla los motores DC mediante un puente H que maneja dos motores independientemente en ambas direcciones.

Un power bank alimenta la electrónica conectado al puerto USB del Arduino: fácil de cargar, reemplazable y proporciona 5V seguros.

Conecta todos los componentes según el esquemático. Necesitarás cables jumper para el ESP8266 (no es compatible con protoboard), puente H y motores. Puedes usar Proto Shield, protoboard común o diseñar tu propio shield para Arduino.

El ESP8266-01 no es compatible con protoboard; se conecta con jumpers pero no se fija a la estructura. Conecta USB al Arduino y pasa al siguiente paso.

wiDC_Esquematico.pdf wiDC.fzz wiDC_bb.pdf

Paso 7: Código Arduino

Instala el último Arduino IDE. No se necesitan librerías adicionales para comunicación con ESP8266 ni control de motores. Verifica el baudrate de tu ESP8266 y ajústalo en el código. Descarga el código (WiDC.ino) y reemplaza XXXXX por el SSID de tu router Wi-Fi e YYYYY por la contraseña. Conecta Arduino por USB y sube el código.

// Incluir librerías
#include <SoftwareSerial.h>
SoftwareSerial esp8266(3, 2); // RX pin = 3, TX pin = 2

// Definición de variables
#define DEBUG true
int state = 5; // Estado inicial (5 = espera)

// Pines de motores
const int motor1Pin1 = 5;
const int motor1Pin2 = 6;
const int motor2Pin1 = 9;
const int motor2Pin2 = 10;

// Velocidad de motores
int motorSpeed = 150; // PWM

void setup() {
  pinMode(motor1Pin1, OUTPUT);
  pinMode(motor1Pin2, OUTPUT);
  pinMode(motor2Pin1, OUTPUT);
  pinMode(motor2Pin2, OUTPUT);

  Serial.begin(9600);
  esp8266.begin(9600);
  
  sendData("AT+RST\r\n", 2000, DEBUG); // Reset módulo
  sendData("AT+CWMODE=1\r\n", 1000, DEBUG); // Modo estación
  sendData("AT+CWJAP=\"XXXXX\",\"YYYYY\"\r\n", 2000, DEBUG); // Conectar Wi-Fi
  delay(5000); // Esperar conexión
  sendData("AT+CIFSR\r\n", 1000, DEBUG); // Mostrar IP
  sendData("AT+CIPMUX=1\r\n", 1000, DEBUG); // Múltiples conexiones
  sendData("AT+CIPSERVER=1,80\r\n", 1000, DEBUG); // Servidor web puerto 80
}

void loop() {
  if (esp8266.available()) {
    if (esp8266.find("+IPD,")) {
      String msg;
      esp8266.find("?");
      msg = esp8266.readStringUntil(' ');
      String command = msg.substring(0, 3);
      Serial.println(command);

      if(command == "cm1") state = 1; // Adelante
      else if(command == "cm2") state = 2; // Atrás
      else if(command == "cm3") state = 3; // Derecha
      else if(command == "cm4") state = 4; // Izquierda
      else if(command == "cm5") state = 5; // Parar
    }
  }

  // Estado 1: Adelante
  if (state == 1) {
    analogWrite(motor1Pin1, motorSpeed); digitalWrite(motor1Pin2, LOW);
    analogWrite(motor2Pin1, motorSpeed); digitalWrite(motor2Pin2, LOW);
  }
  // Estado 2: Atrás
  else if (state == 2) {
    digitalWrite(motor1Pin1, LOW); analogWrite(motor1Pin2, motorSpeed);
    digitalWrite(motor2Pin1, LOW); analogWrite(motor2Pin2, motorSpeed);
  }
  // Estado 3: Derecha
  else if (state == 3) {
    analogWrite(motor1Pin1, motorSpeed); digitalWrite(motor1Pin2, LOW);
    digitalWrite(motor2Pin1, LOW); analogWrite(motor2Pin2, motorSpeed);
  }
  // Estado 4: Izquierda
  else if (state == 4) {
    digitalWrite(motor1Pin1, LOW); analogWrite(motor1Pin2, motorSpeed);
    analogWrite(motor2Pin1, motorSpeed); digitalWrite(motor2Pin2, LOW);
  }
  // Estado 5: Parar
  else if (state == 5) {
    digitalWrite(motor1Pin1, LOW); digitalWrite(motor1Pin2, LOW);
    digitalWrite(motor2Pin1, LOW); digitalWrite(motor2Pin2, LOW);
  }
}

String sendData(String command, const int timeout, boolean debug) {
  String response = "";
  esp8266.print(command);
  long int time = millis();
  while ((time + timeout) > millis()) {
    while (esp8266.available()) {
      char c = esp8266.read();
      response += c;
    }
  }
  if (debug) Serial.print(response);
  return response;
}

Explicación del código:

Se usa SoftwareSerial en pines 2 y 3 para comunicar Arduino con ESP8266, ya que el Uno solo tiene un puerto serial hardware. El baudrate del ESP8266 debe coincidir (9600 en este caso; por defecto suelen venir a 115200, pero SoftwareSerial no funciona bien a esa velocidad).

En setup() se inicializan ambos puertos serie y se envían comandos AT al ESP8266: reset, modo estación, conexión a red Wi-Fi, obtención de IP, habilitación de múltiples conexiones e inicio de servidor web en puerto 80.

La función auxiliar sendData envía comandos, espera respuesta y la muestra en el Monitor Serie si DEBUG es true.

En loop() se escuchan comandos entrantes (+IPD,). Se extraen los primeros 3 caracteres (cm1–cm5) que definen 5 estados: adelante, atrás, derecha, izquierda, parada. El robot mantiene el estado hasta recibir otro comando.

Cada estado define las señales PWM en los pines de los motores. analogWrite permite modular la velocidad. Los motores trabajan entre 3–6V; con 5V se puede variar el voltaje promedio vía PWM entre 3–5V para controlar velocidad.

WiDC.ino

Paso 8: Interfaz de control basada en web

Se diseñó una interfaz HTML para controlar el robot. Descarga interface.rar, extrae los archivos y ábrelos en Firefox. La interfaz tiene un formulario para ingresar la IP del módulo ESP y del servidor de video/audio (app IP Webcam en Android). Incluye un botón de prueba que hace girar el robot. Las flechas del teclado controlan el movimiento.

Un smartphone Android transmite video y audio al interfaz. App recomendada: IP Webcam (Google Play).

HTML explicado:

La interfaz tiene dos divisiones: una para audio/video (servidor IP Webcam) y otra para comandos.

División audio/video: formulario con textbox y botón para ingresar IP del servidor webcam (por defecto 192.168.0.5). Video y audio se cargan en objetos <object>.

<div id="video_and_audio" style="position: absolute; top: 50px; width:25%">
  <form name="myform" action="" method="GET">
    IP Webcam (IP): <input type="text" name="inputbox" value="192.168.0.5">
    <input type="button" name="button1" value="Load" onClick="readUrlAV(this.form)">
  </form>
  <object id="video" type="text/html" data="https://192.168.0.5:8080/video" style="position: absolute; width:100%; height:480px;"></object>
  <object id="audio" type="text/html" data="https://192.168.0.5:8080/audio.opus" style="position: absolute; width:388px; height:30px; left:8px; top:425px;"></object>
</div>

División comandos: formulario para ingresar IP del ESP8266. Imagen de teclado e instrucciones.

<div id="commands" style="position: absolute; top: 50px; left:35%; width:65%">
  <form name="myform2" action="" method="GET">
    Arduino IP Address: <input type="text" name="inputbox" Value="192.168.0.5">
    <input type="button" name="button3" Value="Test" onClick="testarArduino(this.form)">
  </form>
  <img src="images/keyboard.png" style="margin-left:100px; margin-top:50px;">
  <h4> Press and hold keyboard arrow keys to move the robot </h4>
</div>

JavaScript (archivos jquery.js y myscript.js) maneja la interfaz y envía comandos al Arduino.

JavaScript explicado:

Función readUrlAV lee la IP del formulario y la carga en los objetos video y audio.

function readUrlAV(form) {
  TextVar = form.inputbox.value;
  VideoVar = "https://" + TextVar + ":8080/video";
  AudioVar = "https://" + TextVar + ":8080/audio.opus";
  document.getElementById("video").setAttribute('data', VideoVar);
  document.getElementById("audio").setAttribute('data', AudioVar);
}

El script detecta pulsaciones de teclas de flecha (arriba=38, abajo=40, izquierda=37, derecha=39) y envía comandos (cm1–cm4) vía HTTP GET a la IP del Arduino. Un latch evita repeticiones.

var latch = false;
document.onkeydown = checkKeyDown;
function checkKeyDown(e) {
  e = e || window.event;
  if (e.keyCode == '38') { // Flecha arriba
    if (!latch) { sendCommand("cm1"); latch = true; }
  } else if (e.keyCode == '40') { // Flecha abajo
    if (!latch) { sendCommand("cm2"); latch = true; }
  } else if (e.keyCode == '37') { // Flecha izquierda
    if (!latch) { sendCommand("cm3"); latch = true; }
  } else if (e.keyCode == '39') { // Flecha derecha
    if (!latch) { sendCommand("cm4"); latch = true; }
  }
}
function sendCommand(cmd) {
  TextVar = myform2.inputbox.value;
  ArduinoVar = "https://" + TextVar + ":80";
  $.get(ArduinoVar, { [cmd]: 1000 });
}

Al soltar cualquier flecha, se ejecuta doNothing (envía cm5 y resetea latch).

document.onkeyup = checkKeyUp;
function checkKeyUp(e) {
  if (['38','40','37','39'].includes(e.keyCode)) setTimeout(doNothing, 200);
}
function doNothing() {
  TextVar = myform2.inputbox.value;
  ArduinoVar = "https://" + TextVar + ":80";
  $.get(ArduinoVar, { "cm5": 1000 });
  latch = false;
}

interface.rar

Paso 9: Uso

Al reiniciar Arduino, intentará conectar a tu Wi-Fi automáticamente. Usa el Monitor Serie para verificar la conexión y obtener la IP asignada al ESP8266. Abre el archivo HTML en Firefox e ingresa esa IP en el cuadro de texto. Desconecta Arduino del PC y conéctalo al power bank. Espera a que reconecte. Inicia la app IP Webcam en el smartphone montado en el robot. Ingresa la IP de video/audio en la interfaz y conecta al servidor. Puede ser necesario bajar la resolución de video en la app para reducir latencia. Mantén pulsadas las flechas del teclado para mover el robot y diviértete explorando.

Nota: El robot funciona en lazo abierto, por lo que es difícil que avance en línea recta; pequeñas diferencias entre motores y alineación causan desviaciones acumulativas. El robot mantiene el estado hasta recibir un comando distinto. A veces el ESP8266 pierde mensajes; si se pierde un "cm5", el robot seguirá moviéndose tras soltar la tecla. Se puede mejorar la interpretación de comandos para evitarlo.

Código

Piezas personalizadas y cajas

base_7JLgOpcox6.svg

Esquemáticos

Ver archivos PDF y Fritzing en la sección de electrónica.

Proceso de manufactura

  1. Construya un robot Raspberry Pi controlado por Bluetooth con retroalimentación de audio
  2. Proyecto Dados Digitales Arduino: Construye tu Propio Generador de Números Aleatorios con LCD
  3. Mando USB para juegos DIY con Arduino – Construye tu propio gamepad de alto rendimiento
  4. Robot Seguidor de Línea Autónomo con Arduino UNO: Guía Paso a Paso
  5. Construye un robot controlado por voz con Arduino Nano
  6. MobBob: Robot Arduino Impreso en 3D, Controlado por Smartphone Android
  7. Pixel Chaser: Juego LED Interactivo de Un Toque con Arduino Nano
  8. Levitación magnética repulsiva con Arduino: Circuito simple y guía DIY
  9. PiBot: Robot Pianista con Arduino para Interpretación Musical de Precisión
  10. Robot Asistente Doméstico Autónomo "O'nine" – Integración ROS, Alexa y Brazo Robótico
  11. Pong Neón en Matriz NeoPixel con Arduino Nano