TODOPIC
Microcontroladores PIC => Todo en microcontroladores PIC => Mensaje iniciado por: xabc2007 en 25 de Agosto de 2009, 09:12:20
-
hola, un saludo a todo el foro.
Intento visualizar la temperatura en un LCD de un proyecto ya hecho del libro "Compilador C CCS y simulador PROTEUS para microcontroladores PIC" y no funciona.
El libro viene con un cd donde viene el programa en c y el programa ya compilado (.hex) para cargarlo directamente en el pic. Tengo varios problemas.
-Aunque ya viene compilado, intento compilarlo yo para poderlo editar posteriormente y me sale el siguiente error:
Error 12 "c:\"archivodeprograma\PICC\drivers\lcd.c" line 91(29,30) undefined identifier -- set_tris_d
Error 12 "c:\"archivodeprograma\PICC\drivers\lcd.c" line 103(30,31) undefined identifier -- set_tris_d
Error 12 "c:\"archivodeprograma\PICC\drivers\lcd.c" line 133(28,29) undefined identifier -- set_tris_d
Da error la propia libreria que viene con el programa PCWHD Compiler
-Cargo el archivo .hex que viene en el cd en el pic para visualizar en el LCD y no sale nada. Solo se pone en negro la primera linea en el LCD
el conexionado del pic16f876 con el LCD es el siguiente
B0 enable
B1 rs
B2 rw
B4 D4
B5 D5
B6 D6
B7 D7
-Eso si, en la simulacion con el Proteus si que funciona.
Mis dudas son como puedo hacer para que al compilar el programa la libreria lcd.c no de error y como puedo hacer para visualizar en el display y no me salga la linea negra en el LCD.
Gracias de antemano.
Programa del termometro
#include "16f876.h"
#device adc=10
#fuses XT,NOWDT
#use delay(clock=4000000)
#include <math.h> //Necesaria para los cálculos matemáticos
#include <lcd.c>
void main() {
float tv,tr,temp,y; //Variables de ecuación
int16 value;
lcd_init();
// setup_port_a( ALL_ANALOG );
// setup_adc( ADC_CLOCK_INTERNAL );
// set_adc_channel( 0 );
delay_us(10);
do {
value = Read_ADC();
tv = 5.0 * value / 1024.0;
tr = tv * 10000.0 / (5.0 - tv);
y = log(tr/20000.0);
y = (1.0/298.15) + (y *(1.0/4050.0));
temp=1.0/y;
temp = temp -273.15;
printf(lcd_putc,"\nT = %04.2fC", temp);
} while (TRUE);
}
Libreria del LCD extraida del programa PCWHD Compiler lcd.c
//// licensed users of the CCS C compiler. No other use, reproduction ////
//// or distribution is permitted without written permission. ////
//// Derivative programs created using this software in object code ////
//// form are not restricted in any way. ////
///////////////////////////////////////////////////////////////////////////
// As defined in the following structure the pin connection is as follows:
// D0 enable
// D1 rs
// D2 rw
// D4 D4
// D5 D5
// D6 D6
// D7 D7
//
// LCD pins D0-D3 are not used and PIC D3 is not used.
// Un-comment the following define to use port B
// #define use_portb_lcd TRUE
struct lcd_pin_map { // This structure is overlayed
BOOLEAN enable; // on to an I/O port to gain
BOOLEAN rs; // access to the LCD pins.
BOOLEAN rw; // The bits are allocated from
BOOLEAN unused; // low order up. ENABLE will
int data : 4; // be pin B0.
} lcd;
#if defined use_portb_lcd
//#locate lcd = getenv("sfr:PORTB") // This puts the entire structure over the port
#ifdef __pch__
#locate lcd = 0xf81
#else
#locate lcd = 6
#endif
#define set_tris_lcd(x) set_tris_b(x)
#else
//#locate lcd = getenv("sfr:PORTD") // This puts the entire structure over the port
#ifdef __pch__
#locate lcd = 0xf83
#else
#locate lcd = 8
#endif
#define set_tris_lcd(x) set_tris_d(x)
#endif
#ifndef lcd_type
#define lcd_type 2 // 0=5x7, 1=5x10, 2=2 lines
#endif
#define lcd_line_two 0x40 // LCD RAM address for the second line
BYTE const LCD_INIT_STRING[4] = {0x20 | (lcd_type << 2), 0xc, 1, 6};
// These bytes need to be sent to the LCD
// to start it up.
// The following are used for setting
// the I/O port direction register.
struct lcd_pin_map const LCD_WRITE = {0,0,0,0,0}; // For write mode all pins are out
struct lcd_pin_map const LCD_READ = {0,0,0,0,15}; // For read mode data pins are in
BYTE lcd_read_byte() {
BYTE low,high;
set_tris_lcd(LCD_READ);
lcd.rw = 1;
delay_cycles(1);
lcd.enable = 1;
delay_cycles(1);
high = lcd.data;
lcd.enable = 0;
delay_cycles(1);
lcd.enable = 1;
delay_us(1);
low = lcd.data;
lcd.enable = 0;
set_tris_lcd(LCD_WRITE);
return( (high<<4) | low);
}
void lcd_send_nibble( BYTE n ) {
lcd.data = n;
delay_cycles(1);
lcd.enable = 1;
delay_us(2);
lcd.enable = 0;
}
void lcd_send_byte( BYTE address, BYTE n ) {
lcd.rs = 0;
while ( bit_test(lcd_read_byte(),7) ) ;
lcd.rs = address;
delay_cycles(1);
lcd.rw = 0;
delay_cycles(1);
lcd.enable = 0;
lcd_send_nibble(n >> 4);
lcd_send_nibble(n & 0xf);
}
void lcd_init() {
BYTE i;
set_tris_lcd(LCD_WRITE);
lcd.rs = 0;
lcd.rw = 0;
lcd.enable = 0;
delay_ms(15);
for(i=1;i<=3;++i) {
lcd_send_nibble(3);
delay_ms(5);
}
lcd_send_nibble(2);
for(i=0;i<=3;++i)
lcd_send_byte(0,LCD_INIT_STRING);
}
void lcd_gotoxy( BYTE x, BYTE y) {
BYTE address;
if(y!=1)
address=lcd_line_two;
else
address=0;
address+=x-1;
lcd_send_byte(0,0x80|address);
}
void lcd_putc( char c) {
switch (c) {
case '\f' : lcd_send_byte(0,1);
delay_ms(2);
break;
case '\n' : lcd_gotoxy(1,2); break;
case '\b' : lcd_send_byte(0,0x10); break;
default : lcd_send_byte(1,c); break;
}
}
char lcd_getc( BYTE x, BYTE y) {
char value;
lcd_gotoxy(x,y);
while ( bit_test(lcd_read_byte(),7) ); // wait until busy flag is low
lcd.rs=1;
value = lcd_read_byte();
lcd.rs=0;
return(value);
}
-
El problema es sencillo, el PIC16F876 no tiene puerto D :mrgreen: Así que cambia de puerto para el manejo del LCD o cambia al 16F877.
Saludos!
-
Muchas gracias por tu respuesta. ¿Cómo puedo programar el archivo lcd.c para poder utilizar el puerto b?
-
Debes colocar #define use_portb_lcd TRUE antes de llamar a la libreria.
Saludos!
-
Si, he añadido la linea #define use_portb_lcd TRUE antes de llamar a la libreria y al compilar no da errores.
Ahora con la simulacion con proteus el LCD no visualiza nada.
¿Hay que modificar el circuito electrico o la libreria Lcd.c?
Gracias.
-
El circuito debe corresponder al código, verifica que:
* B0 enable
* B1 rs
* B2 rw
* B4 D4
* B5 D5
* B6 D6
* B7 D7
Después haciendo la definición #define use_portb_lcd TRUE se pasa a usar el puerto B y no habría que cambiar nada en la librería.
Saludos!
-
gracias por tu tiempo,
la configuracion que me indicas es la que yo tengo puesta y el lcd en el simulador proteus no visualiza nada. Te adjunto el programa en c con la modificion #define use_portb_lcd TRUE que me has dicho:
#include "16f876.h"
#device adc=10
#fuses XT,NOWDT
#use delay(clock=4000000)
#include <math.h> //Necesaria para los cálculos matemáticos
#define use_portb_lcd TRUE
#include <lcd.c>
void main() {
float tv,tr,temp,y; //Variables de ecuación
int16 value;
lcd_init();
// setup_port_a( ALL_ANALOG );
// setup_adc( ADC_CLOCK_INTERNAL );
// set_adc_channel( 0 );
delay_us(10);
do {
value = Read_ADC();
tv = 5.0 * value / 1024.0;
tr = tv * 10000.0 / (5.0 - tv);
y = log(tr/20000.0);
y = (1.0/298.15) + (y *(1.0/4050.0));
temp=1.0/y;
temp = temp -273.15;
printf(lcd_putc,"\nT = %04.2fC", temp);
} while (TRUE);
}
-
Te adjunto otra librería, colócala en la carpeta de tu proyecto y solo cambia el include.
Saludos!
-
He cargado la nueva libreria y sigue sin ir la simulación.
No se que puede ser.
Gracias
-
Mil disculpas, si que funciona la simulacion en Proteus
Había sido fallo mio en el programa del termometro.
Voy a probar a programar el Pic en la placa a ver si consigo que funcione el LCD
Muchas gracias
-
Acabo de probar el LCD en la placa y sale la primera linea en negro. El LCD es de Powertip modelo PC1602F. Tengo dos LCD y en los dos hace lo mismo. ¿Qué puede ser?
-
Comprueba que las conexiones estén bien realizadas y fijas. Colocaste el potenciometro para controlar el contraste?
-
si, este modelo de LCD lo he conseguido de CEBEK y he leido que da problemas y hay que modificar el programa. ¿Tu sabes algo de esto?
-
Ya he conseguido que se visualice el LCD. Lo tenia montado en una placa de esas que puedes hacer el montaje soldando los cables. Lo monte en una protoboard y ya funciona. Ahora ya solo me queda hacer el circuito impreso.
Muchas gracias Suky por tu tiempo.