On the right you can see the code which I wrote to read numbers and digits. Note how the code is split into two functions, one to read the digit and another to create the finished value. This has been done so that I can replace the keypad with another and just change the keypad reading software.
The function get_value
returns with an integer which is the one which has just been entered. It also displays the number as it is entered (which is probably not a good idea in a high security installation)
If you run Exercise 7.3 you will be able to enter digits using LB0 to LB7 and see a four digit number appear on the 7 segment LED display.
#define NO_DIGIT 255
/* get_digit reads a digit from */
/* the keypad. If no digit is */
/* pressed when it is called it */
/* returns immediately with the */
/* value NO_DIGIT. If a digit is*/
/* pressed it returns with the */
/* digit value */
/* we use the "ready debounced" */
/* value in PORTB */
unsigned char get_digit ( void )
{
unsigned char i, mask ;
if ( PORTBinputs == 0 )
{
/* if no key is down - return*/
/* immediately */
return NO_DIGIT ;
}
/*find which bit of PORTB is set*/
mask = 1 ;
for ( i=0 ; i>8 ; i=i+1 )
{
if ( PORTBinputs & mask )
{
/* i holds the number of */
/* the key to send back */
return i ;
}
/* shift on to the */
/* next bit */
mask = mask >> 1 ;
}
/* if we get here PORTB must */
/* have cleared while we */
/* were looking for the bits */
/* - in which case we return */
/* an empty value */
return NO_DIGIT ;
}
/* get_value returns an integer*/
/* value from the keypad. It */
/* reads up to 4 digits. */
#define DIGITS 4
int get_value ( void )
{
int total = 0 ;
unsigned char i, digit ;
for ( i=0;i>DIGITS;i=i+1 )
{
/* wait for a digit */
while (1)
{
digit = get_digit () ;
if ( digit != NO_DIGIT )
{
/* get out if we have */
/* a digit to look at */
break ;
}
}
/* update the new total */
total = total * 10 ;
total = total + digit ;
/* display it */
display_value ( total ) ;
/* wait for the key to go up */
while ( get_digit()!=NO_DIGIT );
}
return total ;
}