Saltar al contenido

Teclado Matricial con PIC

En esta entrada aprenderas a manejar el Teclado Matricial 4×3 y el Teclado Matricial 4×4 con cualquier microcontrolador PIC usando el PIC C Compiler.

Además de Aprender sobre Teclado Matricial PIC, si no has visto las otras entradas del Curso de Microcontroladores PIC, te invito a darle un vistazo para que Aprendas más: 👉 Curso de Microcontroladores PIC

También te puedes suscribir al canal de YouTube si deseas seguir aprendiendo sobre estos temas.

Teclado Matricial

Un teclado matricial es un arreglo o matriz de pulsadores que permiten darle a nuestros proyectos un método de interacción con el usuario para el ingreso de diferentes datos que posteriormente pueden ser procesados dentro del programa del microcontrolador PIC.

En el mercado podemos encontrar Teclados matriciales de diferentes tamaños, como el teclado matricial 4×4, 3×3, 4×3, entre otros. Estos teclados pueden tener una estructura de membrana o una estructura rigida.

Teclados Matriciales de Membrana
Teclados Matriciales de Membrana

Funcionamiento y programación de un Teclado Matricial

Para programar un Teclado Matricial o un Keypad en un PIC o en cualquier otro microcontrolador, basta con seguir en orden la siguiente secuencia:

  1. Inicialmente conectamos el teclado matricial en un puerto configurando los PINES como DIGITALES. Para eso será importante poder identificar cuales son las columnas y las filas del teclado.
  2. Las Filas del Teclado estarán conectadas en PINES DIGITALES configurados como SALIDAS.
  3. Las Columnas del Teclado estarán conectadas en PINES DIGITALES configurados como ENTRADAS y con las Resistencias PULLUP activadas (por lo tanto, estas entradas siempre estarán recibiendo un 1 lógico, si ningún botón es presionado).
    Si el puerto NO posee resistencias PULLUP estás deben ser agregadas fisicamente (resistencias conectadas a las columnas y a +5v)
  4. Configuramos TODAS las SALIDAS (Filas) en 1 lógico o 5v, es decir vamos a dejarlas encendidas.
  5. Aplicamos el concepto de la MULTIPLEXACIÓN: Aquí vamos a mandar un 0 lógico por cada fila y vamos a leer todas las columnas, si se detecta que alguna columna recibió el cero lógico, indica que el botón que comparte la fila y la columna fue presionado, en caso contrario vuelvo a colocar la fila en 1 lógico y verifico la siguiente fila.

En la siguiente animación podemos ver como se establece el presionado de un botón sobre el keypad.

Teclado Matricial Animado

Teclado Matricial PIC C Compiler CCS C

En el compilador hay un driver conocido como KBD.c para manejar un teclado telefónico, que es de gran utilidad en algunas aplicaciones donde el usuario necesita digitar un número.

Teclado telefonico pic 16f887

Los pasos que se deben seguir para manejar un teclado telefónico son:

Teclado Matricial 4×3

1. Incluir en el encabezado el driver para manejar el teclado telefónico:

#INCLUDE<KBD.C>

2. Por defecto el teclado matricial está configurado para conectarse al puerto D, sin embargo, la documentación de la librería detalla que el puerto debe poseer las resistencias PULL-UP del microcontrolador o de lo contrario deberemos colocar dichas resistentcias de forma física si deseamos usar un puerto que no posea estas resistencias internamente.

El microcontrolador 16F887, 16F877A, 18F4550 entre otros posee las resistencias PULL-UP en el puerto B por lo tanto debemos añadir al encabezado la siguiente línea:

#DEFINE USE_PORTB_KBD

3. En el programa principal se debe habilitar las resistencias pullup del puerto B, con esto simplemente se habilitan internamente unas resistencias del puerto B a a positivo.

PORT_B_PULLUPS(TRUE);

Si la instrucción anterior no funciona, o marca algún error, puedes usar la siguiente instrucción.

PORT_B_PULLUPS(0xFF);

4. En el programa principal debemos inicializar el driver del teclado matricial usando la siguiente función de la propia libreria KBD:

KBD_INIT()

5. Para llamar la función del teclado y almacenar el valor digitado en una variable tipo carácter usamos el siguiente comando, donde si no se oprime ninguna tecla el teclado retorna el carácter nulo.

K=KBD_GETC(); // K debe ser una variable tipo caracter (char)

NOTA: Si se utiliza otro microcontrolador y se conecta el teclado telefónico al puerto D se debe poner resistencias a +5V en RD1, RD2, RD3 y RD4.

teclado matricial 4×3 pic 16f887 o cualquier 16F

#INCLUDE <16F887.H>
#FUSES XT,NOPROTECT,NOBROWNOUT,PUT,NOLVP,WRT
#USE DELAY(CLOCK=4000000)
#DEFINE USE_PORTB_KBD
#INCLUDE <KBD.C>

Para cambiarlo por ejemplo para el 16F877A,  solo basta cambiar la libreria

#INCLUDE <16F877A.H>

Para Cambiarlo para el 18F4550, debes colocar en el encabezado:

#INCLUDE <18F4550.H>
#FUSES XT,NOPROTECT,NOBROWNOUT,PUT,NOLVP,WRT
#USE DELAY(CLOCK=4000000)
#DEFINE USE_PORTB_KBD
#INCLUDE <KBD.C>
#byte porta = 0xf80 // Identificador para el puerto A. 
#byte portb = 0xf81 // Identificador para el puerto B. 
#byte portc = 0xf82 // Identificador para el puerto C. 
#byte portd = 0xf83 // Identificador para el puerto D. 
#byte porte = 0xf84 // Identificador para el puerto E.

Teclado Matricial 4×4 PIC C Compiler CCS C

TECLADO MATRICIAL 4X4

No existe una libreria lista para usar el teclado matricial 4×4 en PIC C Compiler, pero podemos modificar la libreria del teclado 4×3 para poder manejar este dispositivo sin problemas.

En el video 2 de esta entrada explico como puedes modificar la libreria y como puedes usar el teclado 4×4. Puedes descargar la libreria modificada y la debes almacenar en tu computador en el directorio (C:\Program Files (x86)\PICC\Drivers)

Descargar Libreria:

1. Incluir en el encabezado el driver para manejar el teclado telefónico:

#INCLUDE<KBD4x4.C>

Proyectos con Teclados Matriciales

Prepare los siguientes video donde te explico el código implementado (Que se encuentra al final de este post) con el teclado matricial 4×3 y con el teclado matricial 4×4 paso a paso, con su respectiva explicación y como podemos simularlo por medio del proteus, para que posteriormente podamos llevarlo a la practica. No olvides suscribirte a mi canal de youtube dando click en el siguiente botón, para que puedas recibir toda la información que allí voy publicando.

 

Teclado 4×3 PIC 16F887

Esta practica también puede ser usada con teclado matricial pic 18F4550 o pic16F877A o cualquier otro PIC, simplemente cambiando los encabezados como lo vimos al comienzo del post.

Teclado Matricial PIC16F887

Realizar un programa que muestre en un display 7 segmentos los números presionados en un teclado matricial de 4×3.

Código del teclado matricial 4×3 con PIC

Para descargar directamente el código:

#INCLUDE <16F887.H>
#FUSES XT,NOPROTECT,NOBROWNOUT,PUT,NOLVP
//#USE DELAY(CLOCK=4000000) //Reloj interno 4MHz
#use delay(clock=4000000,crystal)//Crystal Externo 4MHz
Byte CONST display[10]= {0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x67};
#DEFINE USE_PORTB_KBD
#INCLUDE <KBD.C>
#BYTE PORTC= 7
#BYTE PORTB= 6
#BYTE WPUB= 0X95 // declarar registro option
#BYTE OPTION_REG = 0X81

CHAR K;


VOID MAIN()
{
   //PORT_B_PULLUPS(TRUE);
   OPTION_REG = 0; //en el MAIN desactivas el registro OPTION
   WPUB= 0B11111111;// y seleccionas los pullups q vas a utilizar
   
   KBD_INIT(); //Inicializar la rutina del teclado
   SET_TRIS_C(0); //Configurar el puerto C como salida
   PORTC=(display[0]);//Muestre en el display el número cero
   WHILE (TRUE)
   {
      K=0; //Ponga la variable K en cero
      K=KBD_GETC(); //Captura cualquier tecla oprimida
      IF(K=='0') //Si la tecla que se oprime es igual al caracter cero
         PORTC=(display[0]);//Muestre en el display el número cero
      IF(K=='1') //Si la tecla que se oprime es igual al caracter uno
         PORTC=( display [1]);//Muestre en el display el número uno
      IF(K=='2') //Tecla que se oprime = al caracter dos
         PORTC=( display [2]); //Muestre en el display el número dos
      IF(K=='3') // Tecla que se oprime = al caracter tres
         PORTC=( display [3]);//Muestre en el display el número tres
      IF(K=='4') // Tecla que se oprime = caracter cuatro
         PORTC=( display [4]);//Muestre en el display el número cuatro
      IF(K=='5') // Tecla que se oprime = caracter cinco
         PORTC=( display [5]);//Muestre en el display el número cinco
      IF(K=='6') // Tecla que se oprime = caracter //seis
         PORTC=( display [6]);//Muestre en el display el número seis
      IF(K=='7') // Tecla que se oprime = caracter siete
         PORTC=( display [7]);//Muestre en el display el número siete
      IF(K=='8') // Tecla que se oprime = caracter ocho
         PORTC=( display [8]);//Muestre en el display el número ocho
      IF(K=='9') // Tecla que se oprime = caracter nueve
         PORTC=( display [9]);//Muestre en el display el número nueve
   }
}

Teclado Matricial 4×4 PIC 16F887

De la misma forma, puedes usar esta practica para cualquier otro microcontrolador PIC.

Leer un teclado matricial PIC 4×4 y mostrar los numeros digitados en un LCD, adicionalmente se debe leer un sensor de temperatura y también mostrarla en el LCD, debes hacer que el PIC no se quede pegado unicamente leyendo el teclado, si no que continue leyendo la temperatura y mostrandola independientemente si el usuario digita o no el teclado telefonico 4×4. 

Para esta practica debes daber usar el LCD (Click aca para aprender)

Para esta practica debes daber usar el convertidor analogo digital (Click aca para aprender)

Teclado Matricial 4x4

Demostración práctica del teclado matricial 4×4

Código del Teclado 4×4 con PIC

Para descargar directamente el código (recordando que ya debiste descargar la librería que se encuentra en la parte superior de este post)

#INCLUDE <16F887.H>
#device adc=10
#USE DELAY(CLOCK=4000000)
#FUSES XT,NOPROTECT,NOWDT,NOBROWNOUT,NOPUT,NOLVP
//#DEFINE USE_PORTB_LCD TRUE
#DEFINE USE_PORTB_KBD   //Por defecto el teclado se conecta al puerto D,
                        //como el microcontrolador que se esta usando
                        //no tiene puerto D se conecta al puerto B.*/
#INCLUDE <LCD.C>
#INCLUDE <KBD4x4.C>  //Incluir en el encabezado el driver para
                      //manejar el teclado telefónico MODIFICADO
#use     standard_io(b) 
#define  KEYHIT_DELAY   200    //Tiempo de espera del teclado en milisegundos
#byte PORTB= 6
#byte PORTC= 7
#BYTE PORTA= 5
#BYTE PORTD= 8
 
long bits;     //Variable almacena los bits
float tem;     //Almacena la temperatura
  
  INT DIR;

/*===========================================================================*/
/*=======================       FUNCION TECLA         =======================*/
/*===========================================================================*/
//Funcion encargada de esperar a que se presione una tecla 
char tecla(void)
{
   char c;
   do{ //espera hasta que se presione una tecla
      c=kbd_getc(); //Captura valor del teclado
     }
   while(c=='
#INCLUDE <16F887.H>
#device adc=10
#USE DELAY(CLOCK=4000000)
#FUSES XT,NOPROTECT,NOWDT,NOBROWNOUT,NOPUT,NOLVP
//#DEFINE USE_PORTB_LCD TRUE
#DEFINE USE_PORTB_KBD   //Por defecto el teclado se conecta al puerto D,
//como el microcontrolador que se esta usando
//no tiene puerto D se conecta al puerto B.*/
#INCLUDE <LCD.C>
#INCLUDE <KBD4x4.C>  //Incluir en el encabezado el driver para
//manejar el teclado telefónico MODIFICADO
#use     standard_io(b) 
#define  KEYHIT_DELAY   200    //Tiempo de espera del teclado en milisegundos
#byte PORTB= 6
#byte PORTC= 7
#BYTE PORTA= 5
#BYTE PORTD= 8
long bits;     //Variable almacena los bits
float tem;     //Almacena la temperatura
INT DIR;
/*===========================================================================*/
/*=======================       FUNCION TECLA         =======================*/
/*===========================================================================*/
//Funcion encargada de esperar a que se presione una tecla 
char tecla(void)
{
char c;
do{ //espera hasta que se presione una tecla
c=kbd_getc(); //Captura valor del teclado
}
while(c=='\0'); 
return(c);
}
/*===========================================================================*/
/*=======================    FUNCION TECLA CON TIMER  =======================*/
/*===========================================================================*/
// Pregunta por una Tecla por un tiempo, si no hay actividad, deja de preguntar
// y deja que el PIC continue con su trabajo
char tecla_time(void) {
char c='\0';
unsigned int16 timeout;
timeout=0;
c=kbd_getc(); //Captura valor del teclado
while(c=='\0' && (++timeout< (KEYHIT_DELAY*100)))
{
delay_us(10);
c=kbd_getc(); //Captura valor del teclado
}
return(c);
}
/*===========================================================================*/
/*=======================       PROGRAMA PRINCIPAL    =======================*/
/*===========================================================================*/
VOID MAIN()
{
CHAR K;
port_b_pullups (0xFF);  //Utiliza las resistencias PULL UP internas del puerto B
set_tris_a(0b00000001);          //Pongo el RA0 como entrada
SET_TRIS_B(0);
SET_TRIS_C(0);    //Puerto C como Salida
setup_adc_ports(sAN0);     //Pongo RA0 como analogo
setup_adc(adc_clock_internal);   //Selecciono reloj interno para conversion
LCD_INIT();       //Inicializar el driver del lcd
KBD_INIT();       //Inicializar el driver del teclado
LCD_PUTC("\f");   //Limpia el LCD
WHILE(1)
{
DIR=9;
LCD_GOTOXY(1,2);  //Ubica el cursor del LCD
LCD_PUTC("Teclas= ");
LCD_GOTOXY(1,2);  //Ubica el cursor del LCD
while (DIR<17)
{
if(k!='\0'){
LCD_GOTOXY(DIR,2);
lcd_putc(k);
k='\0';
DIR++;
}
// ============================================================================= //        
//A continuación se muestran diferentes formas para leer los valores
//del teclado matricial, descomenta la forma de almacenar el dato
//en la variable "k" y observa las diferencias de cada llamado
//k=tecla();      //Lee el valor del teclado y espera hasta que alguna tecla se pulse
k=tecla_time();   //Lee el valor del teclado pero solo espera un tiempo determinado
//k=kbd_getc();   //Función del ccs c para leer el valor del teclado (sin control)
// ============================================================================= //   
if(DIR>16)
LCD_PUTC("\f");
//Lectura ADC
set_adc_channel(0);          //Selecciono el canal 0 (RA0)
delay_ms(1);                 //llamo retardo de 1 ms
bits=read_adc();             //Guarde el dato del LM en tempe
tem=bits*0.4882;              //Conversion de bits a temperatura
lcd_gotoxy(1,1);             //Ubiquese en la posicion 2,2
printf(lcd_putc,"Temp= %f    ",tem);  //Muestra el valor numerico de la conversionconversion
}
}
}
'); return(c); } /*===========================================================================*/ /*======================= FUNCION TECLA CON TIMER =======================*/ /*===========================================================================*/ // Pregunta por una Tecla por un tiempo, si no hay actividad, deja de preguntar // y deja que el PIC continue con su trabajo char tecla_time(void) { char c='
#INCLUDE <16F887.H>
#device adc=10
#USE DELAY(CLOCK=4000000)
#FUSES XT,NOPROTECT,NOWDT,NOBROWNOUT,NOPUT,NOLVP
//#DEFINE USE_PORTB_LCD TRUE
#DEFINE USE_PORTB_KBD   //Por defecto el teclado se conecta al puerto D,
//como el microcontrolador que se esta usando
//no tiene puerto D se conecta al puerto B.*/
#INCLUDE <LCD.C>
#INCLUDE <KBD4x4.C>  //Incluir en el encabezado el driver para
//manejar el teclado telefónico MODIFICADO
#use     standard_io(b) 
#define  KEYHIT_DELAY   200    //Tiempo de espera del teclado en milisegundos
#byte PORTB= 6
#byte PORTC= 7
#BYTE PORTA= 5
#BYTE PORTD= 8
long bits;     //Variable almacena los bits
float tem;     //Almacena la temperatura
INT DIR;
/*===========================================================================*/
/*=======================       FUNCION TECLA         =======================*/
/*===========================================================================*/
//Funcion encargada de esperar a que se presione una tecla 
char tecla(void)
{
char c;
do{ //espera hasta que se presione una tecla
c=kbd_getc(); //Captura valor del teclado
}
while(c=='\0'); 
return(c);
}
/*===========================================================================*/
/*=======================    FUNCION TECLA CON TIMER  =======================*/
/*===========================================================================*/
// Pregunta por una Tecla por un tiempo, si no hay actividad, deja de preguntar
// y deja que el PIC continue con su trabajo
char tecla_time(void) {
char c='\0';
unsigned int16 timeout;
timeout=0;
c=kbd_getc(); //Captura valor del teclado
while(c=='\0' && (++timeout< (KEYHIT_DELAY*100)))
{
delay_us(10);
c=kbd_getc(); //Captura valor del teclado
}
return(c);
}
/*===========================================================================*/
/*=======================       PROGRAMA PRINCIPAL    =======================*/
/*===========================================================================*/
VOID MAIN()
{
CHAR K;
port_b_pullups (0xFF);  //Utiliza las resistencias PULL UP internas del puerto B
set_tris_a(0b00000001);          //Pongo el RA0 como entrada
SET_TRIS_B(0);
SET_TRIS_C(0);    //Puerto C como Salida
setup_adc_ports(sAN0);     //Pongo RA0 como analogo
setup_adc(adc_clock_internal);   //Selecciono reloj interno para conversion
LCD_INIT();       //Inicializar el driver del lcd
KBD_INIT();       //Inicializar el driver del teclado
LCD_PUTC("\f");   //Limpia el LCD
WHILE(1)
{
DIR=9;
LCD_GOTOXY(1,2);  //Ubica el cursor del LCD
LCD_PUTC("Teclas= ");
LCD_GOTOXY(1,2);  //Ubica el cursor del LCD
while (DIR<17)
{
if(k!='\0'){
LCD_GOTOXY(DIR,2);
lcd_putc(k);
k='\0';
DIR++;
}
// ============================================================================= //        
//A continuación se muestran diferentes formas para leer los valores
//del teclado matricial, descomenta la forma de almacenar el dato
//en la variable "k" y observa las diferencias de cada llamado
//k=tecla();      //Lee el valor del teclado y espera hasta que alguna tecla se pulse
k=tecla_time();   //Lee el valor del teclado pero solo espera un tiempo determinado
//k=kbd_getc();   //Función del ccs c para leer el valor del teclado (sin control)
// ============================================================================= //   
if(DIR>16)
LCD_PUTC("\f");
//Lectura ADC
set_adc_channel(0);          //Selecciono el canal 0 (RA0)
delay_ms(1);                 //llamo retardo de 1 ms
bits=read_adc();             //Guarde el dato del LM en tempe
tem=bits*0.4882;              //Conversion de bits a temperatura
lcd_gotoxy(1,1);             //Ubiquese en la posicion 2,2
printf(lcd_putc,"Temp= %f    ",tem);  //Muestra el valor numerico de la conversionconversion
}
}
}
'; unsigned int16 timeout; timeout=0; c=kbd_getc(); //Captura valor del teclado while(c=='
#INCLUDE <16F887.H>
#device adc=10
#USE DELAY(CLOCK=4000000)
#FUSES XT,NOPROTECT,NOWDT,NOBROWNOUT,NOPUT,NOLVP
//#DEFINE USE_PORTB_LCD TRUE
#DEFINE USE_PORTB_KBD   //Por defecto el teclado se conecta al puerto D,
//como el microcontrolador que se esta usando
//no tiene puerto D se conecta al puerto B.*/
#INCLUDE <LCD.C>
#INCLUDE <KBD4x4.C>  //Incluir en el encabezado el driver para
//manejar el teclado telefónico MODIFICADO
#use     standard_io(b) 
#define  KEYHIT_DELAY   200    //Tiempo de espera del teclado en milisegundos
#byte PORTB= 6
#byte PORTC= 7
#BYTE PORTA= 5
#BYTE PORTD= 8
long bits;     //Variable almacena los bits
float tem;     //Almacena la temperatura
INT DIR;
/*===========================================================================*/
/*=======================       FUNCION TECLA         =======================*/
/*===========================================================================*/
//Funcion encargada de esperar a que se presione una tecla 
char tecla(void)
{
char c;
do{ //espera hasta que se presione una tecla
c=kbd_getc(); //Captura valor del teclado
}
while(c=='\0'); 
return(c);
}
/*===========================================================================*/
/*=======================    FUNCION TECLA CON TIMER  =======================*/
/*===========================================================================*/
// Pregunta por una Tecla por un tiempo, si no hay actividad, deja de preguntar
// y deja que el PIC continue con su trabajo
char tecla_time(void) {
char c='\0';
unsigned int16 timeout;
timeout=0;
c=kbd_getc(); //Captura valor del teclado
while(c=='\0' && (++timeout< (KEYHIT_DELAY*100)))
{
delay_us(10);
c=kbd_getc(); //Captura valor del teclado
}
return(c);
}
/*===========================================================================*/
/*=======================       PROGRAMA PRINCIPAL    =======================*/
/*===========================================================================*/
VOID MAIN()
{
CHAR K;
port_b_pullups (0xFF);  //Utiliza las resistencias PULL UP internas del puerto B
set_tris_a(0b00000001);          //Pongo el RA0 como entrada
SET_TRIS_B(0);
SET_TRIS_C(0);    //Puerto C como Salida
setup_adc_ports(sAN0);     //Pongo RA0 como analogo
setup_adc(adc_clock_internal);   //Selecciono reloj interno para conversion
LCD_INIT();       //Inicializar el driver del lcd
KBD_INIT();       //Inicializar el driver del teclado
LCD_PUTC("\f");   //Limpia el LCD
WHILE(1)
{
DIR=9;
LCD_GOTOXY(1,2);  //Ubica el cursor del LCD
LCD_PUTC("Teclas= ");
LCD_GOTOXY(1,2);  //Ubica el cursor del LCD
while (DIR<17)
{
if(k!='\0'){
LCD_GOTOXY(DIR,2);
lcd_putc(k);
k='\0';
DIR++;
}
// ============================================================================= //        
//A continuación se muestran diferentes formas para leer los valores
//del teclado matricial, descomenta la forma de almacenar el dato
//en la variable "k" y observa las diferencias de cada llamado
//k=tecla();      //Lee el valor del teclado y espera hasta que alguna tecla se pulse
k=tecla_time();   //Lee el valor del teclado pero solo espera un tiempo determinado
//k=kbd_getc();   //Función del ccs c para leer el valor del teclado (sin control)
// ============================================================================= //   
if(DIR>16)
LCD_PUTC("\f");
//Lectura ADC
set_adc_channel(0);          //Selecciono el canal 0 (RA0)
delay_ms(1);                 //llamo retardo de 1 ms
bits=read_adc();             //Guarde el dato del LM en tempe
tem=bits*0.4882;              //Conversion de bits a temperatura
lcd_gotoxy(1,1);             //Ubiquese en la posicion 2,2
printf(lcd_putc,"Temp= %f    ",tem);  //Muestra el valor numerico de la conversionconversion
}
}
}
' && (++timeout< (KEYHIT_DELAY*100))) { delay_us(10); c=kbd_getc(); //Captura valor del teclado } return(c); } /*===========================================================================*/ /*======================= PROGRAMA PRINCIPAL =======================*/ /*===========================================================================*/ VOID MAIN() { CHAR K; port_b_pullups (0xFF); //Utiliza las resistencias PULL UP internas del puerto B set_tris_a(0b00000001); //Pongo el RA0 como entrada SET_TRIS_B(0); SET_TRIS_C(0); //Puerto C como Salida setup_adc_ports(sAN0); //Pongo RA0 como analogo setup_adc(adc_clock_internal); //Selecciono reloj interno para conversion LCD_INIT(); //Inicializar el driver del lcd KBD_INIT(); //Inicializar el driver del teclado LCD_PUTC("\f"); //Limpia el LCD WHILE(1) { DIR=9; LCD_GOTOXY(1,2); //Ubica el cursor del LCD LCD_PUTC("Teclas= "); LCD_GOTOXY(1,2); //Ubica el cursor del LCD while (DIR<17) { if(k!='
#INCLUDE <16F887.H>
#device adc=10
#USE DELAY(CLOCK=4000000)
#FUSES XT,NOPROTECT,NOWDT,NOBROWNOUT,NOPUT,NOLVP
//#DEFINE USE_PORTB_LCD TRUE
#DEFINE USE_PORTB_KBD   //Por defecto el teclado se conecta al puerto D,
//como el microcontrolador que se esta usando
//no tiene puerto D se conecta al puerto B.*/
#INCLUDE <LCD.C>
#INCLUDE <KBD4x4.C>  //Incluir en el encabezado el driver para
//manejar el teclado telefónico MODIFICADO
#use     standard_io(b) 
#define  KEYHIT_DELAY   200    //Tiempo de espera del teclado en milisegundos
#byte PORTB= 6
#byte PORTC= 7
#BYTE PORTA= 5
#BYTE PORTD= 8
long bits;     //Variable almacena los bits
float tem;     //Almacena la temperatura
INT DIR;
/*===========================================================================*/
/*=======================       FUNCION TECLA         =======================*/
/*===========================================================================*/
//Funcion encargada de esperar a que se presione una tecla 
char tecla(void)
{
char c;
do{ //espera hasta que se presione una tecla
c=kbd_getc(); //Captura valor del teclado
}
while(c=='\0'); 
return(c);
}
/*===========================================================================*/
/*=======================    FUNCION TECLA CON TIMER  =======================*/
/*===========================================================================*/
// Pregunta por una Tecla por un tiempo, si no hay actividad, deja de preguntar
// y deja que el PIC continue con su trabajo
char tecla_time(void) {
char c='\0';
unsigned int16 timeout;
timeout=0;
c=kbd_getc(); //Captura valor del teclado
while(c=='\0' && (++timeout< (KEYHIT_DELAY*100)))
{
delay_us(10);
c=kbd_getc(); //Captura valor del teclado
}
return(c);
}
/*===========================================================================*/
/*=======================       PROGRAMA PRINCIPAL    =======================*/
/*===========================================================================*/
VOID MAIN()
{
CHAR K;
port_b_pullups (0xFF);  //Utiliza las resistencias PULL UP internas del puerto B
set_tris_a(0b00000001);          //Pongo el RA0 como entrada
SET_TRIS_B(0);
SET_TRIS_C(0);    //Puerto C como Salida
setup_adc_ports(sAN0);     //Pongo RA0 como analogo
setup_adc(adc_clock_internal);   //Selecciono reloj interno para conversion
LCD_INIT();       //Inicializar el driver del lcd
KBD_INIT();       //Inicializar el driver del teclado
LCD_PUTC("\f");   //Limpia el LCD
WHILE(1)
{
DIR=9;
LCD_GOTOXY(1,2);  //Ubica el cursor del LCD
LCD_PUTC("Teclas= ");
LCD_GOTOXY(1,2);  //Ubica el cursor del LCD
while (DIR<17)
{
if(k!='\0'){
LCD_GOTOXY(DIR,2);
lcd_putc(k);
k='\0';
DIR++;
}
// ============================================================================= //        
//A continuación se muestran diferentes formas para leer los valores
//del teclado matricial, descomenta la forma de almacenar el dato
//en la variable "k" y observa las diferencias de cada llamado
//k=tecla();      //Lee el valor del teclado y espera hasta que alguna tecla se pulse
k=tecla_time();   //Lee el valor del teclado pero solo espera un tiempo determinado
//k=kbd_getc();   //Función del ccs c para leer el valor del teclado (sin control)
// ============================================================================= //   
if(DIR>16)
LCD_PUTC("\f");
//Lectura ADC
set_adc_channel(0);          //Selecciono el canal 0 (RA0)
delay_ms(1);                 //llamo retardo de 1 ms
bits=read_adc();             //Guarde el dato del LM en tempe
tem=bits*0.4882;              //Conversion de bits a temperatura
lcd_gotoxy(1,1);             //Ubiquese en la posicion 2,2
printf(lcd_putc,"Temp= %f    ",tem);  //Muestra el valor numerico de la conversionconversion
}
}
}
'){ LCD_GOTOXY(DIR,2); lcd_putc(k); k='
#INCLUDE <16F887.H>
#device adc=10
#USE DELAY(CLOCK=4000000)
#FUSES XT,NOPROTECT,NOWDT,NOBROWNOUT,NOPUT,NOLVP
//#DEFINE USE_PORTB_LCD TRUE
#DEFINE USE_PORTB_KBD   //Por defecto el teclado se conecta al puerto D,
//como el microcontrolador que se esta usando
//no tiene puerto D se conecta al puerto B.*/
#INCLUDE <LCD.C>
#INCLUDE <KBD4x4.C>  //Incluir en el encabezado el driver para
//manejar el teclado telefónico MODIFICADO
#use     standard_io(b) 
#define  KEYHIT_DELAY   200    //Tiempo de espera del teclado en milisegundos
#byte PORTB= 6
#byte PORTC= 7
#BYTE PORTA= 5
#BYTE PORTD= 8
long bits;     //Variable almacena los bits
float tem;     //Almacena la temperatura
INT DIR;
/*===========================================================================*/
/*=======================       FUNCION TECLA         =======================*/
/*===========================================================================*/
//Funcion encargada de esperar a que se presione una tecla 
char tecla(void)
{
char c;
do{ //espera hasta que se presione una tecla
c=kbd_getc(); //Captura valor del teclado
}
while(c=='\0'); 
return(c);
}
/*===========================================================================*/
/*=======================    FUNCION TECLA CON TIMER  =======================*/
/*===========================================================================*/
// Pregunta por una Tecla por un tiempo, si no hay actividad, deja de preguntar
// y deja que el PIC continue con su trabajo
char tecla_time(void) {
char c='\0';
unsigned int16 timeout;
timeout=0;
c=kbd_getc(); //Captura valor del teclado
while(c=='\0' && (++timeout< (KEYHIT_DELAY*100)))
{
delay_us(10);
c=kbd_getc(); //Captura valor del teclado
}
return(c);
}
/*===========================================================================*/
/*=======================       PROGRAMA PRINCIPAL    =======================*/
/*===========================================================================*/
VOID MAIN()
{
CHAR K;
port_b_pullups (0xFF);  //Utiliza las resistencias PULL UP internas del puerto B
set_tris_a(0b00000001);          //Pongo el RA0 como entrada
SET_TRIS_B(0);
SET_TRIS_C(0);    //Puerto C como Salida
setup_adc_ports(sAN0);     //Pongo RA0 como analogo
setup_adc(adc_clock_internal);   //Selecciono reloj interno para conversion
LCD_INIT();       //Inicializar el driver del lcd
KBD_INIT();       //Inicializar el driver del teclado
LCD_PUTC("\f");   //Limpia el LCD
WHILE(1)
{
DIR=9;
LCD_GOTOXY(1,2);  //Ubica el cursor del LCD
LCD_PUTC("Teclas= ");
LCD_GOTOXY(1,2);  //Ubica el cursor del LCD
while (DIR<17)
{
if(k!='\0'){
LCD_GOTOXY(DIR,2);
lcd_putc(k);
k='\0';
DIR++;
}
// ============================================================================= //        
//A continuación se muestran diferentes formas para leer los valores
//del teclado matricial, descomenta la forma de almacenar el dato
//en la variable "k" y observa las diferencias de cada llamado
//k=tecla();      //Lee el valor del teclado y espera hasta que alguna tecla se pulse
k=tecla_time();   //Lee el valor del teclado pero solo espera un tiempo determinado
//k=kbd_getc();   //Función del ccs c para leer el valor del teclado (sin control)
// ============================================================================= //   
if(DIR>16)
LCD_PUTC("\f");
//Lectura ADC
set_adc_channel(0);          //Selecciono el canal 0 (RA0)
delay_ms(1);                 //llamo retardo de 1 ms
bits=read_adc();             //Guarde el dato del LM en tempe
tem=bits*0.4882;              //Conversion de bits a temperatura
lcd_gotoxy(1,1);             //Ubiquese en la posicion 2,2
printf(lcd_putc,"Temp= %f    ",tem);  //Muestra el valor numerico de la conversionconversion
}
}
}
'; DIR++; } // ============================================================================= // //A continuación se muestran diferentes formas para leer los valores //del teclado matricial, descomenta la forma de almacenar el dato //en la variable "k" y observa las diferencias de cada llamado //k=tecla(); //Lee el valor del teclado y espera hasta que alguna tecla se pulse k=tecla_time(); //Lee el valor del teclado pero solo espera un tiempo determinado //k=kbd_getc(); //Función del ccs c para leer el valor del teclado (sin control) // ============================================================================= // if(DIR>16) LCD_PUTC("\f"); //Lectura ADC set_adc_channel(0); //Selecciono el canal 0 (RA0) delay_ms(1); //llamo retardo de 1 ms bits=read_adc(); //Guarde el dato del LM en tempe tem=bits*0.4882; //Conversion de bits a temperatura lcd_gotoxy(1,1); //Ubiquese en la posicion 2,2 printf(lcd_putc,"Temp= %f ",tem); //Muestra el valor numerico de la conversionconversion } } }

No olvides compartir el contenido en Redes sociales, para que me ayudes a hacer crecer el sitio, y que la información pueda llegarle a mas personas que lo necesiten y quieran aprender sobre este interesante mundo de los microcontroladores. Hasta la próxima.   Suscribete a mi canal de Youtube y a la Fans Page de Facebook:

Eso es todo por la entrada del dia de hoy, espero les haya gustado y hayan aprendido algo nuevo. Si te ha servido el contenido de esta entrada, de los videos y los códigos de implementación y deseas apoyar mi trabajo invitandome a un café super barato, puedes hacerlo en el siguiente link:

👉 Invitar a Sergio a un Café ☕️

Que esten muy bien, nos vemos en la siguiente entrada.

Entradas relacionadas

Deja una respuesta

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *

Este sitio usa Akismet para reducir el spam. Aprende cómo se procesan los datos de tus comentarios.

Comentarios (13)

una pregunta? se podra hacer con lenguaje ensamblador?

Responder

Qué tal Sergio, gracias por tus vídeos, una pregunta, si quiero borrar dígito por dígito lo que haya escrito en el LCD, por ejemplo, que cuando se presione la tecla ‘#’ se borre un dígito, ya trate de muchas formas y ninguna me sale, ¿Qué código me recomiendas ?

Responder

Puedes colocar un espacio en blanco reescribiendo el digito. Pero debes tener el conteo de la posición, puedes crear dos variables x,y os cuales vas modificando con la instrucción lcd_gotoxy(x,y).

Responder

Buenas noches, para programarlo en pic sin libreria seria igual que el metodo de Arduino haciendo una matriz de 4×4?

Responder

Es correcto Brayan, se usa la misma metodologia vista en la entrada de Arduino.

Responder

Hola ingeniero, muy buen contenido, tengo una duda, me solicitan ingresar un número de cuatro dígitos en hexadecimal (con un teclado 4×4) y que se visualice en una LCD su equivalente a decimal, si pudiera darme alguna idea de cómo hacerlo se lo agradeceré demasiado.

Responder

con el printf lo puedes hacer. Colocas %d para mostrar el número en decimal y %x para mostrar el número en hexadecimal.
printf(lcd_putc,»%d = %x»,numero,numero);

Responder

Muchas gracias por su ayuda, una duda más, para el proceso de conversión, almacenó los números en variables diferentes, es decir ¿cómo hago la lectura de lo que recibo por el teclado para convertirlo a decimal? Gracias

Responder

Debes almacenar los valores en un arreglo de caracteres y puedes convertir el arreglo con la función atol() que se encuentra en la librería estandar, stdlib.h

Responder

Hola Sergio, una pregunta, estoy haciendo la practica con el teclado 4×3 el telefonico con el pic 18f4550, pero no funciona, te pasare el codigo que estoy usando, para ver que tengo mal, gracias Sergio por hacer estos videos.

Responder

Hola Uriel, en el POST está detallado que si deseas usar el teclado matricial en el Puerto D, debes colocar físicamente las resistencias PULL-UP. He modificado el post para dejar esto bien claro. Esa nota puedes encontrarla en el encabezado de la librería KBD.c que dice lo siguiente «Make sure the port used has pull-up resistors (or the LCD) on the column pins» Por lo tanto coloca el teclado en el puerto B para que no tengas que usar hardware adicional y habilita las resistencias pullup del PIC como es especificado en este post. Saludos.

Responder

buenas tardes ingeniero, porfavor podria explicar de forma mas detallada la funcion char tecla_time(void) no entiendo el ciclo while que esta dentro de esta funcion, muchas gracias

Responder

En ese while se pregunta por dos condiciones:
1. Si no se oprime nada en la variable siempre será c=’\0′
2. tenemos un contador timeout que se esta incrementando, dentro del while tenemos un delay 10us, o sea q timeout incrementa cada 10us, si ese contador llega al tiempo predefinido en KEYHIT, la cual se define en el encabezado del programa, quiere decir que pasó el tiempo y nadie digito nada, por lo tanto la condición deja de cumplirse y se sale del while y continua con lo que estaba haciendo antes de entrar a la función.

Responder