锁存器选择Y4,即P2=(P2&0x1f) | 0x80。-toc" style="margin-left:40px;">LED
数码管
按键
ADC输出
DAC输出
DS1302时钟
EEPROM(掉电存储)
DS18B20
PWM
LED
锁存器选择Y4,即P2=(P2&0x1f) | 0x80。
点亮哪个LED就让哪一个LED低电平,8个LED形成16进制数。
数码管
数码管首先选择哪个数码管亮起,锁定器选择Y6,即P2=(P2&0x1f) | 0xc0。
例如:选择第一个数码管,让数码管1置1剩余为0P0=0x01。
锁存器选择显示哪个数字Y7,即P2=(P2&0x1f) | 0xe0。
例如我们的数字管段码会在比赛中给出,除了英文字符。显示1,然后P0=0xf9。
按键
:跳线帽扣到BTN上。可直接sbit 使用定义键号。查看硬件图,给资源包。
例如:sbit s4=P3^3。
:跳线帽扣到KBD上一般来说,矩阵键盘是2×格式考试,我们还是如上,先定义。
然而,这个定义是行列的定义s4,s5,s8,s9为例。
两行定位为:H1=P3^2,H2=P3^3.两列定义为:L1=P4^4,L2=P4^2.按下按钮逐行扫面判断,代码如下,以此类推:
//独立按钮 if(s5==0) { Delay(200); if(s4==0) { //操作 } while(s5==0) { ///通常显示代码 } } //矩阵键盘,例如确定s4按下 H1=0; H2=L1=L2=1; if(L1==0) { Delay(200); if(L1==0) { //需要操作 } while(L1==0) { ///通常显示代码 } }
ADC输出
ADC需要使用输出IIC通信协议从资源包中添加到我们的项目中。
ADC可直接使用输出时序和读取代码。
///读取电位器电压的代码如下 unsigned char Read_Rb() { unsigned char temp; IIC_Start(); IIC_SendByte(0x90); IIC_WaitAck(); IIC_SendByte(0x03);//电位器为0x03,光敏电阻为0x01 IIC_WaitAck(); IIC_Start(); IIC_SendByte(0x91); IIC_WaitAck(); temp=IIC_RecByte(); IIC_SendAck(1); IIC_Stop(); return temp; } ///阅读主函数中使用的代码如下 int v_val; void read_V() { float V; uchar dat; dat=Read_Rb2(); V=dat*5/255.0*100; v_val=V; }
void DA_8591(unsigned char v) { unsigned char u; u=v*51; IIC_Start(); IIC_SendByte(0x90); IIC_WaitAck(); IIC_SendByte(0x43); IIC_WaitAck(); IIC_SendByte(u); IIC_SendAck(1); IIC_Stop(); }
DS1302时钟
DS1302分为写入时间和读取时间,读写地址不同,查询芯片手册。
注:写作时间时,需要打开写作保护,写作时间是关闭写作保护。
unsigned char Time[]={0x18,0x46,0x55}/18:46:55 unsigned char Addr1[]={0x84,0x82,0x80};//写地址,时-分-秒 unsigned char Addr2[]={0x85,0x83,0x81};//阅读地址,时-分-秒 unsigned char time[3]={}; void write_ds1302() { unsigned char i; Write_Ds1302(0x8e,0x00); for(i=0;i<3;i ) { Write_Ds1302(Addr[i],Time[i]); } Write_Ds1302(0x8e,0x80); } void read_ds1302() { unsigned char i; for(i=0;i<3;i ) { time[i]=Read_Ds1302(Addr2[i]); } } 在显示时间时,我们需要/16,将BCD代码转换为二进制数
EEPROM(掉电存储)
eeprom也是运用到IIC总线还有AT24C02芯片,可以查看资源包中的手册,以下是代码
void write_eeprom(unsigned char add,unsigned char dat) { IIC_Start(); IICSendByte(0xa0);
IIC_WaitAck();
IIC_SendByte(add);
IIC_WaitAck();
IIC_SendByte(dat);
IIC_SendAck(1);
IIC_Stop();
}
unsigned char read_eeprom(unsigned char add)
{
unsigned char dat;
IIC_Start();
IIC_SendByte(0xa0);
IIC_WaitAck();
IIC_SendByte(add);
IIC_WaitAck();
IIC_Start();
IIC_SendByte(0xa1);
IIC_WaitAck();
dat=IIC_RecByte();
IIC_SendAck(1);
IIC_Stop();
return dat;
}
DS18B20
使用DS18B20测温芯片,我们需要先将底层驱动文件中的延时都扩大10倍,因为这个文件是 根据传统的8051写的,而我们比赛用的STC15系列的单片机的速度是传统单片机的8~12倍。
void Cov_18B20()
{
init_ds18b20();
Write_DS18B20(0xcc);
Write_DS18B20(0x44);
}
float read_18b20()//此时返回的是整数,若是题目要求显示一位小数则×10,以此类推
{
unsigned char LSB,MSB;
int t;
float T;
init_ds18b20();
Write_DS18B20(0xcc);
Write_DS18B20(0xbe);
LSB=Read_DS18B20();
MSB=Read_DS18B20();
t=(MSB<<8)|LSB;
T=t/16.0;
return T;
}
int temp;
float T;
void Read_T()
{
Cov_18B20();
Delay(5000)//给转换温度反应的时间
T=read_18b20()*10;//此时返回的是整数,若是题目要求显示一位小数则×10,以此类推
temp=T;
}
PWM
PWM脉宽调制,就是用定时器模拟出一个波形。
void Timer0Init(void) //100微秒@12.000MHz
{
AUXR |= 0x80; //定时器时钟1T模式
TMOD &= 0xF0; //设置定时器模式
TL0 = 0x50; //设置定时初值
TH0 = 0xFB; //设置定时初值
TF0 = 0; //清除TF0标志
TR0 = 1; //定时器0开始计时
ET0=1;
EA=1;
}
bit PWM_out=0;
unsigned int PWM_val,PWM_count;
void Timer0() interrupt 1
{
if(++PWM_count<=PWM_val)
{
PWM_out=1;
}
else if(PWM_count>=PWM_val && PWM_count<=100)
{
PWM_out=0;
}
if(PWM_count==100)
{
PWM_count=0;
}
}
下面的是利用这种写法模拟出的波形。
使用的时候,我们直接利用PWM_out的条件来些,例如呼吸灯。PWM_val的值同学们自己定。
void LED()
{
if(PWM_out==1)
{
P2=(P2&0x1f)|0x80;
P0=0xfe;
}
if(PWM_out==0)
{
P2=(P2&0x1f)|0x80;
P0=0xff;
}
}