使用单片机编程实现蜂鸣器模块的1000HZ鸣响,定时器控制特定频率和持续时间

蜂鸣器模块化编程 1000HZ 鸣响 ms 毫秒


//Buzzer.h
#ifndef __BUZZER_H__
#define __BUZZER_H__

void Buzzer_Time(unsigned int ms);

#endif

Buzzer.h文件中只含有一个Buzzer_Time函数,这个函数用来让蜂鸣器以1000HZ固定频率发声ms毫秒。


//Buzzer.c
#include <REGX52.H>
#include <INTRINS.H>

//蜂鸣器端口:
sbit Buzzer=P1^5;

/**
  * @brief  蜂鸣器私有延时函数,延时500us
  * @param  无
  * @retval 无
  */
void Buzzer_Delay500us()                //@12.000MHz
{
        unsigned char i;

        _nop_();
        i = 247;
        while (--i);
}

/**
  * @brief  蜂鸣器发声
  * @param  ms 发声的时长,范围:0~32767
  * @retval 无
  */
void Buzzer_Time(unsigned int ms)
{
        unsigned int i;
        for(i=0;i<ms*2;i++)
        {
                Buzzer=!Buzzer;
                Buzzer_Delay500us();
        }
}

蜂鸣器中BEEP接口接入进电机中12号引脚,P15控制12号引脚,也就是P15高低电平控制蜂鸣器的高低电平。

如何让蜂鸣器响?首先我们要确定蜂鸣器的频率,也就是需要控制高电平低电平交替的周期。

for(i=0;i<ms*2;i++) { Buzzer=!Buzzer; Buzzer_Delay500us(); }

这段函数控制了蜂鸣器以高电平低电平进行交替。高电平维持 500 微秒,低电平维持 500 微秒,一个周期就是 1 毫秒,频率则为 1s/1ms=1000HZ,秒/毫秒等价于乘以 1000。

//蜂鸣器端口: sbit Buzzer=P1^5;

sbit是用于定义特殊功能寄存器的位变量的关键字。在 C51 扩展的变量类型中,sbitbit都是可以用来定义位操作的变量类型。通过使用sbit关键字,可以为特定的端口上的位取一个名字,这样就可以直接通过这个名字来访问和操作这些位,而不需要知道它们在内存中的具体地址。例如,在代码中使用sbit P0_0=P0^0;这样的语句,就是将P0_0定义为P0口的第1位,这样做是为了便于进行位操作。

在给定的问题中,sbit Buzzer=P1^5;的含义是定义了一个名为Buzzer的变量,这个变量指向P1口的第5位。也就是P1_5

其次我们需要控制蜂鸣器的鸣响时间,也就是以确定的周期为单位运行的总时长。

for(i=0;i<ms*2;i++) { Buzzer=!Buzzer; Buzzer_Delay500us(); }

我们已经固定了蜂鸣器的频率,为1000HZ,我们控制蜂鸣器鸣响ms毫秒,因此需要执行Delay500us延时函数ms*2次。

#include <INTRINS.H>头文件,对应使用_nop_();语句。

_nop_();在编程中通常表示一个空操作(no-operation)。它是一个什么也不做的指令,用于占位或确保代码结构的完整性,而不产生任何效果。在单周期指令中,可以通过晶振频率计算出具体的延时时间,例如对于 12M 晶振,延时 1 微秒(uS)。

利用定时器让蜂鸣器以特定频率响 ms 毫秒


//Timer0.h
#ifndef __TIMER0_H__
#define __TIMER0_H__

void Timer0Init(void);

#endif

//Timer0.c
#include <REGX52.H>

/**
  * @brief  定时器0初始化,1毫秒@12.000MHz
  * @param  无
  * @retval 无
  */
void Timer0Init(void)
{
        TMOD &= 0xF0;                //设置定时器模式
        TMOD |= 0x01;                //设置定时器模式
        TL0 = 0x18;                //设置定时初值
        TH0 = 0xFC;                //设置定时初值
        TF0 = 0;                //清除TF0标志
        TR0 = 1;                //定时器0开始计时
        ET0=1;
        EA=1;
        PT0=0;
}

/*定时器中断函数模板
void Timer0_Routine() interrupt 1
{
        static unsigned int T0Count;
        TL0 = 0x18;                //设置定时初值
        TH0 = 0xFC;                //设置定时初值
        T0Count++;
        if(T0Count>=1000)
        {
                T0Count=0;
                
        }
}
*/

定时器初始化函数里面是定时器最基本的配置。

TR0 = 1表示启动定时器,TR0 = 0表示关闭定时器。

TL0 = 0x18; TH0 = 0xFC;

两条语句是设置定时器开始计时的初值。

定时器启动之后,会从初值开始计时,直到超过65536us,此时打断进程去执行中断函数。

也就是定时器最多计时65536us

如果想要记录1s的时间,可以定义一个T0count变量记录有多少个1ms1s=1000*1ms

也就是我们需要让计时器记录1ms的时间,然后中断函数执行1000次的时候就是1s

让定时器记录1ms就需要改变定时器的初值,让初值等于64536us,此时过1ms之后定时器就会执行一次中断函数。

定时器每一次执行中断函数时,初值会默认置0,所以我们可以在中断函数中维护初值为64536us

定义初值为64536us,只需要TL0=64536%256;TH0=64536/256即可。

TL0表示低四位,TH0表示高四位,对256取余表示取低四位,除以256表示取高四位。


//Delay.h
#ifndef __DELAY_H__
#define __DELAY_H__

void Delay(unsigned int xms);

#endif

//Delay.c
void Delay(unsigned int xms)
{
        unsigned char i, j;
        while(xms--)
        {
                i = 2;
                j = 239;
                do
                {
                        while (--j);
                } while (--i);
        }
}


//mian.c
#include <REGX52.H>
#include "Timer0.h"
#include "Delay.h"
//蜂鸣器端口定义
sbit Buzzer=P2^5;
int us=500;
void main(){
        Timer0Init();
        TR0=0;

        while(1){
            if(P3_1==0){
                Delay(20);
                while(P3_1==0);
                Delay(20);
                        
                TR0=1;
                        
                TL0=(65536-us)%256;
                TH0=(65536-us)/256;
                        
                Delay(100);
                TR0=0;
                
            }
        }
}

void Timer0_Routine() interrupt 1{
//        int us_max=65536;

//        int us_num=us_max-us;
        
        TL0=(65536-us)%256;
        TH0=(65536-us)/256;
        Buzzer=!Buzzer;
}

我们需要控制蜂鸣器的频率和持续时间,控制频率相当于控制翻转蜂鸣器 IO 口的周期。只需要控制定时器即可。

int us=500;

void Timer0_Routine() interrupt 1{ // int us_max=65536; // int us_num=us_max-us; TL0=(65536-us)%256; TH0=(65536-us)/256; Buzzer=!Buzzer; }

定时器计时时长为500us,也就是500us翻转一次蜂鸣器IO口,蜂鸣器周期为1ms,频率为1s/1ms=1000HZ

1000HZ的频率让蜂鸣器响。

void main(){ Timer0Init(); TR0=0;

对定时器初始化之后先关闭定时器。 while(1){ if(P3_1==0){ Delay(20); while(P3_1==0); Delay(20); TR0=1; TL0=(65536-us)%256; TH0=(65536-us)/256; Delay(100); TR0=0; } }

当我们按下K1按键(对应P3_1=0)并且抬起按键的时候,启动定时器,并且修改定时器的初值,此时我们延时100ms,也就是让蜂鸣器以1000HZ100ms。响完之后关闭定时器。

结尾

最后,感谢您阅读我的文章,希望这些内容能够对您有所启发和帮助。如果您有任何问题或想要分享您的观点,请随时在评论区留言。

同时,不要忘记订阅我的博客以获取更多有趣的内容。在未来的文章中,我将继续探讨这个话题的不同方面,为您呈现更多深度和见解。

谢谢您的支持,期待与您在下一篇文章中再次相遇!

作者:妖精七七_

物联沃分享整理
物联沃-IOTWORD物联网 » 使用单片机编程实现蜂鸣器模块的1000HZ鸣响,定时器控制特定频率和持续时间

发表评论