LCD / Microchip Schematic

Discussion in 'Embedded Systems and Microcontrollers' started by beeson76, Sep 21, 2010.

  1. beeson76

    Thread Starter Member

    Apr 19, 2010
    185
    1
    Here is my schematic for my hooking up my LCD to my PIC16F886. The LCD is still not initializing correctly (Or I don't think it is anyway). It only does 1 line of black boxes. It is a 2 x 16 display. When it initializes correctly both lines should have black boxes, right? Could I get some advice on whether my schematic looks correct or am I missing anything on the hardware side of things. I really appreciate any help anyone can give, because I have been having problems getting this to work for a long time now. I finally got around to do this schematic. Again thanks for any help or advice.
     
  2. wannaBinventor

    Member

    Apr 8, 2010
    179
    4
    I don't understand MCLR connected to ground through a resistor. I'm use to seeing it pulled high through a pull up with (internal or external).

    Aside from that, the connections look good.

    The code is just important as the connection, so let's have a look at that.
     
  3. beeson76

    Thread Starter Member

    Apr 19, 2010
    185
    1
    Thanks wannaBinventor for the reply. I will look into what you suggested. Here is what I have as code. I at first started out pretty complicated, but through suggestions from you guys, I went very simple and am trying just basic LCD code. I got this code mostly from the sample code from the Samples directory in the Hitech Compiler. Here is my LCDMAIN code:

    Code ( (Unknown Language)):
    1.  
    2.  
    3. #include <htc.h>
    4. #include "lcd.h"
    5.  
    6. void pause (unsigned short usvalue);
    7.  
    8. __CONFIG (INTIO & WDTDIS & MCLRDIS & UNPROTECT);
    9.  
    10. #define number 0x30
    11.  
    12. unsigned char b0;
    13.  
    14. void
    15. main(void)
    16.  
    17. {
    18. ANSEL = 0;
    19. ANSELH = 0;
    20.  
    21. CM1CON0 = 0;
    22. CM2CON0 = 0;
    23.  
    24.  
    25. TRISA = 0;
    26. TRISC = 0;
    27.  
    28. lcd_init();
    29.  
    30. while (1 == 1)
    31. {
    32.     lcd_clear();
    33.     lcd_goto(0);
    34.     lcd_puts("Hello World");
    35.     pause(1000);
    36. }
    37. }
    38.  
    Sorry for not commenting, but its really basic. It is just simple code that displays "Hello World"--it should display after initialization.

    Here is my LCD.C code:

    Code ( (Unknown Language)):
    1.  
    2.  
    3. #include <htc.h>
    4. #include "lcd.h"
    5.  
    6. void pause(unsigned short usvalue);
    7.  
    8. #define     LCD_RS      RA2
    9. #define     LCD_RW      RA4
    10. #define     LCD_EN      RA1
    11. #define     LCD_DATA    PORTC
    12. #define     LCD_STROBE()    ((LCD_EN = 1),(LCD_EN = 0))
    13.  
    14. void
    15. lcd_write (unsigned char c)
    16. {
    17.     pause (1);
    18.     LCD_DATA = ((c >> 4) & 0x0F);
    19.     LCD_STROBE();
    20.     LCD_DATA = (c & 0x0F);
    21.     LCD_STROBE();
    22. }
    23.  
    24. void
    25. lcd_clear(void)
    26. {
    27.     LCD_RS = 0;
    28.     lcd_write (0x1);
    29.     pause(2);
    30. }
    31.  
    32. void
    33. lcd_puts(const char *s)
    34. {
    35.     LCD_RS = 1;
    36.     while (*s)
    37.         lcd_write(*s++);
    38. }
    39.  
    40. void
    41. lcd_putch(char c)
    42. {
    43.     LCD_RS = 1;
    44.     lcd_write(c);
    45. }
    46.  
    47. void
    48. lcd_goto(unsigned char pos)
    49. {
    50.     LCD_RS = 0;
    51.     lcd_write (0x80 + pos);
    52. }
    53.  
    54. void
    55. lcd_init()
    56. {
    57.     char init_value;
    58.  
    59.     ANSEL = 0;
    60.  
    61.     init_value = 0x3;
    62.     TRISA = 0;
    63.     TRISC = 0;
    64.     LCD_RS = 0;
    65.     LCD_EN = 0;
    66.     LCD_RW = 0;
    67.  
    68.     pause(15);                 
    69.     LCD_DATA = init_value;
    70.     LCD_STROBE();
    71.     pause(10);                 
    72.     LCD_STROBE();
    73.     pause(10);                 
    74.     LCD_STROBE();
    75.     pause(10);                 
    76.     LCD_DATA = 2;          
    77.     LCD_STROBE();
    78.  
    79.     lcd_write (0x28);
    80.     lcd_write (0xF);
    81.     lcd_clear();
    82.     lcd_write(0x6);
    83. }
    84.  
    85. void lcd_putint (int i)
    86. {
    87.     LCD_RS = i;
    88.     lcd_write(i);
    89. }
    90.  
    This code was mainly taken from again the Samples directory of the Hitech compiler.

    And here is my LCD.h code:

    Code ( (Unknown Language)):
    1.  
    2.  
    3. extern void lcd_write (unsigned char);
    4. extern void lcd_clear (void);
    5. extern void lcd_puts (const char *s);
    6. extern void lcd_goto (unsigned char pos);
    7. extern void lcd_init (void);
    8. extern void lcd_putch (char);
    9. extern void lcd_putint (int);
    10.  
    Hope this code can help you guys help me. This is driving me crazy. Thanks again for any help, and I certainly appreciate any replies and help received.
     
  4. debjit625

    Well-Known Member

    Apr 17, 2010
    790
    186
    As wannaBinventor mentioned
    You cant put MCLR low because it will reset the MCU,i.e. for the program to run you have to connect the MCLR pin to Vdd.We only pull MCLR low when we want a external reset.

    Good Luck
     
  5. eblc1388

    Senior Member

    Nov 28, 2008
    1,542
    102
    Nope.

    An uninitialized LCD usually has only one row of black blocks.
     
  6. t06afre

    AAC Fanatic!

    May 11, 2009
    5,939
    1,222
    In this case it is wrong. Because the configuration setting has disabled the MLCR option. It is now tied to VDD inside the chip. A very good choice for the beginner. It is also important to sure that all configuration bits are set correct. Because if not set they default to 1. That could in some cases create trouble. PICC also has native functions for delay they are named __delay_ms() and __delay_us() use them instead of the pause() function. Remember to use the
    Code ( (Unknown Language)):
    1. #define _XTAL_FREQ  4000000
    Using 4000000 is correct in your case also. In the compiler install folder you will find a folder named docs. Here is the Hitech C manual.
    In order to master programming you must also master the art of debugging. You can trace many errors by using the internal simulator in MPLAB. Here you will find some useful free websimenar http://techtrain.microchip.com/webseminars/QuickList.aspx
    I would recommend these as a start
    http://techtrain.microchip.com/webseminars/ArchivedDetail.aspx?Active=46
    http://techtrain.microchip.com/webseminars/ArchivedDetail.aspx?Active=61
    http://techtrain.microchip.com/webseminars/ArchivedDetail.aspx?Active=137
    and perhaps this
    http://techtrain.microchip.com/webseminars/ArchivedDetail.aspx?Active=153

    http://www.microchip.com/stellent/idcplg?IdcService=SS_GET_PAGE&nodeId=1406&dDocName=en542849
    Here you can find the latest Hitech C version. 45 days in pro mode then it will only work in lite mode. But that is ok for the hobbyist. One last thing your chip share the include file with the 16f887 chip. All the deffintions are in the pic16f887.h file. The config word settings in the end
    Example on Using the dealy function it should work for your chip, I tested it on 16f690 chip.
    Code ( (Unknown Language)):
    1.  
    2. #include <htc.h>
    3. #define _XTAL_FREQ  500000
    4. unsigned long slow_int=1000;
    5. unsigned long fast_int=30;
    6. int i=0xff;
    7. __CONFIG(INTIO & WDTDIS & NONSENS &PWRTDIS & BORDIS & MCLRDIS & FCMEN  & IESODIS & UNPROTECT);
    8. void fast_blink(void)
    9. {
    10.  PORTC = i;
    11.   __delay_ms(fast_int);
    12. PORTC = 0x0;
    13.   __delay_ms(100);
    14. }
    15. void slow_blink(void)
    16. {
    17. PORTC = i;
    18.  __delay_ms(50);
    19.   PORTC = 0x0;
    20. __delay_ms(1000);
    21. }void main(void)
    22. {
    23.  TRISC = 0b00000000;// port directions: 1=input, 0=output
    24.   OSCCON=0b00110000;//set internal OSC to 500KHz
    25.    PORTC = 0x0;//Zero portC
    26.     ANSEL=ANSELH=0;
    27. while (1){
    28.  fast_blink();
    29.   fast_blink();
    30. __delay_ms(slow_int-100);
    31.  slow_blink();
    32. }
    33. }
    34.  
     
  7. beeson76

    Thread Starter Member

    Apr 19, 2010
    185
    1
    Thanks for the replies. Appreciate it very much. So after reading the replies, here is what I have come up with along with questions.

    Because the MCLR is disabled in my configuration of the chip, I am pulling the pin low?? or high??

    And because of MCLR being disabled, is my circuit right or wrong when it comes to pin 1 of the chip??

    After getting the answers to these questions, it will help me to decide which way to proceed.

    Thanks again, and I look forward to the replies.
     
  8. t06afre

    AAC Fanatic!

    May 11, 2009
    5,939
    1,222
    Then MCLR is disabled, the "MCLR" pin become a general pin. Often (if not allways) on Microchips MCUs the pin used for MCLR is a read only pin(input only). So you do not have to worry about this pin with your current setting. Using internal osc, and MLCR disable is as have said before a good options for the beginner. Because you eliminate two potential sources for trouble.
     
  9. beeson76

    Thread Starter Member

    Apr 19, 2010
    185
    1
    I know this is kinda a vague question, but in this situation, can someone please tell me how to use __delay_ms or __delay_us. I have see it used in #define statement? But then I read that if you #include it as delay.h and delay.c, but I cannot find them, so I don't know if this is the proper way. Any help is greatly appreciated.
     
  10. t06afre

    AAC Fanatic!

    May 11, 2009
    5,939
    1,222
    Just include htc.h In the HItech c install folder you will find a folder named doc here is the manual. but as an axample
    Code ( (Unknown Language)):
    1. __dealy_ms(100);
    will give you a dealy equal to 100 msec or 0.1 seconds if you have used the correct settings for _XTAL_FREQ
    Code ( (Unknown Language)):
    1. #define _XTAL_FREQ xxxxxxx
    Note this will only be used by the compiler. It will NOT set any clock frequncy settings on the MCU
     
  11. beeson76

    Thread Starter Member

    Apr 19, 2010
    185
    1
    Thanks t06afre for replying. Here is what I have. Can you please check it to see if everything looks good.
    Code ( (Unknown Language)):
    1.  
    2.  
    3. #include <htc.h>
    4. #include "lcd.h"
    5.  
    6. ///////////////////////////////////////////////////////////////////////////////////////////////////
    7. //#Define Statements///////////////////////////////////////////////////////////////////////////////
    8. ///////////////////////////////////////////////////////////////////////////////////////////////////
    9. #define  _XTAL_FREQ     4000000  // **ADDED** //Needed for Internal Oscillator
    10. #define __delay_ms(x) _delay((unsigned long)((x)*(_XTAL_FREQ/4000.0)))
    11.  
    12. //  **CHANGED** void pause (unsigned short usvalue);
    13.  
    14. __CONFIG (MCLRDIS, INTIO, WDTDIS, PWRTEN, BORDIS, LVPDIS, UNPROTECT);
    15. // **CHANGED**  __CONFIG (INTIO & WDTDIS & MCLRDIS & UNPROTECT);
    16.  
    17. main()
    18.  
    19. {
    20. ANSEL = 0;
    21. ANSELH = 0;
    22.  
    23. CM1CON0 = 0;
    24. CM2CON0 = 0;
    25.  
    26.  
    27. TRISA = 0;
    28. TRISC = 0;
    29.  
    30. lcd_init();
    31.  
    32. while (1 == 1)
    33. {
    34.    
    35.     lcd_clear();
    36.     lcd_goto(0);
    37.     lcd_puts("Hello World");
    38.     __delay_ms(150);  // **ADDED**
    39.     // **CHANGED** pause(1000);
    40. }
    41. }
    42.  
     
  12. t06afre

    AAC Fanatic!

    May 11, 2009
    5,939
    1,222
    Does it work?
    I am not sure about this. Comparators are by default not active after power on/reset. I think it is best to drop doing anything to them in the start. Which chip are you using
    Code ( (Unknown Language)):
    1.  
    2. CM1CON0 = 0;
    3. CM2CON0 = 0;
    4.  
    And you do not need this either
    Code ( (Unknown Language)):
    1.  
    2. #define __delay_ms(x) _delay((unsigned long)((x)*(_XTAL_FREQ/4000.0)))
    3.  
     
  13. beeson76

    Thread Starter Member

    Apr 19, 2010
    185
    1
    It works. Yes!!!!!! Can't believe it. I've been working on this for about 2 months now. I made the changes you suggested T06afre and it works!! I really do appreciate the help. Here is the final code for this project. I am using the PIC16F886.

    Code ( (Unknown Language)):
    1.  
    2.  
    3. #include <htc.h>
    4. #include "lcd.h"
    5.  
    6. ///////////////////////////////////////////////////////////////////////////////////////////////////
    7. //#Define Statements///////////////////////////////////////////////////////////////////////////////
    8. ///////////////////////////////////////////////////////////////////////////////////////////////////
    9. #define  _XTAL_FREQ     4000000  // **ADDED** //Needed for Internal Oscillator
    10. //  **CHANGED** #define __delay_ms(x) _delay((unsigned long)((x)*(_XTAL_FREQ/4000.0)))
    11.  
    12. //  **CHANGED** void pause (unsigned short usvalue);
    13.  
    14. __CONFIG (MCLRDIS & INTIO & WDTDIS & PWRTEN & BORDIS & LVPDIS & UNPROTECT);
    15. // **CHANGED**  __CONFIG (INTIO & WDTDIS & MCLRDIS & UNPROTECT);
    16.  
    17. main()
    18.  
    19. {
    20. ANSEL = 0;
    21. ANSELH = 0;
    22.  
    23. // **CHANGED**  CM1CON0 = 0;
    24. // **CHANGED**  CM2CON0 = 0;
    25.  
    26.  
    27. TRISA = 0;
    28. TRISC = 0;
    29.  
    30. lcd_init();
    31.  
    32. while (1 == 1)
    33. {
    34.    
    35.     lcd_clear();
    36.     lcd_goto(0);
    37.     lcd_puts("Hello World");
    38.     __delay_ms(150);  // **ADDED**
    39.     // **CHANGED** pause(1000);
    40. }
    41. }
    42.  
    43.  
    Please notice the changes in the code. I have commented out the changes. This has been by far the hardest project I have done yet, and this was pretty basic stuff when it comes to what you do. Thanks again for all the help. I am noticing blinking in the LCD--its quick, so its not too noticeable. Could this have something to do with the way the program is written--it being is a while loop, or does it have to do with my frequency of my oscillator?
     
  14. t06afre

    AAC Fanatic!

    May 11, 2009
    5,939
    1,222
    2 months? You should have asked for help a long time ago. A LCD display is not made for very dynamic display. It will perhaps help some if you put the LCD clear outside the while looop.
     
    beeson76 likes this.
Loading...