Hey Everyone,
A couple weeks ago I worked with LCDs and managed to successfully utilize a 4-bit interface. Shown below!
Now I am trying to implement a shift-register (74HC595) to control it instead, saving I/O pins. For some reason my data will not effectively transfer, do any of you see bugs?
Code:
Let me know if you have any questions!
Thanks,
Austin
A couple weeks ago I worked with LCDs and managed to successfully utilize a 4-bit interface. Shown below!
Now I am trying to implement a shift-register (74HC595) to control it instead, saving I/O pins. For some reason my data will not effectively transfer, do any of you see bugs?
Code:
Rich (BB code):
//**************************************//
// Program: LCD_2.C //
// Author: Austin Schaller //
// Date: January 16th, 2011 //
//**************************************//
//******************************************//
// Configuration of Shift Register //
// QA = RS //
// QB = EN //
// QC - QF = DATA //
//******************************************//
#pragma config WDT = OFF
#pragma config LVP = OFF
#pragma config OSC = INTIO2
#pragma config MCLRE = ON
#pragma config DEBUG = OFF
#pragma config PWRT = ON
#pragma config BOR = OFF
// Define all other config bits so that PICkit2 doesn't moan
#pragma config FSCM = OFF
#pragma config IESO = OFF
#pragma config STVR = OFF
#pragma config CP0 = OFF
#pragma config CP1 = OFF
#pragma config CPB = OFF
#pragma config CPD = OFF
#pragma config WRT0 = OFF
#pragma config WRT1 = OFF
#pragma config WRTB = OFF
#pragma config WRTC = OFF
#pragma config WRTD = OFF
#pragma config EBTR0 = OFF
#pragma config EBTR1 = OFF
#pragma config EBTRB = OFF
#include <p18F1320.h>
#include <delays.h>
// The lower 4 bits of this port will be used
#define DATA LATAbits.LATA0 // Data pins QC-QF
#define LATCH LATAbits.LATA1 // ST-CP pin of shift register
#define CLOCK LATAbits.LATA2 // SH-CP pin of shift register
// Commands for Hitachi LCD
#define CLEAR_DISPLAY 0x01
#define FOUR_BIT 0b00101111 // 4-bit Interface
#define EIGHT_BIT 0b00111111 // 8-bit Interface
#define LINE_5X7 0b00110011 // 5x7 characters, single line
#define LINE_5X10 0b00110111 // 5x10 characters
#define LINES_5X7 0b00111011 // 5x7 characters, multiple line
#define DISPLAY_ON 0b00001111 // Display on
#define DISPLAY_OFF 0b00001011 // Display off
#define CURSOR_ON 0b00001111 // Cursor on
#define CURSOR_OFF 0b00001101 // Cursor off
#define BLINK_ON 0b00001111 // Cursor Blink
#define BLINK_OFF 0b00001110 // Cursor No Blink
#define UNDERLINE_ON 0b00001111
#define UNDERLINE_OFF 0b00001101
#define INCREMENT 0b00000111 // Entry mode increment
#define DECREMENT 0b00000101 // Entry mode decrement
#define SHIFT_ON 0b00000111 // Display shift on
#define SHIFT_OFF 0b00000110 // Display shift off
void LCDInit(void);
void LCDCmd(unsigned char);
void LCDChar(unsigned char);
void shiftOut(unsigned char);
void shiftOutRS(void);
void PulseEnable(void);
void outputData(unsigned char);
// TODO: Add all prototypes
void Delay5ms(void)
{
Delay1KTCYx(1); // Delay of 5ms
return;
}
void Delay15ms(void)
{
Delay1KTCYx(3); // Delay of 15ms
return;
}
void LCDInit(void)
{
shiftOut(0x00); // Clear all data
LCDCmd(FOUR_BIT);
LCDCmd(FOUR_BIT & LINES_5X7);
LCDCmd(INCREMENT & SHIFT_OFF);
LCDCmd(DISPLAY_ON & BLINK_OFF & UNDERLINE_OFF & CURSOR_ON);
LCDCmd(CLEAR_DISPLAY);
}
void LCDCmd(unsigned char c)
{
unsigned char DataHigh, DataLow;
DataHigh |= (c >> 4); // Shift upper nibble to take the place of low-side nibble (XXXX YYYY ---> 0000 XXXX)
outputData(DataHigh); // Output upper nibble data to shift register
DataLow |= (c & 0x0F); // Retrieve lower nibble
outputData(DataLow); // Output lower nibble data to shift register
PulseEnable();
Delay5ms();
}
void LCDChar(unsigned char c)
{
unsigned char DataHigh, DataLow;
shiftOutRS(); // Enable RS (QA) for data register mode
DataHigh |= (c >> 4); // Shift upper nibble to take the place of low-side nibble (XXXX YYYY ---> 0000 XXXX)
outputData(DataHigh); // Output upper nibble data to shift register
PulseEnable();
DataLow |= (c & 0x0F); // Retrieve lower nibble
outputData(DataLow); // Output lower nibble data to shift register
PulseEnable();
Delay5ms();
}
void shiftOutRS(void) // Shift a '1' to RS (QA)
{
CLOCK = 0;
DATA = 1;
CLOCK = 1;
LATCH = 1;
LATCH = 0;
}
void outputData(unsigned char data)
{
if(0x80>data>0x03) // Make sure data is within X constraints: 01XX XX11
{
data = (data<<2) & 0x3C; // Shift data two places to the left, since RS and EN are on QA and QB
shiftOut(data); // Output data to shift register
}
}
void shiftOut(unsigned char data)
{
int i;
for (i=7;i>=0;i--)
{
CLOCK = 0; // Clear Clock
if (data & (1<<i)) // Make bit positive while incrementing with the counting variable 'i'
{
DATA = 1;
}
else
{
DATA = 0;
}
CLOCK = 1; // Delineate between bits through clock transitions
}
LATCH = 1; // Latch data to execute data
LATCH = 0;
}
void PulseEnable()
{
shiftOut(0x02);
Delay5ms();
shiftOut(0x00);
return;
}
void main(void)
{
OSCCON = 0x52; // Set internal oscillator at 2 MHz
ADCON0 = 0x00; // Disable internal ADC
ADCON1 = 0x7F; // Set all PORTB to digital I/O
INTCON2bits.RBPU = 0;
TRISA = 0xF8;
LCDInit();
Delay15ms();
LCDChar('I');
LCDChar(' ');
LCDChar('a');
LCDChar('m');
LCDChar(' ');
LCDChar('a');
LCDChar('l');
LCDChar('i');
LCDChar('v');
LCDChar('e');
LCDChar('!');
LCDChar(' ');
LCDChar('=');
LCDChar(')');
while(1);
}
Thanks,
Austin
Attachments
-
271.7 KB Views: 52
-
209.5 KB Views: 32