基于PIC16F877单片机的简易数字电压表设计及proteus仿真

发布者:创意梦者最新更新时间:2020-07-12 来源: 51hei关键字:PIC16F877  单片机  简易数字电压表设计  proteus仿真 手机看文章 扫描二维码
随时随地手机看文章

1.系统功能

1.1可测0~5V的8路输入电压值;

1.2在LED数码管上轮流显示;

1.3单路选择显示;

2.系统硬件设计

2.1 单片机采用PIC16F877

2.2 键盘为4×4行列式键盘,按键设有10个数字键0……9,和5个功能键依次是:各通道轮流显示键、单通道显示键、向左滚动显示键、显示启动/停止键、回车键。

2.3有3位LED管,左边1位用于指示显示通道,右边2位显示电压值,保留到小数点后面1位。

3系统软件设计

3.1键盘管理程序(包括键扫描、键处理程序);

3.2LED动态显示程序;

3.3各通道轮流显示,共显示8个通道,每通道显示1s;

3.4 单通道显示,仅显示指定通道电压,并保持到其他功能键按下。

仿真原理图如下

@82KKR_003[IEK%OUJ${FSA.png

单片机源程序如下:

//作者:云树阿云

#include

#include

#define uchar unsigned char

#define uint unsigned int

__CONFIG(0x3b32);//状态字

uchar table[]={0x00,0x3F,0x06,0x5B,0x4F,0x66,0x6D,0x7D,0x07,0x7F,0x6F,0xbf,0x86,0xdb,0xcf,0xe6,0xed,0xfd,0x87,0xff,0xef};//数码管显示字符表

uchar channel[]={0x41,0x49,0x51,0x59,0x61,0x69,0x71,0x79};//代表8个通道被按下的状态表

uchar key_num;//按键标志位

uchar disp_num;//通道标志位

uchar left_num;

uchar loop_num;

uint volval=0;//电压值

uint enter=0;//回车被按下标志位

uint on_off=0;//开机标志位

uint loop_disp=0;//循环显示标志位

uint single_disp=0;//单通道显示标志位

uint left_move=0;//左移显示标志位

uint a;//用于显示的换算位

uint b;//用于显示的换算位

uint c;//用于显示的换算位

uint d;//用于左移显示的转移中间值

uchar e=2;

uchar onkey_num;




void delay(uint x)//延时程序

{uint times,num;

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

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

}


void display(uint i,uint j)//显示程序

   {

     a=i/10;//通过电压值和通道值算出需要显示的值

     b=i-a*10;//通过电压值和通道值算出需要显示的值

    a=a+10;//为电压第一位加上小数点

      c=j;

      if(enter==0)

      {a=-1;

         b=-1;

         //c=-1;

         }

    TRISD=0x00;//设置输出端口

    TRISB=0x00;//设置输出端口

      delay(1);//延时

         RB0=0;//选择需要亮起的数码管

         RB1=1;

         RB2=1;         

        PORTD=table[c+1];//输出需要显示的数字

       delay(1);//延时

         RB0=1;//选择需要亮起的数码管

         RB1=0;

         RB2=1;   

      PORTD=table[a+1];

         delay(1);//延时

         RB0=1;//选择需要亮起的数码管

         RB1=1;

         RB2=0;         

         PORTD=table[b+1];//输出需要显示的数字

      }


void getab(uint i,uint j)//左移显示时获得当前的a,b,c值

{ a=i/10;

   b=i-a*10;

   a=a+10;

   c=j;

   }  


void leftdisplay()//左移显示模式的显示程序,类似显示程序

   {

    TRISD=0x00;

    TRISB=0x00;

      delay(1);

         RB0=0;

         RB1=1;

         RB2=1;         

        PORTD=table[c+1];

       delay(1);

         RB0=1;

         RB1=0;

         RB2=1;   

      PORTD=table[a+1];

         delay(1);

         RB0=1;

         RB1=1;

         RB2=0;         

         PORTD=table[b+1];

      }      

      

void leftmove()//实现左移显示的程序(交换abc)

      

   {        if(left_num==8)

      {

         left_num=0;

      ADCON0=channel[0];

        uint adval;

        GO=1;

        while(GO)

        adval=ADRESH;

        adval=adval<<8|ADRESL;

        volval=adval/20;        

         a=-1;

        b=volval/10;

        b=b+10;

        c=left_num;

      }

      else{

         //disp_num++;

        ADCON0=channel[left_num];

         

        uint adval;

        GO=1;

        while(GO)

        adval=ADRESH;

        adval=adval<<8|ADRESL;

        volval=adval/20;        

         a=-1;

        b=volval/10;

        b=b+10;

        c=left_num;

     }

      }

void scan()//扫描程序获得key_num

      {        TRISC=0xf0;//C端口高四位输出,低四位输入

         PORTC=0xfe;//首先扫描第一列

         key_num=PORTC;//读取C端口低四位,获得key_num

         key_num=key_num&0xf0;//判断低四位是否有1存在

         if (key_num!=0xf0)//如果低四位有1(第一行有键被按下)

         { delay(10);//去抖动

         key_num=PORTC;//重新读取

         key_num=key_num&0xf0;//得到低四位中为1的位,其他位置0

            if (key_num!=0xf0)

            {

               key_num=key_num|0x0e;//加上高四位中被扫描的值,获得代表被按下键的值:key_num

               }

            }

          else//其他列依次判断

          {

             PORTC=0xfd;

         key_num=PORTC;

         key_num=key_num&0xf0;

         if (key_num!=0xf0)

         { delay(10);

         key_num=PORTC;

         key_num=key_num&0xf0;

            if (key_num!=0xf0)

            {

               key_num=key_num|0x0d;

               }

            }

            else

            {

             PORTC=0xfb;

         key_num=PORTC;

         key_num=key_num&0xf0;

         if (key_num!=0xf0)

         { delay(10);

         key_num=PORTC;

         key_num=key_num&0xf0;

            if (key_num!=0xf0)

            {

               key_num=key_num|0x0b;

               }

            }

            else

            {

             PORTC=0xf7;

         key_num=PORTC;

         key_num=key_num&0xf0;

         if (key_num!=0xf0)

         { delay(10);

         key_num=PORTC;

         key_num=key_num&0xf0;

            if (key_num!=0xf0)

            {

               key_num=key_num|0x07;

               }

            }

               }

               }

             }

         }

void switched()//根据key_num改变相应标志位

         {

            switch(key_num)

               {case 0xee:disp_num=7;enter=0;break;//通道选择

                case 0xed:disp_num=4;enter=0;break;//通道选择

                case 0xeb:disp_num=1;enter=0;break;//通道选择

                case 0xe7:if(onkey_num!=key_num){on_off=!on_off;enter=0;}break;

                           //on_off=1;                          break;//开机

                //case 0xde:disp_num=7;enter=0;break;//通道选择

                case 0xdd:disp_num=5;enter=0;break;//通道选择

                  case 0xdb:disp_num=2;enter=0;break;//通道选择

                case 0xd7:disp_num=0;enter=0;break;//通道选择

                //case 0xbe:disp_num=7;enter=0;break;//通道选择

                case 0xbd:disp_num=6;enter=0;break;//通道选择

                case 0xbb:disp_num=3;enter=0;break;//通道选择

                case 0xb7:enter=1;break;//回车键

                case 0x7e:loop_disp=1;single_disp=0;left_move=0;enter=0;break;//循环显示功能

                case 0x7d:loop_disp=0;single_disp=1;left_move=0;enter=0;break;//单通道显示功能

                case 0x7b:loop_disp=0;single_disp=0;left_move=1;enter=0;break;//左移显示功能

                //case 0x77:on_off=0;break;//关机

               }

            }

void measure()//AD转化程序&完成相应功能

[1] [2]
关键字:PIC16F877  单片机  简易数字电压表设计  proteus仿真 引用地址:基于PIC16F877单片机的简易数字电压表设计及proteus仿真

上一篇:PIC18F452+Proteus双机通信 串口通信 键盘更改波特率源程序
下一篇:PIC16F877A流水灯Proteus仿真程序

推荐阅读最新更新时间:2024-11-09 09:26

sim900a程序,基于51单片机与sim900a相连接程序
  51单片机是对所有兼容Intel 8031指令系统的单片机的统称。该系列单片机的始祖是Intel的8004单片机,后来随着Flash rom技术的发展,8004单片机取得了长足的进展,成为应用最广泛的8位单片机之一,其代表型号是ATMEL公司的AT89系列,它广泛应用于工业测控系统之中。很多公司都有51系列的兼容机型推出,今后很长的一段时间内将占有大量市场。51单片机是基础入门的一个单片机,还是应用最广泛的一种。需要注意的是51系列的单片机一般不具备自编程能力。   SIM900A模块是一款尺寸紧凑的GSM/GPRS模块,采用SMT封装,基于STE的单芯片案,采用ARM926EJ-S架构,性能强大,可以内置客户应用程序。可
[单片机]
C51全局初始化及精确延时程序,51单片机精确延时程序
/********************************************************************************************************* * Initialization Program * QiZhao,2007 * All Rights Reserved * File : initial.h * By : QiZhao * Contact :zq1987731@163.com * * Version : V2.1 γ * Corrector : QiZhao * Date : 2008.2.1 (Last modified) * * Remarks :
[单片机]
华大电子MCU CIU32M010、CIU32M030循环冗余校验计算单元及电源管理
1.循环冗余校验计算单元(CRC) 1.1模块介绍 循环冗余校验(CRC)计算单元是根据自定义的生成多项式得到任意一个 32 位全字的 CRC 计算结果。 在其他的应用中,CRC 技术主要应用于核实数据传输或者数据存储的正确性和完整性。CRC 计算单元可以在程序运行时计算出软件的标识,之后与在连接时生成的参考标识比较,然后存放在指定的存储器空间。 1.2功能特点 • 支持 16/32 位不同长度的多项式 • 支持自定义的多项式 • 默认是 32 位多项式: x 32 + x26 + x23 + x22 + x16 + x12 + x11 + x10 +x8 + x7 + x5 + x4 + x2+ x +1 • 一个 32 位初始
[单片机]
华大电子<font color='red'>MCU</font> CIU32M010、CIU32M030循环冗余校验计算单元及电源管理
key单片机按键抖动
1 //write by:cyt 2 //Time:2017-2-10 3 //Porject Name:key shake_destory 4 #include reg51.h 5 #define GPIO_KEY P0/// 6 void Delay1ms(unsigned char n); 7 unsigned char Key_Scan() // GPIO_KEY为全局变量,在这里作输入 8 { 9 unsigned char i=0,Key_Value=0; 10 if(GPIO_KEY!=0xff) 11 { 12 Delay1ms(10); 13 if(GPIO_KEY
[单片机]
Microchip推出AVR® DU系列USB单片机,支持增强型代码保护和高达15W 的 功率输出
该系列产品有助于嵌入式设计人员在更广泛的系统中轻松实现USB功能 通用串行总线(USB)接口在嵌入式设计中的优势包括与各种设备的兼容性、简化的通信协议、现场更新能力和供电能力。为了帮助将这一功能轻松集成到嵌入式系统中,Microchip Technology Inc.(微芯科技公司)推出了 AVR® DU 系列单片机。 作为集成USB连接的下一代Microchip 8位MCU,AVR DU系列的设计旨在提供比以往版本更强的安全功能和更高的功率输出。 Microchip负责8 位MCU事业部的副总裁Greg Robinson 表示:“USB是电子设备的标准通信协议和电源输出方案。Microchip的AVR
[单片机]
Microchip推出AVR® DU系列USB<font color='red'>单片机</font>,支持增强型代码保护和高达15W 的  功率输出
51单片机学习笔记0 -- 仿真软件安装(Protues8.0)
对于学习51单片机的小伙伴或者新手来说,在手头没有51开发板的情况下,光有一套代码无法去做功能验证,这时候电路仿真软件就派上很大的作用了;不过有个问题就是需要新学习一个新的软件(仿真软件),这里说的仿真软件不是数电模电的仿真软件,而是protues,这一篇来说说protues的安装破解流程,博主用的是protues 8.0,现在最新的版本应该去到8.好多去了 1.解压protues8.0安装包 该教程适用于protues 8.0破解版,在官网下载的还需要买序列号那些好像 解压安装包后可以看到有个setup.exe的执行文件和一个Crack文件夹 2.安装 右键setup.exe以管理员身份运行 开始protues 8安
[单片机]
51<font color='red'>单片机</font>学习笔记0 -- 仿真软件安装(Protues8.0)
【51单片机快速入门指南】4.4.3:Madgwick AHRS 九轴姿态融合获取四元数、欧拉角
STC15F2K60S2 22.1184MHz Keil uVision V5.29.0.0 PK51 Prof.Developers Kit Version:9.60.0.0 上位机:Vofa+ 1.3.10 移植自AHRS —— LOXO,算法作者:SOH Madgwick 传感器的方向 源码 所用MCU为STC15F2K60S2 使用内部RC时钟,22.1184MHz stdint.h见【51单片机快速入门指南】1:基础知识和工程创建 软件I2C程序见【51单片机快速入门指南】4: 软件 I2C 串口部分见【51单片机快速入门指南】3.3:USART 串口通信 MPU60
[单片机]
【51<font color='red'>单片机</font>快速入门指南】4.4.3:Madgwick AHRS 九轴姿态融合获取四元数、欧拉角
什么是GD32 MCU读保护?
如今电子产品市场风云变幻,暗流汹涌,有没有小伙伴遇到自己费了大力气写出来的代码,很容易就被别人“借鉴”了,真的是让闻者伤心,听着落泪啊。 那有没有什么方法可以防止别人将你的代码从MCU读出来呢?答案当然是肯定的,GD32 MCU全系列都有“读保护”功能,我们以GD32F30x系列为例,来看下用户手册中的选项字节的介绍: 我们可以看到,地址0x1fff f800存储的是安全保护值,也就是我们所说的读保护。当该值为0xA5的时候,MCU处于无保护状态,此时可以通过Jlink、GDlink配合一些上位机比如Jflash、GDlink Programmer就可以读出,当然,通过串口ISP也可以读出代码;当读保护值为非0xA5时,
[单片机]
什么是GD32 <font color='red'>MCU</font>读保护?
小广播
设计资源 培训 开发板 精华推荐

最新单片机文章
何立民专栏 单片机及嵌入式宝典

北京航空航天大学教授,20余年来致力于单片机与嵌入式系统推广工作。

换一换 更多 相关热搜器件

 
EEWorld订阅号

 
EEWorld服务号

 
汽车开发圈

电子工程世界版权所有 京B2-20211791 京ICP备10001474号-1 电信业务审批[2006]字第258号函 京公网安备 11010802033920号 Copyright © 2005-2024 EEWORLD.com.cn, Inc. All rights reserved