PIC16F690: Using RA2 as Both an Input and an Interrupt
I brought some code from a PICDEM DV lab example into a simple program I'd written. The example showed how to use the external interrupt on the PIC16F690 to switch directions in a function.
I've been trying to use that RA2 pin as both the input (start) trigger for one of my functions and as an interrupt to get out of that function, too. So far the interrupt doesn't work, but the function trigger does. Should I use two pushbuttons or add a random timer to the for() loop to execute the function to roll the dice?
Trying to incorporate that example code also seems to have messed up the little random counter [a for() loop] that I used. The dice pattern was reliably random before adding this new stuff, and now I can clearly see repetition.
Sorry for the messy noob coding. I'm only just starting a MC class.
Code:
#pragma config FOSC = INTRCIO // Oscillator Selection bit
#pragma config WDTE = OFF // Watchdog Timer Enable bit
#pragma config PWRTE = OFF // Power-up Timer Enable bit
#pragma config MCLRE = OFF // MCLR Pin Function Select bit
#pragma config CP = OFF // Code Protection bit
#pragma config CPD = OFF // Data Code Protection bit
#pragma config BOREN = ON // Brown-out Reset Selection bits
#pragma config IESO = ON // Internal External Switchover bit
#pragma config FCMEN = ON // Fail-Safe Clock Monitor Enabled bit
#include <xc.h> // Include HITECH CC header file
void FirstFlash(int);
void pause(unsigned short usvalue);
void msecbase(void);
void Initialize(void);
void Delay_5mS(void);
void OneToSixLoop(void);
//----------------------PROGRAM MEMORY----------------------
void Delay_5mS(void)
{ T0IF = 0; //Make sure the T0IF is cleared.
TMR0 = 100; //Preload the TMR0 register.
while (T0IF == 0); //Sit here and wait for Timer0 to overflow.
}
/*** INTERRUPT CODE ***/
void interrupt PB_PressISR(void)
{
if(INTE && INTF) INTF = 0; //Check to see if the interrupt was caused by
//the external interrupt on RA2.
//If so, clear the external interrupt flag
//to allow subsequent interrupts to be detected.
if(RA2 == 0) //Check to see if the RA2 pin is 0;
{ //(i.e. push button pressed).
Delay_5mS(); //If RA2 is 0, delay for 5mS to filter
} //any switch bounce.
if(RA2 == 0)
{
PORTC = 0x00;
OneToSixLoop(); }
}
void main(void)
{
Initialize();
OneToSixLoop();
} //end main
void Initialize(void)
{ /*** Configure Timer0 to overflow ever 5ms ***/
T0CS = 0; // Select FOSC/4 as Timer0 clock source.
T0SE = 0; // Increment TMR0 on rising clock edge.
PSA = 0; // Assign prescaler to Timer0.
PS0 = 0; // Select a 1:32 prescaler.
PS1 = 0;
PS2 = 1;
/*** Initialize Ports ***/
ANSEL = 0; // Intialize A/D ports off
CM1CON0 = 0; // Initialize Comparator 1 off
CM2CON0 = 0; // Initialize Comparator 2 off
PORTC = 0x00; //Clear PortC port
TRISC = 0x00; //All PortC I/O outputs
TRISA = 0xFF; //All PortA I/O inputs
ANS2 = 0;
/*** Initialize Interrupts ***/
INTEDG = 0; // Interrupt occurs on High/Low transition of RA2 voltage.
INTE = 1; // Enable the RA2/PIN17 external interrupt.
INTF = 0; // Clear the external interrupt flag.
GIE = 1; // Enable global interrupt capability on the PIC16F690--
// ***ALWAYS DONE LAST*****
}
//*******************************************************
void pause( unsigned short usvalue ) // Pause function
{
unsigned short x;
for (x=0; x<=usvalue; x++) // Loop through a delay equal to usvalue
{ // in milliseconds.
msecbase(); // Jump to millisec delay routine.
}
}
//*******************************************************
void msecbase(void) // Msecbase function
{
OPTION_REG = 0b00000001; // Set prescaler to TMRO 1:4
TMR0 = 0xD; // Preset TMRO to overflow on 250 counts
while(!T0IF); // Stay until TMRO overflow flag equals 1
T0IF = 0; // Clear the TMR0 overflow flag
}
//*******************************************************
void FirstFlash(int DiceRND)
{ int Pattern;
INTF = 0;
for(Pattern = 0; Pattern <=4; Pattern++)
{ PORTC = 0xFF;
pause(100);
PORTC = 0x00;
pause(100);
}
if(DiceRND==1) PORTC = 0b00001000;
if(DiceRND==2) PORTC = 0b01000001;
if(DiceRND==3) PORTC = 0b01001001;
if(DiceRND==4) PORTC = 0b01100011;
if(DiceRND==5) PORTC = 0b01101011;
if(DiceRND==6) PORTC = 0b01110111;
pause(10000);
PORTC = 0x00;
}
void OneToSixLoop(void)
{ while(1==1)
{ int DiceRND;
for(DiceRND = 1; DiceRND <= 6; DiceRND++)
{ if(RA2 == 0)
{ FirstFlash(DiceRND); }
else if(DiceRND == 6)
{ DiceRND = 0; }
}
}
}