Showing posts with label 8051. Show all posts
Showing posts with label 8051. Show all posts

Friday, October 15, 2021

AT89C52 Character LCD and Keypad Interfacing Using C

We have seen about 4x4 matrix keypad and character LCD interfacing with AT89C52 in previous post. Now let put these two external devices to work together with this controller.

AT89C52 Character LCD and Keypad Interfacing Using C

In this programming example, I use a 4x4 matrix keypad and a HD44780-based character LCD, controlled by AT89C52. The two lines character LCD shows the received the controller received from keypad.

This keypad has 16 value ranging from 1 to 9, and from A to F in ASCII format.

AT89C52 Character LCD and Keypad Interfacing Using C
Circuit diagram
Source code is written in C, using Keil uVision IDE.

  1. /*
  2. AT89C52 8051 Interface to Character LCD
  3. and Matrix Keypad Programming in C using Keil
  4. */
  5.  
  6. #include <REG52.h>
  7.  
  8. #define DPORT P2
  9. #define KEY_PORT P1
  10.  
  11. /*Keypad rows setting*/
  12. sbit row0=P1^4;
  13. sbit row1=P1^5;
  14. sbit row2=P1^6;
  15. sbit row3=P1^7;
  16.  
  17. /*
  18. RS bit 0
  19. RW to GND
  20. EN bit 1
  21. */
  22.  
  23. void lcdInit();
  24. void lcdCmd(unsigned char cmd);
  25. void lcdDat(unsigned char dat);
  26. void lcdStr(unsigned char *str);
  27. void lcdXY(unsigned char x, unsigned char y);
  28. void _delay_us(unsigned int t);
  29. void _delay_ms(unsigned int T);
  30. void lcdClear();
  31.  
  32. /**********KeyPad*************/
  33. unsigned char getKey();
  34.  
  35. unsigned char keypad[4][4]={0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15};
  36. unsigned char output[4]={0xFE,0xFD,0xFB,0xF7};
  37. unsigned row,col,key_value;
  38. bit found=0;
  39.  
  40. unsigned char temp;
  41.  
  42. int main(void)
  43. {
  44. unsigned char keyVal,pressCnt=0;
  45. unsigned char keyStr[16];
  46. unsigned int i=0;
  47. unsigned char keyChar[16]={'7','8','9','F','4','5','6','E','1','2','3','D','A','0','B','C'};
  48. lcdInit();
  49. KEY_PORT=0xF0;
  50. lcdXY(1,1);
  51. P3=0x00;
  52. lcdStr("Enter Key Value:");
  53. lcdXY(1,2);
  54. while(1)
  55. {
  56. keyVal=getKey();
  57. if(found==1){
  58. lcdDat(keyChar[keyVal]);
  59. found=0;
  60. pressCnt++;
  61. for(i=0;i<32800;i++);
  62. }
  63. if(pressCnt>16){
  64. pressCnt=0;
  65. for(i=0;i<50000;i++);
  66. lcdClear();
  67. lcdXY(1,1);
  68. lcdStr("Enter Key Value:");
  69. lcdXY(1,2);
  70. }
  71. }
  72.  
  73. }
  74.  
  75.  
  76. void lcdCmd(unsigned char cmd){
  77. temp=0x02;
  78. DPORT=temp|(cmd&0xF0);
  79. _delay_us(10);
  80. temp=0x00;
  81. DPORT=temp|(cmd&0xF0);
  82. _delay_us(100);
  83.  
  84. temp=0x02;
  85. DPORT=temp|(cmd<<4);
  86. _delay_us(10);
  87. temp=0x00;
  88. DPORT=temp|(cmd<<4);
  89. }
  90.  
  91. void lcdDat(unsigned char dat){
  92. temp=0x03;
  93. DPORT=temp|(dat&0xF0);
  94. _delay_us(10);
  95. temp=0x01;
  96. DPORT=temp|(dat&0xF0);
  97. _delay_us(100);
  98.  
  99. temp=0x03;
  100. DPORT=temp|(dat<<4);
  101. _delay_us(10);
  102. temp=0x01;
  103. DPORT=temp|(dat<<4);
  104. }
  105.  
  106. void lcdInit(){
  107.  
  108. DPORT=0x00;
  109. _delay_ms(2);
  110. lcdCmd(0x33);
  111. _delay_us(100);
  112. lcdCmd(0x32);
  113. _delay_us(100);
  114. /*2-Lines Mode 4-Bit*/
  115. lcdCmd(0x28);
  116. _delay_us(100);
  117. /*Display On Cursor Blink*/
  118. lcdCmd(0x0F);
  119. _delay_us(100);
  120. /*Clear Screen*/
  121. lcdCmd(0x01);
  122. _delay_ms(2);
  123. /*Cursor Increment*/
  124. lcdCmd(0x06);
  125. _delay_us(100);
  126. }
  127.  
  128. void lcdStr(unsigned char *str){
  129. unsigned char i=0;
  130. while(str[i]!=0){
  131. lcdDat(str[i]);
  132. i++;
  133. }
  134. }
  135.  
  136. void lcdXY(unsigned char x, unsigned char y){
  137. /*20x4 LCD Address */
  138. //unsigned char tbe[]={0x80,0xC0,0x94,0xD4};
  139. /*16x2 LCD Address*/
  140. unsigned char tbe[]={0x80,0xC0};
  141. lcdCmd(tbe[y-1]+x-1);
  142. _delay_us(100);
  143. }
  144.  
  145. void _delay_us(unsigned int a){
  146. unsigned int i,j;
  147. for(i=0;i<5;i++)
  148. for(j=0;j<a;j++);
  149. }
  150.  
  151. void _delay_ms(unsigned int b){
  152. unsigned int i;
  153. for(i=0;i<b;i++) _delay_us(1000);
  154. }
  155.  
  156. void lcdClear(){
  157. lcdCmd(0x01);
  158. _delay_us(10);
  159. }
  160.  
  161. /*4x4 Matrix KeyPad Routine*/
  162. unsigned char getKey(){
  163.  
  164. static unsigned char i=0;
  165.  
  166. for (i=0;i<4;i++){
  167. KEY_PORT=output[i];
  168. if((KEY_PORT&0xF0)!=0xF0)
  169. { col=i;
  170. found=1;
  171. break;
  172. }
  173. }
  174.  
  175. if(row0==0) row=0;
  176. else if (row1==0) row=1;
  177. else if (row2==0) row=2;
  178. else if (row3==0) row=3;
  179.  
  180. if(found==1)
  181. return key_value=keypad[row][col];
  182. found=0;
  183. }
  184.  

Click here to download source file.


Wednesday, October 13, 2021

AT89C52 and Character LCD in 4-bit mode Using Keil

Character LCD is commonly found in some digital electronics controlled system. The HD44780 is an easy-to-use character LCD controller so far. Currently, there are many comparable LCD controller manufactured by various companies.

AT89C52 and Character LCD in 4-bit mode Using Keil
A 16x2 LCD I use for prototyping

Its LCD controller could be controlled using 8-bit, or 4-bit mode. Controlling this module in 4-bit mode is very common due to microprocessor data pin saving. I don't show the steps of LCD interfacing in this post due to duplication. 

I draw its circuit in simulator.

AT89C52 and Character LCD in 4-bit mode Using Keil
Circuit Diagram
Source code is written using C in Keil uVision.

  1. /*
  2. AT89C52 8051 Interface to Character LCD
  3. Progamming in C using Keil
  4. */
  5.  
  6. #include <REG52.h>
  7.  
  8. #define DPORT P2
  9.  
  10. /*
  11. RS bit 0
  12. RW to GND
  13. EN bit 1
  14. */
  15.  
  16. void lcdInit();
  17. void lcdCmd(unsigned char cmd);
  18. void lcdDat(unsigned char dat);
  19. void lcdStr(unsigned char *str);
  20. void lcdXY(unsigned char x, unsigned char y);
  21. void _delay_us(unsigned int t);
  22. void _delay_ms(unsigned int T);
  23. void lcdClear();
  24.  
  25. unsigned char temp;
  26.  
  27. int main(void)
  28. {
  29.  
  30. lcdInit();
  31.  
  32. while(1)
  33. {
  34. lcdXY(1,1);
  35. lcdStr("Hello World!");
  36. lcdXY(1,2);
  37. lcdStr("AT89C52 LCD****");
  38. lcdXY(1,3);
  39. lcdStr("Interfacing....");
  40. lcdXY(1,4);
  41. lcdStr("Using C in Keil");
  42. lcdCmd(0x0F);
  43. _delay_ms(100);
  44. lcdClear();
  45. _delay_ms(100);
  46. }
  47. }
  48.  
  49. void lcdCmd(unsigned char cmd){
  50. temp=0x02;
  51. DPORT=temp|(cmd&0xF0);
  52. _delay_us(10);
  53. temp=0x00;
  54. DPORT=temp|(cmd&0xF0);
  55. _delay_us(100);
  56.  
  57. temp=0x02;
  58. DPORT=temp|(cmd<<4);
  59. _delay_us(10);
  60. temp=0x00;
  61. DPORT=temp|(cmd<<4);
  62. }
  63.  
  64. void lcdDat(unsigned char dat){
  65. temp=0x03;
  66. DPORT=temp|(dat&0xF0);
  67. _delay_us(10);
  68. temp=0x01;
  69. DPORT=temp|(dat&0xF0);
  70. _delay_us(100);
  71.  
  72. temp=0x03;
  73. DPORT=temp|(dat<<4);
  74. _delay_us(10);
  75. temp=0x01;
  76. DPORT=temp|(dat<<4);
  77. }
  78.  
  79. void lcdInit(){
  80.  
  81. DPORT=0x00;
  82. _delay_ms(2);
  83. lcdCmd(0x33);
  84. _delay_us(100);
  85. lcdCmd(0x32);
  86. _delay_us(100);
  87. lcdCmd(0x28);
  88. _delay_us(100);
  89. lcdCmd(0x0E);
  90. _delay_us(100);
  91. lcdCmd(0x01);
  92. _delay_ms(2);
  93. lcdCmd(0x06);
  94. _delay_us(100);
  95. }
  96.  
  97. void lcdStr(unsigned char *str){
  98. unsigned char i=0;
  99. while(str[i]!=0){
  100. lcdDat(str[i]);
  101. i++;
  102. }
  103. }
  104.  
  105. void lcdXY(unsigned char x, unsigned char y){
  106. unsigned char tbe[]={0x80,0xC0,0x94,0xD4}; // 20x4
  107. lcdCmd(tbe[y-1]+x-1);
  108. _delay_us(100);
  109. }
  110.  
  111. void _delay_us(unsigned int a){
  112. unsigned int i,j;
  113. for(i=0;i<5;i++)
  114. for(j=0;j<a;j++);
  115. }
  116.  
  117. void _delay_ms(unsigned int b){
  118. unsigned int i;
  119. for(i=0;i<b;i++) _delay_us(1000);
  120. }
  121.  
  122. void lcdClear(){
  123. lcdCmd(0x01);
  124. _delay_us(10);
  125. }
  126.  

Due to ISP absence for AT89C52. I can burned firmware into this controller. Hence I just only simulate this program in simulator.


AT89C52 and Character LCD in 4-bit mode Using Keil
Program simulation

Click here to download this example.



Search This Blog

Labels

25AA010A (1) 8051 (7) 93AA46B (1) ADC (30) Analog Comparator (1) Arduino (15) ARM (6) AT89C52 (7) ATMega32 (56) AVR (57) CCS PICC (28) DAC (1) DHT11 (2) Display (105) Distance Sensor (3) DS18B20 (3) dsPIC (2) dsPIC30F1010 (2) EEPROM (5) Environment Sensor (4) esp8266 (1) I2C (29) Input/Output (67) Interrupt (19) Keil (5) Keypad (10) LCD (47) Master/Slave (1) MAX7221 (1) MCP23017 (5) MCP23S17 (4) Meter (3) MikroC (2) Motor (15) MPLABX (71) Nokia 5110 LCD (3) OLED (2) One-Wire (6) Oscillator (8) PCB (6) PCD8544 (3) PCF8574 (5) PIC (107) PIC12F (2) PIC16F628A (2) PIC16F630 (1) PIC16F716 (3) PIC16F818 (10) PIC16F818/819 (2) PIC16F84A (15) PIC16F876A (1) PIC16F877A (9) PIC16F88 (1) PIC16F887 (60) PIC18 (19) PIC18F1220 (4) PIC18F2550 (3) PIC18F4550 (12) PWM (11) RTC (8) Sensor (10) SH1106 (1) Shift Register (11) Shift Registers (3) SPI (24) STM32 (6) STM32 Blue Pill (6) STM32CubeIDE (6) STM32F103C8T6 (6) SysTick (3) temperature sensor (11) Thermometer (21) Timer/Counter (31) TM1637 (2) UART (7) Ultrasonic (4) Voltmeter (7) WDT (1) XC16 (2) XC8 (94)