TODOPIC
Microcontroladores PIC => Lenguaje C para microcontroladores PIC => Mensaje iniciado por: pablocabrera en 28 de Abril de 2011, 22:29:46
-
Estimados amigos foreres he recorrido el foro y he hecho este codigo y antes de preguntar he tratado re autoayudarme :lol: , el siguiente código lo necesito para poder activar un par de reles de la siguiente forma: de Rele 1 en 3 segundos y el rele 2 en 15 minutos el problema que tengo es que la señal de entrada puede durar 15 segundos hasta 2 minutos y el tiempo de activacion es este bueno en el codigo lo comento. El problema es que cuando lo compilo se compila sin problemas y cuando lo llevo a proteus nada y cuando lo llevo a proto menos bueno les dejo el codigo y el esquemático en proteus
#include <16f628a.h> //pic a utilizar
#fuses XT,NOWDT,NOPROTECT,PUT //ordenes para el programador
#use delay (clock=4000000) //Fosc=4Mhz
#use fast_io(a)
#use fast_io(b)
#byte TRISA = 0x85
//#byte PORTA = 0X5
#byte TRISB = 0x86
#byte PORTB = 0x6 //Direccion del PORTB
#byte PORTA=5
#bit guardia=PORTB.0
#bit salamaquinas=PORTB.1
#bit exterior=PORTB.2
#bit timbreexterior=PORTB.7
//#bit SW_ABAJO=PORTA.6
//#bit SW_INTRO=PORTA.3
/*
#define luz1 PIN_B0
#define luz2 PIN_B1
#define exterior PIN_B2
#define timbre1 PIN_B3
#define timbre2 PIN_B4
#define salidadeco PIN_A0
#define test PIN_A1
#define salidamaquina PIN_A3*/
void activaluces(void);
void activasalida(void);
void main(){
int a;
set_tris_a(0b11001000);
set_tris_b (0x00); //portb como salida
setup_timer_0(RTCC_INTERNAL);setup_wdt(WDT_2304MS);
setup_timer_1(T1_INTERNAL|T1_DIV_BY_8);
setup_timer_2(T2_DISABLED,0,1);
setup_comparator(NC_NC_NC_NC);
setup_vref(FALSE);
//lcd_init();
enable_interrupts(INT_TIMER1);
disable_interrupts (GLOBAL);
setup_oscillator(OSC_4MHZ);
/* set_tris_a (0b00001111); //porta como entrada
set_tris_b (0x00); //portb como salida
BIT_CLEAR(PORTB,0);
/*BIT_CLEAR(PORTB,1);
BIT_CLEAR(PORTB,2);
BIT_CLEAR(PORTB,3);
BIT_CLEAR(PORTB,4);*/
// disable_interrupts(GLOBAL); //todas las interrupciones desactivadas
while(TRUE){ //ciclo eterno XD
a=input_a(); //almaceno el valor del puerto a
//BIT_CLEAR(PORTA);
switch(a)
{//de acuerdo a su valor selecciono la funcion
case 1: // si la entreda es (0b00000001)-->funcion1 haca la señal llega de un decoficador X
activacuartel();
break;
case 2: // si la entreda es (0b00000010)-->funcion2 es un pulsador
activacuartel();
break;
case 4: // si la entreda es (0b00000100)-->funcion3 es un pulsador
activasalida();
break;
default:
break;
}
}
}
void activacuartel()
{
int i,k;
guardia=1;
salamaquinas=1;
for(k=0; k<150; k++){
for(i=0; i<3; i++) //3.026 u[Seg] de periodo-->1.513 al 50%
{
timbreexterior=1;
delay_ms(500);
timbreexterior=0;
delay_ms(250);
timbreexterior=1;
delay_ms(1000);
timbreexterior=0;
}
exterior=1;
for(i=0; i<4; i++) //3.026 u[Seg] de periodo-->1.513 al 50%
{
timbreexterior=1;
delay_ms(500);
timbreexterior=0;
delay_ms(250);
timbreexterior=1;
delay_ms(1000);
timbreexterior=0;
}
exterior=0;
}
guardia=0;
salamaquinas=0;
}
void activasalida(void)
{
int i;
output_high(PIN_B2);
for(i=0; i<4; i++)
{
output_high(PIN_B4);
delay_ms(200);
output_low(PIN_B4);
delay_ms(200);
}
output_low(PIN_B2);
}
muchas gracias si me pueden ayudar
-
Buenas Pablo
He echado un vistazo a tu código y veo algunas cosillas que pueden o de hecho te dan problemas. Por ejemplo, activas la interrupción del Timer1 pero no la usas nunca. Esto no debería ser un problema, sin embargo en la función principal haces un uso exagerado de los delay. Ten en cuenta que cada vez que usas un delay el código principal se paraliza, esperando a que este delay termine para proseguir. Lo único que podría funcionar mientras un delay se produce es precisamente una interrupción. En tu caso, podrías usar la interrupción para chequear el estado de los botones (la estructura de selección switch), o mejor aún, activar una salida de forma alternativa cada cierto tiempo, que creo es lo que haces con los delay, a modo de testigo de funcionamiento. A su vez podrías usar otro Timer para mantener activos los relés el tiempo que necesites, contanto overflows. Por ejemplo, si configuras el timer0 así: setup_timer_0(RTCC_INTERNAL|RTCC_DIV_256); a 4 Mhz conseguirás un overflow cada 65,536ms (256us x 8 bits). Si quieres que tu relé permanezca encendido 15 minutos, serían: 15min=900seg=900000ms, 900000/65,536=13732,9 overflows, que si no necesitas gran precisión puedes redondear a 13733.
Y por último, en la función activacuartel() declaras variables que nunca usas para nada, como "guardia", "salamaquinas" o "exterior", solo les das valores. ¿Para qué te sirve eso?
Espero haberte ayudado en algo. Un saludo.
-
si muchas gracias. he visto otro ejemplo y si timer en eso estoy tratare de mejorarlo y lo otro que vi otra estructura para el codigo muchas gracias en caso de algo lo publico