Monday, July 18, 2016

Displaying Custom Characters on LCD





DISPLAYING CUSTOM CHARACTERS ON LCD USING PIC16F877A 



Reference: https://electrosome.com/custom-characters-lcd-pic-mikroc/

NOTE: Please go through the tutorial on Interfacing Character LCD with PIC Microcontroller – MicroC Pro.



     Let us first discuss some of the basic concepts and terminologies that we are going to use in displaying custom characters on our 16x2 LCD. Basically, the LCD is consist of 3 memory blocks called CGROMDDRAM, and CGRAM.


Character Generation ROM (CGROM)
       This is the memory which holds the 5×8 or the 5×10 dot patterns of predefined characters in the LCD. It can create 208 5x8 character dot patterns and 32 5x10 character dot patterns.





















Display Data RAM (DDRAM)
        Just like our personal computers, the LCD also has a RAM and it is called DDRAM. This is the memory which holds the character data which is currently displayed on the LCD. Its capacity is 80x8 bits.

Character Generation RAM (CGRAM)
        This memory works similar to CGROM as this is a RAM we can modify its data anytime. We can store our custom character patterns in this memory through program. We can store up to eight 5x8 character dot patterns and four 5x10 character dot patterns in this memory.

The starting address of the CGRAM is from 00-07.



Creating your own Custom Characters



  1. On your Microsoft Excel software create a 5x8 box just like the picture above. That will serve as our 5x8 dot pattern as seen on our LCD. 
  2. To create your custom character, just fill the box that will satisfy your design.
  3. The shaded boxes are labeled 1 and the unshaded boxes are labeled as 0. Since we are processing 8 bits of data, the first column of boxes serves as our higher bit data and the remaining column of boxes is our lower bit data.
  4. On our example above, just convert the binary form of data into decimal.

MODIFIED CODE:


// LCD module connections
sbit LCD_RS at RD2_bit;
sbit LCD_EN at RD3_bit;
sbit LCD_D4 at RD4_bit;
sbit LCD_D5 at RD5_bit;
sbit LCD_D6 at RD6_bit;
sbit LCD_D7 at RD7_bit;

sbit LCD_RS_Direction at TRISD2_bit;
sbit LCD_EN_Direction at TRISD3_bit;
sbit LCD_D4_Direction at TRISD4_bit;
sbit LCD_D5_Direction at TRISD5_bit;
sbit LCD_D6_Direction at TRISD6_bit;
sbit LCD_D7_Direction at TRISD7_bit;
// End LCD module connections

const char character0[] = {0,0,10,31,31,14,4,0};
const char character1[] = {14,27,17,17,17,17,31,0};
const char character2[] = {14,27,17,17,17,31,31,0};
const char character3[] = {14,27,17,17,31,31,31,0};
const char character4[] = {14,27,17,31,31,31,31,0};
const char character5[] = {14,31,31,31,31,31,31,0};
const char character6[] = {0,4,2,31,2,4,0,0};
const char character7[] = {0,0,14,17,17,10,27,0};

void CustomChar0() {
  char i;
  Lcd_Cmd(64);
  for (i = 0; i<=7; i++) Lcd_Chr_CP(character0[i]);
  Lcd_Cmd(_LCD_RETURN_HOME);
}

void CustomChar1() {
  char i;
  Lcd_Cmd(72);
  for (i = 0; i<=7; i++) Lcd_Chr_CP(character1[i]);
  Lcd_Cmd(_LCD_RETURN_HOME);
}

void CustomChar2() {
  char i;
  Lcd_Cmd(80);
  for (i = 0; i<=7; i++) Lcd_Chr_CP(character2[i]);
  Lcd_Cmd(_LCD_RETURN_HOME);
}

void CustomChar3() {
  char i;
  Lcd_Cmd(88);
  for (i = 0; i<=7; i++) Lcd_Chr_CP(character3[i]);
  Lcd_Cmd(_LCD_RETURN_HOME);
}

void CustomChar4() {
  char i;
  Lcd_Cmd(96);
  for (i = 0; i<=7; i++) Lcd_Chr_CP(character4[i]);
  Lcd_Cmd(_LCD_RETURN_HOME);
}

void CustomChar5() {
  char i;
  Lcd_Cmd(104);
  for (i = 0; i<=7; i++) Lcd_Chr_CP(character5[i]);
  Lcd_Cmd(_LCD_RETURN_HOME);
}

void CustomChar6() {
  char i;
  Lcd_Cmd(112);
  for (i = 0; i<=7; i++) Lcd_Chr_CP(character6[i]);
  Lcd_Cmd(_LCD_RETURN_HOME);
}

void CustomChar7() {
  char i;
  Lcd_Cmd(120);
  for (i = 0; i<=7; i++) Lcd_Chr_CP(character7[i]);
  Lcd_Cmd(_LCD_RETURN_HOME);
}

void main()  {
  Lcd_Init(); // Initialize LCD

  Lcd_Cmd(_LCD_CLEAR); // Clear display
  Lcd_Cmd(_LCD_CURSOR_OFF); // Cursor off

  //Send Custom Charactors to CGRAM
  CustomChar0();
  CustomChar1();
  CustomChar2();
  CustomChar3();
  CustomChar4();
  CustomChar5();
  CustomChar6();
  CustomChar7();
  //End

  //Display Custom Characters
  Lcd_Chr(1,1,0);
  Delay_ms(1000);
  Lcd_Chr(1,2,1);
  Delay_ms(1000);
  Lcd_Chr(1,3,2);
  Delay_ms(1000);
  Lcd_Chr(1,4,3);
  Delay_ms(1000);
  Lcd_Chr(1,5,4);
  Delay_ms(1000);
  Lcd_Chr(1,6,5);
  Delay_ms(1000);
  Lcd_Chr(1,7,6);
  Delay_ms(1000);
  Lcd_Chr(1,8,7);
  Delay_ms(1000);
}
NOTE: Some of the syntax of the code might not build on your project because of the version of MikroC programmer you are using. Just go to the Help and go to the LCD Library of your MikroC programmer to check the right syntax of your program. It is also nice to drop some of your questions on the comment section below.











22 comments:

  1. Sir Aldrin, what's the difference of ATMEL And PIC COntroller? Which is better to use? :)

    ReplyDelete
    Replies
    1. Hi Rica, It is important to know that ATMEL Corporation is an American-based designer and manufacturer of semiconductors, founded in 1984. The focus of this company is on embeded systems that are built around microcontrollers.

      By ATMEL do you mean 8051 microcontrollers? If that's the case 8051 microcontroller is an 8 bit microprocessor which means its CPU can only work 8 bits of data at a time.

      The 8051 microcontroller has:
      - 128 bytes of RAM
      - 4k bytes of on-chip ROM
      - One serial port
      - Four Input/Output Ports

      A PIC Microcontroller also known as Peripheral Interface Controller are microcontrollers made by Microchip Technology. PIC Microcontrollers also process 8 bits of data at a given time.

      PIC Microcontrollers has:
      - 32k of ROM
      - 4 8 bit timers
      - 5 Input/Output ports

      Basically PIC and 8051 do mostly same things . It only depends on how precisely you can use them.
      8051- if u want a cheap controller with basic functions then 8051 will suffice . It will be of great use in your low cost college projects.

      PIC- Cheap , used in refrigerators and low budget projects . I will not advise for this because of its low community support.

      I hope I've helped you with your question. God Bless.

      Delete
    2. You are very much welcome. Thank you for dropping your question. Always happy to help. :)

      Delete
  2. i want to make a TUP hymn lyrics with a led matrix, does the PIC controller is easy to use? hehehe :D

    ReplyDelete
    Replies
    1. Hi Mark, one great project you have. Pic controllers are easy to use. Just like other microcontroller families, each has different capabilities and have lot of variations.

      Inorder to use PIC controllers, you need to use different tools and you need to learn how to use those tools. PIC microcontrollers can be easily programmed with MIKROC PRO for PIC (http://www.mikroe.com/mikroc/pic/). One of its advantage is that this software has pre-installed libraries that can be use when you're doing your project. Also, if you have a background in C++/C programming it is really one of your advantage because you can program this IC using those programming language.

      If you want to interface the LED matrix with PIC Microcontroller just visit the link below:
      http://www.nbcafe.in/interfacing-dot-matrix-led-display-with-pic-microcontroller/

      Delete
  3. Why in programming PIC controller we use MikroC programmer?

    ReplyDelete
    Replies
    1. Hi there Daisy! There are also other softwares that we can use to program PIC MCU (e.g MPLAB-IDE). But in my case, I use MikroC programmer. One of the advantage of this software is that it has various pre-installed libraries that can be used in your projects. Also, if you have a background on C++/C programming it would be one of your advantage because PIC MCU can be programmed using those programming language. I hope I've helped you with your Query. God Bless. :)

      Delete
  4. Who invented that LCD using PIC16F877A ?

    ReplyDelete
    Replies
    1. Hi Maria, not quite sure how to answer your question.. but if you mean who created the LCD. There are lots of manufacturers who creates and produced different types of LCD. In the case of this project, I used HD44780U (LCD-II), it is produced by Hitachi.

      The HD44780U dot-matrix liquid crystal display controller and driver, displays alphanumerics, Japanese kana characters, and symbols. It can be configured to drive a dot-matrix liquid crystal display under the control of a 4- or 8-bit microprocessor.

      Originally, the code used in this program is by Ligo George of Electrosome.com. I hope I've helped you with your query. God Bless.

      Delete
  5. Hi Sir Aldrin, other than PIC16F877A, what programmable IC that I can use to display in LCD?

    ReplyDelete
    Replies
    1. Hello, Interfacing the LCD can be done in any MCUs. You can try Interfacing your LCD using 8051 Microcontroller (AT89C51). :)

      Delete
    2. Thanks Sir John. What other PIC microcontroller I use?

      Delete
  6. Replies
    1. Hi there Shena! :) PIC means 'Peripheral Interface Controller'. These microcontroller units are produced by Microchip Technology.

      Delete
  7. hi sir aldrin. I am only familiar with the ATMEL AT89C2051 IC, and I use the Atmel programmer software. It uses assembly language which I find very hard to code. In PIC, what programming language does it use?

    ReplyDelete
    Replies
    1. Hi Hannah! :) It's good to hear that you are using the 8051 IC. Assembly language is hard and it requires great effort to understand but it is really one of your advantage and it is fun to know.

      PIC MCUs can be programmed with the use of various programming software like MikroC for PIC and MPLAB-IDE. These programming softwares has pre-installed libraries that will let you create your project. So if you have background on C and C++ programming language you can easily program PIC MCUs.

      Delete
  8. sir, i used your code and something error happens the MikroC languange stated that;
    Lcd_Cmd(_LCD_CLEAR) not defined

    my version of mikroC is v6.2.0.0

    ReplyDelete
    Replies
    1. There's no error in the code.The problem is the version of MikroC programmer you are using.

      Try changing your code on the CustomChar funtion try this:
      -----------------------------------------------------------------------------
      void CustomChar0() {
      char i;
      Lcd_Cmd(64);
      for (i = 0; i<=7; i++) Lcd_Chr_CP(character0[i]);
      Lcd_Cmd(LCD_RETURN_HOME);
      }


      Try to change your LCD module connection to this code:
      -----------------------------------------------------------------------------
      Lcd_Config(unsigned short *port, unsigned short RS, unsigned short EN, unsigned short WR, unsigned short D7, unsigned short D6, unsigned short D5, unsigned short D4);

      NOTE: Instead of putting the code in the beginning of your program, put the code on the main function below 'Lcd_Init()'. Your main function should look like this:
      void main()
      {
      Lcd_Init(&PORTD); // Initialize LCD

      Lcd_Config(&PORTD,2,3,0,7,6,5,4);

      Lcd_Cmd(LCD_CLEAR); // Clear display
      Lcd_Cmd(LCD_CURSOR_OFF); // Cursor off

      //Send Custom Charactors to CGRAM
      CustomChar0();
      CustomChar1();
      CustomChar2();
      CustomChar3();
      CustomChar4();
      CustomChar5();
      CustomChar6();
      CustomChar7();
      //End

      //Display Custom Characters
      Lcd_Chr(1,1,0);
      Delay_ms(1000);
      Lcd_Chr(1,2,1);
      Delay_ms(1000);
      Lcd_Chr(1,3,2);
      Delay_ms(1000);
      Lcd_Chr(1,4,3);
      Delay_ms(1000);
      Lcd_Chr(1,5,4);
      Delay_ms(1000);
      Lcd_Chr(1,6,5);
      Delay_ms(1000);
      Lcd_Chr(1,7,6);
      Delay_ms(1000);
      Lcd_Chr(1,8,7);
      Delay_ms(1000);
      }

      Try the suggestions above. If it is still not working please inform me. I'm more than willing to help you in the best possible way I can. Happy coding. :)

      Delete
  9. Sir Aldrin, below the image "output", there are initials/acronyms like VSS, VDD, VEE, RS, RW and E. What do these stand for?

    ReplyDelete
    Replies
    1. Hi Lourdes :)

      For VSS and VDD:
      [img]https://2.bp.blogspot.com/-8RmCdxYvDHs/V57_yfd2TTI/AAAAAAAAQjo/sfCVOJ6U1EoDqUB2ZdXGITp6oFreDPR8gCLcB/s1600/Screenshot%2Bfrom%2B2016-08-01%2B15-49-57.png[/img]

      Apparently this terminology originated in some way from the terminals of each type of transistor, and their common connections in logic circuits. VCC is often applied to BJT collectors, VEE to BJT emitters, VDD to FET drains, and VSS to FET sources.

      Vss, Vdd - Voltage supply pins

      R/W – Pin writing/reading to/from - LCD

      RS - Pin selects registers between Instruction Register and Data Register

      E - "Enabling" pin; when this pin is set to logical low, the LCD does not care what is happening with R/W, RS, and the data bus lines; when this pin is set to logical high, the - LCD is processing the incoming data.

      I hope I've helped you with your query. God Bless. :)

      Delete
  10. i want to indicate battery voltage with battery symbols...How can i do?

    ReplyDelete

author
John Aldrin T. Mantes
Hi! Welcome to my Blog. This blog is part of our requirement in our Educational Technology class. The content of the blog is comprise of the discussions during the Observation and Participation class. Feel free to ask questions on the comment section. Have a great Day.