您好,您可以用以下程序来实现~ main() { uchar xdata addx=0; //初始值指向U6的开始,用于读取U6 //用于存放已显示汉字的个数 uchar hzdot;//用于存放调整好的汉字点阵的数组首地址,直接用于显示的
7920只能驱动32路,12864为两个7920控制,你想一个一个的卷动必须设置CS1,CS2,加入CS1上屏,CS2,下屏,你先控制CS1=0,CS2=1;然后COM地址加一,32以后,CS2=0,CS1=1; 然后COM地址加一就搞定
我仿真过。proteus里AMPIRE 128x64器件。它是最基本的12864了,基本控制指令就行。比实物要简单。网络上有个“大海橡树”的,他写了比较详细的关于它的教程。你可以找找。
//
#define P0Data P0 //宏定义所接的数据端口,方便移植
sbit RS=P2^0 ; //程序数据存储器选择:=0是程序存储器,=1是数据存储器
sbit RW=P2^1 ; //读写控制选择:=0是写,=1是读
sbit E=P2^2 ; //使能,初端口初始化外,在写指令数据前都要检测busy标志。
sbit CS1=P2^3; //选中显示的芯片
sbit CS2=P2^4; //64x64一块,总共左右两片
#define AddressX 0xb8 //定义第0行
#define AddressY 0x40 //定义第0列
//
static void Delay1ms(uchar x);
static void LcdWriteComOrData(uchar x,uchar content);//写指令或写数据
static void LcdReadComBusy(void); //读指令,读数据没有用到,所以只是读指令中的忙标志
static void ShowPicture(uchar (p)[64]); //显示
static void ShowChar(uchar p[][8][8]); //显示全屏字符
static void ShowCharPage(uchar page,uchar p[2][8][8]); //输出单行的一串字符
static void ShowChinaChar(uchar x,uchar page,uchar range,uchar p[2][16]); //输出一个汉字
static void ShowChinaSinger(uchar p[2][16]);
static void ShowChina32(uchar p[4][8][2][16]); //满屏全32个汉字
//
void _L12864Init(void) //用proteus仿真只用基本的7条指令
{
/ 这段不需要,因为仿真用基本7条指令,而实际模块初始化要根据厂商提供的初始化规范做
uchar i;
for(i=0;i<5;i++)
{
P0Data=0x30; //入口是8位接口,12864只能是8位的,不像L1602有四位的选择;RE=0(右起第2位),选择基本指令集,扩充指令不用。
RS=0;
RW=0;
E=1; //设置开始,至少450ns,执行指令时间差不多够了。
E=0; //设置结束
Delay1ms(3);//要求延时,这个延时比一般指令延时要长 这里延时之前不要设置,防止中断打断设置
}
/
LcdWriteComOrData(0,0x3f); //显示开
LcdWriteComOrData(0,0xc0); //定义起始行,这个指上下的64行从哪行开始,一般是0,有规律改变它,可以实现滚屏
ShowPicture(TabPicture0) ;
ShowChar(TabChar);
ShowCharPage(6,TabCharPageX);
ShowChinaChar(2,4,4,TabPicture0);
ShowChinaSinger(TabPicture0);
ShowChina32(TabChina32);
}
//
//满屏输出4行8个共32个汉字
static void ShowChina32(uchar p[4][8][2][16]) //这里把入口指针直接写明需要32个汉字
{
uchar i,j,k;
for(k=0;k<4;k++) //总共四行汉字
{
CS1=0;CS2=1; //选中左半屏
for(i=0;i<4;i++)
{
LcdWriteComOrData(0,AddressX|(k<<1));
LcdWriteComOrData(0,AddressY|(i<<4));
for(j=0;j<16;j++)
LcdWriteComOrData(1, p[k][i][0][j] );
LcdWriteComOrData(0,AddressX|(k<<1)+1);
LcdWriteComOrData(0,AddressY|(i<<4));
for(j=0;j<16;j++)
LcdWriteComOrData(1, p[k][i][1][j] );
}
CS1=1;CS2=0;//选中右半屏
for(i=5;i<9;i++)
{
LcdWriteComOrData(0,AddressX|(k<<1));
LcdWriteComOrData(0,AddressY|((i-4)<<4));
for(j=0;j<16;j++)
LcdWriteComOrData(1, p[k][i][0][j] );
LcdWriteComOrData(0,AddressX|(k<<1)+1);
LcdWriteComOrData(0,AddressY|((i-4)<<4));
for(j=0;j<16;j++)
LcdWriteComOrData(1, p[k][i][1][j] );
}
}
}
//
//在左上角显示一个汉字
static void ShowChinaSinger(uchar p[2][16])
{
uchar j;
CS1=0;CS2=1;
LcdWriteComOrData(0,AddressX) ; //页决定,这里决定这个汉字是在那一页显示,这里移1位的意思是,让方块汉字开始显示在偶数页上。
LcdWriteComOrData(0,AddressY);
for(j=0;j<16;j++) //输出每个汉字组成的上16个字节,下面一半显示下一页
LcdWriteComOrData(1, p[0][j] );
LcdWriteComOrData(0,AddressX|1) ; //页决定,这里决定这个汉字是在那一页显示,这里移1位的意思是,让方块汉字开始显示在偶数页上。
LcdWriteComOrData(0,AddressY);
for(j=0;j<16;j++) //输出每个汉字组成的上16个字节,下面一半显示下一页
LcdWriteComOrData(1, p[1][j] );
}
//
//在任意屏页列输出单个汉字。
static void ShowChinaChar(uchar x,uchar page,uchar range,uchar (p)[16]) //输出一个汉字
{ //字符来自于一个二维数值,参数分别是屏选1~2,汉字行选1~4(总共能显示四行汉字),列选1~4,半屏一页能显示四个汉字
uchar j;
x--,page--;range--; //把屏选、行、列习惯转为计算方式
switch(x) //x决定输出的汉字在左半屏还是右半屏,0表示左半屏,1表示右半屏
{
case 0: CS1=0;CS2=1; break;
case 1: CS1=1;CS2=0; break;
default: ;
}
LcdWriteComOrData(0,AddressX|(page<<1) ); //页决定,这里决定这个汉字是在那一页显示,这里移1位的意思是,让方块汉字开始显示在偶数页上。
LcdWriteComOrData(0,AddressY|(range<<4) ); //列决定,这里决定这个汉字开始在那一列显示。每16列一个位置,所以左移动4位。
for(j=0;j<16;j++) //输出每个汉字组成的上16个字节,下面一半显示下一页
LcdWriteComOrData(1, p[0][j] );
LcdWriteComOrData(0,AddressX|(page<<1)+1);
LcdWriteComOrData(0,AddressY|(range<<4) );
for(j=0;j<16;j++) //输出每个汉字组成的上16个字节,下面一半显示下一页
LcdWriteComOrData(1, p[1][j] ); //注意这里如果写成指针形式(p+1)[j]不等于p[1][j],通过和[]的互换,得到((p+1)+j)才是p[1][j]。
}
//
//输出某一页(左半屏+右半屏)字符,字符来自于一个三维数值
static void ShowCharPage(uchar page,uchar p[2][8][8]) //以三维数组的形式输出所有的字符
{
uchar i,j;
page--; //把习惯改为计算方式
CS1=0;CS2=1;
LcdWriteComOrData(0,AddressX|page);
LcdWriteComOrData(0,AddressY); //列数值清零
for(i=0;i<8;i++)
for(j=0;j<8;j++) //输出每个字符组成的8个字节,横向的右半屏在下一组,所以这里k每次乘2
LcdWriteComOrData(1, p[0][i][j] );
CS1=1;CS2=0; //输出右半屏8个字符
LcdWriteComOrData(0,AddressX|page); //这行指令不能省,X地址寄存器在片选后是另一个HD61202的x寄存器
LcdWriteComOrData(0,AddressY);
for(i=0;i<8;i++)
for(j=0;j<8;j++)
LcdWriteComOrData(1, p[1][i][j] ); //这里重点说明下,取模工具取数是纵向到底的
}
//
//逐页横向显示字符,修改后也试用于更大屏幕
static void ShowChar(uchar p[][8][8]) //以三维数组的形式输出所有的字符
{ //一维是8位字节,二维是8个8位字节组成一个字符,三维是8个字符组成的半屏的一页。
uchar i,j,k; //显示128x64屏幕就是有16块这样的8个一组的字符串,
for(k=0;k<8;k++) //而192x64的屏幕有24个这样的8个一组的字符串
{ //这里k<8,不能写成k<16,k是页值,用页值来访问不同的三维数组的,下面k<<1就是这个意思
CS1=0;CS2=1; //输出左半屏8个字符
LcdWriteComOrData(0,AddressX|k); //行的改写不能太远,因为下次读写数据才修改页地址
LcdWriteComOrData(0,AddressY); //列数值清零
for(i=0;i<8;i++)
for(j=0;j<8;j++) //输出每个字符组成的8个字节,横向的右半屏在下一组,所以这里k每次乘2
LcdWriteComOrData(1, p[k<<1][i][j] );
CS1=1;CS2=0; //输出右半屏8个字符
LcdWriteComOrData(0,AddressX|k);
LcdWriteComOrData(0,AddressY);
for(i=0;i<8;i++)
for(j=0;j<8;j++)
LcdWriteComOrData(1, p[(k<<1)+1][i][j] ); //这里重点说明下,取模工具取数是纵向到底的
} //因此这里上一块8个字符完了,就是右半屏的一块字符,因此这里三维k值加1
}
//
//左右半屏方式,显示图像
static void ShowPicture(uchar (p)[64])//显示一张,因为是没有字符那样的局部空间,一个整体
{ //显示一页就是64列,这里64是二维数组的第二维是64
uchar i,j;
CS1=0;CS2=1; //显示左半屏
for(i=0;i<8;i++)
{
LcdWriteComOrData(0,AddressX|i); //确定要显示的页
LcdWriteComOrData(0,AddressY); //确定要显示的初始列,不能丢,很重要
for(j=0;j<64;j++)
LcdWriteComOrData(1, p[i<<1][j] ); //把i2变成i<<1,乘法变成移位
}
CS1=1;CS2=0; //换右半屏显示
for(i=0;i<8;i++)
{
LcdWriteComOrData(0,AddressX|i); //page还从第0行开始
LcdWriteComOrData(0,AddressY);
for(j=0;j<64;j++)
LcdWriteComOrData(1, p[(i<<1)+1][j]);
};
}
//
static void LcdWriteComOrData(uchar x,uchar content)
{
LcdReadComBusy(); //检测忙标志
P0Data=content;
E=0; //按照HD44780/KS0066控制器的脉冲时序走
if(x==0){RS=0;RW=0; } //如果是0,选址程序寄存器写;这种程序结构来自于金鹏LCD
else {RS=1;RW=0;} //如果是1,选择数据寄存器写
E=1;
Delay1ms(1); //写程寄存器需要一段延时,执行也有延时。因为控制字写入之后,查书发现,执行至少需要40us,如果在E=1和0之间没有延时,程序不执行
E=0; //这行和上一行Delay1ms(1)交换后,发现检测不到了,原因就是以上的延时问题。
}
//
static void LcdReadComBusy(void) //这种程序结构来自于网友大海橡树的程序
{
P0Data=0; //准备读忙标志,用的是P0口,所以可以直接放低就可以了,如果用其他口,Px不能直接写0,必须先写1才能读入外部信息
RS=0; //选择程序寄存器
RW=1; //读
E=1; //使能打开
while( P0Data & 0x80 ) ; //如果是忙P0data与0x80就不等于0,所以while语句总是执行。
E=0; //使能关闭
}
//
//功能:12MHz下延时1ms标准程序,延时时间为 1msx,
//输入:x ;最大为255,即最大范围255ms
static void Delay1ms(uchar x)
{
uchar i,j;
for(i=0;i<x;i++)
for(j=0;j<=161;j++);
}
//
上面是我写的驱动,你可以直接用。很久以前写的,现在再看了我自己写得太繁杂了,太啰嗦了。没必要,你可以在看懂的基础优化一下。采用的模块化编程,因此您建一个h文件再使用它比较好。
用ad的,改改就能用18b20
LCD点阵12864画温度曲线默认分类 2007-08-17 18:54:58 阅读548 评论3 字号:大中小 订阅
#include<reg51h>
#include"LCD12864h"
#include"zimoh"
#include"LCD1602h"
void hua_zuobiao(void);//画坐标
void delay1ms(uint k);//延时间
void TLC2543(void);//2543读数据子函数
void count_ad(void);//1602的显示
uchar code shuzi[]={0x00,0x80,0x40,0x20,0x10,0x08,0x04,0x02,0x01};//0--8
uchar code number[]={"0123456789"};
uchar tab1[]={" wendu=+4999c "};// 9 10 12 13
uchar code tab2[]={" made of suwei "};
unsigned long int ad;
///////////////////TLC2543
sbit clk=P1^3;//时钟
sbit cs=P1^2;//1变0时TLC2543复位
sbit adtain=P1^1;//数据输入
sbit adtaout=P1^0;//数据输出
////////////////
void main(void)
{uchar x,y;//x页 y列
uchar i;
uint j;
uchar wendu=30,dp;//温度//曲线的点
///////////1602
init_1602();
gotoxy(1,0);
for(i=0;i<16;i++)write_LCD_data(tab1[i]);
gotoxy(2,0);
for(i=0;i<16;i++)write_LCD_data(tab2[i]);
///////////////12864LCD
initi_LCD();//
hua_zuobiao();//画坐标图
y=12;//从12列开始
while(1)
{ TLC2543();//2543读数据子函数
count_ad();//lcd1602的更新显示
delay1ms(1);
j++;
if(j>50){j=0;
wendu=ad/100;//取温度的前2位
x=(wendu-1)/8;
x=6-x;
dp=(wendu-1)%8+1;
if(y<64){ set_adr(x,y);
wdata(shuzi[dp],1,0);
}
else { set_adr(x,y-64);
wdata(shuzi[dp],0,1);
}
y++;//列
if(y==128){y=12;//
clear();//清屏
hua_zuobiao();//画坐标图
}
}
}
}
////////////
/i=0;
initi_LCD();
hua_zuobiao();//画坐标
set_adr(3,12);
y=3;c=13;
while(1)
{i++;
c++;
if(i==8){i=0;
y=y-1;
if(y==0)y=7;
temp=0xb8+y;
wcode(temp,1,1);
}
if(c==64) set_adr(temp,0);
if(c>=127)while(1);
if(c>=64) wdata(shuzhi[i],0,1);
else wdata(shuzhi[i],1,0);
delay1ms(100);
}
}/
/////////////
// }
//}
////1602的显示
void count_ad(void)
{uchar i;
uint temp;
temp=ad;
tab1[13]=number[temp%10];temp=temp/10;
tab1[12]=number[temp%10];temp=temp/10;
tab1[10]=number[temp%10];temp=temp/10;
tab1[9]= number[temp%10];
gotoxy(1,0);
for(i=0;i<16;i++)write_LCD_data(tab1[i]);
}
//////////////////////////////////
void TLC2543(void)//2543读数据子函数
{uchar i;//输入数据为0x00//0x10为第一通道
ad=0;
clk=0;
cs=0;
for(i=0;i<12;i++)
{if(adtaout==1)ad=ad|0x01;//读出数据
adtain=0;//写入数据
clk=1;
clk=0;
ad<<=1;//左移一位
}
cs=1;
ad>>=1;//数据存在ad里
ad=(ad1000)/819;//temp=(ad5000)/4095;
}
///////////////////////////
void hua_zuobiao(void)//画坐标
{uchar j;
uint i;
for(j=0;j<8;j++)//页码
{set_adr(j,0);
for(i=1;i<=64;i++){wdata(zuobiao[i+j128],1,0);
wdata(zuobiao[63+i+j128],0,1);
}
}
}
////////////////////////
void delay1ms(uint k)//延时间
{k=k125;
while(--k);
}
////////////
调用子程序
#include<reg51h>
#define _LCD12864_h
#define uchar unsigned char
#define uint unsigned int
void delay(uint k);//延时
void wcode(uchar com,uchar cs1,uchar cs2);//写指令
void wdata(uchar da,uchar cs1,uchar cs2);//写数据
void set_startline(uchar i);//起始行
void set_adr(uchar x,uchar y);//页值设置,起始列值函数
void clear(void);///clear清屏
void initi_LCD(void);//初始化LCD
//////////单片机与液晶显示的引脚连接/////////
//sbit RST=P2^2;
sbit CS2=P2^0;
sbit CS1=P2^1;
sbit RS=P2^2;//或DI
sbit RW=P2^3;
sbit E=P2^4;
//P0口为数据口
//////////////////////////////
void initi_LCD(void)//初始化LCD
{ wcode(0x3f,1,1);//显示开//0x3e关
set_startline(0);//起始行第0行
clear();//清屏
}
///////////////////////
void delay (uint k)//延时
{
while(k--);
}
////////复位///////////
/void reset()
{
RST=0;
delay(200);
RST=1;
delay(200);
}
/
////////write code写指令///////
void wcode(uchar com,uchar cs1,uchar cs2)//写指令
{
CS1=cs1;
CS2=cs2;
RW=0;
RS=0;
P0=com;
E=0;
delay(10);
E=1;
delay(10);
E=0;
}
/////////write data写数据///////////////
void wdata(uchar da,uchar cs1,uchar cs2)//写数据
{
CS1=cs1;
CS2=cs2;
RW=0;
RS=1;
P0=da;
E=0;
delay(10);
E=1;
delay(10);
E=0;
}
////////////set start设置起始行/////////////
void set_startline(uchar i)//起始行。11A5A4A3A2A1A0 共有64行
{ //液晶显示器的最底层为第0行
i=0xc0+i;//此算法为把最顶层做为第一层
wcode(i,1,1);
}
///////////////////////////////
void set_adr(uchar x,uchar y)//页值设置,起始列值函数
{
x=x+0xb8;//行//页地址设置。10111A2A1A0 DDRAM的8行为一页,A0~A2为页码,LCD为64行8页
y=y+0x40;//列地址设置。01A5A4A3A2A1A0 两半屏分别有64列,A0~A5送入列地址计数器,
//作为列(Y)地址指针。每读写一次其自动加一,指向下一列DDRAM单元
wcode(x,1,1);
wcode(y,1,1);
}
///////////clear清屏///////////////
void clear(void)///clear清屏
{
uchar i,loop;
for(i=0;i<8;i++)///循环页写0/////////
{
set_adr(i,0);//页码//行
for(loop=0;loop<64;loop++)wdata(0x00,1,1);//列//左右屏幕同时写//
}
}
调用子程序
#include<reg51h>
#define _zimo_h
#define uchar unsigned char
#define uint unsigned int/////////////////////////////////////////////////////////////////////////
// 汉字字模表 //
// 汉字库: 宋体16dot 纵向取模下高位,数据排列:从左到右从上到下 //
//字节倒置
uchar code zuobiao[]={
/-- 调入了一幅图像:C:\Documents and Settings\Administrator\桌面\温度坐标bmp --/
/-- 宽度x高度=128x64 --/
0x00,0x00,0x00,0x70,0x50,0xD0,0x00,0xF0,0x10,0xF0,0x00,0xFF,0x40,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0xC1,0x01,0xC1,0x00,0xC1,0x41,0xC1,0x00,0xFF,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x01,0x01,0x07,0x00,0x07,0x04,0x07,0x00,0xFF,0x01,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x15,0x15,0x1F,0x00,0x1F,0x11,0x1F,0x00,0xFF,0x04,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x74,0x54,0x5C,0x00,0x7C,0x44,0x7C,0x00,0xFF,0x10,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0xF0,0x00,0xF0,0x10,0xF0,0x00,0xFF,0x40,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x01,0x00,0x01,0x01,0x01,0x00,0xFF,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x80,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x80,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x80,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x80,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x80,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x80,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x80,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x80,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x80,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x80,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x80,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7C,0x44,0x7C,0x00,0x01,0x01,0x01,0x01,0x01,
0x01,0x01,0x01,0x01,0x01,0x7D,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x75,0x55,
0x5D,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x55,0x55,0x7D,0x01,0x01,0x01,0x01,0x01,
0x01,0x01,0x1D,0x11,0x7D,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x5D,0x55,0x75,0x01,
0x01,0x01,0x01,0x01,0x01,0x01,0x7D,0x55,0x75,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
0x05,0x05,0x7D,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x7D,0x55,0x7D,0x01,0x01,0x01,
0x01,0x01,0x01,0x01,0x1D,0x15,0x7D,0x01,0x01,0x01,0x01,0x01,0x01,0x7D,0x01,0x7D,
0x45,0x7D,0x01,0x01,0x01,0x01,0x01,0x01,0x7D,0x01,0x01,0x7D,0x01,0x01,0x01,0x01,
};
调用子程序
#include <reg51h>
#define _lcd1602_h
#define uint unsigned int
#define uchar unsigned char
void delayus(uint k);//延时
void write_LCD_command(uchar command);//命令写入LCD
void write_LCD_data(uchar LCDdata);//数据写入LCD
void init_1602(void);//初始化LCD
void clear_LCD();//LCD清屏
void gotoxy(uchar x,uchar y);//光标在x行y列
sbit rs=P2^5;//指令寄存器的选择
sbit rw=P2^6;//数据写入/读出lcd
sbit en=P2^7;//始能端
//////////////////////////////////////////////////1
void write_LCD_command(uchar command)//命令写入LCD
{
rw=0;//写入LCM
rs=0;//指令寄存器
en=1;//始能端
P3=command;//写命令
delayus(20);//延时4020us
en=0;//关闭始能端
rw=1;//读取LCM
}
void write_LCD_data(uchar LCDdata)//数据写入LCD//2
{
rw=0;
rs=1;
en=1;
P3=LCDdata;
delayus(1);//40us
en=0;
rw=1;
}
void init_1602(void)//初始化LCD/////3
{
write_LCD_command(0x38);// 0x38 单行显示//8位传输
write_LCD_command(0x0c);// 0x0C 屏幕开启//光标不出现//不闪烁
//write_LCD_command(0x0e);// 0x0C 屏幕开启//光标出现//不闪烁
//write_LCD_command(0x0f);// 0x0C 屏幕开启//光标出现 //闪烁
//write_LCD_command(0x0d);// 0x0C 屏幕开启//光标不出现 //闪烁
}
void clear_LCD()//LCD清屏4
{
write_LCD_command(0x01);//0x01 LCD清屏
write_LCD_command(0x02);//0x02 光标回到左上角
}
void gotoxy(uchar x,uchar y)//光标在x行y列7
{
if(x==1)
write_LCD_command(128+y);//128=0b1000,0000
else
write_LCD_command(192+y);//192=0b1100,0000
}
void delayus(uint k)//延时8
{
k=10k;//40us
while(k--);
}
if(a&(1<<(i-1))) RW_SID=1;
表示1左移i-1位再于a进行与运算,i=8的情况下i-1=7,1左移7位就是0x80。再跟a与运算(全1出1有0出0)即可获得a的最高位。以此类推可以取出a的所有位。
if(RW_SID==1) dat|=(1<<(i-1));
当RW_SID端口为1时把1左移i-1位跟dat或运算。i=8的情况下1左移i-1位正好是0x80,再经过与运算保存最高位,循环移位再或运算就能读取到全部位保存在dat里面
可以写成
//写部分
if(a&0x80)//取出a的最高位
RW_SID=1;//如果是1则输出1
else
RW_SID=0;//否则输出0
a<<=1;//a整体左移,让第7位补到最高位的位置,循环取出
E_CLK=1;
delay(100);
E_CLK=0;
delay(100);
//读部分
E_CLK=1;
delay(100);
dat<<=1;//接收1次数据后左移。第一次为0的情况影响数据
if(RW_SID)//当端口为高的时候
dat++;//dat+1相当于dat|=1 当端口为0的时候默认左移最低位是补零的,所以不用管
E_CLK=0;//循环8次后第一次接受到的数据就在最高位了
delay(100);
效果是一样的相对来说比较好理解
#define uchar unsigned char
#define uint unsigned int
#define iDat 1 //数据标志
#define iCmd 0 //指令标志
#define LCDb_RS 0x20 //定义四个控制引脚
#define LCDb_RW 0x40
#define LCDb_E 0x80
#define LCDb_RST 0x04
#define LCDb_L1 0x80 //第一行的地址
#define LCDb_L2 0x90 //第二行的地址
#define LCDb_L3 0x88 //第三行的地址
#define LCDb_L4 0x98 //第四行的地址
#define LCDb_SET_RS P1OUT|=LCDb_RS //四个控制管脚的控制 *** 作
#define LCDb_SET_RW P1OUT|=LCDb_RW
#define LCDb_SET_E P1OUT|=LCDb_E
#define LCDb_SET_RST P8OUT|=LCDb_RST
#define LCDb_CLR_RS P1OUT&=~LCDb_RS
#define LCDb_CLR_RW P1OUT&=~LCDb_RW
#define LCDb_CLR_E P1OUT&=~LCDb_E
#define LCDb_CLR_RST P8OUT&=~LCDb_RST
#define LCDb_DO P4OUT //输出数据总线端口定义
#define LCDb_FUNCTION 0x38 // 液晶模式为8位,2行,58字符
#define LCDb_BASCMD 0x30 // 基本指令集
#define LCDb_CLS 0x01 // 清屏
#define LCDb_HOME 0x02 // 地址返回原点,不改变DDRAM内容
#define LCDb_ENTRY 0x06 // 设定输入模式,光标加,屏幕不移动
#define LCDb_C2L 0x10 // 光标左移
#define LCDb_C2R 0x14 // 光标右移
#define LCDb_D2L 0x18 // 屏幕左移
#define LCDb_D2R 0x1C // 屏幕又移
#define LCDb_ON 0x0C // 打开显示
#define LCDb_OFF 0x08 // 关闭显示
unsigned char RXData;
unsigned char Result[5]; //整数转化成字符串,给LCD显示
/
函数名称: Delayms
功 能: 延时指定毫秒(8M晶振)
参 数: MS--延时的毫秒数
返回值 : 无
/
void Delayms(uint MS)
{
uint i,j;
for( i=0;i<MS;i++)
for(j=0;j<1141;j++);
}
/
函数名称: Delayus
功 能: 延时指定微秒(8M晶振)
参 数: US--延时的微秒数(大约,不是很精确,MS越大越准确)
返回值 : 无
/
void Delayus(uint US)
{
uint i;
US=US5/4;
for( i=0;i<US;i++);
}
void LCD12864_portini()
{
P1DIR=0xFF;
P4DIR=0xFF;
P8DIR=0xFF; //Trig =P8^3输出;
P8OUT |=LCDb_RST;
// P1OUT=0xFF;
}
/
函数名称: LCD12864_sendbyte
功 能: 向12864液晶写入一个字节数据或者指令
参 数: DatCmd--为iDat时是数据,为iCmd时是指令
dByte--为写入12864的数据或者指令
返回值 : 无
/
void LCD12864_sendbyte(uchar DatCmd, uchar dByte)
{
if (DatCmd == iCmd) //指令 *** 作
LCDb_CLR_RS;
else
LCDb_SET_RS;
LCDb_CLR_RW; //写 *** 作
LCDb_SET_E;
LCDb_DO = dByte; //写入数据
//Delayus(500);
Delayms(1);
LCDb_CLR_E;
}
/
函数名称: LCD12864_sendstr
功 能: 向12864液晶写入一个字符串
参 数: ptString--字符串指针
返回值 : 无
/
void LCD12864_sendstr(uchar ptString)
{
while((ptString)!='\0') //字符串未结束一直写
{
LCD12864_sendbyte(iDat, ptString++);
}
}
/
函数名称: LCD12864_clear
功 能: 12864液晶清屏
参 数: 无
返回值 : 无
/
void LCD12864_clear(void)
{
LCD12864_sendbyte(iCmd,LCDb_CLS);
Delayms(2);// 清屏指令写入后,2ms 的延时是很必要的!!!
}
/
函数名称: LCD12864_gotoXY
功 能: 移动到指定位置
参 数: Row--指定的行
Col--指定的列
返回值 : 无
/
void LCD12864_gotoXY(uchar Row, uchar Col)
{
switch (Row) //选择行
{
case 2:
LCD12864_sendbyte(iCmd, LCDb_L2 + Col); break; //写入第2行的指定列
case 3:
LCD12864_sendbyte(iCmd, LCDb_L3 + Col); break; //写入第3行的指定列
case 4:
LCD12864_sendbyte(iCmd, LCDb_L4 + Col); break; //写入第4行的指定列
default:
LCD12864_sendbyte(iCmd, LCDb_L1 + Col); break; //写入第1行的指定列
}
}
/
函数名称: LCD12864_initial
功 能: 12864液晶初始化
参 数: 无
返回值 : 无
/
void LCD12864_initial(void)
{
Delayms(100); // 等待内部复位
LCD12864_portini(); //端口初始化
LCD12864_sendbyte(iCmd, LCDb_FUNCTION); //功能、模式设定
LCD12864_sendbyte(iCmd, LCDb_ON); //打开显示
LCD12864_clear(); //清屏
LCD12864_sendbyte(iCmd, LCDb_ENTRY); // 输入模式设定
}
void Int_char(int data)
{
if(data/1000)
{
Result[0]=data/1000+'0';
Result[1]=data/100%10+'0';
Result[2]=data/10%10+'0';
Result[3]=data%10+'0';
Result[4]=0;
}
else if(data/100)
{
Result[0]=data/100+'0';
Result[1]=data/10%10+'0';
Result[2]=data%10+'0';
Result[3]=0;
Result[4]=0;
}
else if(data/10)
{
Result[0]=data/10%10+'0';
Result[1]=data%10+'0';
Result[2]=0;
Result[3]=0;
Result[4]=0;
}
else
{
Result[0]=data%10+'0';
Result[1]=0;
Result[2]=0;
Result[3]=0;
Result[4]=0;
}
}
这使msp430单片机的程序,只要在主函数中调用函数,就是调用这个函数Int_char(tmp);每一次循环调用一次,这样可以实时显示这个变化温度数值
LCD12864_gotoXY(2,4);
LCD12864_sendstr(" ");
LCD12864_gotoXY(1,0); //第1行,第1列显示
LCD12864_sendstr("正在检测");
LCD12864_gotoXY(2,0); //第2行,第1列显示
LCD12864_sendstr("距离是:");
Int_char(tmp);
以上就是关于12864是怎么把数组中内容显示出来的全部的内容,包括:12864是怎么把数组中内容显示出来的、请教12864(ST7920)液晶滚动显示的程序问题、谁用proteus仿真过12864啊 求解释啊等相关内容解答,如果想了解更多相关内容,可以关注我们,你们的支持是我们更新的动力!
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)