倾斜角测量仪程序.docx
《倾斜角测量仪程序.docx》由会员分享,可在线阅读,更多相关《倾斜角测量仪程序.docx(17页珍藏版)》请在冰豆网上搜索。
倾斜角测量仪程序
#include//包含头文件,一般情况不需要改动,头文件包含特殊功能寄存器的定义
#include
#defineRS_CLRRS=0
#defineRS_SETRS=1
#defineRW_CLRRW=0
#defineRW_SETRW=1
#defineEN_CLREN=0
#defineEN_SETEN=1
#defineDataPortP0
#defineMEAS0x00//测量模式
#defineRWTR0x08//读写温度数据寄存器
#defineSTX0x0E//x通道自检
#defineSTY0x0F//Y通道自检
#defineRDAX0x10//读X通道加速度值
#defineRDAY0x11//读Y通道加速度值
sbitRS=P2^4;//定义端口
sbitRW=P2^5;
sbitEN=P2^6;
sbitSPK=P2^0;
sbitSCK=P1^7;
sbitMISO=P1^6;
sbitMOSI=P1^5;
sbitCSB=P1^4;
unsignedcharfrq;
sbitP0_0=P0^0;
sbitP0_1=P0^1;
sbitP0_2=P0^2;
sbitP0_3=P0^3;
sbitP0_4=P0^4;
sbitP0_5=P0^5;
sbitP0_6=P0^6;
sbitP0_7=P0^7;
sbitP1_0=P1^0;
sbitP1_1=P1^1;
sbitP1_2=P1^2;
sbitP1_3=P1^3;
sbitP1_4=P1^4;
sbitP1_5=P1^5;
sbitP1_6=P1^6;
sbitP1_7=P1^7;
sbitP2_0=P2^0;
sbitP2_1=P2^1;
sbitP2_2=P2^2;
sbitP2_3=P2^3;
sbitP2_4=P2^4;
sbitP2_5=P2^5;
sbitP2_6=P2^6;
sbitP2_7=P2^7;
sbitP3_0=P3^0;
sbitP3_1=P3^1;
sbitP3_2=P3^2;
sbitP3_3=P3^3;
sbitP3_4=P3^4;
sbitP3_5=P3^5;
sbitP3_6=P3^6;
sbitP3_7=P3^7;
unsignedintSPI_ReadBits(unsignedcharn);
voidSPI_WriteByte(unsignedcharwdata);
voidSPI_Start(void);
voidSPI_Stop(void);
voidSPI_Reset(void);
voidSPI_Delay(unsignedchar);
unsignedintSPI_GetX(void);
unsignedintSPI_GetY(void);
voidSPI_Init(void);
voidSPI_Stop(void)
{
SCK=0;
CSB=1;
SPI_Delay(10);
}
voidSPI_Reset(void)
SPI_Stop();
voidSPI_Delay(unsignedcharn)
while(n--);
voidSPI_Start(void)
CSB=0;
//主机写一个BYTE到器件
//最终状态:
CLK = LOW
voidSPI_WriteByte(unsignedcharwdata)
unsignedchari;
for(i=0;i<8;++i)
MOSI=wdata&0x80;
wdata=wdata<<1;
SCK=1;
//主机读入N个比特
//n限制为16及其以下
//结束状态 CLK = 0
unsignedintSPI_ReadBits(unsignedcharn)
unsignedintrtemp,i;
MISO=1;
for(i=0;i{rtemp<<=1;SPI_Delay(10);if(MISO==1){rtemp|=0x0001;}else{rtemp&=0xFFFE;}SCK=1;SPI_Delay(10);SCK=0;SPI_Delay(10);}returnrtemp;}//读X方向角度unsignedintSPI_GetX(void){unsignedintresult;SPI_Start();SPI_WriteByte(RDAX);result=SPI_ReadBits(11);SPI_Stop();returnresult;}//读Y方向角度unsignedintSPI_GetY(void){unsignedintresult;SPI_Start();SPI_WriteByte(RDAY);result=SPI_ReadBits(11);SPI_Stop();returnresult;}//SPI测量模式voidSPI_Init(void){SPI_Start();SPI_WriteByte(MEAS);SPI_Stop();}unsignedcharcodeC[]={'0','1','2','3','4','5','6','7','8','9'};/*------------------------------------------------uS延时函数,含有输入参数unsignedchart,无返回值unsignedchar是定义无符号字符变量,其值的范围是0~255这里使用晶振12M,精确延时请使用汇编,大致延时长度如下T=tx2+5uS------------------------------------------------*/voidDelayUs2x(unsignedchart){while(--t);}/*------------------------------------------------mS延时函数,含有输入参数unsignedchart,无返回值unsignedchar是定义无符号字符变量,其值的范围是0~255这里使用晶振12M,精确延时请使用汇编------------------------------------------------*/voidDelayMs(unsignedchart){while(t--){//大致延时1mSDelayUs2x(245);DelayUs2x(245);}}/*------------------------------------------------判忙函数------------------------------------------------*/bitLCD_Check_Busy(void){DataPort=0xFF;RS_CLR;RW_SET;EN_CLR;_nop_();EN_SET;return(bit)(DataPort&0x80);}/*------------------------------------------------写入命令函数------------------------------------------------*/voidLCD_Write_Com(unsignedcharcom){while(LCD_Check_Busy());//忙则等待RS_CLR;RW_CLR;EN_SET;DataPort=com;_nop_();EN_CLR;}/*------------------------------------------------写入数据函数------------------------------------------------*/voidLCD_Write_Data(unsignedcharData){while(LCD_Check_Busy());//忙则等待RS_SET;RW_CLR;EN_SET;DataPort=Data;_nop_();EN_CLR;}/*------------------------------------------------清屏函数------------------------------------------------*/voidLCD_Clear(void){LCD_Write_Com(0x01);DelayMs(5);}/*------------------------------------------------写入字符串函数------------------------------------------------*/voidLCD_Write_String(unsignedcharx,unsignedchary,unsignedchar*s){if(y==0){LCD_Write_Com(0x80+x);//表示第一行}else{LCD_Write_Com(0xC0+x);//表示第二行}while(*s){LCD_Write_Data(*s);s++;}}/*------------------------------------------------写入字符函数------------------------------------------------*/voidLCD_Write_Char(unsignedcharx,unsignedchary,unsignedcharData){if(y==0){LCD_Write_Com(0x80+x);}else{LCD_Write_Com(0xC0+x);}LCD_Write_Data(Data);}/*------------------------------------------------角度转化函数------------------------------------------------*/floatangle_transfer(doubleresult){doubleangle,f;f=asin((result-1024)/1638);angle=f*180/3.14;return(angle);}/*------------------------------------------------初始化函数------------------------------------------------*/voidLCD_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);/*显示开及光标设置*/}/*------------------------------------------------LCD显示函数------------------------------------------------*/voidLCD_Display(unsignedinti,doubleangle){intm,n,c,d,e,an;an=(int)(angle*1000);m=an%10;LCD_Write_Char(8,i,C[m]);DelayMs(245);DelayMs(245);an=an/10;n=an%10;LCD_Write_Char(7,i,C[n]);DelayMs(245);DelayMs(245);an=an/10;c=an%10;LCD_Write_Char(6,i,C[c]);DelayMs(245);DelayMs(245);an=an/10;d=an%10;LCD_Write_Char(4,i,C[d]);DelayMs(245);DelayMs(245);e=an/10;LCD_Write_Char(3,i,C[e]);DelayMs(245);DelayMs(245);LCD_Write_Char(5,i,'.');}/*------------------------------------------------定时器初始化子程序------------------------------------------------*/voidInit_Timer0(void){TMOD|=0x01;//使用模式1,16位定时器,使用"|"符号可以在使用多个定时器时不受影响//TH0=0x00;//给定初值//TL0=0x00;EA=1;//总中断打开ET0=1;//定时器中断打开TR0=1;//定时器开关打开}/*------------------------------------------------定时器中断子程序------------------------------------------------*/voidTimer0_isr(void)interrupt1{TH0=0xfe;//重新赋值TL0=frq;//低8位值在主程序中不断累加SPK=!SPK;//端口电平取反}/*------------------------------------------------报警函数------------------------------------------------*/bitWarning(doubleangle,unsignedcharx,unsignedchary){intg;angle=fabs(angle);if(angle>20){g=0;LCD_Write_String(x,y,"DANGER!");while(!P2_0){Init_Timer0();//初始化定时器DelayMs(1);//延时1ms,累加频率值frq++;}}else{LCD_Write_String(x,y,"");EA=0;g=1;}return(g);}/*------------------------------------------------发送函数------------------------------------------------*/voidSend(floata){TMOD=0x20;TL1=0xE6;TH1=0xE6;PCON=0x00;TR1=1;SCON=0x50;/*串口8位异步收发,波特率可变*/if(RI=1){RI=0;SBUF=a;while(TI!=1);TI=0;}}/*------------------------------------------------主函数------------------------------------------------*/voidmain(void){unsignedintresult;doubleangle,a,b;LCD_Init();LCD_Clear();//清屏SPI_Reset();SPI_Delay(1000);SPI_Init();SPI_Delay(1000);while(1){result=SPI_GetX();angle=angle_transfer(result);a=angle;Send(a);P2_0=Warning(angle,9,0);P2_1=Warning(angle,9,0);if(a<0){a=fabs(a);LCD_Write_String(0,0,"X:-");LCD_Display(0,a);}else{LCD_Write_String(0,0,"X:+");LCD_Display(0,a);}result=SPI_GetY();angle=angle_transfer(result);b=angle;Send(b);P2_0=Warning(angle,9,1);P2_2=Warning(angle,9,1);if(b<0){b=fabs(b);LCD_Write_String(0,1,"Y:-");LCD_Display(1,b);}else{LCD_Write_String(0,1,"Y:+");LCD_Display(1,b);}}}
rtemp<<=1;
if(MISO==1){
rtemp|=0x0001;
}else{
rtemp&=0xFFFE;
returnrtemp;
//读X方向角度
unsignedintSPI_GetX(void)
unsignedintresult;
SPI_Start();
SPI_WriteByte(RDAX);
result=SPI_ReadBits(11);
returnresult;
//读Y方向角度
unsignedintSPI_GetY(void)
SPI_WriteByte(RDAY);
//SPI测量模式
voidSPI_Init(void)
SPI_WriteByte(MEAS);
unsignedcharcodeC[]={'0','1','2','3','4','5','6','7','8','9'};
/*------------------------------------------------
uS延时函数,含有输入参数unsignedchart,无返回值
unsignedchar是定义无符号字符变量,其值的范围是
0~255这里使用晶振12M,精确延时请使用汇编,大致延时
长度如下T=tx2+5uS
------------------------------------------------*/
voidDelayUs2x(unsignedchart)
while(--t);
mS延时函数,含有输入参数unsignedchart,无返回值
0~255这里使用晶振12M,精确延时请使用汇编
voidDelayMs(unsignedchart)
while(t--)
//大致延时1mS
DelayUs2x(245);
判忙函数
bitLCD_Check_Busy(void)
DataPort=0xFF;
RS_CLR;
RW_SET;
EN_CLR;
_nop_();
EN_SET;
return(bit)(DataPort&0x80);
写入命令函数
voidLCD_Write_Com(unsignedcharcom)
while(LCD_Check_Busy());//忙则等待
RW_CLR;
DataPort=com;
写入数据函数
voidLCD_Write_Data(unsignedcharData)
RS_SET;
DataPort=Data;
清屏函数
voidLCD_Clear(void)
LCD_Write_Com(0x01);
DelayMs(5);
写入字符串函数
voidLCD_Write_String(unsignedcharx,unsignedchary,unsignedchar*s)
if(y==0)
LCD_Write_Com(0x80+x);//表示第一行
else
LCD_Write_Com(0xC0+x);//表示第二行
while(*s)
LCD_Write_Data(*s);
s++;
写入字符函数
voidLCD_Write_Char(unsignedcharx,unsignedchary,unsignedcharData)
LCD_Write_Com(0x80+x);
LCD_Write_Com(0xC0+x);
LCD_Write_Data(Data);
角度转化函数
floatangle_transfer(doubleresult)
{doubleangle,f;
f=asin((result-1024)/1638);
angle=f*180/3.14;
return(angle);
初始化函数
voidLCD_Init(void)
LCD_Write_Com(0x38);/*显示模式设置*/
LCD_Write_Com(0x38);
LCD_Write_Com(0x08);/*显示关闭*/
LCD_Write_Com(0x01);/*显示清屏*/
LCD_Write_Com(0x06);/*显示光标移动设置*/
LCD_Write_Com(0x0C);/*显示开及光标设置*/
LCD显示函数
voidLCD_Display(unsignedinti,doubleangle)
{intm,n,c,d,e,an;
an=(int)(angle*1000);
m=an%10;
LCD_Write_Char(8,i,C[m]);
DelayMs(245);
an=an/10;
n=an%10;
LCD_Write_Char(7,i,C[n]);
c=an%10;
LCD_Write_Char(6,i,C[c]);
d=an%10;
LCD_Write_Char(4,i,C[d]);
e=an/10;
LCD_Write_Char(3,i,C[e]);
LCD_Write_Char(5,i,'.');
定时器初始化子程序
voidInit_Timer0(void)
TMOD|=0x01;//使用模式1,16位定时器,使用"|"符号可以在使用多个定时器时不受影响
//TH0=0x00;//给定初值
//TL0=0x00;
EA=1;//总中断打开
ET0=1;//定时器中断打开
TR0=1;//定时器开关打开
定时器中断子程序
voidTimer0_isr(void)interrupt1
TH0=0xfe;//重新赋值
TL0=frq;//低8位值在主程序中不断累加
SPK=!
SPK;//端口电平取反
报警函数
bitWarning(doubleangle,unsignedcharx,unsignedchary)
intg;
angle=fabs(angle);
if(angle>20)
{g=0;
LCD_Write_String(x,y,"DANGER!
");
while(!
P2_0)
Init_Timer0();//初始化定时器
DelayMs
(1);//延时1ms,累加频率值
frq++;
LCD_Write_String(x,y,"");
EA=0;
g=1;
return(g);
发送函数
voidSend(floata)
TMOD=0x20;
TL1=0xE6;
TH1=0xE6;
PCON=0x00;
TR1=1;
SCON=0x50;/*串口8位异步收发,波特率可变*/
if(RI=1)
{RI=0;
SBUF=a;
while(TI!
=1);
TI=0;
主函数
voidmain(void)
{unsignedintresult;
doubleangle,a,b;
LCD_Init();
LCD_Clear();//清屏
SPI_Reset();
SPI_Delay(1000);
SPI_Init();
while
(1)
result=SPI_GetX();
angle=angle_transfer(result);
a=angle;
Send(a);
P2_0=Warning(angle,9,0);
P2_1=Warning(angle,9,0);
if(a<0)
{a=fabs(a);
LCD_Write_String(0,0,"X:
-");
LCD_Display(0,a);
{LCD_Write_String(0,0,"X:
+");
result=SPI_GetY();
b=angle;
Send(b);
P2_0=Warning(angle,9,1);
P2_2=Warning(angle,9,1);
if(b<0)
{b=fabs(b);
LCD_Write_String(0,1,"Y:
LCD_Display(1,b);
{LCD_Write_String(0,1,"Y:
copyright@ 2008-2022 冰豆网网站版权所有
经营许可证编号:鄂ICP备2022015515号-1