Вы находитесь на странице: 1из 76

Prácticas de Diseño de Robots Móviles

Dr. Jesús Savage Carmona


Ing. Rubén Anaya Garcı́a
Contenido

1 Introducción general 3
1.1 Duración . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 3
1.2 Introducción . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 3
1.3 Desarrollo . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 4
1.3.1 Actividad 1 . . . . . . . . . . . . . . . . . . . . . . . . . . . . 4
1.3.2 Actividad 2 . . . . . . . . . . . . . . . . . . . . . . . . . . . . 5
1.3.3 Actividad 3 . . . . . . . . . . . . . . . . . . . . . . . . . . . . 7
1.3.4 Actividad 4 . . . . . . . . . . . . . . . . . . . . . . . . . . . . 8
1.3.5 Actividad 5 . . . . . . . . . . . . . . . . . . . . . . . . . . . . 8

2 Sistema mı́nimo del microcontrolador PIC16F877 9


2.1 Duración . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 9
2.2 Introducción . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 9
2.3 Desarrollo . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 9
2.3.1 Actividad 1 . . . . . . . . . . . . . . . . . . . . . . . . . . . . 10
2.3.2 Actividad 2 . . . . . . . . . . . . . . . . . . . . . . . . . . . . 10
2.3.3 Actividad 3 . . . . . . . . . . . . . . . . . . . . . . . . . . . . 11
2.3.4 Actividad 4 . . . . . . . . . . . . . . . . . . . . . . . . . . . . 11
2.3.5 Actividad 5 . . . . . . . . . . . . . . . . . . . . . . . . . . . . 11

i
ii CONTENIDO

3 Control de puertos paralelos 13


3.1 Duración . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 13
3.2 Introducción . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 13
3.3 Desarrollo . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 14
3.3.1 Actividad 1 . . . . . . . . . . . . . . . . . . . . . . . . . . . . 14
3.3.2 Actividad 2 . . . . . . . . . . . . . . . . . . . . . . . . . . . . 14
3.3.3 Actividad 3 . . . . . . . . . . . . . . . . . . . . . . . . . . . . 15

4 Operación de un robot móvil usando el microcontrolador PIC16F877 17


4.1 Duración . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 17
4.2 Desarrollo . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 17
4.2.1 Actividad 1 . . . . . . . . . . . . . . . . . . . . . . . . . . . . 17
4.2.2 Actividad 2 . . . . . . . . . . . . . . . . . . . . . . . . . . . . 18
4.2.3 Actividad 3 . . . . . . . . . . . . . . . . . . . . . . . . . . . . 18
4.2.4 Actividad 4 . . . . . . . . . . . . . . . . . . . . . . . . . . . . 18

5 Generación de Modulación de Ancho de Pulso ”PWM” 27


5.1 Duración . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 27
5.2 Introducción . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 27
5.3 Desarrollo . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 29
5.3.1 Actividad 1 . . . . . . . . . . . . . . . . . . . . . . . . . . . . 29
5.3.2 Actividad 2 . . . . . . . . . . . . . . . . . . . . . . . . . . . . 30

6 Temporizadores 33
6.1 Duración . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 33
6.2 Introducción . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 33
6.2.1 Encoders . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 33
6.2.2 Interrupción (TIMER2) . . . . . . . . . . . . . . . . . . . . . 34
6.3 Desarrollo . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 35
6.3.1 Actividad 1 . . . . . . . . . . . . . . . . . . . . . . . . . . . . 35
6.3.2 Actividad 2 . . . . . . . . . . . . . . . . . . . . . . . . . . . . 35
CONTENIDO iii

6.3.3 Actividad 3 . . . . . . . . . . . . . . . . . . . . . . . . . . . . 38
6.3.4 Actividad 4 . . . . . . . . . . . . . . . . . . . . . . . . . . . . 40

7 Controlador PID 43
7.1 Duración . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 43
7.2 Desarrollo . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 43
7.2.1 Actividad 1 . . . . . . . . . . . . . . . . . . . . . . . . . . . . 43
iv CONTENIDO
Lista de figuras

1.1 Diagrama por trayectoria . . . . . . . . . . . . . . . . . . . . . . . . . 5


1.2 Robot móvil que evade obstáculos . . . . . . . . . . . . . . . . . . . . 6
1.3 Algoritmo de un robot móvil evasor de obstáculos . . . . . . . . . . . 7

4.1 Robot móvil que evade obstáculos . . . . . . . . . . . . . . . . . . . . 24


4.2 Algoritmo de un robot móvil evasor de obstáculos . . . . . . . . . . . 25

5.1 Modulación de ancho de pulso . . . . . . . . . . . . . . . . . . . . . . 28

6.1 Captura de pulsos . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 34


6.2 Encoders usando sensores reflectivos . . . . . . . . . . . . . . . . . . . 38

1 Terminales L293 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 50
2 Control con tres señales . . . . . . . . . . . . . . . . . . . . . . . . . 51
3 Control con dos señales . . . . . . . . . . . . . . . . . . . . . . . . . . 51
4 Uso de optoacopladores . . . . . . . . . . . . . . . . . . . . . . . . . . 52
5 Entorno PIC C Compiler . . . . . . . . . . . . . . . . . . . . . . . . . 53
6 Compilación . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 54
7 Ventana de estado . . . . . . . . . . . . . . . . . . . . . . . . . . . . 55
8 Entorno MPLAB . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 56
9 Configuración Ccsc . . . . . . . . . . . . . . . . . . . . . . . . . . . . 56

v
vi LISTA DE FIGURAS

10 Selección Ccsc . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 57
11 Selección del dispositivo . . . . . . . . . . . . . . . . . . . . . . . . . 57
12 Creación de un proyecto . . . . . . . . . . . . . . . . . . . . . . . . . 58
13 Creación de un archivo nuevo . . . . . . . . . . . . . . . . . . . . . . 58
14 Agregar archivo al proyecto . . . . . . . . . . . . . . . . . . . . . . . 59
15 Opciones de configuración del proyecto . . . . . . . . . . . . . . . . . 59
16 Configuración del proyecto . . . . . . . . . . . . . . . . . . . . . . . . 60
17 Compilar . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 60
18 Resultado de la compilación . . . . . . . . . . . . . . . . . . . . . . . 61
19 Entorno PICDOWNLOADER . . . . . . . . . . . . . . . . . . . . . . 62
20 Proceso de programación . . . . . . . . . . . . . . . . . . . . . . . . . 63
21 Sistema mı́nimo del microcontrolador PIC . . . . . . . . . . . . . . . 64
22 Terminal para comunicación serie . . . . . . . . . . . . . . . . . . . . 65
23 Configuración de la terminal . . . . . . . . . . . . . . . . . . . . . . . 66
24 Entorno de la hyperterminal . . . . . . . . . . . . . . . . . . . . . . . 67
Lista de Tablas

3.1 Puertos paralelos PIC16F877 . . . . . . . . . . . . . . . . . . . . . . 13


3.2 Control a través del puerto serie . . . . . . . . . . . . . . . . . . . . . 14
3.3 Control de motores de CD . . . . . . . . . . . . . . . . . . . . . . . . 15

4.1 Lectura de dos sensores de contacto . . . . . . . . . . . . . . . . . . . 18

1 Control de motores de CD . . . . . . . . . . . . . . . . . . . . . . . . 49

vii
viii LISTA DE TABLAS
Introducción

El manual de prácticas para el laboratorio de Diseño de robots móviles servirá como


apoyo y guı́a a los alumnos que cursen la materia del mismo nombre, ası́ como de
materias afines, los objetivos se centran en encaminar al estudiante a comprender
con mayor profundidad el marco práctico que involucra el uso de los robots móviles.

Construirá el robot móvil que será utilizado durante el semestre, ası́ mismo
aprender a programar en lenguaje de alto nivel usando el compilador CCS para la
familia de microcontroladores PIC; conocerá y programará los periféricos más uti-
lizados en el control de robots móviles.

1
2
Práctica 1

Introducción general

Objetivo: Familiarizar al alumno en los comportamientos de los robots empleando


máquinas de estados. Diseño de la estructura básica del robot móvil que se usará
durante el semestre.

1.1 Duración
Dos semanas

1.2 Introducción
Un robot móvil es un dispositivo que permite realizar tareas de manera autónoma,
que pueden variar su complejidad dependiendo de la aplicación que se quiera dar;
en general, un robot está compuesto básicamente de tres etapas:

1. Etapa mecánica

• Distribución diferencial
• Distribución tipo omnidireccional
• Distribución tipo bicicleta
• Distribución tipo triciclo

2. Etapa electrónica

• Microcontrolador

3
• Sensores
• Driver de poténcia
• Pilas
• Reguladores de voltaje

3. Software

• Agoritmos de control implantados

Es necesario adaptar a los motores un sistema de transmisión que proporcione


la poténcia con la que finalmente se desplazarán en el piso; pudiendo ser através de
engranes, poleas o bandas.

Existen sistemas que tienen integrado un mecanismo de reducción; en estos se


encuentran los motoreductores y los llamados servomotores; los últimos requieren
ser modificados para operar como motoreductores.

El microcontrolador o cualquier otro dispositivo de control no entrega la


corriente suficiente para mover los motores, por lo que se requiere de sistemas de
poténcia externos que proporcionen esta corriente; para efectos del curso se re-
comienda el uso de los circuitos integrados L293 (B/D) o el L298.

En el apéndice de esta práctica se encontrará la información requerida para el


correcto desarrollo de la misma.

1.3 Desarrollo
Para cada uno de los siguientes apartados, realizar los circuitos electrónicos y las
tareas que se piden.

1.3.1 Actividad 1
Leer detalladamente la información del apéndice A; construir el diagrama electrónico
para controlar dos motores de CD en una protoboard y colocarlo sobre la base del
robot.

4
1.3.2 Actividad 2
El direccionamiento por trayectoria guarda el estado siguiente y las salidas de cada
estado de una carta ASM en una localidad de memoria. La porción de la memo-
ria que indica el estado siguiente es llamada la liga, mientras que la porción que
indica las salidas es llamada la parte de las salidas, como se muestra en la figura 1.1.

Figura 1.1: Diagrama por trayectoria

Concatenando la liga del estado presente junto con las entradas se forma la di-
rección de memoria que contiene la dirección del estado siguiente. Esta dirección se
guarda en un registro que está concatenando a las lı́neas de dirección de la memoria,
como se muestra en la figura 1.1. La seal de reloj conectada a los registros es la que
indica la velocidad de la máquina de estados.

Usando un direccionamiento por trayectoria, construya una máquina de es-


tados que ejecute el algoritmo de un robot móvil que evada obstáculos, como se
muestra en la figura 1.2.

5
Figura 1.2: Robot móvil que evade obstáculos

6
En la figura 1.3 se muestra el algoritmo de un robot móvil que evade obstáculos,
cuando los sensores Si y Sd sensan un obstáculo son iguales a cero, en caso contrario
es uno.

Figura 1.3: Algoritmo de un robot móvil evasor de obstáculos

1.3.3 Actividad 3

Usando dos sensores de contacto pruebe la máquina de estados, observando la se-


cuencia de los estados y las salidas con leds.

7
1.3.4 Actividad 4
Conecte la etapa de poténcia con las salidas de la máquina de estados.

1.3.5 Actividad 5
Pruebe el algoritmo que evade los obstáculos con el robot construı́do.

8
Práctica 2

Sistema mı́nimo del


microcontrolador PIC16F877

Objetivo: Conocer la estructura y caracterı́sticas de la tarjeta del microcontrolador


PIC que se dispone en el laboratorio, la programación en lenguaje C, programación
del microcontrolador y la ejecución en tiempo real.

2.1 Duración
Una semanas

2.2 Introducción
El sistema de desarrollo del microcontrolador PIC se representa en el figura 21 del
apéndice B; se distingue el circuito del sistema mı́nimo (fuente de reloj, sistema de
reset y el microcontrolador). Este se comunica al circuito convertidor RS232-TTL
(MAX232) a través de la USART interna, lo que permite enviar y recibir información
con formato serie ası́ncrono con una computadora personal.

2.3 Desarrollo
Realizar las siguientes actividades.

9
2.3.1 Actividad 1
Leer las notas anexas, que describen el uso del ambiente de desarrollo integrado
MPLAB y el PIC C COMPILER

2.3.2 Actividad 2
Usando el entorno de su elección (MPLAB o el PIC C Compiler), escribir el siguiente
programa en C y compilarlo.

#include <16f877.h>
#device ADC=8
#include <stdlib.h>

#fuses HS,NOPROTECT
#use delay(clock=20000000)
#use rs232(baud=19200, xmit=PIN_C6, rcv=PIN_C7)
#org 0x1F00, 0x1FFF void loader16F877(void){}

void main(){

int i,j;
char buffer[20];
float x;

i=0;

while(1) {
printf("\n\r type an integer ->");
gets(buffer);
j=atoi(buffer);
printf("\n\r type a float number ->");
gets(buffer);
x=atof(buffer);
printf("\n\r type a string ->");
gets(buffer);
printf("\n %d %d %f %s\n\r",i,j,x,buffer);
i++;
}
}

10
2.3.3 Actividad 3
Cargue este programa en la tarjeta de desarrollo del PIC usando el PICDOWN-
LOADER, como se indica en el anexo.

2.3.4 Actividad 4
Usando un programa de emulación de una terminal (hyperterminal) vea el texto que
envı́a el programa por el puerto serie e introduzca los datos que se piden.

2.3.5 Actividad 5
Escriba un programa en C que instrumente un contador; en el cuál se ingrese el valor
inicial, final y el incremento deseado; este último puede ser positivo o negativo.

Mostrar los valores del contador en una terminal.

11
12
Práctica 3

Control de puertos paralelos

Objetivo: Emplear los puertos paralelos que tiene el microcontrolador PIC para
obtener datos de dispositivos externos y controlar la operación de dos motores de
corriente directa.

3.1 Duración
Dos semanas

3.2 Introducción
El microcontrolador PIC16F877 tiene 5 puertos paralelos, la tabla 3.1 indica la
disposición de ellos.

Puerto Tamaño en bits Función


A 6 Bidireccional
B 8 Bidireccional
C 8 Bidireccional
D 8 Bidireccional
E 3 Bidireccional

Tabla 3.1: Puertos paralelos PIC16F877

13
3.3 Desarrollo
Realizar las siguientes actividades.

3.3.1 Actividad 1
Empleando el puerto paralelo B del microcontrolador; realizar las acciones de control
indicadas por la tabla 2. Donde x es un dato que es ingresado a través de una
terminal externa hyperterminal.

Valor x Acción puerto B


0 00000000
1 11111111

Tabla 3.2: Control a través del puerto serie

3.3.2 Actividad 2
Empleando el puerto paralelo del microcontrolador, configurado como entrada; conec-
tar un dip-switch a este.

Modificar el siguiente programa, de tal forma que el dato actual del puerto A
sea transmitido a una terminal, además de ser mostrado en el puerto B.

#include <16f877.h>
#device ADC=8
#include <stdlib.h>
#fuses HS,NOPROTECT
#use delay(clock=20000000)
#use rs232(baud=19200, xmit=PIN_C6, rcv=PIN_C7)
#org 0x1F00, 0x1FFF void loader16F877(void){}
void main(){
int var1;
while(1) {
var1=input_a();
output_b(var1);
}
}

14
3.3.3 Actividad 3
De acuerdo a la asignación reservada para las señales de control de la etapa de
poténcia de los motores; realizar un programa que permita controlar el funcionamiento
y sentido de giro de estos por separado. La señal que indica el sentido de giro de
los motores se realiza por medio del puerto A y las seales de control al driver por el
puerto B; la tabla 3.3 presenta los requerimientos.

Entrada puerto A Motor izquierdo Motor derecho Operación del robot


000000 Parado Parado Parado
000010 Adelante Adelante Adelante
000100 Atrás Atrás Atrás
001000 Adelante Atrás Gira a la derecha
010000 Atrás Adelante Gira a la izquierda

Tabla 3.3: Control de motores de CD

15
16
Práctica 4

Operación de un robot móvil


usando el microcontrolador
PIC16F877

Objetivo: Controlar la operación del robot móvil construı́do en las prácticas


anteriores empleando máquinas de estados en un microcontrolador.

4.1 Duración

Tres semanas

4.2 Desarrollo

Para cada uno de los siguientes apartados, realizar los diseños electrónicos y progra-
mas que se piden.

4.2.1 Actividad 1

Configurando el puerto A del PIC como entrada, conecte dos sensores de contacto a
dos pines de éste. Muestre el valor leı́do de los sensores en una hyperterminal cada
10 segundos.

17
SWIizquierdo SWDderecho Salida a la terminal
OFF OFF SWI ABIERTO SWD ABIERTO
OFF ON SWI ABIERTO SWD CERRADO
ON OFF SWI CERRADO SWD ABIERTO
ON ON SWI CERRADO SWD CERRADO

Tabla 4.1: Lectura de dos sensores de contacto

4.2.2 Actividad 2
Escriba una función en C que controle los movimientos de un robot móvil, en el se
indicará el ángulo en radianes que el robot primero girará y la distancia que después
avanzará. La función deberá tener el siguiente formato:

move_robot(float distancia, float angulo)


{

4.2.3 Actividad 3
Escriba una función en C que regrese el valor del sensor indicado. La función deberá
tener el siguiente formato:

float show_sensor(char *sensor, int num_sensor)


{

float x;

return(x);
}

4.2.4 Actividad 4
Cargue el siguiente programa en C , este ejecuta el algoritmo de un robot móvil
que evade obstáculos, como el que se muestra en la figura 4.1, en su robot. En la
figura 4.2 se muestra el algoritmo de un robot móvil que evade obstáculos, cuando

18
los sensores de tacto Si y Sd sensan un obstáculo sus valores son igual a cero, en
caso contrario es uno.

19
Programa en C para un robot móvil que evade obstáculos.

#include <16f877.h>
#device ADC=8
#include <stdlib.h>
#fuses HS,NOPROTECT
#use delay(clock=20000000)
#use rs232(baud=19200, xmit=PIN_C6, rcv=PIN_C7)
#org 0x1F00, 0x1FFF void loader16F877(void){}

// Constantes

#define ADELANTE move_robot(AVANCE, 0.0f);


#define ATRAS move_robot(-AVANCE, 0.0f)
#define GIRO_IZQ move_robot(0.0f, 0.7854f)
#define GIRO_DER move_robot(0.0f, -0.7854f)
#define SENSOR_IZQ 1
#define SENSOR_DER 2
#define SECURE 5.0f

move_robot(float distancia, float angulo)


{
}

float show_sensor(char *sensor, int num_sensor)


{
float x;

return(x);
}

// Esta función lee el sensor indicado

int lee_sensor(int num_sensor){


float sensor;
int valor_sensor;
char buffer[20];
char nombre_sensor[20];

20
strcpy(nombre_sensor,"contacto");
sensor = show_sensor(nombre_sensor, num_sensor);

if (sensor > SECURE)valor_sensor=0;


else valor_sensor=1;

return(valor_sensor);
}

// Función que evade obstáculos

void evade()
{
float AVANCE=10.;
int estado;
int Si, Sd;
char buffer[20];

// Estado inicial
estado = 0;

// Loop infinito
while(1)
{
printf("Estado presente: %d\n\r",estado);

// Acciones
switch ( estado )
{
case 0: // est0
// Lee sensores
Sd = lee_sensor(SENSOR_DER);
Si = lee_sensor(SENSOR_IZQ);

printf("\n\rLectura sensores Si %d Sd %d\n\r",Si,Sd);


if (Si == 0)
if (Sd == 0) ADELANTE;
break;
case 1: // est1
ATRAS;
break;

21
case 2: // est2
GIRO_IZQ;
break;
case 3: // est3
ATRAS;
break;
case 4: // est4
GIRO_DER;
break;
case 5: // est5
ATRAS;
break;
case 6: // est6
GIRO_IZQ;
break;
case 7: // est7
GIRO_IZQ;
break;
case 8: // est8
ADELANTE;
break;
case 9: // est9
ADELANTE;
break;
case 10: // est10
GIRO_DER;
break;
case 11: // est11
GIRO_DER;
break;
}

// Transiciones
switch ( estado )
{
case 0: if (Si == 0)
if (Sd == 0) estado = 0;
else estado = 1;
else
if (Sd == 0) estado = 3;
else estado = 5;

22
break;
case 1: estado= 2;
break;
case 2: estado = 0;
break;
case 3: estado = 4;
break;
case 4: estado = 0;
break;
case 5: estado = 6;
break;
case 6: estado = 7;
break;
case 7: estado = 8;
break;
case 8: estado = 9;
break;
case 9: estado = 10;
break;
case 10:estado = 11;
break;
case 11:estado = 0;
break;
}
}
}

void main(){

// Ejecuta el algoritmo evasor de obstaculos


evade();
}

23
Figura 4.1: Robot móvil que evade obstáculos

24
Figura 4.2: Algoritmo de un robot móvil evasor de obstáculos

25
26
Práctica 5

Generación de Modulación de
Ancho de Pulso ”PWM”

Objetivo: Utilizar el módulo de PWM de un microcontrolador para controlar la


operación de los motores de un robot.

5.1 Duración
Dos semanas

5.2 Introducción
Se genera una señal a un perı́odo constante y se modula el tiempo en alto de la
misma; con lo que se obtendrá un ciclo de trabajo variable, en respuesta a esta
acción el robot se podrá desplazar a diferentes velocidades.

Es usado el TIMER2 y los módulos CCP del microcontrolador PIC para fijar
la señal y controlar el PWM; el perı́odo está dado por (5.1):

(5.1) T = (Tosc int )(P R2 + 1)(P REDIV ISOR)

donde Tosc int es el ciclo de máquina de procesador y es el inverso del reloj externo
dividido por cuatro; P R2 valor cargado en un registro interno de ocho bits y el

27
Figura 5.1: Modulación de ancho de pulso

P REDIV ISOR es el valor seleccionado para que el registro TMR2 se incremente


cada cantidad de ciclos de reloj configurados por este parámetro, pudiendo ser de 1,
4 o 16.

El oscilador externo es de 20 MHz, con lo cual se obtiene un ciclo de máquina


de 0.2µs; considerando un predivisor de uno y un valor en PR2 de 255, al usar la
ecuación (5.3) se tendrá:

T = (0.2µs)(P R2 + 1)(1) = 51.2µs

por lo tanto la frecuencia de la señal será:

f = 19.531KHz

Para ser programado usando el compilador CCS se usa la funcián:

SET U P T IM ER 2(T 2 DIV BY 1, 255, 10);

T 2 DIV BY 1 indica el predivisor de uno, 255 el valor que tendrá PR2 y el número

28
10 es usado para generar peticiones de interrupción.

El tiempo de la señal en alto, es calculado con la ecuación 5.2 cuando sea


empleado una resolución de 8 bits.

1
(5.2) TON = (V ALOR)( )(4)(P REDIV ISOR)
XT AL

Para una resolución de 10 bits se usará 4.8.

1
(5.3) TON = (V ALOR)( )(P REDIV ISOR)
XT AL

5.3 Desarrollo
Para cada uno de los siguientes apartados, realizar los diseños electrónicos y progra-
mas que se piden.

5.3.1 Actividad 1
Busque en la ayuda del compilador CCS C información sobre las siguientes funciones
las cuales configuran pines del puerto C del PIC como salidas PWM:

setup_ccp1(CCP_PWM)
setup_ccp2(CCP_PWM)

set_pwm1_duty(duty)
set_pwm2_duty(duty)

setup_timer_2(T2_DIV_BY_1, 127, 10)


enable_interrupts(INT_TIMER2)

29
5.3.2 Actividad 2
Tomando como base el programa en C que se muestra a continuación, controle
la velocidad de los motores del robot móvil que se ha construido en las prácticas
anteriores. Conecte las lı́neas de la etapa de poténcia que controlan los motores
izquierdo y derecho a los pines 1 y 2 del puerto C los cuáles generan las salidas
PWM.

#include <16f877.h>
#device ADC=8
#include <stdlib.h>
#fuses HS,NOPROTECT
#use delay(clock=20000000)
#use rs232(baud=19200,xmit=PIN_C6, rcv=PIN_C7)
#org 0x1F00, 0x1FFF
void loader16F877(void){}

// Inicializa puertos

inicializa_puertos(){

setup_ccp1(CCP_PWM);
setup_ccp2(CCP_PWM);
}

// Inicializa interrupciones
inicializa_temporizadores(){

// The cycle time will be (1/clock)*4*t2div*(period+1)


// In this program clock=10000000 and period=127 (below)

setup_timer_2(T2_DIV_BY_1, 127, 10);


}

// Se indica el ancho del periodo positivo del PWM

mv(long duty){

30
// Se indica la direccion de movimiento de las llantas

output_d(0x0a);

// Se indican los tiempos del pwm


set_pwm1_duty(duty);
set_pwm2_duty(duty);
}

// Programa principal
void main(){

char linea[20];
long duty;

// Se inicializan las interrupciones


inicializa_temporizadores();

// Se inicializan los puertos


inicializa_puertos();

// Loop infinito
while(TRUE){

// Se lee el valor del periodo positivo


printf("\n\r-> ");
gets(linea);
duty=atol(linea);

// Actualiza el ciclo de trabajo


mv(duty);

}
}

31
32
Práctica 6

Temporizadores

Objetivo: Utilizar el sistema de temporizadores de un microcontrolador, para


capturar las formas de onda generadas por los encoders de los motores de un robot
móvil.

6.1 Duración
Dos semanas

6.2 Introducción

6.2.1 Encoders
La lectura de los pulsos se realiza con las funciones del TIMER0 y TIMER1; estos
temporizadores pueden se configurados como temporizadores o como acumuladores
de eventos externos; en esta La lectura de los pulsos se realiza con las funciones
del TIMER0 y TIMER1; estos temporizadores pueden se configurados como tem-
porizadores o como acumuladores de eventos externos; en estaúltima modalidad, la
información que generan los encoders permitirán conocer la velocidad de rotación
de los motores. Con el valor de los encoders y el radio de la llanta servirán para
estimar la distancia recorrida por el robot y la velocidad angular de las llantas.

En ambos temporizadores se requiere configurar el tipo de flanco que incre-


mentar los registros internos asociados a estos, la figura 6.1 muestra la adecuación
de los encoders al microcontrolador.

33
Figura 6.1: Captura de pulsos

La función de configuración empleada para la detección de flancos de subida


en el motor izquierdo es:

SET U P T IM ER 1(T 1 EXT ERN AL|T 1 DIV 1);

Para la configurar la detección del mismo tipo de pulsos en el motor derecho


se emplea:

SET U P T IM ER 0(RT CC EXT ERN AL L T O H|T 1 DIV 1);

La lectura del encoder izquierdo será adquirida con:

CntLef t = get timer0();

y para el derecho:

CntRight = get timer1();

6.2.2 Interrupción (TIMER2)


El perı́odo de interrupción es controlado por el TIMER2, este será usado para
generar el tiempo de muestreo para la actualización de la lectura de los encoders;
además de las configuraciones descritas en el PWM se utiliza un POSTESCAL-
ADOR, el cuál indicar el periódo de la petición de interrupción del TIMER2; la
expresión quedará ahora como:

(6.1) T = (Tosci nt )(P R2)(P REDIV ISOR)(P OST ESCALADOR)

34
Cuando el valor del registro TMR2 sea igual a PR2 entonces se genera una
comparación exitosa; cuando se han cumplido la cantidad de comparaciones indi-
cadas en el POSTESCALADOR, entonces se genera una solicitud de interrupción.
Para configurar el perı́odo de interrupción se usa la función:

SET U P T IM ER 2(T 2 DIV BY 1, 255, 10);

Con estos datos se especifica que se usará un predivisor de uno, el valor de


PR2 es 255 y el postescalador de 10; con lo que se obtiene un tiempo de 512µs.

6.3 Desarrollo
Para cada uno de los siguientes apartados, realizar los diseños electrónicos y progra-
mas que se piden.

6.3.1 Actividad 1
1. Busque en la ayuda del compilador CCS C información sobre las siguientes
funciones de los temporizadores:

setup_timer_0()
setup_timer_1()
setup_timer_2()
enable_interrupts()

6.3.2 Actividad 2
Tomando como base el programa en C que se encuentra en el programa 1 varı́e los
tiempos en los cuales ocurren las interrupciones de los temporizadores.

Programa 1

35
#include <16f877.h>
#device ADC=8
#include <stdlib.h>
#fuses HS,NOPROTECT #use delay(clock=20000000)
#use rs232(baud=19200, xmit=PIN_C6, rcv=PIN_C7)
#org 0x1f00, 0x1FFF
void loader16F877(void){}

// Esta interrupcion es llamada en forma automatica por el TIMER0.


#INT_TIMER0
void timer0() {
static long i=0,j=0;

set_timer0(0x00);

i++;
if(i>1024){
j++;
printf("T0 %ld\n\r",j);
i=0;
if(j>100)j=0;
}

// Esta interrupcion es llamada en forma automatica por el TIMER1.


#INT_TIMER1
void wave_timer1() {
static long i=0,j=0;

set_timer1(0xF000);

i++;
if(i>1024){
j++;
printf("T1 %ld\n\r",j);
i=0;
if(j>100)j=0;
}

36
}

// Esta interrupcion es llamada en forma automtica por el TIMER2.


#INT_TIMER2
void wave_timer2() {
static long i=0,j=0;

i++;

if(i>4096){
j++;
printf("T2 %ld\n\r",j);
i=0;
if(j>100)j=0;
}

// Inicializa interrupciones
incializa_interrupciones(){

setup_timer_0(T1_INTERNAL|T1_DIV_BY_1); // setup interrupt 0


enable_interrupts(INT_TIMER0);

setup_timer_1(T1_INTERNAL|T1_DIV_BY_1); // setup interrupt 1


enable_interrupts(INT_TIMER1);

setup_timer_2( T2_DIV_BY_1, 128, 10); // setup interrupts 2


enable_interrupts(INT_TIMER2);

enable_interrupts(GLOBAL);

void main() {

incializa_interrupciones();

37
while(TRUE);

6.3.3 Actividad 3
Coloque a un lado de las llantas un fondo negro y lı́neas blancas para detectar cuanto
han girado usando sensores infrarrojos, como se muestran en la figura 6.1. Conecte
estos encodificadores a las pines C0 y A4 del PIC. Programe los temporizadores T0
y T1 con contador de eventos externos dados por las lı́neas de los encodificadores. El
programa 2 captura los pulsos detectados en las transiciones de los encoders usando
interrupciones.

Figura 6.2: Encoders usando sensores reflectivos

Programa 2

#include <16f877.h>
#device ADC=8
#include <stdlib.h>

38
#fuses HS,NOPROTECT
#use delay(clock=20000000)
#use rs232(baud=19200, xmit=PIN_C6, rcv=PIN_C7)
#org 0x1F00, 0x1FFF void loader16F877(void){}

// Definicion de Constantes
#define NUM_PULSES_0 0xFF
#define NUM_PULSES_1 0xFFFF

//Variables Globales
static long CntRight=0,CntLeft=0;

// Esta interrupcion es llamada en forma automatica por el TIMER0.


#INT_TIMER0
void timer0() {
static long i=0;

CntLeft++;
printf("T0 %x\n\r",CntLeft);
set_timer0(NUM_PULSES_0);

// Esta interrupcion es llamada en forma automatica por el TIMER1.


#INT_TIMER1
void wave_timer1() {
static long i=0;

CntRight++;
printf("T1 %ld\n\r",CntRight);
set_timer1(NUM_PULSES_1);

// Inicializa interrupciones
inicializa_interrupciones(){

set_timer1(NUM_PULSES_1);
setup_timer_1(T1_EXTERNAL|T1_DIV_BY_1);

39
enable_interrupts(INT_TIMER1);

set_timer0(NUM_PULSES_0);
setup_timer_0(RTCC_DIV_1|RTCC_EXT_L_TO_H);
enable_interrupts(INT_TIMER0);

enable_interrupts(GLOBAL);

void main(){

inicializa_interrupciones();

while(TRUE);

6.3.4 Actividad 4
Utilice el temporizador T2 para mostrar los contadores de los temporizadores T0 y
T1; como se muestra en el programa 3.

Programa 3

#include <16f877.h>
#device ADC=8
#include <stdlib.h>

#fuses HS,NOPROTECT
#use delay(clock=20000000)
#use rs232(baud=19200, xmit=PIN_C6, rcv=PIN_C7)
#org 0x1FFF, 0x1FFF void loader16F877(void){}

// Definicion de Constantes
#define NUM_TIMES_T2 256
#define NUM_SECOND 14

40
// Esta interrupcion es llamada en forma automatica por el TIMER2.
#INT_TIMER2
void wave_timer2() {
static long k=0,l=0,m=0;
long i,j;

k++;
i=get_timer0();
j=get_timer1();

if(k>NUM_TIMES_T2){
set_timer0(0);
set_timer1(0);
k=0;
l++;
if(l>NUM_SECOND){
printf("T2 Temp. %ld motor Iz. %lu De. %lu\n\r",m,i,j);
l=0;
m++;
}

/* Inicializa interrupciones*/
incializa_interrupciones(){

set_timer1(0);
setup_timer_1(T1_EXTERNAL|T1_DIV_BY_1);

set_timer0(0);
setup_timer_0(RTCC_DIV_1|RTCC_EXT_L_TO_H);

setup_timer_2(T2_DIV_BY_1, 127, 10);


enable_interrupts(INT_TIMER2);

enable_interrupts(GLOBAL);

41
// Programa Principal
void main(){

char linea[20];
long duty;

incializa_interrupciones();

while(TRUE);
}

42
Práctica 7

Controlador PID

Objetivo: Controlar la velocidad de los dos motores del robot construido en las
practicas anteriores usando un controlador PID

7.1 Duración
Dos semanas

7.2 Desarrollo
Realizar la actividad indicada.

7.2.1 Actividad 1
1. 1. Tomando como base el siguiente programa, varié las constantes Kp, Ki y
Kd del controlador PID y modifique el código, si es necesario, para controlar las
velocidades de los motores de su robot.

/********************************************
* robot_pid.c *
* *
* v. 1.0 *
* *

43
* Este programa controla la *
* velocidad de dos motores *
* usando un control PID *
* *
* Jesus Savage *
* Ruben Anaya *
* Carlos Munive *
* *
* FI-UNAM, Nov-2007 *
* *
*********************************************/

// Definiciones PIC
#include <16f877.h>
#device ADC=8
#include <stdlib.h>
#fuses HS,NOPROTECT
#use delay(clock=20000000)
#use rs232(baud=19200, xmit=PIN_C6, rcv=PIN_C7)
#org 0x1FFF, 0x1FFF void loader16F877(void){}

// Definicion de Constantes
#define CNT_T2 3
#define NUM_TIMES_T2 64*CNT_T2
#define NUM_SECOND 80/CNT_T2
#define SIZE_DATA 50
#define ADELANTE 0x0a

// Constantes de acondicionamiento motor izquierdo


#define Kci 0.2
#define Kci1 Kci*2.7
#define Kci2 Kci*2.2
#define Kci3 Kci*2.0
#define Kci4 Kci*1.6
#define Kci5 Kci*1.2

// Constantes de acondicionamiento motor derecho


#define Kcd 0.18
#define Kcd1 Kcd*2.7
#define Kcd2 Kcd*2.2
#define Kcd3 Kcd*2.0

44
#define Kcd4 Kcd*1.6
#define Kcd5 Kcd*1.2

// Constantes del control PID


#define Kp 0.7 //1.7
#define Ki 0.0 //0.35
#define Kd 0.000 //0.005

//Variables Globales
long CntRight=0,CntLeft=0;
int flag=0;
long wi=0,wd=0;
float fCntRight,fCntLeft;

// Control PID
mv_pid(){
long rni=0,rnd=0;
float frni=0.0,frnd=0.0;
float ewi=0,ewd=0;
static float prev_rni=0,prev_rnd=0,prev_ewi=0,prev_ewd=0;
static float prev2_ewi=0,prev2_ewd=0;
float cntder,cntizq;

//Acondiciona los valores de las entradas (encoders)


if(wd<=62)cntder=wd*Kcd1;
else if(wd<125)cntder=wd*Kcd2;
else if(wd<250)cntder=wd*Kcd3;
else if(wd<350)cntder=wd*Kcd4;
else cntder=wd*Kcd5;

if(wi<=62)cntizq=wi*Kci1;
else if(wi<125)cntizq=wi*Kci2;
else if(wi<250)cntizq=wi*Kci3;
else if(wi<350)cntizq=wi*Kci4;
else cntizq=wi*Kci5;

cntizq=cntizq/1024.0;
cntder=cntder/1024.0;

// Calcula el error
ewd=cntder-fCntRight;

45
ewi=cntizq-fCntLeft;

// Calcula el control para cada motor


frni= prev_rni + Kp*(ewi-prev_ewi)+ Ki*(ewi-prev_ewi)+
Kd*(ewi-2*prev_ewi+prev2_ewi);
frnd= prev_rnd + Kp*(ewd-prev_ewd)+ Ki*(ewd-prev_ewd)+
Kd*(ewd-2*prev_ewd+prev2_ewd);

// Guarda valores para la siguiente iteracion


prev_rni=frni;
prev_rnd=frnd;
prev_ewi=ewi;
prev_ewd=ewd;

//Acondiciona los valores de las salidas


if(frni<0)frni=0;
else if(frni>1.0)frni=1.0;
if(frnd<0)frnd=0;
else if(frnd>1.0)rnd=1.0;
rni=2048.0*frni;
rnd=2048.0*frnd;

// Coloca los valores para generar los PWM


set_pwm1_duty(rni);
set_pwm2_duty(rnd);

// Rutina para la interrupcion del TIMER2.


#INT_TIMER2
void wave_timer2() {
static long k=0;
static int i=0;

k++;
if(k>NUM_TIMES_T2){
k=0;
CntLeft=get_timer0();
CntRight=get_timer1();
fCntRight=CntRight/1024.0;
fCntLeft=CntLeft/1024.0;

46
// Muestra los datos
if(flag==1){
i++;
if(i > SIZE_DATA)flag=0;
printf("%f %f\n\r",fCntLeft,fCntRight);
}
else i=0;
// Ejecuta el algoritmo de control PID
mv_pid();
// Inicializan los contadores de los temporizadores de nuevo
set_timer0(0);
set_timer1(0);
}
}

/* Inicializa puertos */
inicializa_puertos(){
// Se inicializan los pines para generar los pwms
setup_ccp1(CCP_PWM);
setup_ccp2(CCP_PWM);
// Se indica la dirrecion de los motores
output_d(ADELANTE);
}

// Inicializa interrupciones y temporizadores


inicializa_interrupciones(){
// Se inicializan los temporizadores 0 y 1 como encoders
set_timer1(0);
setup_timer_1(T1_EXTERNAL|T1_DIV_BY_1);
set_timer0(0);
setup_timer_0(RTCC_DIV_1|RTCC_EXT_L_TO_H);
// Se inicializa el temporizador 2 para generar el PWM
setup_timer_2(T2_DIV_BY_1, 127, 10);
// Se habilitan las salidas
enable_interrupts(INT_TIMER2);
enable_interrupts(GLOBAL);
}

/* Programa principal */
void main(){

47
char linea[5];

inicializa_interrupciones();
inicializa_puertos();

while(TRUE){
// lee las velocidades de los motores
gets(linea);
wi=atol(linea);
flag=1;
gets(linea);
wd=atol(linea);
flag=1;
}
}

48
Apendice A

Circuito L293 B/D


El L293 es un circuito integrado diseñado para manejar motores hasta de 1 A.
Entre las aplicaciones tı́picas, incluye manejo de cargas inductivas como solenoides,
relevadores, motores de corriente directa y motores a pasos, emplea internamente
los transistores de potencia y utiliza un buffer para señales de nivel bajo.
Algunas de sus caracterı́sticas son:

• Salida por canal de 1 A.

• Reemplazo directo L293B y L293D

• Empaquetado DIP de 16 terminales

• Cero logico hasta 1.5 volts

• Cuatro señales de control independientes

• Dos puentes H independientes

• Dos señales de habilitador para cada puente H

• Alimentación independiente al motor (0 a 32 volts)

• Alimentación al circuito de 5 volts

La distribución de pines se muestra en la figura 1 y la asignación de ellos en


la tabla 4.

Terminal Función
16 Alimentación al circuito 5 volts
8 Alimentación independiente al motor (0V a 32 V)
3, 4, 12, 13 0 Volts
2, 7, 10, 15 Control de dirección de los motores
3, 6, 11, 14 Salida a motores
2, 9 Habilitadores

Tabla 1: Control de motores de CD

49
Figura 1: Terminales L293

Algunas de las configuraciones mas usadas se numeran a continuación:

1. Control directo usando tres señales de para cada motor (figura 2)

2. Control directo usando dos señales para cada motor (figura 3)

3. Control usando optoacopladores en cada señal (figura 4)

50
Figura 2: Control con tres señales

Figura 3: Control con dos señales

51
Figura 4: Uso de optoacopladores

Es recomendable contar con una fuente de alimentación para el circuito con-


trolador y otra para el driver para evitar el efecto de las cargas inductivas. Para los
dos primeros casos es necesario conectar la tierra de ambos sistemas con la finalidad
de cerrar el circuito; mientras que en la tercera se contará con independencia total
en la alimentación de ambos sistemas.

52
Apendice B

Compilador CCS
El compilador CCS permite programar los algoritmos empleando programación en
lenguaje C, es posible la implantación de estos usando el entorno de desarrollo
integrado del PIC C Compiler o el IDE del MPLAB. Se recomienda consultar la
ayuda del compilador para conocer las funciones especı́ficas que vienen integradas
en este.

IDE PIC C Compiler


Es un entorno fácil de usar, permite editar los programas, compilar y cuenta con una
terminal que es útil en la comunicación serie ası́ncrona; una véz que se ha compilado
un programa y se desea trabajar con otro, es necesario cerrar este, para continuar
trabajando con el nuevo; en caso contrario seguirá compilado el código original.

Al ejecutar el PIC C Compiler, presenta su entorno, como se muestra en la


figura 5.

Figura 5: Entorno PIC C Compiler

53
Una véz terminado el programa, se debe seleccionar la opción Microchip 14
bits, para configurar las versiones compatibles con los PIC16F877; una vez hecho
esto se procede a compilar; tal como se muestra en la figura 6.

Figura 6: Compilación

En caso de no existir error en el programa, presenta los mensajes que se indican


en la figura 7; generando el código de máquina *.HEX y se proceder a programar
el dispositivo mediante las opciones que se describen ms adelante. En caso de tener
error en el programa, indicará el tipo de este y la lı́nea donde se encuentra.

54
Figura 7: Ventana de estado

MPLAB
Usar este entorno para compilar programas escritos en C, requiere un proceso más
largo; se necesita crear un proyecto, agregar un programa fuente a este y compilar,
de igual manera generará un programa*.HEX.

El entorno de tabajo se muestra en la figura 8.


La configuración de la heramienta empleada para compilar los programas; se-
leccionar P roject y después select languaje toolsuite; deberá seleccionar CCS C
Compiler PIC12/14/16/18 (figura 9).

55
Figura 8: Entorno MPLAB

Figura 9: Configuración Ccsc

56
Comprobar la ubicación del compilador; nuevamente seleccionar project, set
languaje T ool locations, ubicar el compilador Ccsc.exe; tal como se indica en la
figura 10.

Figura 10: Selección Ccsc

Seleccionar la versión del microcontrolador (figura 11).

Figura 11: Selección del dispositivo

57
Para crear un proyecto nuevo, en el menú P roject seleccionar new; indicar el
nombre y la ubicación del proyecto (figura 12).

Figura 12: Creación de un proyecto

Se debe abrir el entorno para escribir el programa fuente, seleccionar F ile y


posteriormente N ew; se abrirá la ventana de captura sin nombre, una véz terminado
indicar el nombre y ubicación donde se almacenará el programa, debe tener extencián
*.C (figura 13).

Figura 13: Creación de un archivo nuevo

58
El programa recién creado se deberá agregar al proyecto, siguiendo el pro-
cedimiento de la figura 14.

Figura 14: Agregar archivo al proyecto

Es necesario configurar el proyecto; por lo que se debe posicionar en el archivo


agregado, presionar el boton izquierdo del mouse y seleccionar Build Option (figura
15).

Figura 15: Opciones de configuración del proyecto

59
Deshabilitar la opción Symbol F ile en Others F iles y habilitar N one en debug
(figura 16).

Figura 16: Configuración del proyecto

Una véz realizado todo el procedimiento anterior, se iniciará la compilación;


accediendo a P roject del menú principal y seleccionar build all; o en su caso usar
el cono de compilación (figura 17).

Figura 17: Compilar

60
En caso de no existir error, mostrará la pantalla de la figura 18. Se tendrá
entonces el código de máquina requerido para programar al microcontrolador.

Figura 18: Resultado de la compilación

61
PICDOWNLOADER
Una véz generado el código *.HEX, se programará en el PIC, este proceso se podrá
hacer utilizando un programador externo (hardware) o un pequeño código que se
programa previamente al microcontrolador llamado Bootloader y que permitirá por
software la programación del mismo.

Al jecutar el programa P ICDOW N LOADER, mostrará la figura 19; se de-


berá seleccionar el programa deseado, configurar la velocidad a la cuál transmitirá
los datos, (informacin del bootloader dependiente de la versión del microcontrolador
y del valor del cristal usado), ası́ mismo indicar el puerto serie (COM) donde se ha
conectado.

Figura 19: Entorno PICDOWNLOADER

Una véz seleccionado el programa, presionar W rite, el ambiente solicitará se


presione el botón de reset del sistema; una vez hecho esto se inicia de programación
del microcontrolador; la barra de estado representa el avance del proceso.

En el momento que se ha concluı́do la programación, despliega el texto All


OK; en caso contrario se deberá revisar problemas en el sistema de desarrollo o en
la configuración realizada. El programa recién cargado iniciará automáticamente la
ejecución (figura 20).

62
Figura 20: Proceso de programación

63
Sistema mı́nimo

Figura 21: Sistema mı́nimo del microcontrolador PIC

64
Hyperterminal
Para establecer esta terminal debe de acceder a P rogramas, accesorios y comunicaciones
para ubicar a la terminal; la primer pantalla que presenta, es para ingresar el nombre
de la conexión (figura 22); posteriormente solicitará el número de COM donde se
este conectando.

Figura 22: Terminal para comunicación serie

Configurar la terminal; esto incluye la velocidad del programa, el protocolo y


el tipo de control de los datos; la figura 23 muestra la configuración tı́pica.

65
Figura 23: Configuración de la terminal

66
Una véz que se ha tecleado aplicar y posteriormente aceptar, se tendrá abierta
la terminal para la comunicación serie ası́ncrona entre una computadora personal y
el microcontrolador. Tal véz requiera presionar el botón de reset a procesador para
reiniciar el programa; en caso de requerir reprogramar al procesador mediante el
bootloader, deberá desconectarse de la hyperterminal para liberar el puerto.

Figura 24: Entorno de la hyperterminal

67

Вам также может понравиться