LCD Module Speed Issue

Status
Not open for further replies.

trevor261

New Member
Hi all. I am a trainee electronics technician and I have been assigned to a project which involves interfacing a PIC18F6723 to a New Haven Display 0420DZ-FSW LCD Module. This display uses an SPLC780D-01 controller. I am using Port D on the pic for the data lines and RE5-7 for the control lines. The connections are correct and working fine.

The crystal for the PIC was initially 3.6864MHz but I have bumped it up to 14.7456MHz to get things done quicker. I have changed the configuration of the PIC to deal with the faster crystal and that is all working fine. The only problem introduced by increasing the crystal frequency is that my LCD library no longer works like it did. When I try to display a string of characters with it, only some of them are displayed. I have found that putting a 30µs delay in my Send_Character function fixes this issue, but this introduces a significant delay for each LCD line and the whole process is slower than it was with the slower crystal.

This is a really weird bug and it has me stumped. My signals look fine on the scope, well within their limits. I will post the library that I am using, if you have encountered this problem before or have some helpful thoughts on this then please feel free to reply.

Code:
#include <htc.h>
#include "lcd_8bit.h"
#include "delay.h"

void Send_Command(char command)
{
	PORTD = command;		//Assign command byte to Port D outputs,
	LCD_RS = 0;				//Send instructions.
	LCD_RW = 0;				//Write mode.
	
	NOPLoop(20);			//I need this delay for some reason.
	
	LCD_EN = 1;				//Send Enable pin hi.
	delay_Us(5);			//More than enough delay here.
	LCD_EN = 0; 			//Trigger Enable (falling edge).
}

void Send_Character(char character)
{
	PORTD = character;		//Assign character to Port D.
	LCD_RS = 1;				//Send characters.
	LCD_RW = 0;				//Write mode.
	
	delay_Us(30);			//<<<Won't print characters properly without this.
		
	LCD_EN = 1;				//Send Enable pin hi.
	delay_Us(5);			//More than enough delay here.
	LCD_EN = 0;				//Trigger Enable (falling edge).
	
}

void lcd_Clear(void)
{
	Send_Command(0x01);		//(Clear screen)
	delay_Ms(5);
}

void lcd_Print(const char * s)
{
	while(*s)
	{
		Send_Character(*s++);
	}	
}

void lcd_Goto(unsigned char position)
{
	Send_Command(0x80+position);	//Set DDRAM Address in counter.
}

void lcd_Init()
{
	LCD_EN = 0;				//Ensure Enable pin is low.
	delay_Ms(20);			//Delay of 15ms.
	Send_Command(0x30);		//Wake up.
	delay_Ms(5);			//Delay of 5ms.
	Send_Command(0x30);		//Wake up #2.
	delay_Us(160);			//Delay of 160us.
	Send_Command(0x30);		//Wake up #3.
	delay_Us(160);			//Delay of 160us.
	Send_Command(0x38);		//Function set: 8-bit, 2-line, 5 X 8 font.
	Send_Command(0x10); 
	Send_Command(0x0F);		//Display on, no cursor or blink.
	Send_Command(0x06);		//Entry mode set.
}
 
When comparing your code with the code in the datasheet everything looks to be ok. That said I do have a question, did you write "lcd_8bit.h" or was in included in you IDE or a download somewhere? Are there delays in the header file somewhere?
 
The delays are needed because the display is busy. As you have the R/W line connected, why don't you check the busy flag? Simply do a ReadCommand (TRISD=0;RS=0;RW=1;) and check bit 7 of PORTD for being zero.

Edit, here is my wait busy routine,
Code:
//wait for the LCD to finish last command.
void WaitLCDBusy(void){
    LCD_RS=0;
    LCD_RW=1;
    LCDTRIS=0;
    LCD_E=1;
    while(LCDPORT&128);
    LCD_E=0;
    LCDTRIS=0xff;
    LCD_RW=0;
}

Edit2, you should be able to write that whole display 250 times a second.

Mike.
 
Last edited by a moderator:
LTX71CM: My delay function is defined in delay.c, included via delay.h, and it is quite accurate as I have calibrated it for 14.7456MHz XTAL.


Pommie: That doesn't explain why I need a 30µs delay anywhere in my Send_Character() function now, whereas i didn't need any delay before with a 3.6864MHz crystal. My Send_Character function now takes significantly longer with 4 times the oscillator frequency. The firmware is spending the majority of its time printing to the LCD which is unacceptable as I have a maximum time for each program cycle.

What is the significance of PORTD.7? I wasn't aware that I could use the R/W pin of the LCD module to read the data like that. Are you saying that the LCD controller clears the internal data lines once the byte has been read?

Writing the whole display 250 times a seconds is 50µs per character which is too slow. I am well clear of the specified timing minimums in my code so it does not make sense for the LCD module to be behaving like this.
 
Edit, sorry misread your post. How is 4mS for the whole display too slow? That is faster than the eye can see!!

Mike.
 
Last edited:
Status
Not open for further replies.
Cookies are required to use this site. You must accept them to continue using the site. Learn more…