单片机教程实战2 蜂鸣器唱歌.docx

上传人:b****5 文档编号:8030545 上传时间:2023-01-28 格式:DOCX 页数:17 大小:40.67KB
下载 相关 举报
单片机教程实战2 蜂鸣器唱歌.docx_第1页
第1页 / 共17页
单片机教程实战2 蜂鸣器唱歌.docx_第2页
第2页 / 共17页
单片机教程实战2 蜂鸣器唱歌.docx_第3页
第3页 / 共17页
单片机教程实战2 蜂鸣器唱歌.docx_第4页
第4页 / 共17页
单片机教程实战2 蜂鸣器唱歌.docx_第5页
第5页 / 共17页
点击查看更多>>
下载资源
资源描述

单片机教程实战2 蜂鸣器唱歌.docx

《单片机教程实战2 蜂鸣器唱歌.docx》由会员分享,可在线阅读,更多相关《单片机教程实战2 蜂鸣器唱歌.docx(17页珍藏版)》请在冰豆网上搜索。

单片机教程实战2 蜂鸣器唱歌.docx

单片机教程实战2蜂鸣器唱歌

单片机教程实战2蜂鸣器唱歌

发布:

2009-11-0409:

01 |  作者:

平凡 |  来源:

网络 | 查看:

189次

利用单片机(或单板机)奏乐大概是无线电爱好者感兴趣的问题之一。

本文从单片机的基本发间实验出发,谈谈音乐程序的设计原理,并给出具体实例,以供参考。

电子爱好者社区4`_L9?

5~!

V

  单片机的基本发音实验

1X_s_S+}_U_?

-v"J0  我们知道,声音的频谱范围约在几十到几千赫兹,若能利用程序来控制单处机某个口线的“高”电平或低电平,则在该口线上就能产生一定频率的矩形波,接上喇叭就能发出一定频率的声音,若再利用延时程序控制“高”“低”电平的持续时间,就能改变输出频率,从而改变音调。

电子爱好者社区3X_`_q"g*d

  例如,要产生200HZ的音频信号,按图1接入喇叭(若属临时实验,也可将喇叭直接接在P1口线上),实验程序为:

电子爱好者社区^7r_q6Q9@6I_Z(o

  其中子程序DEL为延时子程序,当R3为1时,延时时间约为20us,R3中存放延时常数,对200HZ音频,其周期为1/200秒,即5ms。

这样,当P1.4的高电平或低电平的持续时间为2.5ms,即R3的时间常数取2500/20=125(7DH)时,就能发出200HZ的音调。

将上述程序键入学习机,并不断修改R3的常数可以感到音调的变化。

电子爱好者社区_Y'l\_sM_h7tX-}0B

  乐曲中,每一音符对应着确定的频率,表1给出C调时各音符频率及其相应的时间常数。

!

{_q!

d_]

~_S_^_Q-Ft0  读者可以根据表1所提供的常数,将其16进制代码送入R3,反复练习体会。

根据表1可以奏出音符。

仅这还不够,要准确奏出一首曲子,必须准确地控制乐曲节奏,即一音符的持续时间。

电子爱好者社区'jp_p_C!

L*X-G_w

  音符的节拍我们可以用定时器T0来控制,送入不同的初值,就可以产生不同的定时时间。

便如某歌曲的节奏为每分钟94拍,即一拍为0.64秒。

其它节拍与时间的对应关系见表2。

-A2hV_S_x7X_L0  但时,由于T0的最大定时时间只能为131毫秒,因此不可能直接用改变T0的时间初值来实现不同节拍。

我们可以用T0来产生10毫秒的时间基准,然后设置一个中断计数器,通过判别中断计数器的值来控制节拍时间的长短。

表2中也给出了各种节拍所对应的时间常数。

例如对1/4拍音符,定时时间为0.16秒,相应的时间常数为16(即10H);对3拍音符,定时时间为1.92秒,相应时间长数为192(即C0H)。

___h#g%\_?

+L_H_o:

N0  我们将每一音符的时间常数和其相应的节拍常数作为一组,按顺序将乐曲中的所有常数排列成一个表,然后由查表程序依次取出,产生音符并控制节奏,就可以实现演奏效果。

电子爱好者社区d_R

d_r\,x!

|

  此外,结束符和体止符可以分别用代码00H和FFH来表示,若查表结果为00H,则表示曲子终了;若查表结果为FFH,则产生相应的停顿效果。

_I&O_?

_iK_g_c_k1N0  为了产生手弹的节奏感,在某些音符(例如两个相同音符)音插入一个时间单位的频率略有不同的音符。

3q2}/\(q7[_T7K9Z5R_l0  程序框图如图2所示。

电子爱好者社区_G0G_y{!

LV;t_k_s

  下面给出程序序请单,可直接在TD-III型学习机上演奏,对其它不同型号的学习机,只需相应地改变一下地址即可。

本程序演奏的是民歌“八月桂花遍地开”,C调,节奏为94拍/分。

读者也可以自行找出一首歌,按表1和表2给定的常数,将乐曲翻译成码表输入机器,而程序不变。

本实验方法简便,即使不懂音乐的人,将一首陌生的曲子翻译成代码也是易事,和着机器的演奏学唱一首歌曲,其趣味无穷。

电子爱好者社区'A6n_?

_I_O#F!

W_x'I

  程序清单(略,请参看源程序的说明)。

电子爱好者社区#v_Q_T1Z1Q_Y_cl

《无线电》1992年第3期。

电子爱好者社区6K%SN_z_e_e

  硬件连接说明:

电子爱好者社区1Qi_F%s'or_k}

  随便找一个仿真机或者什么单片机实验板,只要能工作的就行,将程序输入,运行,然后找个音箱(你计算机旁边应当就有一对吧)拨出插头,插头的前端接在P1。

0上,后面部分找根线接单片机的地,就应当有声了,然后怎么改进硬件连接就是你的事了。

单片机教程实战3键盘扫描识别

发布:

2009-11-0409:

02 |  作者:

平凡 |  来源:

网络 | 查看:

150次

键盘是由若干按键组成的开关矩阵,它是微型计算机最常用的输入设备,用户可以通过键盘向计算机输入指令、地址和数据。

一般单片机系统中采和非编码键盘,非编码键盘是由软件来识别键盘上的闭合键,它具有结构简单,使用灵活等特点,因此被广泛应用于单片机系统。

b_e?

F_p-mS0  1、按键开关的抖动问题电子爱好者社区_jW_F*y_I

 

_u$s2y/x/Y#K+vu|_[#j_K6V0

电子爱好者社区$|_K_])k%x

图1电子爱好者社区(D_v~-V_f_\

电子爱好者社区_t_m%h_K_D

_PF+R-[_i0

图2

+r1]_\

i;[_jq5g0

电子爱好者社区4a1`_xK,t_^

  组成键盘的按键有触点式和非触点式两种,单片机中应用的一般是由机械触点构成的。

在下图中,当开关S未被按下时,P1。

0输入为高电平,S闭合后,P1。

0输入为低电平。

由于按键是机械触点,当机械触点断开、闭合时,会有抖动动,P1。

0输入端的波形如图2所示。

这种抖动对于人来说是感觉不到的,但对计算机来说,则是完全可以感应到的,因为计算机处理的速度是在微秒级,而机械抖动的时间至少是毫秒级,对计算机而言,这已是一个“漫长”的时间了。

前面我们讲到中断时曾有个问题,就是说按键有时灵,有时不灵,其实就是这个原因,你只按了一次按键,可是计算机却已执行了多次中断的过程,如果执行的次数正好是奇数次,那么结果正如你所料,如果执行的次数是偶数次,那就不对了。

电子爱好者社区3t_r2L!

@_?

.z_A

  为使CPU能正确地读出P1口的状态,对每一次按键只作一次响应,就必须考虑如何去除抖动,常用的去抖动的方法有两种:

硬件方法和软件方法。

单片机中常用软件法,因此,对于硬件方法我们不介绍。

软件法其实很简单,就是在单片机获得P1。

0口为低的信息后,不是立即认定S1已被按下,而是延时10毫秒或更长一些时间后再次检测P1。

0口,如果仍为低,说明S1的确按下了,这实际上是避开了按键按下时的抖动时间。

而在检测到按键释放后(P1。

0为高)再延时5-10个毫秒,消除后沿的抖动,然后再对键值处理。

不过一般情况下,我们通常不对按键释放的后沿进行处理,实践证明,也能满足一定的要求。

当然,实际应用中,对按键的要求也是千差万别,要根据不同的需要来编制处理程序,但以上是消除键抖动的原则。

电子爱好者社区0s_`:

~4{_H

  2、键盘与单片机的连接电子爱好者社区(b"X_j,w_o

.Z3j_t+M1Zn_a"J

l0

_SD#J%P)z2^(wFV:

E0

图3电子爱好者社区2u

j_e0L%K,a

_^i0t,S:

O,T_h0

_HH6}*G9G_E"x0电子爱好者社区X__'lj#P0`_H

%P\"`_h_u?

_Q1\_Z0 

_I_]+@5Z_j'`0

图4电子爱好者社区#e2D4u,s`*Y!

J_S_E%Z_W#^

6iH7sQ&F_M-a0  1、通过1/0口连接。

将每个按键的一端接到单片机的I/O口,另一端接地,这是最简单的方法,如图3所示是实验板上按键的接法,四个按键分别接到P3.2、P3.3、P3.4和P3.5。

对于这种键各程序可以采用不断查询的方法,功能就是:

检测是否有键闭合,如有键闭合,则去除键抖动,判断键号并转入相应的键处理。

下面给出一个例程。

其功能很简单,四个键定义如下:

_l_vW7L_K_U_k*Y0P3.2:

开始,按此键则灯开始流动(由上而下)

-n_B6|/h}4t8f%A&S0P3.3:

停止,按此键则停止流动,所有灯为暗电子爱好者社区@4T_Pa8YU_DZ

P3.4:

上,按此键则灯由上向下流动电子爱好者社区:

N.D:

{&C

H_T9y'n!

n8i4R:

G

P3.5:

下,按此键则灯由下向上流动

R$N)Sa+WA!

b0UpDownEQU00H;上下行标志电子爱好者社区:

?

_uP7et

StartEndEQU01H;起动及停止标志电子爱好者社区x_O_`_Z_Z_N6w3V

LAMPCODEEQU21H;存放流动的数据代码电子爱好者社区%[(M_ef_@|bL

ORG0000H

_J{@

ki_g_H_q0AJMPMAIN

aV9V_T_S2r$U/]9K0ORG30H电子爱好者社区}_h5A7n_K;_+F_R8F

MAIN:

_G_H_R5Y_d-P0MOVSP,#5FH电子爱好者社区_c(MM5h%t_R:

N6D

MOVP1,#0FFH

_w_Y'a_h-],J0CLRUpDown;启动时处于向上的状态电子爱好者社区B.}q_yE"m

CLRStartEnd;启动时处于停止状态电子爱好者社区_d_q_bC_BM

MOVLAMPCODE,#0FEH;单灯流动的代码电子爱好者社区_t4]_w_r3m|_E(C_Z!

t

LOOP:

%d7Wr:

I]0ACALLKEY;调用键盘程序电子爱好者社区

pm_o(m_g"qA_R

JNBF0,LNEXT;如果无键按下,则继续

TG_ZI_`_p_P_F_g0ACALLKEYPROC;否则调用键盘处理程序电子爱好者社区_Q$\_g%t_S,Qz_f_M!

Ce3P

LNEXT:

'v_mX"a+__S/nr_S___}0ACALLLAMP;调用灯显示程序电子爱好者社区_K.\r0h_D%g

AJMPLOOP;反复循环,主程序到此结束

__:

S!

z_@:

^m,Q&V$u5m0;---------------------------------------

T_P)W(K|y_f_A

O0DELAY:

电子爱好者社区Q_O%f6a*m_E_pW

MOVR7,#100

_G_i_B!

t9y"}+r0D1:

MOVR6,#100电子爱好者社区/kd+Z_~_G9J

DJNZR6,$电子爱好者社区___jQ

k_F8\_]_x

DJNZR7,D1电子爱好者社区_S_q%S)jT_j,u

RET电子爱好者社区7~[$E&Q5s_e%b_E_w

;----------------------------------------延时程序,键盘处理中调用

_q_?

_i_pj0KEYPROC:

_k3O_\^_?

0MOVA,B;从B寄存器中获取键值

*E3~-F_z

|#j0JBACC.2,KeyStart;分析键的代码,某位被按下,则该位为1(因为在键盘程序中已取反)电子爱好者社区_Q_h/yn-K

JBACC.3,KeyOver电子爱好者社区Ku0d_G_U_L_X_Y

JBACC.4,KeyUp电子爱好者社区_r_K/c_v_]*Z;d:

]_P

JBACC.5,KeyDown

_M_G_M+c(s/F7H0AJMPKEY_RET电子爱好者社区A_q3z_k_?

_l_I_{

KeyStart:

_t_Y#I_~__0SETBStartEnd;第一个键按下后的处理

#D7R_p3A_[0AJMPKEY_RET电子爱好者社区+g_o:

y'w1|_E9z)v!

h

KeyOver:

电子爱好者社区_x_^6M&~_}_O)s#X-X

CLRStartEnd;第二个键按下后的处理电子爱好者社区!

_(w:

{_ZdA4pu4W1j_A

AJMPKEY_RET

_q2c_~_ro0KeyUp:

SETBUpDown;第三个键按下后的处理电子爱好者社区'i:

Fw_y_A3s)@

AJMPKEY_RET

_R)AG;e9r-[^0KeyDown:

电子爱好者社区%_1]4U_E_n[__

CLRUpDown;第四个键按下后的处理

)k'BL.E;Cz(s1F4LB0KEY_RET:

RET

_f_U_Q/B_By_U5U/~"F0KEY:

电子爱好者社区_?

_y_N_y_n9R_T

CLRF0;清F0,表示无键按下。

K4F:

K$N_F6X)l0ORLP3,#00111100B;将P3口的接有键的四位置1

_s&Or0k_]Y0MOVA,P3;取P3的值电子爱好者社区_H_w*y_|6D*y_u8q&b/s_x

ORLA,#11000011B;将其余4位置1电子爱好者社区_J1b1}_e_[pk

CPLA;取反电子爱好者社区,Wn|_c_]_k_l

JZK_RET;如果为0则一定无键按下

_g*a*J\+@0ACALLDELAY;否则延时去键抖电子爱好者社区6li2m%Az_?

_p_{

ORLP3,#00111100B电子爱好者社区_O_|_`+N_c_S

MOVA,P3电子爱好者社区_j_Q!

n_aa

Xw~

ORLA,#11000011B

q5?

2m*__?

#G0CPLA电子爱好者社区_f_G9K#f_z_Z@

JZK_RET电子爱好者社区2~8~5y$mV5i_`_s/v.t

MOVB,A;确实有键按下,将键值存入B中

.P

F-UB/h_m0SETBF0;设置有键按下的标志

&sT_wO-g_]_xB_a"`0K_RET:

电子爱好者社区(c4U(o__s6s

ORLP3,#00111100B;此处循环等待键的释放电子爱好者社区-]:

o_JJ'vD-B_g0F_j

MOVA,P3电子爱好者社区_y._~&D_G_E

ORLA,#11000011B电子爱好者社区'?

O4Q_G_H_]g

CPLA

'Q:

l5b)L;QsZ'j0JZK_RET1;直到读取的数据取反后为0说明键释放了,才从键盘处理程序中返回电子爱好者社区&Ak'J_e}_N$d

AJMPK_RET

_tr/C_x_hq|0K_RET1:

电子爱好者社区6v3W_?

D_L_Z5}

RET

SB2M_u_F_x/`0;-----------------------------------电子爱好者社区_n1~:

M+Cw_B

D500MS:

;流水灯的延迟时间

Q_l_|_E9|"N_g0PUSHPSW电子爱好者社区.H_Q_X_V_c+fYM

SETBRS0电子爱好者社区*O_O5]E_Q_aI_T_m&s

MOVR7,#200电子爱好者社区_B_s_S/K#S*L_ht

D51:

MOVR6,#250

_E_\_nT_E

z.a%Tg_r0D52:

NOP电子爱好者社区C_d$^K_[,u5}_b

NOP电子爱好者社区!

l_J2J0P!

a5^_jG

NOP电子爱好者社区.W_I1x:

\2B%D'V

NOP

_f_v

k!

A_t%^*n0DJNZR6,D52

_S;_%x_x'S

g8uI0DJNZR7,D51电子爱好者社区_a(k_J#o's___y_O

POPPSW电子爱好者社区0a%e_m5D'n-u)U

RET电子爱好者社区_s9G&F)I_~_Ld,PY_

;-----------------------------------电子爱好者社区/C}0i_H_Q2o_q)c#f

LAMP:

/A/~_c8]_q4`-^-`)S_O0JBStartEnd,LampStart;如果StartEnd=1,则启动

4`_A,K5x~_SX;G1r0MOVP1,#0FFH

0oh_T8q_fv0AJMPLAMPRET;否则关闭所有显示,返回

p_czs/^;zi_d"U9bQ0LampStart:

*[J!

d]x2_:

DQ0JBUpDown,LAMPUP;如果UpDown=1,则向上流动电子爱好者社区_u!

C_@_u_z#`

MOVA,LAMPCODE电子爱好者社区t&Fckj3c-@

RLA;实际就是左移位而已

_Fd_x_F1l_A0MOVLAMPCODE,A电子爱好者社区_W$W3W([&[_el~_M

MOVP1,A电子爱好者社区_F9J!

m__m&{

A/t_UF

LCALLD500MS

6Q4H5I_D.D_S0AJMPLAMPRET电子爱好者社区_o_Pd_k_t?

_z;H

LAMPUP:

电子爱好者社区_E9J'k7d*R']_\"]&G

MOVA,LAMPCODE电子爱好者社区_M$[:

E9F_~

RRA;向下流动实际就是右移电子爱好者社区4l/|2C'hC3r

MOVLAMPCODE,A电子爱好者社区_*V_Zt_n,v_p

MOVP1,A

_HX_I_|7O9P_`0LCALLD500MS

0w7K__&oo

F_u0LAMPRET:

g-l_N_`#vxS0RET电子爱好者社区+`2F%X6D)N1J

END

_t/O9f_A1Ic#L_C0T_t0  以上程序功能很简单,但它演示了一个键盘处理程序的基本思路,程序本身很简单,也不很实用,实际工作中还会有好多要考虑的因素,比如主循环每次都调用灯的循环程序,会造成按键反应“迟钝”,而如果一直按着键不放,则灯不会再流动,一直要到松开手为止,等等,大家可以仔细考虑一下这些问题,再想想有什么好的解决办法。

1J,m2K_w_nQ"u8U_h0  2、采用中断方式:

如图4所示。

各个按键都接到一个与非上,当有任何一个按键按下时,都会使与门输出为低电平,从而引起单片机的中断,它的好处是不用在主程序中不断地循环查询,如果有键按下,单片机再去做相应的处理

 

单片机音乐程序设计

作者:

佚名文章来源:

点击数:

3744更新时间:

2009/4/115:

25:

50   热     ★★★

利用单片机(或单板机)奏乐大概是无线电爱好者感兴趣的问题之一。

本文从单片机的基本发间实验出发,谈谈音乐程序的设计原理,并给出具体实例,以供参考。

单片机的基本发音实验我们知道,声音的频谱范围约在几十到几千赫兹,若能利用程序来控制单处机某个口线的“高”电平或低电平,则在该口线上就能产生一定频率的矩形波,接上喇叭就能发出一定频率的声音,若再利用延时程序控制“高”“低”电平的持续时间,就能改变输出频率,从而改变音调。

例如,要产生200HZ的音频信号,按图1接入喇叭(若属临时实验,也可将喇叭直接接在P1口线上),实验程序为:

其中子程序DEL为延时子程序,当R3为1时,延时时间约为20us,R3中存放延时常数,对200HZ音频,其周期为1/200秒,即5ms。

这样,当P1.4的高电平或低电平的持续时间为2.5ms,即R3的时间常数取2500/20=125(7DH)时,就能发出200HZ的音调。

将上述程序键入学习机,并持续修改R3的常数能感到音调的变化。

乐曲中,每一音符对应着确定的频率,表1给出C调时各音符频率及其对应的时间常数。

读者能根据表1所供给的常数,将其16进制代码送入R3,反复练习体会。

根据表1能奏出音符。

仅这还不够,要准确奏出一首曲子,必须准确地控制乐曲节奏,即一音符的持续时间。

音符的节拍我们能用定时器T0来控制,送入不一样的初值,就能产生不一样的定时时间。

便如某歌曲的节奏为每分钟94拍,即一拍为0.64秒。

其它节拍与时间的对应关系见表2。

但时,由于T0的最大定时时间只能为131毫秒,因此不可能直接用改变T0的时间初值来实现不一样节拍。

我们能用T0来产生10毫秒的时间基准,然后设置一个中断计数器,通过判别中断计数器的值来控制节拍时间的长短。

表2中也给出了各种节拍所对应的时间常数。

例如对1/4拍音符,定时时间为0.16秒,对应的时间常数为16(即10H);对3拍音符,定时时间为1.92秒,对应时间长数为192(即C0H)。

我们将每一音符的时间常数和其对应的节拍常数作为一组,按次序将乐曲中的所有常数排列成一个表,然后由查表程序依次取出,产生音符并控制节奏,就能实现演奏效果。

此外,结束符和体止符能分别用代码00H和FFH来表示,若查表结果为00H,则表示曲子终了;若查表结果为FFH,则产生对应的停顿效果。

为了产生手弹的节奏感,在某些音符(例如两个相同音符)音插入一个时间单位的频率略有不一样的音符。

下面给出程序序清单,可直接在TD-III型学习机上演奏,对其它不一样型号的学习机,只需对应地改变一下地址即可。

本程序演奏的是民歌“八月桂花遍地开”,C调,节奏为94拍/分。

读者也能自行找出一首歌,按表1和表2给定的常数,将乐曲翻译成码表输入机器,而程序不变。

本实验办法简便,即使不懂音乐的人,将一首陌生的曲子翻译成代码也是易事,和着机器的演奏学唱一首歌曲,其趣味无穷。

程序清单(略,请参看源程序的说明)。

程序框图如图2所示。

<单片机音乐程序的设计图>

单片机教程网

硬件连接说明:

随便找一个仿真机或者什么单片机实验板,只要能工作的就行,将程序输入,运行,然后找个音箱(你计算机旁边应当就有一对吧)拨出插头,插头的前端接在P1。

0上,后面部分找根线接单片机的地,就应当有声了,然后怎么改进硬件连接就是你的事了。

音乐程序汇编代码代码1-------------Voice.asm--------------------------

ORG0000H

LJMPSTART

ORG000BH

INC20H;中断服务,中断计数器加1

MOVTH0,#0D8H

MOVTL0,#0EFH;12M晶振,形成10毫秒中断

RETI

START:

MOVSP,#50H

MOVTH0,#0D8H

MOVTL0,#0EFH

MOVTMOD,#01H

MOVIE,#82H

MUSIC0:

NOP

MOVDPTR,#DAT;表头地址送DPTR

MOV20H,#00H;中断计数器清0

MOVB,#00H;表序号清0

MUSIC1:

NOP

CLRA

MOVCA,@A+DPTR;查表取代码

JZEND0;是00H,则结束

CJNEA,#0FFH,MUSIC5

LJMPMUSIC3

MUSIC5:

NOP

MOVR6,A

INCDPTR

MOVA,B

MOVCA,@A+DPTR;取节拍代码送R7

MOVR7,A

SETBTR0;启动计数

MUSIC2:

NOP

CPLP1.0

MOVA,R6

MOVR3,A

LCALLDEL

MOVA,R7

CJNEA,20H,MUSIC2;中断计数器(20H)=R7否?

;不等,则继续循环

MOV20H,#00H;等于,则取下一代码

INCDPTR

;INCB

LJMPMUSIC1

MUSIC3:

NOP

CLRTR0;休止100毫秒

MOVR2,#0DH

MUSIC4:

NOP

MOVR3,#0FFH

LCA

展开阅读全文
相关资源
猜你喜欢
相关搜索

当前位置:首页 > 总结汇报 > 学习总结

copyright@ 2008-2022 冰豆网网站版权所有

经营许可证编号:鄂ICP备2022015515号-1