高级流水灯水滴效果.docx
- 文档编号:6307475
- 上传时间:2023-01-05
- 格式:DOCX
- 页数:14
- 大小:269.12KB
高级流水灯水滴效果.docx
《高级流水灯水滴效果.docx》由会员分享,可在线阅读,更多相关《高级流水灯水滴效果.docx(14页珍藏版)》请在冰豆网上搜索。
高级流水灯水滴效果
简介
学习嵌入式第一个例子通常都是控制一个LED亮灭,然后是花样繁多的流水灯,但不管灯的花样如何变化,单个LED的亮度没有变化,只有亮、灭两个状态,本章我们实现如何控制LED的亮度。
1什么是PWM
脉冲宽度调制(PulseWidthModulation,简称PWM),是利用微处理器的数字输出来对模拟电路进行控制的一种技术。
在本章的应用中可以认为PWM就是一种方波。
比如图1:
(原文件名:
120611_0.png)图1方波
是周期为10ms,占空比为60%的PWM。
占空比:
高电平在一个周期之内所占的时间比率。
2硬件设计
在例说51单片机的第三章,我们讲过如何控制开发板上LED的亮灭。
首先译码器输出端LEDS6为低,T10导通,给8个LED供电,然后通过缓冲器8个输出端BD0~BD7的控制LED的亮灭(低亮高灭)。
(原文件名:
120611_1.png)图2LED硬件连接
如果BD口输出高低不断变化,则LED会闪烁;如果这种高低电平变化非常快,由于人的视觉暂留现象,LED就会出现不同的亮度。
3软件设计
3.1PWM能否控制亮度
下面我们就用实践验证PWM是否能够控制LED的亮度,测试代码如下:
程序清单L1:
验证PWM能否控制LED的亮度
1 #include
2 #include"my_type.h"
3 #include"hw_config.h"
4
5
6 voidmain(void)
7 {
8 u8i=0;
9
10 //使能独立LED的供电,即LEDS6输出低电平
11 LEDEN=0;
12 ADDR0=0;
13 ADDR1=1;
14 ADDR2=1;
15 ADDR3=1;
16
17 //第一个LED亮
18 P0=0xFE;
19
20 while
(1)
21 {
22 for(i=0;i<250;i++)
23 {
24 if(i<10)
25 {
26 P0&=0xFD; //第二个灯亮
27 }
28 else
29 {
30 P0|=0x02; //第二个灯灭
31 }
32 }
33 }
34 }
L1(22-32):
这段代码实现P0.1输出占空比为96%的方波,而P0.0恒为低。
P0.1输出如图3所示(受纸张限制,图中高低电平长度比例和实际有偏差)。
(原文件名:
120611_2.png)图3
下载验证:
从开发板上可以看到运行效果,D1比D2亮。
(这里说明一点:
当P0输出低电平时,LED亮,所以,PWM的占空比越小越亮)。
3.2产生8个亮度级别
3.1节的例子证实了我们的设想,PWM可控制LED的亮度,下面我们设计几组占空比不同的PWM,看看对LED亮度的控制效果。
代码如下:
程序清单L2:
不同占空比对LED亮度的控制
1 #include
2 #include"hw_config.h"
3 #include"my_type.h"
4
5
6 //亮度级别表
7 codeu8LightLevel[8]={0,1,2,4,8,16,32,64};
8
9 voidmain(void)
10 {
11 u8i=0;
12 u8j=0;
13 u8k=0;
14 u8temp=0;
15
16 //使能独立LED的供电,即LEDS6输出低电平
17 LEDEN=0;
18 ADDR0=0;
19 ADDR1=1;
20 ADDR2=1;
21 ADDR3=1;
22
23 //开始全灭
24 P0=0xFF;
25
26 while
(1)
27 {
28 //P0端口输出8组占空比不同的PWM
29 for(i=0;i<64;i++)
30 {
31 for(j=0;j<8;j++)
32 {
33 if(LightLevel[j]<=i)
34 {
35 temp|=(1< 36 } 37 else 38 { 39 temp&=~(1< 40 } 41 } 42 43 P0=temp; 44 } 45 } 46 } L2(29-45).此段程序是让P0口输出8组占空比不同的PWM,如图4: (原文件名: 120611_3.png)图4 下载验证: 从开发板上可以看到运行效果,从D1到D8的亮度逐渐增大。 3.3水滴下落效果 根据PWM可控制LED亮度的原理,我们用8个LED实现水滴下落的效果。 第一步,水滴逐渐变大,用D1从暗变亮模拟;第二步,水滴下落,带有拖尾效果,LED逐个亮,移动速度加快,且越靠前的LED亮度越大。 程序清单L3水滴流水灯 1 #include 2 #include"hw_config.h" 3 #include"my_type.h" 4 5 //亮度级别表 6 codeu8LightLevel[8]={0,1,2,4,8,16,32,64}; 7 8 //水滴时间,实现加速效果 9 codeu8LightTime[16]={16,15,14,13,12,11,10,9,8,7,6,5,4,3,2,1}; 10 11 12 voidmain(void) 13 { 14 u8i,j,k; 15 u8temp,count; 16 u8state; 17 18 //使能独立LED的供电,即LEDS6输出低电平 19 LEDEN=0; 20 ADDR0=0; 21 ADDR1=1; 22 ADDR2=1; 23 ADDR3=1; 24 25 while (1) 26 { 27 //开始全灭 28 P0=0xFF; 29 30 //---------------水滴逐渐变大(第一个LED亮度逐渐变大)--------- 31 for(i=0;i<64;i++) 32 { 33 //一个亮度级别发送64个脉冲 34 for(j=0;j<64;j++) 35 { 36 P0=0xFE; 37 //以i为亮度级别,随着i的增大,占空比增大 38 for(k=0;k<64;k++) 39 { 40 if(k>i) 41 { 42 P0=0xFF; 43 } 44 } 45 } 46 } 47 48 //----------------------水滴降落过程--------------------- 49 for(state=0;state<16;state++) 50 { 51 //每一状态维持LightTime[state]个脉冲 52 for(count=0;count<=LightTime[state];count++) 53 { 54 //temp记录8个LED的状态,0代表亮,1代表灭 55 temp=0x00; 56 57 //一个脉冲长度j从0到63 58 for(j=0;j<64;j++) 59 { 60 //根据亮度表,依次确定8个LED当前状态,亮或灭 61 for(k=0;k<8;k++) 62 { 63 //以j为亮度级别,每个LED亮度不一样 64 if(LightLevel[k]==j) 65 { 66 temp|=(1< 67 } 68 } 69 70 if(state<=7) 71 { 72 P0=~((~temp)>>(7-state)); 73 } 74 else 75 { 76 P0=~((~temp)<<(state-7)); 77 } 78 } 79 } 80 } 81 } 82 } L2(31-46).实现水滴变大效果,这段代码的作用可用图形表达,如图5: (原文件名: 120611_4.png)图5 控制D1由暗变亮,用了64个亮度级别,每个级别发送64个脉冲。 L2(49-81).实现水滴下落。 代码就不逐行解释了,大家可根据注释自己分析,主要说一下实现的方法。 定义LED有8个亮度级别,若用开发板上的8个LED表示,如图6: (原文件名: 120611_5.png)图6 图中的红色面积代表亮度程度。 实现流水效果的方法就是: 让所有的亮度依次经过在所有LED,如图7: (原文件名: 120611_6.png)图7 状态的持续时间从0-15逐渐减小,以模拟水滴加速。 下载验证: 下载到开发板上,可以看到水滴下落效果。 3.4定时器产生PWM 前面3个例子中,我们用循环语句虽然能产生占空比不同的PWM,但PWM的周期不好控制,对此,我们学习如何用定时器产生特定周期PWM。 关于8051定时器的使用方法,大家可以参考例说51单片机的4章和5章。 我们用定时器0产生PWM,代码如下: 程序清单L4定时器0产生PWM 1 #include 2 #include"hw_config.h" 3 #include"my_type.h" 4 5 6 //亮度级别表 7 codeu8LightLevel[8]={1,2,4,8,16,28,50,64}; 8 9 //函数声明 10 voidtimer0_init(void); 11 12 voidmain(void) 13 { 14 //使能独立LED的供电,即LEDS6输出低电平 15 LEDEN=0; 16 ADDR0=0; 17 ADDR1=1; 18 ADDR2=1; 19 ADDR3=1; 20 21 timer0_init(); 22 23 while (1) 24 { 25 } 26 } 27 28 /********************************************************** 29 函数名称: timer0_init 30 功 能: 初始化定时器0 31 **********************************************************/ 32 voidtimer0_init(void) 33 { 34 TMOD=0x01; //运行模式1 35 TH0 =0xFF; //10us中断 36 TL0 =0xFA; 37 EA =1; //开启中断 38 ET0 =1; 39 TR0 =1; //启动定时器 40 41 } 42 43 /************************************************************ 44 函数名称: timer0_overflow 45 功 能: 定时器0溢出中断 46 ************************************************************/ 47 voidtimer0_overflow(void)interruptTIMER0_OVERFLOW 48 { 49 u8i,temp=0; 50 staticu8count=0; 51 52 count++; 53 count%=64; 54 55 for(i=0;i<8;i++) 56 { 57 if(LightLevel<=count) 58 { 59 temp|=(1< 60 } 61 else 62 { 63 temp&=~(1< 64 } 65 } 66 67 P0=temp; 68 69 TR0=0; 70 TH0=0xFF; //重新赋值 71 TL0=0xF7; 72
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- 高级 流水 水滴 效果