打印
[应用相关]

STM32驱动压电式蜂鸣器发出和弦音原理图加程序

[复制链接]
561|9
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
观海|  楼主 | 2021-7-2 11:53 | 只看该作者 |只看大图 回帖奖励 |倒序浏览 |阅读模式
一、原理图


使用特权

评论回复
沙发
观海|  楼主 | 2021-7-2 11:54 | 只看该作者
一、驱动代码



#include "beep.h"



void beep_init(void)
{
        GPIO_InitTypeDef  GPIO_InitStructure;

        RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB, ENABLE);         //使能GPIOB端口时钟

        GPIO_InitStructure.GPIO_Pin = GPIO_Pin_8;                                 //BEEP-->PB.8 端口配置
        GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;                  //推挽输出
        GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;         //速度为50MHz
        GPIO_Init(GPIOB, &GPIO_InitStructure);         //根据参数初始化GPIOB.8

        GPIO_ResetBits(GPIOB,GPIO_Pin_8);//输出0,关闭蜂鸣器输出
}



使用特权

评论回复
板凳
观海|  楼主 | 2021-7-2 11:56 | 只看该作者
void beep_pwm_Init(u16 arr,u16 psc)
{  
        GPIO_InitTypeDef GPIO_InitStructure;
        TIM_TimeBaseInitTypeDef  TIM_TimeBaseStructure;
        TIM_OCInitTypeDef  TIM_OCInitStructure;
       

        RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM4, ENABLE);        //使能定时器3时钟
        RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB  | RCC_APB2Periph_AFIO, ENABLE);  //使能GPIO外设和AFIO复用功能模块时钟
       
//        GPIO_PinRemapConfig(GPIO_PartialRemap_TIM4, ENABLE); //Timer3部分重映射  TIM3_CH2->PB5   

   //设置该引脚为复用输出功能,输出TIM4 CH2的PWM脉冲波形        GPIOB.5
        GPIO_InitStructure.GPIO_Pin = GPIO_Pin_7; //TIM_CH2
        GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;  //复用推挽输出
        GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
        GPIO_Init(GPIOB, &GPIO_InitStructure);//初始化GPIO

   //初始化TIM4
        TIM_TimeBaseStructure.TIM_Period = arr; //设置在下一个更新事件装入活动的自动重装载寄存器周期的值
        TIM_TimeBaseStructure.TIM_Prescaler =psc; //设置用来作为TIMx时钟频率除数的预分频值
        TIM_TimeBaseStructure.TIM_ClockDivision = 0; //设置时钟分割:TDTS = Tck_tim
        TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up;  //TIM向上计数模式
        TIM_TimeBaseInit(TIM4, &TIM_TimeBaseStructure); //根据TIM_TimeBaseInitStruct中指定的参数初始化TIMx的时间基数单位
       
        //初始化TIM3 Channel2 PWM模式         
        TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM2; //选择定时器模式:TIM脉冲宽度调制模式2
        TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable; //比较输出使能
        TIM_OCInitStructure.TIM_OCPolarity = TIM_OCPolarity_High; //输出极性:TIM输出比较极性高
        TIM_OC2Init(TIM4, &TIM_OCInitStructure);  //根据T指定的参数初始化外设TIM3 OC2

        TIM_OC2PreloadConfig(TIM4, TIM_OCPreload_Enable);  //使能TIM3在CCR2上的预装载寄存器

        TIM_Cmd(TIM4, ENABLE);  //使能TIM3
       

}


使用特权

评论回复
地板
观海|  楼主 | 2021-7-2 12:01 | 只看该作者
/*******************************************************************************
k07样板  2     2.2    2.4
db_pwm  69      65      62      59      56      54    50     43         41                                                  
fxx     1.8k    1.9k    2.0k    2.1k    2.2k    2.3k  2.47K  2.86K      3K
*******************************************************************************/



/*******************************************************************************
k07样板  2     2.46    3
db_pwm  69      65      62      59      56      54    50     43         41                                                  
fxx     1.8k    1.9k    2.0k    2.1k    2.2k    2.3k  2.47K  2.86K      3K
*******************************************************************************/

#define     F1      486                                                                  //2.057 KHZ
#define     F1PSC      71                                                                  //2.057 KHZ

#define     F2      442                                                                 //2.257 KHZ
#define     F2PSC      71                                                                  //2.257 KHZ

#define     F3      413                                                                  //2.415 KHZ
#define     F3PSC      71                                                                  //2.415 KHZ

#define     F4      464                                                                  //2.15        KHZ
#define     F4PSC      71                                                                  //2.15 KHZ




u16 const db_table_10 [6] = { F1, F1, F2, F2, F3, F3,        };            //底 嗒 帝  开机频率  
u16 const db_table_20 [6] = { 3,  7,  3,         7,  9,  35,        };                //每个频率所用的时间10ms单位
u16 const db_table_psc0 [6] = { F1PSC,F1PSC,  F2PSC,         F2PSC,  F3PSC,  F3PSC,        };                //每个频率所用的时间10ms单位

u16 const db_table_11 [6] = { F3, F3, F2, F2, F1, F1,        };            //帝 嗒  底         关机频率
u16 const db_table_21 [6] = { 3,  7,  3,  7,  9,  35,        };          //每个频率所用的时间10ms单位
u16 const db_table_psc1 [6] = { F3PSC,  F3PSC,  F2PSC,  F2PSC,  F1PSC,  F1PSC,        };          //每个频率所用的时间10ms单位

u16 const db_table_12 [2] = { F4, F4,         };                           //帝         按键频率
u16 const db_table_22 [2] = { 8,  35,         };                                    //每个频率所用的时间10ms单位   
u16 const db_table_psc2 [2] = { F4PSC,  F4PSC,         };                                    //每个频率所用的时间10ms单位

u16 const db_table_13 [4] = { F3, F3, F2, F2,         };                    //底 嗒        上电模式频率
u16 const db_table_23 [4] = { 3,  20, 7,  60,        };                                //每个频率所用的时间10ms单位
u16 const db_table_psc3 [4] = { F3PSC,  F3PSC, F2PSC,  F2PSC,        };                                //每个频率所用的时间10ms单位

u16 const db_table_14 [16] = { F3, F3, F3, F3, F3, F3, F3, F3, F3, F3, F3, F3, F3, F3, F3, F3,        };         //测试模式 加速模式
u16 const db_table_24 [16] = { 3,  18, 3,  18, 3,  18, 3,  18, 3,  18, 3,  18, 3,  18, 3,  18,        };        //每个频率所用的时间10ms单位
u16 const db_table_psc4 [16] = { F3PSC,  F3PSC, F3PSC,  F3PSC, F3PSC,  F3PSC, F3PSC,  F3PSC, F3PSC,  F3PSC, F3PSC,  F3PSC, F3PSC,  F3PSC, F3PSC,  F3PSC,        };        //每个频率所用的时间10ms单位

u8  const size_table1x []=
{
        (sizeof (db_table_10)) / (sizeof (db_table_10[0])),                                                                                         //求数组字节总数
        (sizeof (db_table_11)) / (sizeof (db_table_11[0])),
        (sizeof (db_table_12)) / (sizeof (db_table_12[0])),
        (sizeof (db_table_13)) / (sizeof (db_table_13[0])),
        (sizeof (db_table_14)) / (sizeof (db_table_14[0])),
};
/******************************************************************************/


使用特权

评论回复
5
观海|  楼主 | 2021-7-2 12:02 | 只看该作者
//================================================
//                        使能蜂鸣器函数
//================================================

u16   
        buz_musc_fz,                                                                //赋数组的频率
        buz_fz_timer,                                                                //赋数组每个频率的时间
        buz_kong_timer;                                                                //防止响蜂鸣超时
u8                 
        buz_musc_type,                                                                //选择使用蜂鸣类型        0=开机音 1=关机音        2=按键音        3=上电音        4=测试音                                               
        buz_musc_num,                                                                //决定选择数组的第几位
        buz_musc_len,                                                                //赋数组字节总位数                                                
        buz_musc_read_type;                                                        // 蜂鸣类型        1=开机声        2=关机声        3=按键声        4=上电声        5=加速测试声

u8 F_buz_start,buzzer_flag;

u16 timerPsc;
void start_musc (u8 _musc_nm)
{
        buz_musc_read_type = 0;
       
        buz_musc_fz = 0;                                                                                                // 所有变量清0
        buz_fz_timer = 0;
        buz_musc_type = 0;
        buz_musc_num = 0;
        buz_musc_len = 0;
        buzzer_flag = 0;
       
       
        buz_musc_type = _musc_nm;                                                                                 // 蜂鸣声音的类型
        if (buz_musc_type > 4)        { F_buz_start = 0;buz_musc_type = 0; }        // 不使能蜂鸣函数
        else                                        { F_buz_start = 1; }                                        // 开始使能蜂鸣函数
       
        close_beep();                                                                                                // 关闭蜂鸣器电源脚输出
        disable_beep_pwm();                                                                                        // 关闭蜂鸣器PWM输出       

        buz_kong_timer = 0;                                                                                                // 响蜂鸣超时清0
}


使用特权

评论回复
6
观海|  楼主 | 2021-7-2 12:02 | 只看该作者
//================================================
//                        使能蜂鸣器函数
//================================================

void musc_scan (void)
{
        //===========================================================  开始
        if (F_buz_start)
        {       
                //======================================================== 无蜂鸣时间
                if (buz_fz_timer == 0)
                {
                        switch (buz_musc_type)                                                                                 //蜂鸣声音的类型
                        {
                                case 0:
                                                buz_musc_fz = db_table_10 [buz_musc_num];                //赋频率
                                                buz_fz_timer = db_table_20 [buz_musc_num];                //赋频率所需的时间                               
                                                timerPsc=db_table_psc0[buz_musc_num];
                                                break;
                                case 1:
                                                buz_musc_fz = db_table_11 [buz_musc_num];
                                                buz_fz_timer = db_table_21 [buz_musc_num];                                       
                                                timerPsc=db_table_psc1[buz_musc_num];
                                                break;
                                case 2:
                                                buz_musc_fz = db_table_12 [buz_musc_num];
                                                buz_fz_timer = db_table_22 [buz_musc_num];                                       
                                                timerPsc=db_table_psc2[buz_musc_num];
                                                break;
                                case 3:
                                                buz_musc_fz = db_table_13 [buz_musc_num];
                                                buz_fz_timer = db_table_23 [buz_musc_num];                                       
                                                timerPsc=db_table_psc3[buz_musc_num];
                                                break;
                                case 4:
                                                buz_musc_fz = db_table_14 [buz_musc_num];
                                                buz_fz_timer = db_table_24 [buz_musc_num];                                       
                                                timerPsc=db_table_psc4[buz_musc_num];
                                                break;                                               
                        }

                        //装载 pwm1蜂鸣器        周期与占空比       
                       
                        beep_pwm_Init(buz_musc_fz,timerPsc);
                        TIM_SetCompare2(TIM4, buz_musc_fz/2);
                //        enable_beep_pwm();
                                       
                       
                        if (buz_musc_num & 0x01)        { close_beep(); }                                //数组单数就关闭蜂鸣电源脚
                        else                                                { open_beep(); }                                //数组双数就打开蜂鸣电源脚
                        buz_musc_len = size_table1x [buz_musc_type];                                //计算数组的总字节数
                }
                //======================================================== 无蜂鸣时间 end
               
                //======================================================== 有蜂鸣时间
                if (buz_fz_timer)
                {
                        buz_fz_timer--;                                                                                                                //每个蜂鸣频率的时间减减
                        if (buz_fz_timer == 0)       
                        {
                                buz_musc_num++;
                                if (buz_musc_num >= buz_musc_len)                                                                //与数组字节相等就结束
                                {
                                        start_musc (5);                                                                                                // 其它关闭蜂鸣PWM及变量清0       
                                }
                        }
                }
                //======================================================= 有蜂鸣时间 end
        }
        else
        {
                close_beep();                // 关闭蜂鸣器电源脚输出
                disable_beep_pwm();        // 关闭蜂鸣器PWM输出
        }
        //===========================================================结束
}


使用特权

评论回复
7
观海|  楼主 | 2021-7-2 12:04 | 只看该作者
//================================================
//                        扫描使能蜂鸣器函数
//================================================

void musc_select_num_scan (void)
{
        switch (buz_musc_read_type)
        {
                case 1:        start_musc (0);                break;                // 开机蜂鸣               
                case 2:        start_musc (1);                break;                // 关机蜂鸣               
                case 3:        start_musc (2);                break;                // 按键蜂鸣       
                case 4:        start_musc (3);                break;                // 上电蜂鸣               
                case 5:        start_musc (4);                break;                // 加速蜂鸣       
                default:
                                if (F_buz_start)
                                {
                                        if (++buz_kong_timer > 1000)        // 如果响蜂鸣超过了10sec
                                        {
                                                start_musc (5);                                // 其它关闭蜂鸣PWM及变量清0               
                                        }
                                }
                                else { buz_kong_timer = 0; }
                                break;                                               
        }
}


使用特权

评论回复
8
观海|  楼主 | 2021-7-2 12:05 | 只看该作者
主函数中调用



int main(void)
{       
        u8 i,led=0x00;
        delay_init();       
        program_led_init();       
        can_led_init();
        rs485_led_init();
        beep_init();
        while(1)
        {       

                i++;
                if(i>=100)
                {
                        i=0;
                        led=~led;
                        buz_musc_read_type=1;
                        program_led_data(0x00,led-0xf0,0x00);       
                }


                       
                musc_select_num_scan ();                                                // 蜂鸣
                musc_scan ();
                delay_ms(10);
        }
}

三、注意点
1、BEEP_CLK是一路硬件PWM口


使用特权

评论回复
9
kiwis66| | 2021-7-2 16:36 | 只看该作者
和弦音,好久没听到这个词了。

使用特权

评论回复
10
两只袜子| | 2021-7-2 17:22 | 只看该作者
的确是,我也第一次听说

使用特权

评论回复
发新帖 我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则

99

主题

3912

帖子

1

粉丝