×
嵌入式 > 技术百科 > 详情

【蓝桥杯单片机组】(2)锁存器、数码管、蜂鸣器、继电器

发布时间:2021-12-22 发布时间:
|

1、C51数据类型扩充

sfr 声明8位寄存器

sfr16 声明16为寄存器

sbit 声明寄存器中某一位,某IO口

bit 位变量声明


用sbit声明某一个端口


sbit LED = P1^0;


2、74HC573(锁存器)


WR端通过J13一直接地

Y4~Y7端通过138译码器接P25~P27

控制部分代码:


P2 |= 0xe0; //选为Y7,使Y7=0

P0 = 0xc0; //传输到锁存器的数据

P2 &= 0X1F; //锁存,数据为第一行的取反


3、数码管


数码管采用共阳级(3.1更正)


数据:char code num[] = {0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90};


com1~com7为位选,置高为选通:

控制流程:


P2 |= 0Xc0; //Y6C = 1

P0 = 0X01; //钻中第一位数码管com1

P2 &= 0X3F; //Y6C = 0; LOCK

P0 = 0xff; //消隐

//当 P2 |= ...不起作用时,可能是P2之前的数据不对,导致无法用或操作修改为正确的数据;换成=即可

P2 |= 0XF0; //Y7C = 1;

P0 = num[3]; //数字数据

P2 &= 0X0F; //Y7C = 0; LOCK

delay();

//TODO:设置其他位


附:display.c


#include "display.h"

unsigned char num[] = {0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90};

void delayms(int x)

{

int i,j;

for(i=x;i>0;i--)

{

for(j=110;j>0;j--);

}

}

void display1(unsigned int displaynum) // 在第一组数码管上显示一个int数据

{

unsigned char bit1,bit2,bit3,bit4;

if(displaynum >= 10000)

{

bit1 = 9;

bit2 = 9;

bit3 = 9;

bit4 = 9;

}

else if(displaynum >= 1000)

{

bit1 = displaynum/1000;

bit2 = (displaynum%1000)/100;

bit3 = (displaynum%100)/10;

bit4 = (displaynum%10);

}

else if(displaynum >= 100)

{

bit1 = 0;

bit2 = displaynum/100;

bit3 = (displaynum%100)/10;

bit4 = (displaynum%10);

}

else if(displaynum >= 10)

{

bit1 = 0;

bit2 = 0;

bit3 = displaynum/10;

bit4 = displaynum%10;

}

if(displaynum < 10)

{

bit1 = 0;

bit2 = 0;

bit3 = 0;

bit4 = displaynum;

}

P2 = 0xc0;

P0 = 0x01; //bit1

P2 &= 0x3f;

P0 = 0xff;

P2 = 0xe0;

P0 = num[bit1];

P2 &= 0x1f;

delayms(5);

P2 = 0xc0;

P0 = 0x02; //bit2

P2 &= 0x3f;

P0 = 0xff;

P2 = 0xe0;

P0 = num[bit2];

P2 &= 0x1f;

delayms(5);

P2 = 0xc0;

P0 = 0x04; //bit3

P2 &= 0x3f;

P0 = 0xff;

P2 = 0xe0;

P0 = num[bit3];

P2 &= 0x1f;

delayms(5);

P2 = 0xc0;

P0 = 0x08; //bit4

P2 &= 0x3f;

P0 = 0xff;

P2 = 0xe0;

P0 = num[bit4];

P2 &= 0x1f;

delayms(5);

}

void display2(unsigned int displaynum) // 在第一组数码管上显示一个int数据

{

unsigned char bit1,bit2,bit3,bit4;

if(displaynum >= 10000)

{

bit1 = 9;

bit2 = 9;

bit3 = 9;

bit4 = 9;

}

else if(displaynum >= 1000)

{

bit1 = displaynum/1000;

bit2 = (displaynum%1000)/100;

bit3 = (displaynum%100)/10;

bit4 = (displaynum%10);

}

else if(displaynum >= 100)

{

bit1 = 0;

bit2 = displaynum/100;

bit3 = (displaynum%100)/10;

bit4 = (displaynum%10);

}

else if(displaynum >= 10)

{

bit1 = 0;

bit2 = 0;

bit3 = displaynum/10;

bit4 = displaynum%10;

}

if(displaynum < 10)

{

bit1 = 0;

bit2 = 0;

bit3 = 0;

bit4 = displaynum;

}

P2 = 0xc0;

P0 = 0x10; //bit1

P2 &= 0x3f;

P0 = 0xff;

P2 = 0xe0;

P0 = num[bit1];

P2 &= 0x1f;

delayms(5);

P2 = 0xc0;

P0 = 0x20; //bit2

P2 &= 0x3f;

P0 = 0xff;

P2 = 0xe0;

P0 = num[bit2];

P2 &= 0x1f;

delayms(5);

P2 = 0xc0;

P0 = 0x40; //bit3

P2 &= 0x3f;

P0 = 0xff;

P2 = 0xe0;

P0 = num[bit3];

P2 &= 0x1f;

delayms(5);

P2 = 0xc0;

P0 = 0x80; //bit4

P2 &= 0x3f;

P0 = 0xff;

P2 = 0xe0;

P0 = num[bit4];

P2 &= 0x1f;

delayms(5);

}

void display_reg(int x) //在数码管上显示两个8位寄存器的值,方便调试

{

int a,b;

if(x == 0)

{

a = TH0;

b = TL0;

display1(a);

display2(b);

}

if(x == 1)

{

a = TH1;

b = TL1;

display1(a);

display2(b);

}

}


P.S:之前在使用display(thenum)做频率计的时候出现显示乱码的问题

问题出在:用在索引字形码的bitx变量使用了int数据类型,int类型在实际使用时,未被使用的高位用1填充了,如:


int a;

char tl1;

tl1 = TL1; //设TL1 = 0x0d;

a = th1; //此时在仿真观察窗口内a = 0xff0d;

此时使用num[a]无法索引数据,导致乱码。


4、ULN2003(反相器)


5、继电器/蜂鸣器

蜂鸣器采用有源蜂鸣器


P2 = 0 ; //Y5C

buzz = 0; //close;open=1

P2 &= 0x5f;

P2 = 0 ; //Y5C

relay = 0; //close;open=1

P2 &= 0x5f;


『本文转载自网络,版权归原作者所有,如有侵权请联系删除』

热门文章 更多
分拣机器人的工作原理是什么