随着Internet技术的发展,人们的日常生活已经离不开网络。未来社会人们的生活和工作将越来越依赖于数字技术的发展,越来越数字化、网络化、电子化、虚拟化。Internet的发展历程以及目前的应用状况和发展趋势,可以充分地相信网络技术将极大的改变我们的生活和工作方式,甚至社会的价值观也会发生某种变化。
本设计实现在二进制、八进制、十进制间的转换。主要用到的是STC89C52RC系列的单片机,LCD1602显示屏以及4x4矩阵键盘。首先进行模式选择(共有六种模式)然后从矩阵键盘输入要转换的数字,按下转换键,在LCD1602显示屏上显示结果。
将4×4矩阵键盘的S1、S2、S3、S5、S6、S7、S9、S10、S11、S14设为数字键(0~9),S15设置为功能键,S16为转换键。有六种进制转换的选项(B,O,D之间相互转换)。
#include<reg52.h>
#include<intrins.h>
sbit RS = P1^0; //定义端口
sbit RW = P1^1;
sbit EN = P2^5;
sbit DU = P2^6;
sbit WE = P2^7;
#define RS_CLR RS=0
#define RS_SET RS=1
#define RW_CLR RW=0
#define RW_SET RW=1
#define EN_CLR EN=0
#define EN_SET EN=1
#define DataPort P0
void cmg88()//关数码管,点阵函数
{
DU=1;
WE=1;
P0=0X00;
DU=0;
WE=0;
}
/*------------------------------------------------
uS延时函数,含有输入参数 unsigned char t,无返回值
unsigned char 是定义无符号字符变量,其值的范围是
0~255 这里使用晶振12M,精确延时请使用汇编,大致延时
长度如下 T=tx2+5 uS
------------------------------------------------*/
void DelayUs2x(unsigned char t)
{
while(--t);
}
/*------------------------------------------------
mS延时函数,含有输入参数 unsigned char t,无返回值
unsigned char 是定义无符号字符变量,其值的范围是
0~255 这里使用晶振12M,精确延时请使用汇编
------------------------------------------------*/
void DelayMs(unsigned char t)
{
while(t--)
{
//大致延时1mS
DelayUs2x(245);
DelayUs2x(245);
}
}
/*------------------------------------------------
判忙函数
------------------------------------------------*/
bit LCD_Check_Busy(void)
{
DataPort= 0xFF;
RS_CLR;
RW_SET;
EN_CLR;
_nop_();
EN_SET;
return (bit)(DataPort & 0x80);
}
/*------------------------------------------------
写入命令函数
------------------------------------------------*/
void LCD_Write_Com(unsigned char com)
{
while(LCD_Check_Busy()); //忙则等待
RS_CLR;
RW_CLR;
EN_SET;
DataPort= com;
_nop_();
EN_CLR;
}
/*------------------------------------------------
写入数据函数
------------------------------------------------*/
void LCD_Write_Data(unsigned char Data)
{
while(LCD_Check_Busy()); //忙则等待
RS_SET;
RW_CLR;
EN_SET;
DataPort= Data;
_nop_();
EN_CLR;
}
//----------------------------------------------
/*------------------------------------------------
清屏函数
------------------------------------------------*/
void LCD_Clear(void)
{
LCD_Write_Com(0x01);
DelayMs(5);
}
/*------------------------------------------------
写入字符串函数
------------------------------------------------*/
void LCD_Write_String(unsigned char x,unsigned char y,unsigned char *s)
{
if (y == 0)
{
LCD_Write_Com(0x80 + x); //表示第一行
}
else
{
LCD_Write_Com(0xC0 + x); //表示第二行
}
while (*s)
{
LCD_Write_Data( *s);
s ++;
}
}
/*------------------------------------------------
写入字符函数
------------------------------------------------*/
void LCD_Write_Char(unsigned char x,unsigned char y,unsigned char Data)
{
if (y == 0)
{
LCD_Write_Com(0x80 + x);
}
else
{
LCD_Write_Com(0xC0 + x);
}
LCD_Write_Data( Data);
}
/*------------------------------------------------
初始化函数
------------------------------------------------*/
void LCD_Init(void)
{
LCD_Write_Com(0x38); /*显示模式设置*/
DelayMs(5);
LCD_Write_Com(0x38);
DelayMs(5);
LCD_Write_Com(0x38);
DelayMs(5);
LCD_Write_Com(0x38);
LCD_Write_Com(0x08); /*显示关闭*/
LCD_Write_Com(0x01); /*显示清屏*/
LCD_Write_Com(0x06); /*显示光标移动设置*/
DelayMs(5);
LCD_Write_Com(0x0C); /*显示开及光标设置*/
}
void delay(unsigned int xms) //延迟xms
{
unsigned char i,j;
for(i=xms;i>0;i--)
for(j=112;j>0;j--);
}
/*void display(unsigned char x,unsigned char y,uchar num)
{
LCD_Write_Char(x,y,num+0x30);
} */
void Transform10To2(unsigned int num){
unsigned char e,x=0;
unsigned long int n=2;
while(1){ //计算需要几个二进制位表示这个数字
n*=2;
x++;
if(n>num) break;
}
// LCD_Write_Char(14,1,x+0x30);
while(x>=0){
e=num%2;
LCD_Write_Char(x+2,1,e+0x30);
num=num/2;
x--;
if(x==-1) break;
}
}
void TransformTo10(unsigned long int num){
unsigned char e,x=0;
unsigned long int n=10;
while(1){ //计算需要几个十进制位表示这个数字
n*=10;
x++;
if(n>num) break;
}
// LCD_Write_Char(14,1,x+0x30);
while(x>=0){
e=num%10;
LCD_Write_Char(x+2,1,e+0x30);
num=num/10;
x--;
if(x==-1) break;
}
}
void Transform10To8(unsigned long int num){
unsigned char e,x=0;
unsigned long int n=8;
while(1){ //计算需要几个八进制位表示这个数字
n*=8;
x++;
if(n>num) break;
}
// LCD_Write_Char(14,1,x+0x30);
while(x>=0){
e=num%8;
LCD_Write_Char(x+2,1,e+0x30);
num=num/8;
x--;
if(x==-1) break;
}
}
char keyscan4x4()
{
unsigned char temp,key;
///第一行扫描///
P3=0xfe;//1111 1110 让P3.0口输出低
temp=P3;
temp=temp&0xf0;//1111 0000 位与操作 屏蔽后四位
if(temp!=0xf0)
{
delay(10); //消抖
temp=P3;
temp=temp&0xf0;
if(temp!=0xf0)
{
temp=P3;
//i++;
switch(temp)
{
case 0xee: //1110 1110 S1被按下
key=7;
break;
case 0xde: //1101 1110 S2被按下
key=8;
break;
case 0xbe: //1011 1110 S3被按下
key=9;
break;
}
while(temp!=0xf0)
{
temp=P3;
temp=temp&0xf0;
}
//display(i-1,0,key);
return key;
}
}
///第二行扫描///
P3=0xfd;//1111 1101 让P3.1口输出低
temp=P3;
temp=temp&0xf0;//1111 0000 位与操作 屏蔽后四位
if(temp!=0xf0)
{
delay(10);
temp=P3;
temp=temp&0xf0;
if(temp!=0xf0)
{
temp=P3;
//i++;
switch(temp)
{
case 0xed: //1110 1101 S5被按下
key=4;
break;
case 0xdd: //1101 1101 S6被按下
key=5;
break;
case 0xbd: //1011 1101 S7被按下
key=6;
break;
}
while(temp!=0xf0)
{
temp=P3;
temp=temp&0xf0;
}
//display(i-1,0,key);
return key;
}
}
///第三行扫描///
P3=0xfb;//1111 1011 让P3.2口输出低
temp=P3;
temp=temp&0xf0;//1111 0000 位与操作 屏蔽后四位
if(temp!=0xf0)
{
delay(10);
temp=P3;
temp=temp&0xf0;
if(temp!=0xf0)
{
temp=P3;
//i++;
switch(temp)
{
case 0xeb: //1110 1011 S9被按下
key=1;
break;
case 0xdb: //1101 1011 S10被按下
key=2;
break;
case 0xbb: //1011 1011 S11被按下
key=3;
break;
}
while(temp!=0xf0)
{
temp=P3;
temp=temp&0xf0;
}
//display(i-1,0,key);
return key;
}
}
///第四行扫描///
P3=0xf7;//1111 0111 让P3.0口输出低
temp=P3;
temp=temp&0xf0;//1111 0000 位与操作 屏蔽后四位
if(temp!=0xf0)
{
delay(10);
temp=P3;
temp=temp&0xf0;
if(temp!=0xf0)
{
temp=P3;
//i++;
switch(temp)
{
case 0xd7: //1101 0111 S14被按下
key=0;
break;
case 0xb7: //1011 0111 S15被按下,功能选择
key=11;
break;
case 0x77:
key=10; //0111 0111 S16被按下,确认转化
break;
}
while(temp!=0xf0)
{
temp=P3;
temp=temp&0xf0;
}
//display(i-1,0,key);
return key;
}
}
return -1;
}
void main()
{
unsigned long int number;
unsigned char key,i=0,count=0,g;
cmg88(); //关数码管,点阵函数
DelayMs(15);
LCD_Init();
LCD_Clear(); //清屏
LCD_Write_String(0,0,"Select function");
while(1)
{
key=keyscan4x4();
if(key==11){ //功能选择
g=count%6+1; //count++;
}
switch(g){
case 1: //十进制转二进制
//LCD_Write_String(0,0,"D:");
//LCD_Write_String(0,1,"B:");
if(i==0&&key!=-1&&key!=11){
LCD_Clear();
LCD_Write_String(0,0,"D:");
LCD_Write_String(0,1,"B:");
}
if(key!=-1&&key!=11){
if(key==10){ //按下确定按钮后
//LCD_Write_Char(i,0,key+0x30);
if(number>16383){ //判断是否超过范围
LCD_Write_String(2,1,"error!");
number=0;
i=0;
continue; //使输入确定键转化后不让10计算到number中
}else{ //未超过范围则转化为二进制
Transform10To2(number);
number=0;
//key=-1;
i=0;
continue;
}
}
else{
LCD_Write_Char(i+2,0,key+0x30); //第一行显示输入的数字
i++; //输入数字的位置
}
number=key+number*10; //将输入的数字字符转化为十进制
}
if(key==11){
count++;
LCD_Clear();
LCD_Write_String(0,0,"D:");
LCD_Write_String(0,1,"B:");
//while(1);
//key=-1;
//break;
}
//}
break;
case 2: //二进制转十进制
//LCD_Write_String(0,0,"B:");
//LCD_Write_String(0,1,"D:");
if(i==0&&key<=1){
LCD_Clear();
LCD_Write_String(0,0,"B:");
LCD_Write_String(0,1,"D:");
}
if(key==0||key==1||key==10){
switch(key){
case 10:
TransformTo10(number);
number=0;
i=0;
break;
default:
LCD_Write_Char(i+2,0,key+0x30);
i++;
number=key+number*2;
}
}
if(key==11){
count++;
LCD_Clear();
LCD_Write_String(0,0,"B:");
LCD_Write_String(0,1,"D:");
break;
}
//}
break;
case 3: //八进制转二进制
//LCD_Write_String(0,0,"O:");
// LCD_Write_String(0,1,"B:");
if(i==0&&key>=0&&key<=7){
LCD_Clear();
LCD_Write_String(0,0,"O:");
LCD_Write_String(0,1,"B:");
}
if((key>=0&&key<=7)||key==10){
switch(key){
case 10:
if(number>16383){ //判断是否超过范围
LCD_Write_String(2,1,"error!");
number=0;
i=0;
continue;
}else{ //未超过范围则转化为二进制
Transform10To2(number);
number=0;
i=0;
continue;
}
break;
default:
LCD_Write_Char(i+2,0,key+0x30);
i++;
number=key+number*8;
}
}
if(key==11){
count++;
LCD_Clear();
LCD_Write_String(0,0,"O:");
LCD_Write_String(0,1,"B:");
break;
}
break;
case 4: //二进制转八进制
//LCD_Write_String(0,0,"B:");
//LCD_Write_String(0,1,"O:");
if(i==0&&key<=1){
LCD_Clear();
LCD_Write_String(0,0,"B:");
LCD_Write_String(0,1,"O:");
}
if(key==0||key==1||key==10){
switch(key){
case 10:
Transform10To8(number);
number=0;
i=0;
break;
default:
LCD_Write_Char(i+2,0,key+0x30);
i++;
number=key+number*2;
}
}
if(key==11){
count++;
LCD_Clear();
LCD_Write_String(0,0,"B:");
LCD_Write_String(0,1,"O:");
break;
}
break;
case 5: //八进制转十进制
//LCD_Write_String(0,0,"O:");
//LCD_Write_String(0,1,"D:");
if(i==0&&key<=7&&key>=0){
LCD_Clear();
LCD_Write_String(0,0,"O:");
LCD_Write_String(0,1,"D:");
}
if((key<=7&&key>=0)||key==10){
switch(key){
case 10:
if(number>4294967290){ //判断是否超过范围
LCD_Write_String(2,1,"error!");
number=0;
i=0;
continue;
}else{
TransformTo10(number);
number=0;
i=0;
}
break;
default:
LCD_Write_Char(i+2,0,key+0x30);
i++;
number=key+number*8;
}
}
if(key==11){
count++;
LCD_Clear();
LCD_Write_String(0,0,"O:");
LCD_Write_String(0,1,"D:");
break;
}
break;
case 6: //十进制转八进制
//LCD_Write_String(0,0,"D:");
//LCD_Write_String(0,1,"O:");
if(i==0&&key!=-1&&key!=11){
LCD_Clear();
LCD_Write_String(0,0,"D:");
LCD_Write_String(0,1,"O:");
}
if(key!=-1&&key!=11){
switch(key){
case 10: ;
if(number>4294967290){ //判断是否超过范围
LCD_Write_String(2,1,"error!");
number=0;
i=0;
continue;
}else{
Transform10To8(number);
number=0;
i=0;
continue;
}
break;
default:
LCD_Write_Char(i+2,0,key+0x30); //第一行显示输入的数字
i++;
number=key+number*10;
}
}
if(key==11){
count++;
LCD_Clear();
LCD_Write_String(0,0,"D:");
LCD_Write_String(0,1,"O:");
break;
}
break;
}
continue;
}
while(1);
}