4X4 Matrix keypad and AVR + LCD

Thread Starter

ElectroHead

Joined May 16, 2013
4
Dear Users,

Can you please help me with the following problem?

I have written some C code on AVR studio 4 to run an AVR Atmega 164p chip, to take input from a 4X4 matrix keypad and output the number pressed on an LCD.

The LCD and the code behind it is fine. However, there is a problem reading in the numbers from the keypad. When I press the keys '0' to '9' and 'A' to 'C' I get no response whatsoever. When I press 'D' and 'F' I get the number 0 appearing on the LCD. When I press 'E' I get the number two appearing on the LCD.

I have connected the Column wires from the keypad to 4.3Kohm resistors down to ground, I have set the row wires to constantly get a signal in from the AVR.

Additional information:
I am using an 8MHZ crystal oscillator


Please let me know if you need more information in order to help me.


***THE CODE IS BELOW:***



#include <avr/io.h>
#include <avr/interrupt.h>
#include <util/delay.h>
#include <stdlib.h>
#include <string.h>
#include <stdio.h>

/*----------- LCD and PORTA(Data) PORTD(Commands)------------------*/

#define LCD_Data PORTA //LCD Data output
#define LCD_Data_DDR DDRA //LCD Direction port
#define LCD_Data_RD PINA //LCD Data input

#define LCD_Control PORTD //Port where LCD control signals are
#define LCD_Control_RD PIND
#define LCD_Control_DDR DDRD
#define LCD_RS 0 //Pin on which LCD Register Select is
#define LCD_RW 1 //Pin on which LCD Read/Write is
#define LCD_E 2 //Pin on which LCD Enable is



/*------------------------- HEX keypad and PORTC----------------------*/
//define pins0-3 as rowsA-D (the rows of the hexadecinal keypad)***They will be defined as outputs from AVR to the Keypad****
#define rowA PC7 //This row is the bottom row, the numbers 0,1,2 and 3
#define rowB PC6
#define rowC PC5
#define rowD PC4//this row is the top row; the keys C,D,E and F

//define pins4-7 as columns 1-4 (columns of the hexadecimal keypad)
#define column1 PC3 // This is the leftmost column, the number 0,4,8 and C
#define column2 PC2
#define column3 PC1
#define column4 PC0// This is the rightmost column; the keys 3,7,B and F

// Meanings of the keys:
// A-
// B- Back to previous section
// C- Cancel
// D- Delete
// E- Enter (as in confirm)
// F-


/*Constants derived from information within Hitachi HD44780 datasheet--*/

// This command structure is used on every alphanumeric LCD.
#define DISP_FS 0x3f //Function set
#define DISP_ON 0x0c //Display on w/o blink or flash
#define DISP_OFF 0x08 //Display, blink, cursor off
#define DISP_CL 0x01 //Clear display
#define DISP_EN 0x06 //Data entry mode
#define LINE_1 0x80 //DDRAM address for first line
#define LINE_2 0xc0 //DDRAM address for second line
#define SH_LFT 0x18 //Left-shift display
#define SH_RT 0x1c //Right-shift display
#define HOME 0x02 //Return home


char dispstr[17];

uint8_t Captured;
uint16_t amplitude;

/*******************************************************/
/* LCD Function prototypes */
void LCD_Send_Command(uint8_t);
void LCD_Send_Data(uint8_t);
void LCD_Initialise(void);
void LCD_GOTOXY(uint8_t,uint8_t);
void LCD_Send_Data_XY(uint8_t /*data*/,uint8_t/*X coord*/,uint8_t/*Y coord*/);
void LCD_Send_String(char *);

/*******************************************************/
//#define Interval_1s 15625
//char freq[17] ="Frequency: Hz";
//char ampl[17] ="Average: V";
/********************************************************/


int main (void)
{


DDRC=(1<<rowA |1<<rowB | 1<<rowC| 1<<rowD);

LCD_Data_DDR=0xff;

LCD_Control_DDR|=(1<<LCD_RS | 1<<LCD_RW | 1<<LCD_E);

LCD_Control &=~(1<<LCD_RW);
LCD_Initialise();
_delay_ms(1);
//LCD_Send_String("");
//_delay_ms(1);
//LCD_GOTOXY(0,1);//sends the above string to the left-most position (x=0) on the top line (y=1 [indexed from zerol; zero being the bottom line])




while (1)
{



int some_var = PINC & 0x0F;//some variable that holds the value of the column you are on
//0001 is the right key/column of the particular row you are on
//1000 is the left key of the particular row you are on

PORTC = 1<<rowA; // Make rowA high
if(some_var)//if some var is not zero (i.e a button is pressed) do the following
{
if(some_var == 0x01)//0000 0001
{
LCD_Send_String("3");
_delay_ms(500);
LCD_GOTOXY(0,0);
}

else if(some_var == 0x02) //0000 0010
{
LCD_Send_String("2");
_delay_ms(500);
LCD_GOTOXY(0,0);
}

else if(some_var == 0x03)
{
LCD_Send_String("1");
_delay_ms(500);
LCD_GOTOXY(0,0);
}

else if(some_var == 0x04)
{
LCD_Send_String("0");
_delay_ms(500);
LCD_GOTOXY(0,0);
}
}


PORTC = 1<<rowB; // Make rowA high
if(some_var)
{
if(some_var == 0x01)
{
LCD_Send_String("7");
_delay_ms(500);
LCD_GOTOXY(0,0);
}
else if(some_var == 0x02)
{
LCD_Send_String("6");
_delay_ms(500);
LCD_GOTOXY(0,0);/
}


else if(some_var == 0x03)
{
LCD_Send_String("5");
_delay_ms(500);
LCD_GOTOXY(0,0);
}


else if(some_var == 0x04)
{
LCD_Send_String("4");
_delay_ms(500);
LCD_GOTOXY(0,0);
}
}


PORTC = 1<<rowC; // Make rowA high
if(some_var)
{
if(some_var == 0x01)
{
LCD_Send_String("B");
_delay_ms(500);
LCD_GOTOXY(0,0);
}

else if(some_var == 0x02)
{
LCD_Send_String("A");
_delay_ms(500);
LCD_GOTOXY(0,0);
}

else if(some_var == 0x03)
{
LCD_Send_String("9");
_delay_ms(500);
LCD_GOTOXY(0,0);
}
else if(some_var == 0x04)
{
LCD_Send_String("8");
_delay_ms(500);
LCD_GOTOXY(0,0);
}
}

PORTC = 1<<rowD; // Make rowA high

if(some_var)
{
if(some_var == 0x01)
{
LCD_Send_String("F");
_delay_ms(500);
LCD_GOTOXY(0,0);
}
else if(some_var == 0x02)
{
LCD_Send_String("E");
_delay_ms(500);
LCD_GOTOXY(0,0);
}
else if(some_var == 0x03)
{
LCD_Send_String("D");
_delay_ms(500);
LCD_GOTOXY(0,0);
}
else if(some_var == 0x04)
{
LCD_Send_String("C");
_delay_ms(500);
LCD_GOTOXY(0,0);
}
}





// Enable global interrupts
asm("sei");

asm("nop");
}

return(0);

}

/****************************************************************/
/*
LCD ROUTINES

Below are the routines to write data and commands to the
LCD. They differ only in the state of the Register
Select (LCD_RS) pin.
*/

void LCD_Send_Command(uint8_t command)
{
_delay_us(100);
LCD_Control &= ~(1<<LCD_RS);
LCD_Data = command;
LCD_Control |= (1<<LCD_E);
LCD_Control &= ~(1<<LCD_E);
}


void LCD_Send_Data(uint8_t data)
{
_delay_us(100);
LCD_Control |= (1<<LCD_RS);
LCD_Data = data;
LCD_Control |= (1<<LCD_E);
LCD_Control &= ~(1<<LCD_E);
}

//Go to a specific location on the LCD. 0,0 is the top left character
void LCD_GOTOXY(uint8_t x,uint8_t y)
{
if (x>39) x=0;
if (y>1) y=0;
//Ensure that the x,y values are within range
if (y==0) LCD_Send_Command(LINE_1+x);
if (y==1) LCD_Send_Command(LINE_2+x);
}

//Send a single character to a specific loaction
void LCD_Send_Data_XY(uint8_t d,uint8_t x,uint8_t y)
{
LCD_GOTOXY(x,y);
LCD_Send_Data(d);
}

//Send a string to the display.
void LCD_Send_String(char *ch)
{
int i=0;

while(ch!='\0')
{
LCD_Send_Data(ch[i++]);
}
}


//Initialise the LCD
void LCD_Initialise(void)
{
_delay_ms(10); //Ensure start-up delay
LCD_Send_Command(DISP_FS);
//Function set #
_delay_ms(16);
//16ms delay
LCD_Send_Command(DISP_FS);
//Function set
_delay_ms(5);
//5ms Delay
LCD_Send_Command(DISP_FS); //Function set
_delay_ms(5);
//1ms delay
LCD_Send_Command(DISP_FS); //Function set
_delay_ms(1);
//1ms delay
LCD_Send_Command(DISP_ON); //Turn Display on
_delay_ms(1);
//1ms delay
LCD_Send_Command(DISP_EN); //Set entry mode
_delay_ms(1);
//1ms delay
LCD_Send_Command(DISP_CL); //Clear Display
_delay_ms(1); //1ms delay
}
 

Thread Starter

ElectroHead

Joined May 16, 2013
4
Just to add, when I use the below if statements in place of the if statements above, I get the correct output when I press '5' 'A' and 'F' (i.e the LCD displays 5,A and F respectively), and no response when I press any of the other keys.

Code section below:

if(PINC & (1<<column1))//check to see if column1 is high at the same time as rowA is high
{//if so, display the number 0 on the LCD
// Initialise the ports used be the LCD


_delay_ms(50);//5ms delay to debounce the buttons
}
else if(PINC & (1<<column2))//check to see if column2 is high at the same time as rowA is high
{//if so, display the number 1 on the LCD
_delay_ms(5);
}
else if(PINC & (1<<column3))//check to see if column3 is high at the same time as rowA is high
{//if so, display the number 2
_delay_ms(5);
}
else if(PINC & (1<<column4))//check to see if column4 is high at the same time as rowA is high
{//if so, display the number 3
_delay_ms(5);
}
//PORTC &=~(1<<rowA);

PORTC = 1<<rowB; // Make rowB high

if(PINC & (1<<column1))//check to see if column1 is high at the same time as rowB is high
{//if so, display the number 4 on the LCD
_delay_ms(5);//5ms delay to debounce the buttons
}
else if(PINC & (1<<column2))//check to see if column2 is high at the same time as rowB is high
{//if so, display the number 5 on the LCD
LCD_Send_String(" 5");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
}
else if(PINC & (1<<column3))//check to see if column3 is high at the same time as rowB is high
{//if so, display the number 6
_delay_ms(5);
}
else if(PINC & (1<<column4))//check to see if column4 is high at the same time as rowB is high
{//if so, display the number 7
_delay_ms(5);
}
// PORTC &=~(1<<rowB);


PORTC = 1<<rowC; // Make rowC high

if(PINC & (1<<column1))//check to see if column1 is high at the same time as rowC is high
{//if so, display the number 8 on the LCD
_delay_ms(5);//5ms delay to debounce the buttons
}
else if(PINC & (1<<column2))//check to see if column2 is high at the same time as rowC is high
{//if so, display the number 9 on the LCD
_delay_ms(5);
}
else if(PINC & (1<<column3))//check to see if column3 is high at the same time as rowC is high
{//if so, display "Please do not use the 'A' key"
LCD_Send_String(" A");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
}
else if(PINC & (1<<column4))//check to see if column4 is high at the same time as rowC is high (i.e.B has been pressed)
{//if so, display "Press E to confirm you want to go back"
_delay_ms(5);
}
//PORTC &=~(1<<rowC);

PORTC = 1<<rowD; // Make rowD high

if(PINC & (1<<column1))//check to see if column1 is high at the same time as rowD is high
{//if so, display "cancle?"
_delay_ms(5);//5ms delay to debounce the buttons
}
else if(PINC & (1<<column2))//check to see if column2 is high at the same time as rowD is high
{//if so, display the "Delete?"
_delay_ms(5);
}
else if(PINC & (1<<column3))//check to see if column3 is high at the same time as rowD is high
{//if so, display "Enter' key"
_delay_ms(5);
}
else if(PINC & (1<<column4))//check to see if column4 is high at the same time as rowD is high (i.e.F has been pressed)
{//if so, display "Wat da rassklart?"
LCD_Send_String(" F");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);

}
// PORTC &=~(1<<rowD);
 

ErnieM

Joined Apr 24, 2011
8,377
Ummm... three things:

1 - Use code tags so your code is readable.

2 - If your code looks exactly the same it has Zacherly disease* and you need to read a code style guide to make it readable.

3 - Useless without schematic.

Just try to post the section of code that reads the key.

*Zacherly disease is defined as the condition where your code looks zacherly like a bung hole. :D
 

Thread Starter

ElectroHead

Joined May 16, 2013
4
The correct solution is below.

#include <avr/io.h>
#include <avr/interrupt.h>
#include <util/delay.h>
#include <stdlib.h>
#include <string.h>
#include <stdio.h>



#define LCD_Data PORTA //LCD Data output
#define LCD_Data_DDR DDRA //LCD Direction port
#define LCD_Data_RD PINA //LCD Data input

#define LCD_Control PORTD //Port where LCD control signals are
#define LCD_Control_RD PIND
#define LCD_Control_DDR DDRD
#define LCD_RS 0 //Pin on which LCD Register Select is
#define LCD_RW 1 //Pin on which LCD Read/Write is
#define LCD_E 2 //Pin on which LCD Enable is

#define rowA PC7
#define rowB PC6
#define rowC PC5
#define rowD PC4


#define column1 PC3
#define column2 PC2
#define column3 PC1
#define column4 PC0


#define DISP_FS 0x3f //Function set
#define DISP_ON 0x0c //Display on w/o blink or flash
#define DISP_OFF 0x08 //Display, blink, cursor off
#define DISP_CL 0x01 //Clear display
#define DISP_EN 0x06 //Data entry mode
#define LINE_1 0x80 //DDRAM address for first line
#define LINE_2 0xc0 //DDRAM address for second line
#define SH_LFT 0x18 //Left-shift display
#define SH_RT 0x1c //Right-shift display
#define HOME 0x02 //Return home


char dispstr[17];

uint8_t Captured;//what are these? global variables? what is thier purpose?
uint16_t amplitude;



void LCD_Send_Command(uint8_t);
void LCD_Send_Data(uint8_t);
void LCD_Initialise(void);
void LCD_GOTOXY(uint8_t,uint8_t);
void LCD_Send_Data_XY(uint8_t /*data*/,uint8_t/*X coord*/,uint8_t/*Y coord*/);
void LCD_Send_String(char *);




int main (void)
{


DDRC=(1<<rowA | 1<<rowB | 1<<rowC | 1<<rowD);

LCD_Data_DDR=0xff;

LCD_Control_DDR|=(1<<LCD_RS | 1<<LCD_RW | 1<<LCD_E);

LCD_Control &=~(1<<LCD_RW);
LCD_Initialise();
_delay_ms(1);
//LCD_Send_String("");
//_delay_ms(1);
//LCD_GOTOXY(0,1);//sends the above string to the left-most position (x=0) on the top line (y=1 [indexed from zerol; zero being the bottom line])




while (1)
{


PORTC = 1<<rowA; // Make rowB high
if(PINC & (1<<column1 |1<< column2));

else if(PINC & (1<<column1)) //check to see if column1 is high at the same time as rowC is high
{//if so, display the number 8 on the LCD
LCD_Send_String(" 0");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
_delay_ms(5);//5ms delay to debounce the buttons
}
else if(PINC & (1<<column2))//check to see if column2 is high at the same time as rowC is high
{//if so, display the number 9 on the LCD
LCD_Send_String(" 1");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
_delay_ms(5);
}
else if(PINC & (1<<column3))//check to see if column3 is high at the same time as rowC is high
{//if so, display "Please do not use the 'A' key"
LCD_Send_String(" 2");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
}
else if(PINC & (1<<column4))//check to see if column4 is high at the same time as rowC is high (i.e.B has been pressed)
{//if so, display "Press E to confirm you want to go back"
LCD_Send_String(" 3");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
_delay_ms(5);
}



PORTC = 1<<rowB; // Make rowB high

if(PINC & (1<<column1 |1<< column2));

else if(PINC & (1<<column1)) //check to see if column1 is high at the same time as rowC is high
{//if so, display the number 8 on the LCD
LCD_Send_String(" 4");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
_delay_ms(5);//5ms delay to debounce the buttons
}
else if(PINC & (1<<column2))//check to see if column2 is high at the same time as rowC is high
{//if so, display the number 9 on the LCD
LCD_Send_String(" 5");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
_delay_ms(5);
}
else if(PINC & (1<<column3))//check to see if column3 is high at the same time as rowC is high
{//if so, display "Please do not use the 'A' key"
LCD_Send_String(" 6");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
}
else if(PINC & (1<<column4))//check to see if column4 is high at the same time as rowC is high (i.e.B has been pressed)
{//if so, display "Press E to confirm you want to go back"
LCD_Send_String(" 7");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
_delay_ms(5);
}



PORTC = 1<<rowC; // Make rowC high
if(PINC & (1<<column1 |1<< column2));

else if(PINC & (1<<column1)) //check to see if column1 is high at the same time as rowC is high
{//if so, display the number 8 on the LCD
LCD_Send_String(" 8");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
_delay_ms(5);//5ms delay to debounce the buttons
}
else if(PINC & (1<<column2))//check to see if column2 is high at the same time as rowC is high
{//if so, display the number 9 on the LCD
LCD_Send_String(" 9");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
_delay_ms(5);
}
else if(PINC & (1<<column3))//check to see if column3 is high at the same time as rowC is high
{//if so, display "Please do not use the 'A' key"
LCD_Send_String(" A");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
}
else if(PINC & (1<<column4))//check to see if column4 is high at the same time as rowC is high (i.e.B has been pressed)
{//if so, display "Press E to confirm you want to go back"
LCD_Send_String(" B");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
_delay_ms(5);
}


PORTC = 1<<rowD; // Make rowD high
if(PINC & (1<<column1 |1<< column2));

else if(PINC & (1<<column1))//check to see if column1 is high at the same time as rowD is high
{//if so, display "cancle?"
LCD_Send_String(" C");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
_delay_ms(5);//5ms delay to debounce the buttons
}
else if(PINC & (1<<column2))//check to see if column2 is high at the same time as rowD is high
{//if so, display the "Delete?"
LCD_Send_String(" D");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
_delay_ms(5);
}
else if(PINC & (1<<column3))//check to see if column3 is high at the same time as rowD is high
{//if so, display "Enter' key"
LCD_Send_String(" E");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
_delay_ms(5);
}
else if(PINC & (1<<column4))//check to see if column4 is high at the same time as rowD is high (i.e.F has been pressed)
{//if so, display "Wat da rassklart?"
LCD_Send_String(" F");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);

}




// Enable global interrupts
asm("sei");

asm("nop");
}

return(0);

}


void LCD_Send_Command(uint8_t command)
{
_delay_us(100);
LCD_Control &= ~(1<<LCD_RS);
LCD_Data = command;
LCD_Control |= (1<<LCD_E);
LCD_Control &= ~(1<<LCD_E);
}


void LCD_Send_Data(uint8_t data)
{
_delay_us(100);
LCD_Control |= (1<<LCD_RS);
LCD_Data = data;
LCD_Control |= (1<<LCD_E);
LCD_Control &= ~(1<<LCD_E);
}

//Go to a specific location on the LCD. 0,0 is the top left character
void LCD_GOTOXY(uint8_t x,uint8_t y)
{
if (x>39) x=0;
if (y>1) y=0;
//Ensure that the x,y values are within range
if (y==0) LCD_Send_Command(LINE_1+x);
if (y==1) LCD_Send_Command(LINE_2+x);
}

//Send a single character to a specific loaction
void LCD_Send_Data_XY(uint8_t d,uint8_t x,uint8_t y)
{
LCD_GOTOXY(x,y);
LCD_Send_Data(d);
}

//Send a string to the display.
void LCD_Send_String(char *ch)
{
int i=0;

while(ch!='\0')
{
LCD_Send_Data(ch[i++]);
}
}


//Initialise the LCD
void LCD_Initialise(void)
{
_delay_ms(10); //Ensure start-up delay
LCD_Send_Command(DISP_FS);
//Function set #
_delay_ms(16);
//16ms delay
LCD_Send_Command(DISP_FS);
//Function set
_delay_ms(5);
//5ms Delay
LCD_Send_Command(DISP_FS); //Function set
_delay_ms(5);
//1ms delay
LCD_Send_Command(DISP_FS); //Function set
_delay_ms(1);
//1ms delay
LCD_Send_Command(DISP_ON); //Turn Display on
_delay_ms(1);
//1ms delay
LCD_Send_Command(DISP_EN); //Set entry mode
_delay_ms(1);
//1ms delay
LCD_Send_Command(DISP_CL); //Clear Display
_delay_ms(1); //1ms delay
}
 

Thread Starter

ElectroHead

Joined May 16, 2013
4
Hi Ernie,

Im sorry, I am new to this so am not too sure what the posting etiquette is (other than being respectful and as informative as possible). I am not much of a coder, I am more a hardware person.

Thank you for getting back to me so quickly tho!
*Now that I have the solution should I remove the post, or leave it in the hopes that it helps someone else with a similar query in the future?

Finally, how do I go about putting up a schematic of the circuitry onto this post?
 

ErnieM

Joined Apr 24, 2011
8,377
Oh no, please leave it now that it's here. Thread fade fast off the first page here so they disappear on their own soon enough.

One comment: the # icon above the rely box adds "code tags" to your post, and anything between code tags keeps the formatting; it makes code readable.

Schematics can be posted, but I think you need 10 posts to do that. One easy way is to add it as an attachment, and copy the link of the attachment. You get a normal size image where you want it in your post, and a little icon graphic at the end of your post where everyone ignores it.

And welcome to the forums!
 

mo12347867

Joined Mar 9, 2016
1
Hey i am encountering the same problem are you sure the code below is the solution as it doesnt work



The correct solution is below.

#include <avr/io.h>
#include <avr/interrupt.h>
#include <util/delay.h>
#include <stdlib.h>
#include <string.h>
#include <stdio.h>



#define LCD_Data PORTA //LCD Data output
#define LCD_Data_DDR DDRA //LCD Direction port
#define LCD_Data_RD PINA //LCD Data input

#define LCD_Control PORTD //Port where LCD control signals are
#define LCD_Control_RD PIND
#define LCD_Control_DDR DDRD
#define LCD_RS 0 //Pin on which LCD Register Select is
#define LCD_RW 1 //Pin on which LCD Read/Write is
#define LCD_E 2 //Pin on which LCD Enable is

#define rowA PC7
#define rowB PC6
#define rowC PC5
#define rowD PC4


#define column1 PC3
#define column2 PC2
#define column3 PC1
#define column4 PC0


#define DISP_FS 0x3f //Function set
#define DISP_ON 0x0c //Display on w/o blink or flash
#define DISP_OFF 0x08 //Display, blink, cursor off
#define DISP_CL 0x01 //Clear display
#define DISP_EN 0x06 //Data entry mode
#define LINE_1 0x80 //DDRAM address for first line
#define LINE_2 0xc0 //DDRAM address for second line
#define SH_LFT 0x18 //Left-shift display
#define SH_RT 0x1c //Right-shift display
#define HOME 0x02 //Return home


char dispstr[17];

uint8_t Captured;//what are these? global variables? what is thier purpose?
uint16_t amplitude;



void LCD_Send_Command(uint8_t);
void LCD_Send_Data(uint8_t);
void LCD_Initialise(void);
void LCD_GOTOXY(uint8_t,uint8_t);
void LCD_Send_Data_XY(uint8_t /*data*/,uint8_t/*X coord*/,uint8_t/*Y coord*/);
void LCD_Send_String(char *);




int main (void)
{


DDRC=(1<<rowA | 1<<rowB | 1<<rowC | 1<<rowD);

LCD_Data_DDR=0xff;

LCD_Control_DDR|=(1<<LCD_RS | 1<<LCD_RW | 1<<LCD_E);

LCD_Control &=~(1<<LCD_RW);
LCD_Initialise();
_delay_ms(1);
//LCD_Send_String("");
//_delay_ms(1);
//LCD_GOTOXY(0,1);//sends the above string to the left-most position (x=0) on the top line (y=1 [indexed from zerol; zero being the bottom line])




while (1)
{


PORTC = 1<<rowA; // Make rowB high
if(PINC & (1<<column1 |1<< column2));

else if(PINC & (1<<column1)) //check to see if column1 is high at the same time as rowC is high
{//if so, display the number 8 on the LCD
LCD_Send_String(" 0");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
_delay_ms(5);//5ms delay to debounce the buttons
}
else if(PINC & (1<<column2))//check to see if column2 is high at the same time as rowC is high
{//if so, display the number 9 on the LCD
LCD_Send_String(" 1");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
_delay_ms(5);
}
else if(PINC & (1<<column3))//check to see if column3 is high at the same time as rowC is high
{//if so, display "Please do not use the 'A' key"
LCD_Send_String(" 2");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
}
else if(PINC & (1<<column4))//check to see if column4 is high at the same time as rowC is high (i.e.B has been pressed)
{//if so, display "Press E to confirm you want to go back"
LCD_Send_String(" 3");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
_delay_ms(5);
}



PORTC = 1<<rowB; // Make rowB high

if(PINC & (1<<column1 |1<< column2));

else if(PINC & (1<<column1)) //check to see if column1 is high at the same time as rowC is high
{//if so, display the number 8 on the LCD
LCD_Send_String(" 4");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
_delay_ms(5);//5ms delay to debounce the buttons
}
else if(PINC & (1<<column2))//check to see if column2 is high at the same time as rowC is high
{//if so, display the number 9 on the LCD
LCD_Send_String(" 5");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
_delay_ms(5);
}
else if(PINC & (1<<column3))//check to see if column3 is high at the same time as rowC is high
{//if so, display "Please do not use the 'A' key"
LCD_Send_String(" 6");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
}
else if(PINC & (1<<column4))//check to see if column4 is high at the same time as rowC is high (i.e.B has been pressed)
{//if so, display "Press E to confirm you want to go back"
LCD_Send_String(" 7");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
_delay_ms(5);
}



PORTC = 1<<rowC; // Make rowC high
if(PINC & (1<<column1 |1<< column2));

else if(PINC & (1<<column1)) //check to see if column1 is high at the same time as rowC is high
{//if so, display the number 8 on the LCD
LCD_Send_String(" 8");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
_delay_ms(5);//5ms delay to debounce the buttons
}
else if(PINC & (1<<column2))//check to see if column2 is high at the same time as rowC is high
{//if so, display the number 9 on the LCD
LCD_Send_String(" 9");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
_delay_ms(5);
}
else if(PINC & (1<<column3))//check to see if column3 is high at the same time as rowC is high
{//if so, display "Please do not use the 'A' key"
LCD_Send_String(" A");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
}
else if(PINC & (1<<column4))//check to see if column4 is high at the same time as rowC is high (i.e.B has been pressed)
{//if so, display "Press E to confirm you want to go back"
LCD_Send_String(" B");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
_delay_ms(5);
}


PORTC = 1<<rowD; // Make rowD high
if(PINC & (1<<column1 |1<< column2));

else if(PINC & (1<<column1))//check to see if column1 is high at the same time as rowD is high
{//if so, display "cancle?"
LCD_Send_String(" C");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
_delay_ms(5);//5ms delay to debounce the buttons
}
else if(PINC & (1<<column2))//check to see if column2 is high at the same time as rowD is high
{//if so, display the "Delete?"
LCD_Send_String(" D");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
_delay_ms(5);
}
else if(PINC & (1<<column3))//check to see if column3 is high at the same time as rowD is high
{//if so, display "Enter' key"
LCD_Send_String(" E");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);
_delay_ms(5);
}
else if(PINC & (1<<column4))//check to see if column4 is high at the same time as rowD is high (i.e.F has been pressed)
{//if so, display "Wat da rassklart?"
LCD_Send_String(" F");
_delay_ms(500);
LCD_GOTOXY(0,0);//sends the above string to the leftmost position on the bottom line
_delay_ms(5);

}




// Enable global interrupts
asm("sei");

asm("nop");
}

return(0);

}


void LCD_Send_Command(uint8_t command)
{
_delay_us(100);
LCD_Control &= ~(1<<LCD_RS);
LCD_Data = command;
LCD_Control |= (1<<LCD_E);
LCD_Control &= ~(1<<LCD_E);
}


void LCD_Send_Data(uint8_t data)
{
_delay_us(100);
LCD_Control |= (1<<LCD_RS);
LCD_Data = data;
LCD_Control |= (1<<LCD_E);
LCD_Control &= ~(1<<LCD_E);
}

//Go to a specific location on the LCD. 0,0 is the top left character
void LCD_GOTOXY(uint8_t x,uint8_t y)
{
if (x>39) x=0;
if (y>1) y=0;
//Ensure that the x,y values are within range
if (y==0) LCD_Send_Command(LINE_1+x);
if (y==1) LCD_Send_Command(LINE_2+x);
}

//Send a single character to a specific loaction
void LCD_Send_Data_XY(uint8_t d,uint8_t x,uint8_t y)
{
LCD_GOTOXY(x,y);
LCD_Send_Data(d);
}

//Send a string to the display.
void LCD_Send_String(char *ch)
{
int i=0;

while(ch!='\0')
{
LCD_Send_Data(ch[i++]);
}
}


//Initialise the LCD
void LCD_Initialise(void)
{
_delay_ms(10); //Ensure start-up delay
LCD_Send_Command(DISP_FS);
//Function set #
_delay_ms(16);
//16ms delay
LCD_Send_Command(DISP_FS);
//Function set
_delay_ms(5);
//5ms Delay
LCD_Send_Command(DISP_FS); //Function set
_delay_ms(5);
//1ms delay
LCD_Send_Command(DISP_FS); //Function set
_delay_ms(1);
//1ms delay
LCD_Send_Command(DISP_ON); //Turn Display on
_delay_ms(1);
//1ms delay
LCD_Send_Command(DISP_EN); //Set entry mode
_delay_ms(1);
//1ms delay
LCD_Send_Command(DISP_CL); //Clear Display
_delay_ms(1); //1ms delay
}
 

WBahn

Joined Mar 31, 2012
29,979
Don't expect a response -- Electrohead hasn't been seen on the boards since he posted that code nearly three years ago. You might be better served by starting your own thread, perhaps with a link to this one, that focuses on the problems that YOU are having. In either case, just stating that a long piece of unformatted code doesn't work isn't going to attract the attention of many people that might be able to help. Format the code well (using the CODE tags) and clearly describe what it is doing and what it is not doing. Be sure to indicate exactly which MCU you are using and which development environment you are using.
 
Top