#include <16F88.h>
#device adc=8
#FUSES NOWDT,INTRC_IO,MCLR,PUT,NOBROWNOUT,NOCPD,NOLVP,NOIESO,NODEBUG
//--- Constantes ---
#define SERVO_1 PIN_A0 //linea de control por PWM para el servo
#define ADC_SERVO 1 //canal adc que se usa para el potenciometro
//------------------
#use delay(clock=4000000)
#use standard_io(a)
#use standard_io(b)
//--- Variables ---
int1 flag5RTCC = TRUE; //indica si se completaron 5 RTCC
int1 flag50mS = FALSE; //indica si ocurrio interrupcion de timer1
int1 flagPulso_Alto = FALSE; //indica si esta el pulso en alto
int8 Posicion_Servo = 93; //donde se posiciona el servo segun la lectura del adc
int8 ContRTCC = 0; //contador de RTCC
//-----------------
//--- Funciones ---
void Calcular_Posicion(void);
//-----------------
#int_TIMER0
void TIMER0_isr(void){ //timer que cuenta 20mS
//Timer de 8 bits --> 256 = 1 RTCC
//Pescaler de 1:16
//1 tick cada 16 uS = 0.016mS
//1 RTCC cada 4.0mS (256 - 6 Ticks)
//5 RTCC = 20mS
ContRTCC = ContRTCC + 1;
set_TIMER0(6);
if(ContRTCC == 5){
flag5RTCC = TRUE;
ContRTCC=0;
}
}
#int_TIMER1
void TIMER1_isr(void) { //timer que cuenta 50mS
//Timer de 16 bits --> 65536 = 1 RTCC
//Pescaler de 1:1
//1 tick cada 1 uS
//1 RTCC cada 50mS (65536 - 15536 Ticks)
set_TIMER1(15535);
flag50mS = TRUE;
}
void main(void) {
int8 ValTMR0;
setup_adc_ports(sAN1|VSS_VDD);
setup_adc(ADC_CLOCK_INTERNAL);
setup_spi(FALSE);
setup_timer_0(RTCC_INTERNAL|RTCC_DIV_16);
setup_timer_1(T1_INTERNAL|T1_DIV_BY_1);
setup_timer_2(T2_DISABLED,0,1);
setup_comparator(NC_NC_NC_NC);
setup_vref(FALSE);
enable_interrupts(INT_TIMER1);
enable_interrupts(INT_TIMER0);
enable_interrupts(GLOBAL);
setup_oscillator(OSC_4MHZ|OSC_INTRC);
set_adc_channel(ADC_SERVO);
do {
//>-----------------------Movimiento del servo--------------------------------->
//--- Calcula posicion servo segun lectura adc ---
if(flag50mS == TRUE){
Calcular_Posicion();
flag50mS = FALSE;
}
//------------------------------------------------
//--- Dispara pulso PWM cuando se completan 5 RTCC ---
if(flag5RTCC == TRUE){
flag5RTCC = FALSE;
output_high(SERVO_1);
flagPulso_Alto = TRUE;
}
//----------------------------------------------------
//--- Baja pulso PWM cuando corresponda ---
valTMR0 = get_TIMER0() - 6;
if((flagPulso_Alto == TRUE) && (valTMR0 > Posicion_Servo)){ //baja el pulso en el tiempo correspondiente a Posicion
output_low(SERVO_1);
flagPulso_Alto = FALSE;
}
//-----------------------------------------
//<----------------------------------------------------------------------------<
} while(true);
}
void Calcular_Posicion(void){
int16 ValorADC;
ValorADC = read_adc();
Posicion_Servo = 31 + (int16)((int16)(ValorADC * 124) / 255);
}