AVR单片机教程——数字输出
本文隶属于AVR单片机教程系列。
从上一篇教程中我们了解到,按键与开关的输入本质上就是数字信号的读取。这一篇教程要讲的是,控制LED的原理是数字信号的输出。数字IO是单片机编程之有别于桌面编程的各项内容中最简单、最基础的。
在讲数字信号输出之前,我们先来了解一下它控制的器件。LED,是一种二极管,在理想模型中,加以正向电压会发光,反向电压则不会。在稍微实际一点的模型中,当正向电压超过一定阈值时,二极管会发光,其电流会随着正向电压的增大而急剧增大;对反向电压的耐受力也是有限的。现实中的LED的具体参数因生产厂家而异,一般红色与黄色LED的导通压降为2V多,绿、蓝、白色的为3V左右或多一点;反向耐压一般为5V。
电流大到一定程度,任何器件都会烧毁,我们最好要把LED的电压控制在比导通压降高一点,但直接获得这样的电压比较困难,而且与LED的参数和温度等都是相关的。一种方案是用电流源来驱动LED,但由于现代计算机,包括单片机,都以电压方式来工作,在控制亮暗这种简单应用中一般不会使用(大功率LED一般有专用的恒流电源来驱动)。常见的方案是将LED与一个电阻串联。这个电阻能保证LED的电流不太大,因此称为限流电阻。至于这种接法下电流是多少,可以通过“负载线”来求得。本系列教程不会专门讲电路,你可以自己搜索相关知识,早晚会用到的。
早期的单片机设计中,一般把LED和电阻接在引脚和正电源之间,这是因为TTL的拉电流能力强而灌电流能力很弱,只能这样接。CMOS工艺的单片机不必在意这一点,由于我们习惯让1代表有而0代表无,因此一般将LED与电阻接在引脚与地之间。电阻接在LED的正极还是负极是无所谓的。
以上都是对单个LED而言的。对于一些多色LED,比如RGB的,各个单色光源的一极是接在一起的,以节省引脚。当正极接在一起时,称为共阳接法:
为了亮度均匀,需要为每个LED接一个限流电阻(阻值一般不同),这时电阻就必须接在LED负极上了,然后再连接单片机引脚,而LED的另一端则连接正电源。引脚输出低电平会让对应颜色亮起。
当负极接在一起时,称为共阴接法:
LED的两极称为正极负极,接法称为共阳和共阴,都是习惯而已,不必纠结其中的不一致性。
我们的开发板上有一颗RGBW的LED,4种颜色的LED都有独立的正负极,但我把它们的负极都接到了地,可以理解为共阴接法。LED右边的4个针脚分别连接电阻,然后再连接LED的正极。因此,连接单片机引脚和LED的针脚后,使引脚输出高电平能让LED亮,反之则不亮。
将引脚4~7分别连接到RGBW上,我们来实现一个略微复杂(相比之前)的效果:红,红+绿,绿,绿+蓝,蓝,蓝+红;然后重复,只是加上白色;循环。
- #include <ee1/pin.h>
- #include <ee1/delay.h>
- #define RED PIN_4
- #define GREEN PIN_5
- #define BLUE PIN_6
- #define WHITE PIN_7
- void rgb_cycle()
- {
- for (uint8_t i = ; i != ; ++i)
- {
- pin_write(RED , i == || i == || i == );
- pin_write(GREEN, i == || i == || i == );
- pin_write(BLUE , i == || i == || i == );
- delay();
- }
- }
- int main()
- {
- uint8_t pins[] = {RED, GREEN, BLUE, WHITE};
- for (uint8_t i = ; i != sizeof(pins) / sizeof(pins[]); ++i)
- pin_mode(pins[i], OUTPUT);
- while ()
- {
- pin_write(WHITE, false);
- rgb_cycle();
- pin_write(WHITE, true);
- rgb_cycle();
- }
- }
这段代码虽然略长,但还是比较容易理解的:rgb_cycle 即为6种状态的枚举,包含了延时;main 函数中,先初始化,然后进入主循环;每一遍循环中先控制白色灯,然后调用 rgb_cycle ,对于白色灯的两种状态调用两次;整体效果的循环周期为12次改变。
另外,你也许已经发现,对于数字输入的引脚,即使没有调用 pin_mode 来配置模式,也能正常检测输入。这是因为输入是单片机复位后默认的设置。那么,对于输出来说,就必须调用 pin_mode 将引脚配置为输出模式。如果没有将引脚配置为输出而写高电平会怎样?自己试试吧。原因我们以后分析。
由于今天的教程非常简单,就没有作业了。复习一下之前的内容,下一篇教程会比较难。
AVR单片机教程——数字输出的更多相关文章
- AVR单片机教程——数码管
先解答之前一个思考题:如果不把引脚配置为输出而写高电平,连接LED会怎样? 实验结果是,LED会亮,但相比于输出高电平的情况,亮度很低.这是为什么呢? 通过上一篇教程我们知道,引脚输入输出模式是由寄存 ...
- AVR单片机教程——旋转编码器
好久没写这个系列了.今天讲讲旋转编码器. 旋转编码器好像不是单片机玩家很常用的器件,但是我们的开发板上有,原因如下: 旋转编码器挺好用的.电位器能旋转的角度有限,旋转编码器可以无限圈旋转:旋转时不连续 ...
- AVR单片机教程——数字输入
我们已经学习了如何使用按键和拨动开关,不知你有没有好奇 button_down 和 switch_status 等函数是如何实现的.本篇教程带你一探究竟,让我们从按键的原理开始. 在原理图中,按键的符 ...
- AVR单片机教程——拨动开关
在按键的上方有4个拨动开关.开关与按键,在原理和使用方法上都是很类似的,但有不同的用途——按键按下后松开就会弹起,而开关可以保存其状态. <switch.h> 定义了与开关相关的函数.sw ...
- AVR单片机教程——按键动作
上一篇教程中我们学习了如何读取按键状态.而按键的动作,比如单击,至少需要两个状态才能判定,长按.双击的判定更加复杂.今天我们来学习如何使用库函数判断按键单击,以及其实现原理. 我们要实现的是:当一个按 ...
- AVR单片机教程——按键状态
好久没更新了,今天开始继续,争取日更. 今天我们来讲按键.开发板的右下角有4个按键,按下会有明显的“咔嗒”声.如何检测按键是否被按下呢?首先要把按键或直接或间接地连接到单片机上.与之前使用的4个LED ...
- AVR单片机教程——随机点亮LED
之前我们做的闪烁LED和流水灯,灯效都是循环的.这次我们来尝试一些不一样的——每一次随机选择一个LED并点亮. 要实现随机的效果,我们要用C语言标准库中的相关设施: #define RAND_MAX ...
- AVR单片机教程——流水灯
上次我们用 delay 函数与 while 循环实现了一个LED的闪烁.这一次我们把所有LED加入进来,让它们依次闪烁,形成流水灯的效果. 开发板上有4个LED,我们可以用不多的语句把循环体直接描述出 ...
- AVR单片机教程——闪烁LED
上次我们把LED点亮了.你可能已经试过把 LED_RED 换成其他灯,也可能已经用 led_on() 把所有LED一起点亮了.但是LED点亮以后,程序就退出了,之后LED一直没有暗,直到没有供电.这一 ...
随机推荐
- am335x system upgrade kernel ethernet(四)
1 Scope of Document This document describes ethernet hardware design and porting KZS8081 to ubo ...
- CLR 调试概述
利用公共语言运行时 (CLR) 调试 API,工具供应商可以编写调试器来调试运行于 CLR 环境中的应用程序. 要调试的代码可为 CLR 支持的任何代码种类.CLR 调试 API 主要是使用非托管代码 ...
- 18-ESP8266 SDK开发基础入门篇--TCP 服务器 RTOS版,串口透传,TCP客户端控制LED
https://www.cnblogs.com/yangfengwu/p/11112015.html 先规定一下协议 aa 55 02 01 F1 4C 控制LED点亮 F1 4C为CRC高位和低位 ...
- GoCN每日新闻(2019-10-15)
GoCN每日新闻(2019-10-15) GoCN每日新闻(2019-10-15) 1. Go Module 存在的意义与解决的问题 https://www.ardanlabs.com/blog/20 ...
- webpack系列之安装(Mac OS)
1. webpack介绍,可参考Webpack中文文档 2. 安装webpack之前先需要安装npm,可参看NPM的使用介绍 3. 安装webpack,可参考Webpack入门教程 ========= ...
- [后渗透]Metasploit使用基础
0x00 简介 Metasploit是一个免费的.可下载的框架,通过它可以很容易地获取.开发并对计算机软件漏洞实施攻击.它本身附带数百个已知软件漏洞的专业级漏洞攻击工具.当H.D. Moore在200 ...
- docker nginx安装
安装nginx镜像docker search nginxdocker pull nginx 启动Nginx容器docker run -it -d --name n1 -v/home/n1/nginx. ...
- vue---发送数据请求的一些列的问题
使用vue做数据请求,首先考虑的是封装请求方法request.js import axios from 'axios' import Qs from 'qs' // 创建一个axios实例 const ...
- Spark资源调度及任务调度
1. 资源分配 通过SparkSubmit进行提交应用后,首先会创建Client将应用程序(字节码文件.class)包装成Driver,并将其注册到Master.Master收到Client的注册请 ...
- ABS函数 去掉金额字段值为负数问题
)) from OrderDetail