目录

定时器

晶振

时钟周期

机械周期

每经过一个机械周期经过多长时间

定时器和计数器的区别

定时器相关寄存器

定时10ms,相关寄存器的配置

单片机中断

什么是中断

中断源

中断优先级

中断函数

中断嵌套

中断相关寄存器

PWM信号

超声波(HC-SR04)测距

感应开盖垃圾桶

思路

代码实现

定时器

晶振

晶体震荡器,又称数字电路的“心脏”,是各种电子产品里面必不可少的频率元器件。数字电路的所有工作都离不开时钟,晶振的好坏、晶振电路设计的好坏,会影响到整个系统的稳定性。

时钟周期

时钟周期也称为振荡周期,定义为时钟频率的倒数。时钟周期是计算机中最基本的、最小的时间单 位。在一个时钟周期内,CPU仅完成一个最基本的动作。时钟周期是一个时间的量。更小的时钟周 期就意味着更高的工作频率。

机械周期

机器周期也称为CPU周期。在计算机中,为了便于管理,常把一条指令的执行过程划分为若干个阶 段(如取指、译码、执行等),每一阶段完成一个基本操作。完成一个基本操作所需要的时间称为 机器周期。一般情况下,一个机器周期由若干个时钟周期组成。

每经过一个机械周期经过多长时间

以晶振频率11.0592MHZ为例,时钟周期为晶振的倒数,即1/1105920000秒 

  • 如果是12T模式,机械周期 = 12 X 时钟周期,即12/11059200000秒 = 1.085微秒
  • 如果是6T模式,机械周期 = 6 X 时钟周期,即6/11059200000秒 = 0.5425微秒

定时器和计数器的区别

51单片机中的定时器和计数器使用同一个硬件电路,通过修改寄存器的配置来将该硬件电路变成定时器或者计数器。

  • 当配置成定时器时,每经过一个机械周期,计数存储器的值加1,C51有两个定时器T0和T1。
  • 当配置成计数器时,每来一个负跳变信号(高电平跳到低电平),计数存储器的值加1。

定时器相关寄存器

定时器计时(TH和TL寄存器)

  • 当定时器的TH寄存器和TL寄存器都用起来,即一共有16位,那么该定时器最多数2^16 = 65536下,即大概65536*1.085微秒 = 71毫秒,也就是说定时器T0或者定时器T1最多定时71毫秒。
  • 如现在需要使用定时器0定时10毫秒,怎么配置寄存器TH0和TL0,只需要配置TH0 = 0xDC , TL0 = 0x00。

定时器控制寄存器(TCON寄存器)

以定时器0和外部中断0为例

  • TF标志位:当定时器0爆表后(即定时结束后),TF标志位,TF0会置1(TF0 = 1),此时会向CPU请求中断,如果中断条件允许的话就执行外部中断0,执行完中断后,TF0会硬件置0(TF = 0),当我们不想它执行中断就可以软件置0,即手动将TF0置0(TF =0)。
  • TR标志位:当TR0 =1 时,定时器0才1会允许计数,即开始计时,当TR0 = 0时,不允许定时器0进行计数。
  • IE标志位:当IE0 = 1时,会向CPU请求外部中断0,当CPU响应外部中断0后会将IE0硬件置零(IE0 = 0)。
  • IT标志位:当IT0 = 1时,低电平触发外部中断0;当IT0 = 0时,下降沿触发外部中断0。

定时器模式寄存器(TMOD寄存器)

以定时器0为例

  • GATE标志位:一般为0,GATE = 0时,当TR0 = 0时,定时器0开始计数。
  • C/T标志位:一般为0,C/T为0时,让定时器0作为定时器
  • M1、M0标志位:一般为0、1,16位定时器,TL0和TH0两个寄存器都使用。

通过定时器0,让蜂鸣器叫一秒,不叫一秒,定时器0爆表后,不执行中断 

#include "reg52.h"sbit buzzer = P1^2;void main()
{int cnt = 0;buzzer = 1;TMOD = 0x01; //设置定时器0为16为计时模式//设置定时器0定时时间为10msTH0 = 0xDC;TL0 = 0x00;TR0 = 1; //定时器0开始计时TF0 = 0; //外部中断0标志位置0,不进行定时器0产生的中断while(1){//当定时器0爆表时if(TF0 == 1){ TF0 = 0; //外部中断0标志位置0,不进行定时器0产生的中断cnt++;TH0 = 0xDC;TL0 = 0x00;if(cnt == 100){cnt = 0;buzzer = !buzzer;}}}
}

定时10ms,相关寄存器的配置

AUXR寄存器

单片机中断

什么是中断

  • 当中央处理机CPU正在处理某件事的时候外界发生了紧急事件请求,要求CPU暂停当前的工作,转而去处理这个紧急事件,处理完以后,再回到原来被中断的地方,继续原来的工作,这样的过程称为中断。
  • 实现这种功能的部件称为中断系统。
  • 请示CPU中断的请求源称为中断源。
  • CPU总是先响应优先级别最高的中断请求。

中断源

中断优先级

中断函数

中断嵌套

当CPU正在处理一个中断源请求的时候(执行相应的中断服务程序),发生了另外一个优先级比它还高的中断源请求。如果CPU能够暂停对原来中断源的服务程序,转而去处理优先级更高的中断请求源,处理完以后,再回到原低级中断服务程序,这样的过程称为中断嵌套。

中断相关寄存器

中断允许寄存器(IE寄存器)


辅助中断控制寄存器(XICON寄存器)


中断优先级控制寄存器高(IPH寄存器)

 中断优先级控制寄存器低(IP寄存器)

 对于XICON寄存器、IP寄存器、IPE寄存器可配置的一些功能

  • IPH寄存器的位PX3H和XICON寄存器的位PX3可控制外部中断3的优先级
  • IPH寄存器的位PX2H和XICON寄存器的位PX2可控制外部中断2的优先级
  • IPH寄存器的位PX1H和IP寄存器的位PX1可控制外部中断1的优先级
  • IPH寄存器的位PX0H和IP寄存器的位PX0可控制外部中断0的优先级
  • IPH寄存器的位PSH和IP寄存器的位PS可控制串口1的优先级
  • IPH寄存器的位PTH2和IP寄存器的位PT2可控制定时器2的优先级
  • IPH寄存器的位PTH1和IP寄存器的位PT1可控制定时器1的优先级
  • IPH寄存器的位PTH0和IP寄存器的位PT0可控制定时器0的优先级

通过定时器0和外部中断0,让蜂鸣器叫一秒,不叫一秒,定时器0爆表后,执行外部中断0

#include "reg52.h"
#include <intrins.h>sbit buzzer = P1^2;int cnt = 0;void timer0Init()
{TMOD = 0x01; //设置定时器0为16为计时模式//设置定时器0定时时间为10msTH0 = 0xDC;TL0 = 0x00;TR0 = 1; //定时器0开始计时TF0 = 0; //外部中断0标志位置0,不进行定时器0产生的中断ET0 = 1; //定时器0中断开关EA = 1; //总中断开关
}void Delay300ms()      //@11.0592MHz
{unsigned char i, j, k;_nop_();i = 3;j = 26;k = 223;do{do{while (--k);} while (--j);} while (--i);
}void main()
{buzzer = 1;timer0Init()while(1);
}//定时器0的中断函数
void Time0Handler() interrupt 1
{cnt++;TH0 = 0xDC;TL0 = 0x00;if(cnt == 100){buzzer = !buzzer;cnt = 0;}
}

PWM信号

PWM,英文名Pulse Width Modulation,是脉冲宽度调制缩写,它是通过对一系列脉冲的宽度进行调制,等效出所需要的波形(包含形状以及幅值),对模拟信号电平进行数字编码,也就是说通过调节占空比的变化来调节信号、能量等的变化,占空比就是指在一个周期内,信号处于高电平的
时间占据整个信号周期的百分比,例如方波的占空比就是50%。

  • PWM是脉冲宽度调制。
  • 通过调节占空比来调节信号。
  • 一个周期内,高电平占据的时长的百分比称为占空比。

软件模拟pwm波驱动sg90舵机转动不同角度,驱动sg90舵机时,PWM信号的频率不能太高,大概为50HZ,即0.02s(20ms)左右。

  • 0.5ms--->舵机转动45°,即占空比为2.5%。、
  • 1.0ms--->舵机转动90°,即占空比为5.0%。
  • 1.5ms--->舵机转动135°,即占空比为7.5%。
  • 2.0ms--->舵机转动45°,即占空比为10.0%。
  • 2.5ms--->舵机转动180°,即占空比为12.5%。
#include "reg52.h"
#include <intrins.h>sbit sg90 = P1^2;int angle;
int cnt;void timer0Init()
{TMOD = 0x01; //设置定时器0为16为计时模式//设置定时器0定时时间为0.5msTH0 = 0xFE;TL0 = 0x33;TR0 = 1; //定时器0开始计时TF0 = 0; //外部中断0标志位置0,不进行定时器0产生的中断ET0 = 1; //定时器0中断开关EA = 1; //总中断开关
}void Delay300ms()      //@11.0592MHz
{unsigned char i, j, k;_nop_();i = 3;j = 26;k = 223;do{do{while (--k);} while (--j);} while (--i);
}void Delay1000ms()     //@11.0592MHz
{unsigned char i, j, k;_nop_();i = 8;j = 1;k = 243;do{do{while (--k);} while (--j);} while (--i);
}void main()
{Delay300ms();timer0Init();angle = 1; //设置舵机转动角度45° cnt = 0;sg90 = 1;while(1){angle = 3; //设置舵机转动角度135°cnt = 0;Delay1000ms();angle = 1; //设置舵机转动角度45°cnt = 0;Delay1000ms();}
}//定时器0的中断函数
void Time0Handler() interrupt 1
{TH0 = 0xFE;TL0 = 0x33;//控制占空比if(cnt < angle){sg90 = 1;}else{sg90 = 0;}cnt++;if(cnt == 40){  //每个周期为20mscnt = 0;sg90 = 1;}
}

超声波(HC-SR04)测距

超声波时序图

  • 发送超声波:当Trig引脚接收到一个10微秒以上的高电平后开始发送超声波,当开始发送超声波后,Echo引脚会从低电平跳转到高电平。
  • 接收超声波:当发出去的超声波返回来并被接收后,Echo引脚会从高电平跳转到低电平。
  • 超声波从发出到被接收的时间:Echo持续高电平的时间,当超声波发出去的瞬间启动定时器,超声波被接收的瞬间停止定时器,查看中间经过的时间。
  • 测距:距离 = 声音速度(340m/s)* 时间 / 2,除以2是因为超声波经过了两倍距离。

 超声波测距,距离少过10cm时,蜂鸣器叫,距离超过10cm时,蜂鸣器不叫

#include "reg52.h"
#include <intrins.h>sbit buzzer = P1^4;
sbit Trig = P1^2;
sbit Echo = P1^3;void Delay15us()      //@11.0592MHz
{unsigned char i;i = 4;while (--i);
}void timer1Init()
{   TMOD = 0x10;TH1 = 0x00;TL1 = 0x00;TF1 = 0;
}void ultrasonicStart()
{Trig = 0;Trig = 1;Delay15us();Trig = 0;
}void main()
{double time = 0;double distance = 0;timer1Init();while(1){ultrasonicStart();while(Echo == 0);  //当Echo引脚从低电平跳到高电平时开启定时器1TR1 = 1;while(Echo == 1);  //当Echo引脚从高电平跳到低电平时关闭定时器1TR1 = 0;time = (TH1*256 + TL1) * 1.085;  //微秒/*定时器16位全用时:高八位TH寄存器每加次1,计数存储器的值就加256;低八位TL寄存器每次加1,计数存储器的值就加1;计数存储器的值每次加1时,就经过了一个机械周期(经过时间1.085微秒)*/distance = time * 0.017;  //CMif(distance < 10){buzzer = 0;}else{buzzer = 1;}//定时器1清0TH1 = 0x00;TL1 = 0x00;}}

感应开盖垃圾桶

思路

当检测到有人靠近垃圾桶时,垃圾桶通过sg90舵机开盖,并让蜂鸣器叫一秒,三秒后关盖。当发生垃圾桶震动时, 垃圾桶通过sg90舵机开盖,并让蜂鸣器叫一秒,三秒后关盖。(舵机的软件PWM用定时器0实现,超声波的距离检测用定时器1实现,震动传感器用外部中断1实现)

代码实现

#include "reg52.h"
#include <intrins.h>sbit Trig = P1^5;
sbit Echo = P1^6;
sbit sg90 = P1^1;
sbit vibrate = P3^2;
sbit buzzer = P3^1;int angle;
int angleBack;
int cnt = 0;
int markVibrate = 0;void Delay100ms()      //@11.0592MHz
{unsigned char i, j;i = 180;j = 73;do{while (--j);} while (--i);
}void Delay500ms()      //@11.0592MHz
{unsigned char i, j, k;_nop_();i = 4;j = 129;k = 119;do{do{while (--k);} while (--j);} while (--i);
}void Delay10us()       //@11.0592MHz
{unsigned char i;i = 2;while (--i);
}void interrupt0Init()
{EX0 = 1;  //外部中断0中断开关IT0 = 0;  //外部中断0为低电平触发
}void timer0Init()
{//设置定时器0为16为计时模式TMOD &=0xF0; TMOD |=0x01; //设置定时器0定时时间为0.5msTH0 = 0xFE;TL0 = 0x33;TR0 = 1;  //定时器0开始计时TF0 = 0;  //不执行定时器0爆表时导致的中断ET0 = 1;  //定时器0中断开关EA = 1;  //总中断开关
}void timer1Init()
{   //设置定时器1为16为计时模式TMOD &= 0x0F;TMOD |= 0x10;  TH1 = 0x00;TL1 = 0x00;TF1 = 0;  //定时器1中断开关
}void ultrasonicStart()
{Trig = 0;Trig = 1;Delay10us();Trig = 0;
}double getDistance()
{double time = 0;//定时器1清0TH1 = 0x00;TL1 = 0x00;ultrasonicStart();while(Echo == 0);  //当Echo引脚从低电平跳到高电平时开启定时器1TR1 = 1;while(Echo == 1);  //当Echo引脚从高电平跳到低电平时关闭定时器1TR1 = 0;time = (TH1*256 + TL1) * 1.085;  //微秒return (time * 0.017);
}void sg90Init()
{angle = 1; //设置舵机转动角度45° cnt = 0;sg90 = 1;
}
//开盖
void openLib()
{angle = 4; //设置舵机转动角度135°if(angleBack != angle){  cnt = 0;buzzer = 0;Delay500ms();buzzer = 1;}angleBack = angle;
}
//关盖
void closeLib()
{angle = 1; //设置舵机转动角度45°if(angleBack != angle){cnt = 0;}angleBack = angle;Delay100ms();
}void main()
{double distance = 0;timer0Init();timer1Init();interrupt0Init();sg90Init();while(1){//超声波测距distance = getDistance();if(distance < 10 || markVibrate == 1){openLib();markVibrate = 0;}else{closeLib();}}
}//定时器0的中断函数
void Time0Handler() interrupt 1
{TH0 = 0xFE;TL0 = 0x33;//控制占空比if(cnt < angle){sg90 = 1;}else{sg90 = 0;}cnt++;if(cnt == 40){  //每个周期为20mscnt = 0;sg90 = 1;}
}void Int0_Routine() interrupt 0
{markVibrate = 1;
}

51单片机之感应开盖垃圾桶相关推荐

  1. 基于Wemos的感应开盖垃圾桶

    基于Wemos的感应开盖垃圾桶 一.绪论 1.研究背景 2.研究意义 二.系统总体设计方案 1.设计思路 2.硬件平台功能介绍 3.软件开发环境 三.设计思路实现步骤 1.Wemos的IO口研究驱动蜂 ...

  2. 基于Wemos的智能感应开盖垃圾桶——日记

    参考:基于Wemos的智能感应开盖垃圾桶--日记 作者:9art0 发布时间:2020-09-24 00:40:59 网址:https://blog.csdn.net/GatoWong/article ...

  3. 基于Wemos D1的感应开盖垃圾桶

    参考:基于Wemos D1的感应开盖垃圾桶(增加自己的代码实现部分) 作者:LEO-max 发布时间:2020-12-29 15:21:26 网址:https://blog.csdn.net/zouc ...

  4. 基于Wemos的智能感应开盖垃圾桶

    基于Wemos的智能感应开盖垃圾桶 前言 硬件部分 软件部分 一.舵机控制 二.超声波控制 三.项目整体代码 思考 前言 记录嵌入式学习的第一个小项目吧,基于Wemos的智能感应开盖垃圾桶(上官可编程 ...

  5. 基于 wemos d1 智能感应开盖垃圾桶

    基于WEMOS d1的智能感应开盖垃圾桶 1.需要用的软件: arduino 垃圾桶视频: 智能感应开盖垃圾桶 2.硬件清单 1.Wemos d1 板子 2.超声波模块 3.SG90 舵机 4.垃圾桶 ...

  6. 基于Wemos D1的智能感应开盖垃圾桶

    硬件:这个项目我们主要用到的东西有环保型垃圾桶,Wemos D1模块,舵机,超声波模块,串口助手,若干条杜邦线等等. 环境:arduino 思路:首先这个项目又超声波,wemos d1模块,舵机SG9 ...

  7. 基于51单片机来开发的智能感应开盖垃圾桶

    为什么要引入定时器呢? 因为定时到报表的时候,可以由硬件执行那部分程序,软件部分仍然单独运行. 一.智能垃圾桶需求分析: 当距离小于等于10时,垃圾桶开盖持续两秒钟,否则垃圾桶关闭盖子 当检测到震动时 ...

  8. 初识嵌入式之WeMos D1超声波感应开盖垃圾桶

    目录 硬件平台介绍:WeMos D1 开发环境介绍:ARDUINO开发环境 WeMos的IO口测试:驱动蜂鸣器 蜂鸣器 接线 由于该芯片基于串口连接------安装串口驱动 开发环境配置 选择端口 让 ...

  9. 第四篇 小项目整合-感应开盖垃圾桶v3.0

    目录 一.项目概述 1.功能描述 2.所需硬件 3.接线说明 二.开发步骤 1.SG90和HC-SR04代码整合 2.添加按键控制(433M)和开盖滴滴声(蜂鸣器) 3.添加震动控制(外部中断配合)

最新文章

  1. RelativeLayout布局,不希望文本盖住其他组件
  2. [HNOI2002]营业额统计
  3. 《HTML5 canvas开发详解(第2版)》——1.3 本书使用的基础HTML页面
  4. 【温故知新】CSS学习笔记(盒子水平居中方法)
  5. 整合Swagger2文档api
  6. 使用Redis创建分布式锁
  7. Debug ASP.NET Core 2.0源代码
  8. Android中简单的日期格式化
  9. selenium常用的API
  10. Unity移动端使用 Handheld.PlayFullScreenMovie播放视频参数
  11. C#与.NET程序员面试宝典 1.2.4 简历中的闪光点----突出可转移技能(可能是你忽略的优势)...
  12. TS流基本知识【HI3798 AVPLAY播放TS流】
  13. 计算机论文的主要研究方法有哪些,9大实用的论文研究方法盘点
  14. DP/eDP协议学习--视频传输格式
  15. 重磅!微信二维码引擎OpenCV开源!3行代码让你拥有微信扫码能力
  16. Java 实验8 《抽象类与接口》
  17. Android录制桌面视频screenrecord
  18. 【IT】计算机体系结构
  19. 简易爬虫实现校园网剩余流量查询
  20. mysql 备份 ftp_如何将数据库备份文件备份到FTP上?

热门文章

  1. 嵌入式实践项目(二)——机房温度监控系统
  2. 怎么看java是不是1.8_jdk从1.8换成1.7后,查看版本还是1.8解决方法
  3. 如果让测试员来拍《程序员那么可爱》,剧情会是什么样的?
  4. Windows 7 Boot Updater 如何使用
  5. 查看在线人物 修改金币 元宝 等人物属性
  6. 如何防止你的爬虫被网管一巴掌拍死
  7. 互联网快讯:华为云正式推出区块链服务;猿辅导布局素质教育;轻松筹回应裁员
  8. 剑指 Offer 12. 矩阵中的路径
  9. 加快BITMAP像素访问速度,取代GetPixel
  10. arthes—线上debug好帮手