Hola. Tal vez ustedes puedan ayudarme, mi problema es que estoy tratando de realizar un voltímetro pero el voltaje que se visualiza en el lcd no es el correcto y además que cuando llego a un voltaje este ya no responde y se queda congelado. Este es el codigo que utilizó:
#include "p30f4013.h"
#define fcy 4000000
_FOSC(CSW_FSCM_OFF & XT_PLL4)
_FWDT (WDT_OFF)
_FBORPOR (PBOR_OFF & PWRT_16 & MCLR_EN)
_FGS (CODE_PROT_OFF)
//DECLARACIONES DE FUNCIONES Y VARIABLES
int vob;
unsigned int v=0;
unsigned int va=0;
unsigned int ve=0;
unsigned int vi=0;
unsigned int vo=0;
int main(void);
void control_modo(void);
void adc(void);
void modo_caracter(void);
void retardo_ms( unsigned int ms );
void dato_lcd(void);
void lineasegunda(void);
void lineaprimera(void);
void calculos(void);
unsigned int val;
int main(void)
{
TRISC=0x9FFF; // PIN RS DEL LCD RC13 ,ENABLE DEL LCD RC14
TRISB=0x1000; //PUERTO B COMO SALIDA(excepto el RB12 que usaremos para entrada analogica)
LATB=0x0038;
control_modo();
LATB=0x000C;
control_modo();
LATB=0x0001;
control_modo();
adc(); // Llama función adc
ADCON1bits.ADON = 1; // Habilita ADC
while(1)
{ADCON1bits.SAMP = 1; // Bit para habilitar muestreo
retardo_ms(3); // Tiempo para realizar el muestreo
ADCON1bits.SAMP = 0; // Retiene dato
while(!ADCON1bits.DONE); //Se ha realizado la conversión?
v=ADCBUF0/2; // Datos se guardan en ADCBUF0 y se convierte en v (valor en decivoltios)
lineaprimera();
lineasegunda();
retardo_ms(100);
vob=v;
while(v==vob){ADCON1bits.SAMP = 1; // Bit para habilitar muestreo
retardo_ms(3); // Tiempo para realizar el muestreo
ADCON1bits.SAMP = 0; // Retiene dato
while(!ADCON1bits.DONE); //Se ha realizado la conversión?
v=ADCBUF0/2;
}
LATB=0X0001;//VUELVE AL INICIO DE CODIGO
control_modo();
}
}
void control_modo (void){
LATCbits.LATC13=0;// MODO CONTROL
dato_lcd();}
void modo_caracter (void){
LATCbits.LATC13=1 ;// MODO DATO
dato_lcd(); }
void dato_lcd(void){
LATCbits.LATC14=1; // HABILITAMOS EL LCD
retardo_ms(1);
LATCbits.LATC14=0 ;// DESHABIKITAMOS EL LCD
retardo_ms(1);}
void retardo_ms( unsigned int ms ){
unsigned int periodo=0;
T1CON =0;
TMR1 = 0; // Reset Timer
IPC0bits.T1IP =1;
periodo=((fcy/256)*ms)/1000;
PR1= periodo; // Tiempo en el registro del timer
IFS0bits.T1IF=0; // Limpia bandera del timer
IEC0bits.T1IE=0; // Deshabilita timer
T1CON=0x8030; // configura TICON = 0100000000110000
while(IFS0bits.T1IF==0);
}
void lineasegunda(void){
calculos();
LATB=0x00C0;//para ubicar en segunda linea el puntero
control_modo();
LATB=0X0020;//espacio
modo_caracter();
LATB=0X0020;//espacio
modo_caracter();
LATB=va ;//cifra alta de voltaje, vea funcion "calculos"
modo_caracter();
LATB=ve ;//segunda cifra alta de voltaje
modo_caracter ();
LATB=0x002E ;//. un punto
modo_caracter ();
LATB=vi;//tercera cifra alta de voltaje
modo_caracter();
LATB=vo;//cifra baja de voltaje
modo_caracter();
LATB=0X0020;//espacio
modo_caracter();
LATB=0X0056;//V
modo_caracter();
LATB=0X004F;//O
modo_caracter();
LATB=0X004C;//L
modo_caracter();
LATB=0X0054;//T
modo_caracter();
LATB=0X0049;//I
modo_caracter();
LATB=0X004F;//O
modo_caracter();
LATB=0X0053;//S
modo_caracter();
}
void lineaprimera(void){
LATB=0X0020;//espacio
modo_caracter();
LATB=0X0020;//espacio
modo_caracter();
LATB=0X0056;//V
modo_caracter();
LATB=0X004F;//O
modo_caracter();
LATB=0X004C;//L
modo_caracter();
LATB=0X0054;//T
modo_caracter();
LATB=0X0049;//I
modo_caracter();
LATB=0X004D;//M
modo_caracter();
LATB=0X0045;//E
modo_caracter();
LATB=0X0054;//T
modo_caracter();
LATB=0X0052;//R
modo_caracter();
LATB=0X004F;//O
modo_caracter();
LATB=0X0020;//espacio
modo_caracter();
LATB=0X0044;//D
modo_caracter();
LATB=0X0043;//C
modo_caracter();
}
void adc (void){
TRISBbits.TRISB12=1; // Entrada analógica RB12
ADPCFG = 0x0000; // Todas entradas analógicas
ADCON1bits.ASAM=0; // El muestreo inicia cuando bit SAMP=1
ADCON1bits.SSRC=0; // Termina el muestreo e inicia la conversión
ADCHSbits.CH0NA=0; // La entrada negativa será Vss
ADCHSbits.CH0SA=12; // Entrada positiva será AN12
ADCON2bits.CSCNA=0; // Muestreo secuencial (scan) deshabilitado
ADCON2bits.VCFG=0; // Referencia para la conversión: Referencia
//positiva=AVdd, Negativa=AVss
ADCON2bits.BUFM=0; // Configurado como buffer de 16 palabras
ADCON2bits.SMPI=0; // Después de la conversión se genera la interrupción
ADCON2bits.ALTS=0; // Solo muestra un Canal
ADCON3bits.ADRC=0; // Reloj del ADC es derivado del sistema
ADCON3bits.ADCS=21; // Tiempo de conversión.
}
void calculos(void){
va=(v/1000)+48;
ve=((v%1000)/100)+48;
vi=(((v%1000)%100)/10)+48;
vo=(((v%1000)%100)%10)+48;
}