En nuestra introducción a la serie de blogs sobre vehículos robóticos, hemos mencionado que nuestro tablero de microcontroladores es compatible con atmega328p, atmega16u2 y arduino uno R3, tanto en términos de potencia como de conveniencia para principiantes.Hoy vamos a hacer nuestro primer robot.Con la ayuda de la segunda placa MC, queremos desarrollar un controlador remoto simple con un transmisor / receptor de 433 MHz.Empecemos.
Hardware necesario para la primera parte
Número | Componentes |
---|---|
1 | Tablero de Microcontrolador con atmega328p, atmega16u2, compatible con arduino uno R3 |
1 | Conductor blindado l293d de 4 canales |
1 | Chasis de robot de dos o cuatro ruedas |
Batería / batería, por ejemplo 2 x 18650 batería lipo |
Parte II equipo necesario
Número | Componentes |
---|---|
1 | Tablero de Microcontrolador con atmega328p, atmega16u2, compatible con arduino uno R3 |
1 | El teclado LCD bloquea uno R3 y otros. |
2 | Módulo transmisor / receptor de 433 MHz HC - 12 (desafortunadamente ya no en rango) |
Batería / batería, por ejemplo 2 x 18650 batería lipo o bloque 9V |
Además de las instrucciones de construcción que vienen con el kit, algunos consejos para la instalación de microcontroladores y cajas de baterías:
El protector del conductor del motor protege múltiples contactos con una pequeña placa de espuma.Usé cinta adhesiva de doble cara (alfombra) para pegarlos debajo del Microcontrolador y luego pegarlos al chasis.Esto me ahorra la molestia de perforar nuevos agujeros y apretar con una Junta.
He pegado cinta autoadhesiva a los accesorios de la Sala de baterías si es necesario.Se puede eliminar rápidamente.
Biblioteca de aplicaciones del motor:
Por lo general, Lady ada (Limor Fried) y el equipo de adafruit desarrollan una biblioteca muy buena que podemos integrar fácilmente con el gestor de bibliotecas en el entorno de desarrollo.El IC 74hc595 (registro deslizante) hace que la programación del blindaje del conductor del motor sea relativamente complicada, pero este trabajo nos ha hecho perder algunos resultados.Usando el método de la Biblioteca afmotor.h (funciones), podemos enviar fácilmente comandos de accionamiento a un robot.Tenga en cuenta que el motor de campo V2 de adafruit de hoy está en su rango.Podemos decir que estamos usando la Biblioteca "vieja", no V2.Vea la siguiente imagen "Library Manager", la entrada superior.
Los fragmentos de código para el Servicio de cuatro motores son:
« 35; incluye < afmotor.h >
Motor AF / DC 1 (4);
Motor AF / DC 2 (3);
Motor AF / DC 3 (1);
Motor AF / DC 4 (2);
¿Quieres saber la diferencia de números?No quiero cambiar la conexión del motor en la configuración de la Biblioteca, pero también quiero mantener el sistema que numera el motor (impar izquierdo, derecho, adelante y atrás).Para ambos motores, puede anotar o eliminar filas innecesarias.
En código adicional, puede utilizar los métodos Run () y setspeed () para cambiar los cuatro objetos del motor 1 al motor 4, por ejemplo.
Motor 1. Ejecutar (hacia adelante);
1. Establecer la velocidad de rotación (200);
El método Run () conoce los parámetros Forward (Forward), Backward (Back) y Release (standstation).
El método setspeed () acepta enteros entre 0 y 255, o puede ser una variable que acepta estos valores.Sin embargo, en este momento me gustaría emitir una advertencia sobre los efectos que discutiremos más adelante: el valor 255 representa el voltaje total proporcionado por la fuente de tensión externa, es decir, el voltaje de mis dos baterías lipo es de aproximadamente 8 v. Sin embargo, el voltaje de diseño del motor es de 5 V.¡Así que mi valor máximo es sólo alrededor de 150!
Como primer paso, recomiendo probar la funcionalidad usando las pruebas del motor de bocetos de muestra instaladas en la biblioteca.Pruebe los números 1 a 4 en esta línea
Motor AF / DC (4);
Si utiliza un voltaje superior a 5v, determine la instalación de la conexión y considere el valor máximo de setspeed () en el Bucle for.
Estarás de acuerdo conmigo en que es aburrido usar un modo de conducción pre - programado.De alguna manera, quieres conducir este coche.En Raspberry Pi, puedo conectar el Estado de radio o usar una conexión WLAN, al igual que un Microcontrolador ESP.Esto se puede hacer simplemente Tablero de Microcontrolador con atmega328p, atmega16u2, compatible con arduino uno R3 Me temo que no.Pero hace unos meses probé el módulo transmisor / receptor de 433 MHz HC - 12 y un blog de tres Partes (enlace a Parte 1, Parte 2, Tercera parteEscribir cartas.Tal vez pueda usar este conocimiento de nuevo.
Preliminary:
- Si quiero enviar un código de control remoto, necesita ser resuelto explícitamente, pero no puede ser demasiado largo.En experimentos anteriores con HC - 12, usé con éxito un código de cuatro dígitos para encender y apagar LEDs.
- Si conecto un joystick analógico al Microcontrolador, una entrada analógica de 10 bits me da un valor entre 0 y 1023, con los valores de los ejes X e y de cada 511 en el Centro.
Para la dirección y (más tarde hacia adelante y hacia atrás), divido este valor por 100 para obtener 11 etapas de conducción de 0 a 10, que se detienen a 5.El concepto de nivel de accionamiento puede transferirse a otros controladores y proporcionar otras ventajas (véase más adelante).
- El control de velocidad se realiza a través de la modulación de ancho de pulso (PWM), por lo que la etapa de conducción debe ser convertida en la relación de trabajo de PWM en el diagrama esquemático del controlador del motor del carro robot.Sólo se utiliza la etapa de accionamiento en el boceto del controlador remoto.
- Girar en un robot significa que un motor gira más rápido y el otro más lento.Aquí elijo cuatro etapas, cada una de las cuales es un crecimiento separado.Disminución de los valores de izquierda o derechaMotor derecho.
- Para realizar múltiples posibilidades de entrada (joystick, teclado con teclas o entrada de teclado), elegí el Código 505 como posición de reposo.Los números siguientes (entre 1 y 9) representan la curva, y los números anteriores (entre 0 y 10) representan la velocidad.Por ejemplo, el Código 1005 representa la salida recta más rápida, 505 representa reposo y 707 representa el Frente derecho.
Eje y 0 x x x |
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
← |
↖ |
↑ |
↗ |
→ |
||||
9 |
← |
↖ |
↑ |
↗ |
→ |
||||
8 |
← |
↖ |
↑ |
↗ |
→ |
||||
7 |
← |
↖ |
↑ |
↗ |
→ |
||||
6 |
← |
↖ |
↑ |
↗ |
→ |
||||
5 |
← |
↖ |
0 |
↗ |
→ |
||||
4 |
← |
↙ |
↓ |
↘ |
→ |
||||
3 |
← |
↙ |
↓ |
↘ |
→ |
||||
2 |
← |
↙ |
↓ |
↘ |
→ |
||||
1 |
← |
↙ |
↓ |
↘ |
→ |
||||
0 |
← |
↙ |
↓ |
↘ |
→ |
Esta es la primera vez que elijo el escudo de teclado LCD porque tiene cinco teclas de control remoto y una pantalla LCD integrada para mostrar el Código enviado.
- El Código limita el número máximo de consultas if.
- Para otras funciones, como servos, el Código es superior a 1010.
Pantalla de teclado LCD:
Los cinco botones protegidos por el teclado LCD están conectados al elemento de tensión en la entrada A0.Andreas Walter escribió en su blog Arduino: múltiples Io y EEPROM - [Parte 1] Una buena explicación.
Además, los pines A1 a A5 son fácilmente accesibles y me gustaría utilizar el transmisor de 433 MHz HC - 12.Quiero soldar una pluma.Hice lo mismo con el blindaje de la unidad del motor; la entrada analógica aquí es fácil de acceder.
Pintura:
Gpio15 para una fuente de alimentación A1 = 5v
A2 = puesta a tierra gpio16
A3 = gpio17 y A4 = gpio18, RX / TX para el uso de software serial
Hay dos comentarios más sobre el protector del motor:
1.Aunque los cables son intercambiables en los terminales del motor (izquierda, derecha oculta por HC - 12 en la figura), la polaridad de la fuente de alimentación externa debe ser estrictamente observada.
2. El saltador (conector de cortocircuito) pwrjmp en el Centro de la imagen genera la conexión entre el Microcontrolador y la fuente de alimentación externa.Sólo cuando el Código pin está encendido, la mcu se puede conectar al ordenador a través de USB.Sin embargo, incluso en este caso, la separación de corriente no ocurre en todo el circuito.
Esquema del controlador remoto:
/*
LCD-Keypad-Shield as MotorController, stand still = 505
je 5 Stufen vor/zurück, je 3 Stufen rechts/links
*/
#include <SoftwareSerial.h>
//Pin assignment for HC-12 Transceiver
SoftwareSerial mySerial(18, 17); //RX, TX
int HC12PWR = 15;
int HC12GND = 16;
//int HC12SET = 19;
// LCD without I2C-Adapter
// Die Daten werden über die Pins D4 bis D7 übertragen
#include <LiquidCrystal.h>
//LCD pin to Arduino
const int pin_EN = 9;
const int pin_RS = 8;
const int pin_D4 = 4;
const int pin_D5 = 5;
const int pin_D6 = 6;
const int pin_D7 = 7;
LiquidCrystal lcd( pin_RS, pin_EN, pin_D4, pin_D5, pin_D6, pin_D7);
int x = 5;
int y = 5;
int delay4bounce = 250;
void setup() {
pinMode(HC12PWR,OUTPUT);
digitalWrite(HC12PWR,HIGH);
pinMode(HC12GND,OUTPUT);
digitalWrite(HC12GND,LOW);
// pinMode(HC12SET,OUTPUT);
// digitalWrite(HC12SET,LOW);
mySerial.begin(9600);
// Initialisierung des eingebauten LCD
lcd.begin(16, 2); //LCD1602 mit 16 Zeichen und 2 Zeilen
lcd.setCursor(0,0); //Zählung beginnt bei Null, erst Zeichen, dann Zeile
lcd.print("AZ-Delivery.com");
lcd.setCursor(0,1); // 0=Erstes Zeichen, 1=zweite Zeile
lcd.print("Press Key:");
}
void sendcode() {
mySerial.println(100*y + x); //send code for motor
delay(200); // little delay for next button press
}
void loop() {
int A0;
// alle Taster liegen über einen Spannungsteiler an A0
// mit 3,9 kOhm Widerstand liegen die Spannungen zwischen 0 und 3,3 V
// Werte des ADC liegen zwischen 0 und 1023
// ggf. müssen die Werte angepasst werden
A0 = analogRead (0); //
lcd.setCursor(10,1); // Cursor beginnt hinter "Press Key"
if (A0 < 60) {
x = x+1;
if (x>9) {x=9;}
delay(delay4bounce);
lcd.print (" ");
lcd.setCursor(10,1);
lcd.print (100*y + x);
sendcode();
}
else if (A0 < 250) {
y = y+1;
if (y>10) {y=10;}
delay(delay4bounce);
lcd.print (" ");
lcd.setCursor(10,1);
lcd.print (100*y + x);
sendcode();
}
else if (A0 < 400){
y = y-1;
if (y<0) {y=0;}
delay(delay4bounce);
lcd.print (" ");
lcd.setCursor(10,1);
lcd.print (100*y + x);
sendcode();
}
else if (A0 < 700){
x = x-1;
if (x<1) {x=1;}
delay(delay4bounce);
lcd.print (" ");
lcd.setCursor(10,1);
lcd.print (100*y + x);
sendcode();
}
else if (A0 < 900){
x = 5;
y = 5;
delay(delay4bounce);
lcd.print (" ");
lcd.setCursor(10,1);
lcd.print (100*y + x);
sendcode();
}
else {
lcd.setCursor(10,1);
lcd.print (100*y + x);
sendcode();
}
}
Antes de mostrar los posibles bocetos de los robots mencionados anteriormente, me gustaría ver lo que hay detrás del ascensor:
La suposición de que el régimen del motor es proporcional a la tensión es condicional.Por razones de diseño, el motor no gira a baja tensión.Oyes un rugido, pero el PAR no es suficiente para arrancar.Por consiguiente, los niveles críticos de la primera fase son al menos del 30% al 40%.Hemos visto que, dependiendo de la fuente de tensión utilizada, tenemos que reducir el voltaje al máximo, en mi caso alrededor del 66%.Así que mis cinco etapas de conducción en cada dirección están entre 30 y 66.Los he introducido en una list A y he usado índices para acceder a los valores correspondientes.Usé los siguientes valores y el llamado repositorio en el boceto de arduino.
Int Speed level [11] = {65, -57, -49, -41, -33,0,33,41,49,57,65};
Nota: Los microcontroladores también difieren: para PWM de 8 bits, los valores están entre 0 y 255, para PWM de 10 bits, los valores están entre 0 y 1023, y para Raspberry Pi, el gpiocero del módulo está entre - 1 y + 1.
El factor multiplicador se utiliza para ajustar el valor del sistema correspondiente.Por supuesto, los valores de la lista también se pueden ajustar caso por caso.
También hay valores para el recorrido de la curva que puede necesitar.Tartamudea un poco.Para los cuatro pasos, utilizo cada dirección, aumento o disminuoReducir el valor del nivel de velocidad correspondiente en ambos lados.
Aquí está. Boceto de robot car Usando el control remoto:
// Adafruit Motor shield library
// copyright Adafruit Industries LLC, 2009
// this code is public domain, enjoy!
// modified for AZ-Delivery
#include <AFMotor.h>
AF_DCMotor motor1(4);
AF_DCMotor motor2(3);
AF_DCMotor motor3(1);
AF_DCMotor motor4(2);
#include <SoftwareSerial.h>
// initialize HC-12
SoftwareSerial mySerial(18, 17); // RX, TX
int HC12PWR = 15;
int HC12GND = 16;
//int HC12SET = 19;
int x = 0;
int y = 0;
int left = 0;
int right = 0;
int code = 505;
int codeRead = 505;
int speedL = 0;
float faktor = 2.2; // Korrektur für Fahrtstufe
void setup() {
Serial.begin(9600); // set up Serial Monitor at 9600 bps
Serial.println("Motor test!");
mySerial.begin(9600); // set up transmission speed for HC-12
// initialize HC-12 power supply
pinMode(HC12PWR,OUTPUT);
digitalWrite(HC12PWR,HIGH);
pinMode(HC12GND,OUTPUT);
digitalWrite(HC12GND,LOW);
// pinMode(HC12SET,OUTPUT);
// digitalWrite(HC12SET,LOW);
// turn on motor
// motor4.setSpeed(200);
// motor4.run(RELEASE);
}
void loop() {
if (mySerial.available() > 1) {
//read serial input and convert to integer (-32,768 to 32,767)
codeRead = mySerial.parseInt();
Serial.print("code received: ");
Serial.println(codeRead);
if (codeRead<=1010) {
if (code != codeRead) {
code = codeRead;
}
}
else {
Serial.print("wrong code received: ");
code = 505;
}
}
else {
code = 505;
}
motor();
mySerial.flush();//clear the serial buffer for unwanted inputs
delay(20); //little delay for better serial communication
}
void motor(){
int speedLevel[11]={-65,-57,-49,-41,-33,0,33,41,49,57,65};
y = int(code /100);
x = code - 100*y;
speedL = speedLevel[y];
Serial.print("code = ");
Serial.print(code);
Serial.print(" y = ");
Serial.print(y);
Serial.print(" x = ");
Serial.print(x);
Serial.print(" speedL = ");
Serial.println(speedL);
//Korrektur der Fahrtstufen für Kurvenfahrt
if (x==0){
right = speedL+16;
left = speedL-16;
}
else if (x==1){
right = speedL+16;
left = speedL-16;
}
else if (x==2){
right = speedL+13;
left = speedL-13;
}
else if (x==3) {
right = speedL+10;
left = speedL-10;
}
else if (x==4) {
right = speedL+7;
left = speedL-7;
}
else if (x==6) {
right = speedL -7;
left = speedL+7;
}
else if (x==7) {
right = speedL-10;
left = speedL+10;
}
else if (x==8) {
right = speedL-13;
left = speedL+13;
}
else if (x==9) {
right = speedL-16;
left = speedL+16;
}
else if (x==10) {
right = speedL-16;
left = speedL+16;
}
else {
right = speedL;
left = speedL;
}
//Eingabe der Fahrtstufen für "left" und "right"
Serial.print("left = ");
Serial.print(left);
Serial.print(" right = ");
Serial.println(right);
if (left < 25 & left > -25) {
motor1.run(RELEASE);
motor3.run(RELEASE);
}
if (right < 25 & right > -25) {
motor2.run(RELEASE);
motor4.run(RELEASE);
}
if (left>=25) {
if (left>65) left=65;
motor1.run(FORWARD);
motor3.run(FORWARD);
motor1.setSpeed(left * faktor);
motor3.setSpeed(left * faktor);
}
if (right>=25) {
if (right>65) right=65;
motor2.run(FORWARD);
motor4.run(FORWARD);
motor2.setSpeed(right * faktor);
motor4.setSpeed(right * faktor);
}
if (left<= -25) {
if (left<-65) left=-65;
motor1.run(BACKWARD);
motor3.run(BACKWARD);
motor1.setSpeed(-left * faktor);
motor3.setSpeed(-left * faktor);
}
if (right<= -25) {
if (right<-65) right=-65;
motor2.run(BACKWARD);
motor4.run(BACKWARD);
motor2.setSpeed(-right * faktor);
motor4.setSpeed(-right * faktor);
}
}
Y Tablero de Microcontrolador con atmega328p, atmega16u2, compatible con arduino uno R3 Tenemos un entorno de desarrollo integrado de microcomputadoras de un solo chip potentes y fáciles de programar con arduino.Es mejor no sólo empezar En el mundo de la programación (no alemán: pensamiento computacional), pero también para el acceso a circuitos electrónicos (no alemán: Computación física).
Y Conductor blindado l293d de 4 canales Fácil acceso a la robótica con bibliotecas existentes como la Biblioteca adafruit < afmotor.h >.
En un blog adicional, mostraremos soluciones alternativas a otros microcontroladores y otras opciones de control remoto.