Monday, April 20, 2015

Giao tiếp LCD với avr atmega8 bằng 3 dây tín hiệu sử dụng 74hc595

Giao tiếp LCD với avr atmega8 bằng 3 dây tín hiệu sử dụng 74hc595





Code trình biên dịch atmelstudio 6.0
#include <util/delay.h>
#define sbi(sfr,bit) sfr|=_BV(bit)
#define cbi(sfr,bit) sfr&=~(_BV(bit))
#define EN                            2
#define RW                           1
#define RS                            0
#define CTRL                       PORTB
#define DDR_CTRL             DDRB

int DATA_O=0;//                  PORTB
#define DATA_I                    PINB
#define DDR_DATA             DDRB
/*
#define LCD8BIT
#define DATA_O                  PORTD
#define DATA_I                    PIND
#define DDR_DATA             DDRD
*/
#define hc PORTD
#define data 6
#define sck 5
#define src 7
unsigned char i;

void nap()
{
cbi(hc,sck);
sbi(hc,sck);
}
void chot()
{
cbi(hc,src);
sbi(hc,src);
}
void bit(int i)
{
if (i==1) sbi(hc,data);
if (i==0) cbi(hc,data);
}
int xuat595(int n)
{
int bien;
for (i=0;i<=7;i++)
{
bien=n&0x80;
if (bien==0)
{
cbi(hc,data);
}
else sbi(hc,data);
nap();
n=n<<1;
}
chot();
}

int sbi595(int dt ,int bi){
dt|=(1<<bi);
DATA_O=dt;
xuat595(DATA_O);
}
int cbi595(char dt ,char bi){
dt&=~(1<<bi);
DATA_O=dt;
xuat595(DATA_O);
}
/*char Read2Nib(){
char HNib, LNib;
DATA_O |=0xF0;

sbi(CTRL,EN); //enable
DDR_DATA &=0x0F; //set 4 bits cao cua PORT DATA lam input
HNib=DATA_I & 0xF0;
cbi(CTRL,EN); //disable

sbi(CTRL,EN); //enable
LNib = DATA_I & 0xF0;
cbi(CTRL,EN); //disable
LNib>>=4;
return (HNib|LNib);
}*/

void Write2Nib(uint8_t chr){
uint8_t HNib, LNib, temp_data;
temp_data=DATA_O & 0x0F; //doc 4 bit thap cua DATA_O de mask,

HNib=chr & 0xF0;
LNib=(chr<<4) & 0xF0;

DATA_O =(HNib |temp_data);
xuat595(DATA_O);
sbi595(DATA_O,EN); //enable
cbi595(DATA_O,EN); //disable

DATA_O =(LNib|temp_data);
xuat595(DATA_O);
sbi595(DATA_O,EN); //enable
cbi595(DATA_O,EN); //disable
}

void Write8Bit(uint8_t chr){
DATA_O=chr;   //out 8 bits to DATA Line
xuat595(DATA_O);
sbi595(DATA_O,EN); //enable
cbi595(DATA_O,EN); //disable
}

void wait_LCD(){
_delay_ms(2);
}
void init_LCD()
{
//Function set------------------------------------------------------------------------------
cbi595(DATA_O,RS);   // the following data is COMMAND
cbi595(DATA_O, EN);
sbi595(DATA_O,EN); //enable
sbi595(DATA_O, 5);
cbi595(DATA_O,EN); //disable
wait_LCD();
Write2Nib(0x28);//4 bit mode, 2 line, 5x8 font
wait_LCD();
//Display control-------------------------------------------------------------------------
cbi595(DATA_O,RS); // the following data is COMMAND
Write2Nib(0x0C);
wait_LCD();
//Entry mode set------------------------------------------------------------------------
cbi595(DATA_O,RS); // the following data is COMMAND
Write2Nib(0x06);
wait_LCD();
}

void home_LCD()
{
cbi595(DATA_O,RS); // the following data is COMMAND
Write2Nib(0x02);
wait_LCD();
}
void move_LCD(uint8_t y,uint8_t x)
{
uint8_t Ad;
Ad=64*(y-1)+(x-1)+0x80; // tính mã l?nh
cbi595(DATA_O,RS); // the following data is COMMAND
Write2Nib(Ad);
wait_LCD();
}
void clr_LCD(){ //xóa toàn b? LCD
cbi595(DATA_O,RS); //RS=0 mean the following data is COMMAND (not normal DATA)
Write2Nib(0x01);
wait_LCD();
}
void putChar_LCD(uint8_t chr){ //hi?n th? 1 ký t? chr lên LCD
sbi595(DATA_O,RS); //this is a normal DATA
Write2Nib(chr);
wait_LCD();
}
void print_LCD(char* str, unsigned char len){ //Hiển thị 1 chuỗi ký tự
       unsigned char i;
       for (i=0; i<len; i++){
              if(str[i] > 0) putChar_LCD(str[i]);
             else putChar_LCD(' ');
       }
}

3 comments:

  1. Bài viết rất hay.
    Và nếu bạn có thể sửa lại cách hiển thị thì sẽ rất tuyêt. Các dấu "" khiến việt đọc rất khó khăn.
    Cám ơn đã chia sẽ

    ReplyDelete
  2. bạn có thể cho mình cả project được không ? thank

    ReplyDelete

inmoov finger voice test

Inmoov finger voice test