I am stuck with ST7920. Help please!

Author
Francesco C
Senior Member
  • Total Posts : 147
  • Reward points : 0
  • Joined: 2010/08/08 14:33:14
  • Location: UK
  • Status: offline
2014/11/05 14:00:37 (permalink)
0

I am stuck with ST7920. Help please!

Hi,
 I am trying to interface a PIC18F452 to a GLCD12824 (128x64).
This is driven by a ST7920 controller.
I have spend a lot of time on line for information, but i have failed to make it work.
 
So far i have managed to understand only how to initialize the display by reading the datasheet.
I have tried to modify some example found on line, but i could not make it work.
 
I am sure that my the hardware is correctly wired.
I would like someone to give a simple example on how to display a message on the GLCD.
If i manage to do that i will understand the sequence of command and timings required, to make it work.
 
The code below is what  i got so far!
 
Thanks in advance.
Grateful for any help.
 
Francesco.
=============     Sorry about this i cannot found out how to attach code   ===========
 
 
#define _XTAL_FREQ 4000000
#include "lcd.h"
#include <p18f452.h>
#include <xc.h>
#include "bits.h"
#include "string.h"
#include <delays.h>

void LCD_Init(void);
int main(void)
{
   
    TRISB=0;
    PORTB=0;
    TRISD=0;
    PORTD=0;
      
    LCD_Init();

// LCD_TextDisplayString(1,"hello");   //call this function (eventually)

}

void LCD_Init(void)
{
    __delay_ms(50);
    LCD_RST =0;
    __delay_us(1);
 LCD_RST=1;

BIT8_LCD_BASIC;
__delay_us(100);
BIT8_LCD_BASIC;

__delay_us(40);
CLEAR_LCD ;

__delay_ms(10);
MODE2_LCD;
 __delay_us(73);
 CURSOR_BLINK;

}
 
 
============== more ==================
*
 * File: lcd.h
 * Author: FC
 *
 * Created on 24 October 2014, 21:56
 */



//**********************************************************************************************************************************
//********************   Interface for a 128x64 Graphics LCD with a  ST7920 controller  *************************************


#define LCD_DATA                  PORTB                          // Port B set for 8bit data bus
#define LCD_RW                      PORTDbits.RD0        // Read/ Write line
#define LCD_RS                       PORTDbits.RD1             // LCD Register select
#define LCD_EN                       PORTDbits.RD2       // LCD Enable
#define LCD_RST                     PORTDbits.RD3       // LCD Reset

// ***********************************************************************************************************************************



//*************************       RS=0, RW=0 TO SET THE PARAMETERS BELOW   ***********************************************************


//           LCD BASIC instruction codes


#define CLEAR_LCD              PORTB=0b00000001              // clear display
#define HOME_LCD               PORTB=0b00000010              // Return Home
#define MODE1_LCD             PORTB=0b00000100              //Entry mode set  for: Cursor moves to left after writing
#define MODE2_LCD             PORTB= 0b00000110            // Entry mode set for: Cursor moves to the right after writing
#define MODE3_LCD             PORTB= 0b00000101            // Entry mode set for: Display shift to left after writing
#define MODE4_LCD             PORTB= 0b00000111           // Entry mode set for: Display shift to right after writing
#define BIT8_LCD_BASIC     PORTB= 0b00100000           //  8bit Interface & basic instruction set
#define ON_LCD                    PORTB= 0b00001100              // Turn display ON
#define OFF_LCD                   PORTB= 0b00000000             // Turn display OFF
#define CURSOR_BLINK       PORTB= 0b00001111            // Cursor On & Blinking
#define SET_RAM_ADDR      PORTB=  0b10000000            // Set DDRAM Address. (Add address to command)

// ******** Verify Operation of RW and RS Controll Lines *********************************************

#define READ_BUSY_FLAG                                    // Pull RW High & RS loaw, to  read data bus.  Undefined for the moment
#define WRITE_TO_RAM                                           // Pull RS High & RW Low, to Write data to RAM
#define READ_FROM_RAM                                       // Pull RS & RW High to read from RAM






//                        LCD  extended instruction codes

//*************************       RS=0, RW=0 TO SET THE PARAMETERS BELOW   **************

#define BIT8_LCD_EXT            0b00110100           //  8bit Interface &  extended instruction set
#define GRPHICS_ON              0b00110110          // Set Graphic mode
#define STANDBY                    0b00000001           // Set LCD in Standby mode
#define REVERSE_LCD            0b00000111           // LCD in 'Reverse'Mode.


 
#1

7 Replies Related Threads

    ric
    Super Member
    • Total Posts : 22101
    • Reward points : 0
    • Joined: 2003/11/07 12:41:26
    • Location: Australia, Melbourne
    • Status: offline
    Re: I am stuck with ST7920. Help please! 2014/11/05 14:15:05 (permalink)
    +1 (1)
    To post code, either attach it in a file, or place "code" tags around it if embedded in your post.
    i.e. [ code ] before and [ /code ] after, but without the spaces I added.
    The first thing you should do is use LAT registers for output, not PORT registers.
    i.e. change:
    #define LCD_DATA                  PORTB                          // Port B set for 8bit data bus
    #define LCD_RW                      PORTDbits.RD0        // Read/ Write line
    #define LCD_RS                       PORTDbits.RD1             // LCD Register select
    #define LCD_EN                       PORTDbits.RD2       // LCD Enable
    #define LCD_RST                     PORTDbits.RD3       // LCD Reset

    to
    #define LCD_DATA                  LATB                          // Port B set for 8bit data bus
    #define LCD_RW                      LATDbits.LATD0        // Read/ Write line
    #define LCD_RS                       LATDbits.LATD1             // LCD Register select
    #define LCD_EN                       LATDbits.LATD2       // LCD Enable
    #define LCD_RST                     LATDbits.LATD3       // LCD Reset

    The next thing you should do is write a function to send data to the LCD, by outputting the data byte and correctly twiddling the  LCD_RW, LCD_RS, and LCD_EN pins. Just sending the data to PORTB without all that won't do anything at all.

    I also post at: PicForum
    Links to useful PIC information: http://picforum.ric323.co...opic.php?f=59&t=15
    NEW USERS: Posting images, links and code - workaround for restrictions.
    To get a useful answer, always state which PIC you are using!
    #2
    Francesco C
    Senior Member
    • Total Posts : 147
    • Reward points : 0
    • Joined: 2010/08/08 14:33:14
    • Location: UK
    • Status: offline
    Re: I am stuck with ST7920. Help please! 2014/11/10 14:11:54 (permalink)
    0
    Hi,
    I have made some progress since last post.
    I can reset the GLCD, but cannot write to display.
    I have had a good go. Now i start to despair....
     
    I really need some help from anybody, please.
     
    Regards and thanks.
     
    Francesco
     

    #define _XTAL_FREQ 4000000
    #include "lcd.h"
    #include <p18f452.h>
    #include <xc.h>
    #include "bits.h"
    #include <delays.h>

    char  alfa[1]="A";
    void LCD_Init(void);
    void LCD_Text1(void);
    void LCD_Write();
    int main(void)
    {
        
         __delay_ms(100);  // power-up delay to stabilize Vdc
        TRISB=0;
        TRISD=0;
        LATB=0;
        LATD=0;

        LCD_RST =0;
         LCD_Init();
        __delay_ms(100);
        LCD_Write();
        while (1)
        {
     
        }
    }

    void LCD_Init(void)
    {
        
       LCD_RS=0;         
       LCD_RW=0;       
        __delay_ms(4);
         LCD_RST=1;
    __delay_ms(110);       // Wait
    BIT8_LCD_BASIC;      //  Set for 8 bit data bus
    __delay_ms(5);           // wait
    BIT8_LCD_BASIC;      // repeat
    __delay_ms(5);           // wait
    ON_LCD;                     // LCD is on
    __delay_ms(5);           // wait
    CLEAR_LCD ;             // Clear
    __delay_ms(20);        //wait
    ENTRY_MODE;
    __delay_ms(5);
    HOME_LCD;
    __delay_ms(5);         // wait
    }


    void LCD_Write()
    {
        
      LCD_RS=0;
     LCD_RW=0;
     __delay_us(40);
     LCD_EN=1;
     LCD_BUS=(0b00110000);  //set for basic instruction,8bit
     __delay_us(100);
     LCD_EN-0;

    //send command for Char location
     __delay_ms(20);
    LCD_RS=0;
     LCD_RW=0;
     LCD_EN=1;
      __delay_us(40);
     LCD_BUS=0x80;    //set for first row
     __delay_ms(5);
     LCD_EN-0;
     __delay_us(40);


    /// send data
     LCD_RS=1;
     LCD_RW=0;
      LCD_EN=1;
     __delay_us(40);
     LCD_BUS=(*alfa);
     __delay_us(100);
     LCD_EN=0;
     __delay_ms(5);
    }
     
     
     

    //**********************************************************************************************************************************
    //********************   Interface for a 128x64 Graphics LCD with a  ST7920 controller  and PIC18F452    ******************


    #define LCD_BUS                    LATB                            // Port B set for 8bit data bus
    #define LCD_RW                      LATDbits.LATD0         // Read/ Write line
    #define LCD_RS                       LATDbits.LATD1         // LCD Register select
    #define LCD_EN                       LATDbits.LATD2         // LCD Enable
    #define LCD_RST                     LATDbits.LATD3         // LCD Reset


    #define CLEAR_LCD              LATB=0b00000001              // clear display
    #define HOME_LCD               LATB=0b00000010              // Return Home
    #define ENTRY_MODE          LATB= 0b00000110             // Entry mode set for: Cursor moves to the right after writing
    #define BIT8_LCD_BASIC     LATB= 0b00100000             // 8bit Interface & basic instruction set
    #define ON_LCD                    LATB= 0b00001000             // Turn display ON
    #define OFF_LCD                   LATB= 0b00000000             // Turn display OFF
     

    #3
    ric
    Super Member
    • Total Posts : 22101
    • Reward points : 0
    • Joined: 2003/11/07 12:41:26
    • Location: Australia, Melbourne
    • Status: offline
    Re: I am stuck with ST7920. Help please! 2014/11/10 14:34:04 (permalink)
    0 (1)
    How does that compile with all the #defines AFTER the code that uses them?
    In your #includes, move xc.h to first in the list, and get rid of p18f452.h from the list
    What is in "lcd.h" ?
     

    I also post at: PicForum
    Links to useful PIC information: http://picforum.ric323.co...opic.php?f=59&t=15
    NEW USERS: Posting images, links and code - workaround for restrictions.
    To get a useful answer, always state which PIC you are using!
    #4
    Francesco C
    Senior Member
    • Total Posts : 147
    • Reward points : 0
    • Joined: 2010/08/08 14:33:14
    • Location: UK
    • Status: offline
    Re: I am stuck with ST7920. Help please! 2014/11/11 14:30:17 (permalink)
    0
    Hi ric,
    it compiles OK.
    Sorry about the confusion.
    There are two files in the post. The lcd.h is the bit below the lines of ********.
    I have missed the code tag so it got merged.
    I have followed your suggestion by moving <xc.h> at the top and removed <18f452.h>
    it made no difference.
     
    May i ask, why do ask to remove the device definition?
     
    Can you think of another reason why it is not working?
     
    Regards
     
    Francesco
     
    #5
    ric
    Super Member
    • Total Posts : 22101
    • Reward points : 0
    • Joined: 2003/11/07 12:41:26
    • Location: Australia, Melbourne
    • Status: offline
    Re: I am stuck with ST7920. Help please! 2014/11/11 14:40:41 (permalink)
    0 (1)
    Francesco C
    ...
    May i ask, why do ask to remove the device definition?

    Because xc.h includes the device definition itself, so you have it twice (and will get conflicts if you change device).
     

    Can you think of another reason why it is not working?
     

    Not right now. I haven't worked with that particular controller chip, and don't have time right now to study its datasheet and see if  your commands are correct.



    I also post at: PicForum
    Links to useful PIC information: http://picforum.ric323.co...opic.php?f=59&t=15
    NEW USERS: Posting images, links and code - workaround for restrictions.
    To get a useful answer, always state which PIC you are using!
    #6
    Francesco C
    Senior Member
    • Total Posts : 147
    • Reward points : 0
    • Joined: 2010/08/08 14:33:14
    • Location: UK
    • Status: offline
    Re: I am stuck with ST7920. Help please! 2014/11/16 14:31:07 (permalink)
    0
     Hi,
    FINALLY Smile: Smile I have done it!
     
    After a long time, and a lot of trial and errors i worked it out.
    What I found incredible is that although there are a lot of examples on line, the explanation
    of how this works is either non existent or so badly presented that creates more confusion than
    you had before. 
    I hope the code below gives a reasonably good explanation on how to write a string to an ST7920
    GLCD module.
    Please feel free to comment and improve on the code.
     
    Regards
    Francesco.
     

    //  This code was written using MPLABX and XC8 compiler.
    // The definition of the connection is for a PIC18F452


    #include <xc.h>
    #include  "bits.h"                                          //Just  configuration settings Use yours.
    #define _XTAL_FREQ 4000000

    #define DATA_OUT   LATB
    #define RW                LATDbits.LATD0
    #define RS                 LATDbits.LATD1
    #define EN                LATDbits.LATD2
    #define RST              LATDbits.LATD3

    void Send_Data(unsigned char data);
    void Send_Command(unsigned char command);
    void Set_GraphicMode();
    void Initialize();
    void Clear_Graphics();
    void Write_String ( unsigned Y ,char * string );

    char message[16] =  "Hello World!";

      void main(void)
     {
        __delay_ms(100);       // Allow time for Vdc to settle on GLCD
       TRISB = 0x00;              //Set data port  B as output
       TRISD = 0x00;             // Set control port D as output
       LATB=0;                     // port B =0x00
       LATD=0;                     // port D=0x00
       RST = 0;                      // Set reset line to low
        Initialize();                  //Initialise GLCD


         Send_Command(0x80);    // Setting location to write characters. In this case 0,0 - Top Left Corner
         Send_Data(0x03);             // Sending a PREDEFINED character as described in ST7920 Datasheet.
         Send_Data(0x04);             // another one
         Send_Data(0x05);             // another one
         Send_Data(0x06);             // and another one.

         Write_String(0x90, message);  // Calling a function to send a String of characters, as defined in 'message' string.
                                                            // In Extended mode there are four line to print your text. Each line is 16 characters long.
                                                            // Line 1 starts at 0x80 , line 2 starts at 0x90, line 3 starts at 0x88, line 4 starts at 0x99.
         Set_GraphicMode();                 // Set the display in Extended mode
         Clear_Graphics();                     // Must send a Clear command otherwise display could be corrupt.
     
        while(1)
       {
          
       }
          return ;
      }


     //======================== All the command codes below can be found on the ST7920 datasheet ======================
       void Initialize()
     {
          __delay_ms(100);
           RS=0;
           RW=0;
        __delay_us(400);
        RST = 1;
       __delay_ms(10);                           // Short delay after resetting.
      Send_Command(0b00110000) ;    // 8-bit mode.
       __delay_us(100);
      Send_Command(0b00110000) ;     // 8-bit mode again.
       __delay_us(110);
       Send_Command(0b00001100);     // display on
       __delay_us(100);
       Send_Command(0b00000001);  // Clears screen.
       __delay_ms(2);
       Send_Command(0b00000110);  // Cursor moves right, no display shift.
       __delay_us(80);
       Send_Command(0b00000010);  // Returns to home. Cursor moves to starting point.
     }


     //========= Setting the control lines to send a Command to the data bus ================
    void Send_Command(unsigned char command)
     {
         RW=0;
        RS = 0;
       __delay_us(20);
         EN = 1;
       DATA_OUT = command;
        __delay_us(50);
          EN = 0;
        }

    //============= Setting the control lines to send Data to the data bus =====================
     void Send_Data(unsigned char data)
     {
       RS = 1;
      __delay_us(40);
       DATA_OUT = data;
      __delay_us(30);
      EN = 1;
     __delay_us(20);
      EN = 0;
       __delay_us(20);
     }


     //======================= Sent Command to set Extanded mode ====================
     void Set_GraphicMode()
     {
       Send_Command(0b00110100); // Extended instuction set, 8bit
       __delay_us(100);
       Send_Command(0b00110110);   // Repeat instrution with bit1 set
       __delay_us(100);
     }


     //=========== This function set all the pixels to off in the graphic controller =================
     void Clear_Graphics()
     {
       unsigned char x, y;
       for(y = 0; y < 64; y++)
       {
           if(y < 32)
           {
             Send_Command(0x80 | y);
             Send_Command(0x80);
           }
           else
           {
             Send_Command(0x80 | (y-32));
             Send_Command(0x88);
           }
           for(x = 0; x < 16; x++)
           {
             Send_Data(0x00);
           }
       }
     }

     
    //==== Send one character at the time from the 'message' string ===========
     void Write_String ( unsigned Y ,char * string )
     {
       
         Send_Command(Y);
       while(*string!= '\0')      // Looking for code signigying 'end of line' .
       {
         Send_Data  (*string++);
       }
     }



     
    #7
    JanJansen
    Super Member
    • Total Posts : 530
    • Reward points : 0
    • Joined: 2012/08/25 03:26:34
    • Location: 0
    • Status: offline
    Re: I am stuck with ST7920. Help please! 2016/12/25 09:43:41 (permalink)
    0
    Hello, thank you for posting your usefull code example.
     
    I have a question :
    How did you find out about the 8 X offset, and the Y lines to 32, i could have searched for hours without your code,
    where did you find it in the datasheet ?
     
    The pixel map at page 15/49 the GDRAM vertical adres goes to 63, not 2 times 32 with 8 X offset.
    Even with it working already, i still would like to know how to find out such thing, thanks.
    #8
    Jump to:
    © 2019 APG vNext Commercial Version 4.5