
A31基于51单片机汇编语言数字电压表Proteus设计
用51单片机汇编语言配合ADC0809做一个三位数字电压表:电位器分压接到IN0,程序给START一个脉冲启动转换、查询EOC等转换结束、拉高OE读回8位结果,再拆成三位十进制数在数码管上动态扫描显示。定时器0工作在方式2,专门负责给ADC0809提供时钟——这一步是这个设计里最容易被漏掉、也最容易卡住的地方。
一、设计实现功能
本设计功能简介:使用51单片机和汇编语言设计一个简易数字电压表(ADC采集)的proteus仿真,要求以下功能:
1、使用汇编语言编写程序。
2、ADC0809采集IN0通道的模拟电压,8位转换结果送单片机P1口。
3、三位共阴数码管动态扫描,显示000~255的AD码值。
4、定时器0方式2溢出翻转P2.4,为ADC0809提供工作时钟。
二、资源汇总
1、仿真文件:Proteus工程,7.8和8.6两个版本都能直接打开。
2、程序文件:main.asm汇编源码,以及编译好的cx.hex。
3、修改日期小工具:购买资料后赠送,用于修改文件创建日期,下载地址在文章最后。
三、设计介绍
拿到压缩包之后先解压,没有解压软件的直接搜"压缩",下载解压软件后先解压文件,再运行仿真和程序。
图1 Proteus仿真总览

接线按下面这张表对,错一根线现象就完全不一样:
| 信号 | 单片机引脚 | ADC0809引脚 | 说明 |
| 数据 | P1.0~P1.7 | OUT1~OUT8 | 8位转换结果 |
| 时钟 | P2.4 | CLOCK | T0中断翻转产生 |
| 启动 | P2.5 | START、ALE | 两脚并联,一个脉冲启动 |
| 结束 | P2.6 | EOC | 转换中为低,结束变高 |
| 输出使能 | P2.7 | OE | 高电平才允许读数据 |
| 通道选择 | — | ADD A/B/C | 全接地,固定IN0 |
时钟不用外部器件,靠定时器0方式2自动重装来凑。方式2下TL0溢出后自动从TH0重新装载,不需要在中断里重装初值:
| 参数 | 值 | 说明 |
| 工作方式 | TMOD=02H | 方式2,8位自动重装 |
| 重装值 | TH0=TL0=245(0F5H) | 每次溢出计 256-245=11 个机器周期 |
| 溢出周期 | 11微秒 | 12MHz晶振,机器周期1微秒 |
| 时钟频率 | 约45.5kHz | 中断里CPL一次,周期是2×11微秒 |
ADC0809要求时钟在10kHz~640kHz之间,45.5kHz完全够用。代价是转换变慢:一次转换大约1.4毫秒,程序里那句JNB EOC,$就是在原地干等这段时间。
主循环只有四步:启动、等待、读出、显示。
`asm
WAIT: CLR ST ;先拉低
SETB ST ;给出启动脉冲
CLR ST
JNB EOC,$ ;等EOC变高,转换结束
SETB OE ;打开输出
MOV ADC,P1 ;读回8位结果
CLR OE ;读完立刻关掉,释放P1
MOV A,ADC
MOV B,#100 ;拆百位
DIV AB
MOV LED_2,A
MOV A,B
MOV B,#10 ;拆十位和个位
DIV AB
MOV LED_1,A
MOV LED_0,B
LCALL DISP
SJMP WAIT`
拆数用的是两条DIV AB:先除100得百位,余数再除10得十位和个位,比连续减法省事。3位数码管接在P2.1、P2.2、P2.3(低电平选中),段码走P0,每位数码管点亮5毫秒,一轮15毫秒,刷新率约66Hz,肉眼看不出闪。
读数与实际电压的换算关系是:参考电压5V、8位分辨率时,1个码值≈19.5毫伏。所以显示的015代表0.29V左右,看代码里没有乘法标定,显示的是裸AD值。想让它直接读伏特,把MOV B,#100那段改成先乘196再除100(196≈500/255×100),就能显示0.00~5.00。
特别注意: 数码管全黑而ADC有读数,先查P2.1~P2.3位选有没有接反(低电平才亮);读数一直是000或255不动,八成是CLOCK没接或者T0没启动,EOC永远不置位程序就卡在JNB EOC,$;读数乱跳,检查P1有没有被其它器件占用,读完必须CLR OE;P0口一定要上拉(图里那两个排阻R1、R2),8051的P0是开漏,不加上拉数码管会暗得看不清;电位器要接在VREF+和地之间分压,中间抽头进IN0,直接接5V会一直显示255。
四、日期修改
资料中提供修改日期的小工具,购买资料赠送修改文件创建日期的小工具,三个下载地址都在文章最后。
五、资料下载
付费后获取下载链接,直接下载到电脑上,然后解压即可!每个链接前面都配了二维码,手机扫码可以直接跳转。
/

