LED篇第四章渐明渐暗的灯

上传人:文*** 文档编号:63205401 上传时间:2022-03-17 格式:DOC 页数:9 大小:30KB
返回 下载 相关 举报
LED篇第四章渐明渐暗的灯_第1页
第1页 / 共9页
LED篇第四章渐明渐暗的灯_第2页
第2页 / 共9页
LED篇第四章渐明渐暗的灯_第3页
第3页 / 共9页
点击查看更多>>
资源描述
文档供参考,可复制、编制,期待您的好评与关注! LED篇第四章-渐明渐暗的灯 看着学习板上的LED按照我们的意愿开始闪烁起来,你心里是否高兴了,我相信你会的。但是很快你就会感觉到太单调,总是同一个频率在闪烁,总是同一个亮度在闪烁。如果要是能够由暗逐渐变亮,然后再由亮变暗该多漂亮啊。嗯,想法不错,可以该从什么地方入手呢。 在开始我们的工程之前,首先来了解一个概念:PWM。 PWM(Pulse Width Modulation)是脉冲宽度调制的英文单词的缩写。下面这段话是通信百科中对其的定义: 脉冲宽度调制(PWM)是利用微处理器的数字输出来对模拟电路进行控制的一种非常有效的技术,广泛应用在从测量、通信到功率控制与变换的许多领域中。脉宽调制是开关型稳压电源中的术语。这是按稳压的控制方式分类的,除了PWM型,还有PFM型和PWM、PFM混合型。脉宽调制式开关型稳压电路是在控制电路输出频率不变的情况下,通过电压反馈调整其占空比,从而达到稳定输出电压的目的。 读起来有点晦涩难懂。其实简单的说来,PWM技术就是通过调整一个周期固定的方波的占空比,来调节输出电压的平均当电压,电流或者功率等被控量。我们可以用一个水龙头来类比,把1S时间分成50等份,即每一个等份20MS。在这20MS时间里如果我们把水龙头水阀一直打开,那么在这20MS里流过的水肯定是最多的,如果我们把水阀打开15MS,剩下的5MS关闭水阀,那么流出的水相比刚才20MS全开肯定要小的多。同样的道理,我们可以通过控制20MS时间里水阀开启的时间的长短来控制流过的水的多少。那么在1S内平均流出的水流量也就可以被控制了。 当我们调整PWM的占空比时,就会引起电压或者电流的改变,LED的明暗状态就会随之发生相应的变化,听起来好像可以通过这种方法来实现我们想要的渐明渐暗的效果。让我们来试一下吧。 大家都知道人眼有一个临界频率,当LED的闪烁频率达到一定的时候,人眼就分辨不出LED是否在闪烁了。就像我们平常看电视一样,看起来画面是连续的,实质不是这个样子,所有连续动作都是一帧帧静止的画面在1S的时间里快速播放出来,譬如每秒24帧的速度播放,由于人眼的视觉暂留效应,看起来画面就是连续的了。同样的道理,为了让我们的LED在变化的过程中,我们感觉不到其在闪烁,可以将其闪烁的频率定在50Hz以上。同时为了看起来明暗过渡的效果更加明显,我们在这里定义其变化范围为099(100等分).即最亮的时候其灰度等级为99,为0的时候最暗,也就是熄灭了。 于是乎我们定义PWM的占空比上限为99, 下限定义为0 #define LED_PWM_LIMIT_MAX 99 #define LED_PWM_LIMIT_MIN 0 假定我们LED的闪烁频率为50HZ,而亮度变化的范围为099共100等分。则每一等分所占用的时间为 1/(50*100) = 200us 即我们在改变LED的亮灭状态时,应该是在200us整数倍时刻时。在这里我们用单片机的定时器产生200us的中断,同时每20MS调整一次LED的占空比。这样在20MS * 100 = 2S的时间内LED可以从暗逐渐变亮,在下一个2S内可以从亮逐渐变暗,然后不断循环。 由于大部分的内容都可以在中断中完成,因此,我们的大部分代码都在Timer.c这个文件中编写,主函数中除了初始化之外,就是一个空的死循环。 Timer.c内容如下。 #include #include MacroAndConst.h #define LED P0 /定义LED接口 #define LED_ON() LED = 0x00 ; /所有LED亮 #define LED_OFF() LED = 0xff ; /所有LED熄灭 #define LED_PWM_LIMIT_MAX 99 #define LED_PWM_LIMIT_MIN 0 static uint8 s_u8TimeCounter = 0 ; /中断计数 static uint8 s_u8LedDirection = 0 ; /LED方向控制 0 :渐亮 1 :渐灭 static int8 s_s8LedPWMCounter = 0 ; /LED占空比 void Timer0Init(void) TMOD &= 0xf0 ; TMOD |= 0x01 ; /定时器0工作方式1 TH0 = 0xff ; /定时器初始值(200us中断一次) TL0 = 0x47 ; TR0 = 1 ; ET0 = 1 ; void Time0Isr(void) interrupt 1 static int8 s_s8PWMCounter = 0 ; TH0 = 0xff ; /定时器重新赋初值 TL0 = 0x47 ; if(+s_u8TimeCounter = 100) /每20MS调整一下LED的占空比 s_u8TimeCounter = 0 ; /如果是渐亮方向变化,则占空比递增 if(s_s8LedPWMCounter LED_PWM_LIMIT_MAX) s_u8LedDirection = 1 ; s_s8LedPWMCounter = LED_PWM_LIMIT_MAX ; /如果是渐暗方向变化,则占空比递渐 if(s_s8LedPWMCounter = LED_PWM_LIMIT_MIN) &(1 = s_u8LedDirection) s_s8LedPWMCounter- ; if(s_s8LedPWMCounter 0) /占空比大于0,则点亮LED,否则熄灭LED LED_ON() ; s_s8PWMCounter- ; else LED_OFF(); 其实PWM技术在我们实际生活中应用的非常多。比较典型的应用就是控制电机的转速,控制充电电流的大小,等等。而随着技术的发展,也出现了其他类型的PWM技术,如相电压PWM,线电压PWM,SPWM等等,如果有兴趣可以到网上去获取相应资料学习。 关于渐明渐暗的灯就简单的讲到这里。 hjack 发短消息 佩服,自以为小灯玩烂了没想到还有这么玩的。 jack.how 发短消息 PWM用来写单片机的一些简单音乐是十分不错的选择! fishrlog 发短消息 真够细致的 dbdaf 发短消息 请问用51模拟PWM控制调光 ,可以控制到人眼察觉不到光敏三级管可以检测到的亮度嘛? 红金龙吸味 发短消息 回复 12# dbdaf 要根据光敏三极管的实际参数来定。你做啥玩意,点阵屏,光笔? dbdaf 发短消息 回复 13# 红金龙吸味 是的! jiaojy (觉醒)当前离线 看来我的路还有很长很长要走啊。 我们的老师讲的太快了。才四周就讲到中断源了。这周非得让我们用单片机唱歌。哎,他是高兴了,没得讲了,我们可惨了,下课还得肯资料。可是图书馆里的书都是用汇编写的,我们老师教的都是C语言啊。红金龙大哥,支个招吧,看汇编和看C的一样吗? 红金龙吸味 当前离线 发表于 2010-4-15 12:33 | 只看该作者 看C和看汇编肯定不一样啊。C清晰些,复杂运算时候很简单。用汇编则比较复杂。 红金龙吸味 当前离线 MacroAndConst.h 是什么头文件 还有,从void Time0Isr(void) interrupt 1 这里就开始看不明白 记忆碎片 发表于 2010-4-20 22:06 MacroAndConst 从字面意思就可以看出是一些常数和宏的定义。 void Time0Isr(void) interrupt 1 后面的interrupt 1 是单片机的开发环境对标准C关键字进行的扩展,用于表示C51中的中断函数。 其作用就是区分普通函数和中断函数。另外还有一点区别是它无返回值,无参数。 dbdaf (dbdaf)当前离线 发表于 2010-4-21 18:45 | 只看该作者 怎么用PWM调的亮度来扫描呢?试了一下好像时间很难配合! 红金龙吸味 当前离线 回复 20# dbdaf 扫描什么?说具体点。 回复 21# 红金龙吸味 就是在PWM调光的基础上,有规律的让某一些等灭掉! huangji 当前离线 请问static uint8 s_u8TimeCounter = 0 ;可以写成static uint8 s_u8TimeCounter ;吗? 还有uint8是否就是unsigned char 红金龙吸味 当前离线 30楼 发表于 2010-6-26 17:15 | 只看该作者 static uint8 s_u8TimeCounter 记得 初始化为0 就可以了。 uint8 就是unsigned char ,用typedef 定义 LED篇第四章-渐明渐暗的灯 huangji 发短消息 为什么每次进中断时都用static int8 s_s8PWMCounter = 0 ;对s_s8PWMCounter 清零, if(s_s8PWMCounter 0) /占空比大于0,则点亮LED,否则熄灭LED LED_ON() ; s_s8PWMCounter- ; s_s8PWMCounter- ;怎么实现呢, 红金龙吸味 发短消息 static 的用法,请查阅相关语法书籍。 颖均子 发短消息 我也有同样的问题,为什么每次进入中断函数时,都要对占空比计数器清零呢? 小颜 发短消息 if(s_s8PWMCounter 0) /占空比大于0,则点亮LED,否则熄灭LED LED_ON() ; s_s8PWMCounter- ; 这块有点不太理解 为什么是s_s8PWMCounter那 每200us都进一次中断 每次都初始化s_s8PWMCounter为零 是不是应该改成 s_s8LedPWMCounter -啊 jiaohuashangren 发短消息 请问,led等的亮灭时间分布规律是怎样的? 9 / 9
展开阅读全文
相关资源
正为您匹配相似的精品文档
相关搜索

最新文档


当前位置:首页 > 管理文书 > 各类标准


copyright@ 2023-2025  zhuangpeitu.com 装配图网版权所有   联系电话:18123376007

备案号:ICP2024067431-1 川公网安备51140202000466号


本站为文档C2C交易模式,即用户上传的文档直接被用户下载,本站只是中间服务平台,本站所有文档下载所得的收益归上传人(含作者)所有。装配图网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对上载内容本身不做任何修改或编辑。若文档所含内容侵犯了您的版权或隐私,请立即通知装配图网,我们立即给予删除!