设为首页收藏本站|繁體中文 快速切换版块

 找回密码
 立即加入
搜索
查看: 1374|回复: 0

一个超声波测距的程序源码(和大家分享一下)

[复制链接]

该用户从未签到

尚未签到

发表于 2010-11-2 18:12:11 | 显示全部楼层 |阅读模式

马上加入,结交更多好友,共享更多资料,让你轻松玩转电力研学社区!

您需要 登录 才可以下载或查看,没有账号?立即加入

×
下面是一个超声波测距的程序,硬件电路由于电脑格盘已丢失,下面的代码是从样机上复制的。
5 b* v% }; x- m) o9 f1 H) p+ c% O硬件电路包括液晶显示、超声波的发射、超声波的接受、滤波、单片机处理。1 r0 ^6 O5 f0 N; _  ^& h
液晶显示采用LCD1602模块,下面的代码里有液晶的驱动,可以拷贝用于它处。
6 y; B7 L: O7 ~超声波发射电路包括压电换能器及其支持电路,发射约44KHz的超声波。
3 \# c) ~6 g7 }% K超声波的接收电路包含一块CD40106处理芯片。
* y9 q2 V8 {( t0 }; ~, u( t1 S) e技术指标大约是测距范围在三米左右,测量精度约在厘米级别。大量用于倒车雷达的测距中。2 ]# J: Q! c6 R, S* Z# L5 D! n
#include<reg51.h>
" @+ W( h: K/ j. B2 j/ b, U+ u5 \#include <intrins.h>+ r( i0 K5 e$ N9 L
#define Busy    0x80  //用于检测LCM状态字中的Busy标识
3 T; \+ l) d/ H# T#define LCM_Data  P0
; W: Z) ?8 q5 }& m! l#define uchar unsigned char* V1 B! `, I9 @" V( v2 m: h
#define uint  unsigned int
$ k9 R& n( B% W* g; q1 V#define ulong unsigned long
; W' I6 w6 c1 c: I/ y
4 C' V. q, v) ?, [" t
! A" d% B: U+ A+ Xextern void cs_t(void);* m. \# G; P! F) X* C
extern void delay(uint);2 T* t" Z2 S4 {* J, q& j

& D! _8 r$ s" ]
: W! {- A0 k8 [& j3 _3 v0 N) z% G# \9 B  ~
void LCMInit(void);7 Y1 d5 S4 h( Y& h, Y
void DisplayOneChar(uchar X, uchar Y, uchar DData);6 ~: b9 I* D/ R+ G9 n0 x7 }
void DisplayListChar(uchar X, uchar Y, uchar  *DData);
2 @% |4 ~* s/ @$ @& pvoid Delay5Ms(void);
  T* }0 l* `# X5 {$ nvoid Delay100Ms(void);
9 L# L) E* ]3 F* m7 Z" ?3 `! W! ~7 q, `0 Z  ~
void WriteDataLCM(uchar WDLCM);6 ~: I, J5 T; h& p
void WriteCommandLCM(uchar WCLCM,BuysC);7 W5 d- ]# U" z3 f% w; b3 ^! y

. a7 ~  P& y: i. F0 V/ @$ s: |! O' n9 l* s' ?& r4 k
data float distant=0.0;% \4 N$ p- b2 e
uchar ReadDataLCM(void);- Y1 j7 D7 G- l, f9 Y( e$ ~
uchar ReadStatusLCM(void);
, e1 J2 S0 u' e& i$ _8 z4 p! tuchar  cdle_net[] = {"--Daoche_Leida--"};
5 ?/ y. _7 u. Z  B# Fuchar  email[] = {"Juli:"};/ k9 r1 A& _$ \1 B
uchar  cls[]={"         "};" _: ~) ?0 K) y& K8 }% [% V0 ]
uchar DIS[7];" G. n; ^9 O( S! P7 [' D- Z" I  b
data ulong time;7 Y1 k" h* K4 {4 I
float distant;
& i9 p3 y0 x9 O; f. U; csbit LCM_RS=P1^1;  //定义LCD引脚/ F! v5 |" }/ x' U" p
sbit LCM_RW=P1^2;
8 l  |% y& s/ `/ xsbit LCM_E=P1^3;
. ?6 s/ L  {$ e6 y6 [9 {1 f$ p" r7 Bsbit P10=P1^0;# M" k! M! x, p6 I" f) B
3 T; l' q' p5 V+ ^+ j

$ l3 Z$ H2 Z, I* ]; o6 odata uchar flag;
2 s# b) S' P0 |& L6 @8 f% X! U8 p: T" _+ Z9 |) s
void zhuanhuan(float juli)* a, D( B3 w( K. Q' `
{
% {+ h% K1 l+ Q5 bunsigned long juli1;
! ^6 V) n- K: `& U# gjuli1=juli*100;3 |7 ~( e" w5 K
DIS[6]=juli1%10+0x30;4 T" p6 ]* E6 t8 m! u7 }- y
juli1=juli1/10;0 R, N. I# C9 ^5 E1 t
DIS[5]=juli1%10+0x30;
: k: g* ?0 Q! T: G" s) Vjuli1=juli1/10;0 q  F" ^7 N" q* t- v1 y
DIS[4]='.';
+ b" g: R& o  M5 h3 p" BDIS[3]=juli1%10+0x30;2 i0 {- `  j2 j6 a1 [; u; P$ c9 I
juli1=juli1/10;
# ]$ a2 V6 t) ^! MDIS[2]=juli1%10+0x30;8 ~- N9 ]& {' h
juli1=juli1/10;3 \0 ]' h$ }$ \/ o4 c7 x
DIS[1]=juli1%10+0x30;
9 d) _+ c/ N3 ?0 q2 y+ xDIS[0]=juli1/10+0x30;
# N5 Q& H, W' Q4 D1 @
4 n" z. i6 m3 q7 Y- Z1 q  k}
4 D. D' w" S7 z- I/ i: {' b6 h. K
void main(void). n3 ^( F' P  R- m2 E- ?* l
{
; \. y' ^) s2 }$ d: l   
" B5 Q: N" f/ t* [% s2 ~6 p- P. s    Delay100Ms(); //启动等待,等LCM讲入工作状态- K7 A- ~3 A) P8 w4 B7 M
    P10=1;    4 J( }! G% }- S; Y0 O+ i( e; N1 j
    TMOD=0x01;             //计数器0工作在方式1
/ P% v3 e' f% }5 Q5 }6 v# c    TH0=0;# s) L- }3 d3 s
    TL0=0;                  //计数值初始化! U6 U# P6 {1 _: H
    IT1=0;                 //低电平触发中断
8 y3 E% m5 e8 D! f+ l/ t8 R    EA=1;                //开总中断
( c' V' T1 g" z% m# ?! H    //IP=0x04;             //设置外部中断1为高优先级中断
5 r' U" w+ W. Q3 N    flag=0;
7 b8 @5 r8 @5 u; D    LCMInit(); //LCM初始化  E4 H4 u* ^7 [& u9 {& ^
   
6 p) _  D1 I6 u( m# r2 @! M" W    ; S" `# ~: Z1 p7 ^
    while(1)
' R2 E' {0 ?/ T    {
5 T( h! V/ f2 Z: h: W* {3 W3 M2 o     cs_t();% M$ [$ `: r4 s* F- L& C
     Delay5Ms();        
, s) @  \* k% e4 J1 r4 s/ ]7 R     ET0=1;         //打开计数器0中断- b9 B4 S0 S: m9 y" N
     EX1=1;         //打开外部中断1
, R1 m2 t- Q6 m8 b2 j: r     TR0=1;0 O3 u8 b9 o, M# B8 Q7 U7 f
     while(!flag)
8 ]' M* J: u/ V$ v; c9 O$ {     {
- F0 y) _: j) `1 w5 p4 M5 E      DisplayListChar(0, 0, cdle_net);
: Z* U% ^* z; z4 Y! ~& E" v6 T      DisplayListChar(0, 1, email);, ~' W+ N  T/ u' n2 V
     }3 M' p9 D% E( E- c, Y* C3 G2 R
     if(flag==1)
5 ]/ k% \- s: t, J     {% R; L& T3 m  @8 m9 G
      time=TH0;
: U0 B! g+ U9 U8 e/ ]! N      time=(time<<8)|TL0;2 M  R# r! ~* p
      distant=time*1.72/100;
, M8 V+ s& K9 k  V' Q; W( Z1 R      zhuanhuan(distant);4 [6 G  E# p: I: T
      if(DIS[0]=='0')      DisplayOneChar(5,1,' ');
0 t( a: N7 U* C" W! H9 O      else   DisplayOneChar(5,1,DIS[0]);; Q% H: w% y( [4 L# |0 Z7 ^
      if((DIS[0]=='0')&&(DIS[1]=='0'))      DisplayOneChar(6,1,' ');" n) ?# B& n4 H- ^& w
      else   DisplayOneChar(6,1,DIS[1]);4 P4 ^+ h# y! D
      if((DIS[0]=='0')&&(DIS[1]=='0')&&(DIS[2]=='0'))  DisplayOneChar(7,1,' ');
  k4 e* V6 `" Q1 L9 t! O      else   DisplayOneChar(7,1,DIS[2]);
6 h/ d0 v$ D3 Q7 }4 s8 W      DisplayOneChar(8,1,DIS[3]);# ?( K1 K2 f. ?4 ?0 u/ o
      DisplayOneChar(9,1,DIS[4]);
- W& r- l/ \1 f2 B* U* Q      DisplayOneChar(10,1,DIS[5]);
+ q7 W* n* l: T      DisplayOneChar(11,1,DIS[6]);
) c# [; C: W! ?) S5 s7 ?* N. M      DisplayOneChar(12,1,'c');$ \1 @5 O! O* l8 C2 j
      DisplayOneChar(13,1,'m');7 Y% i! ]8 o5 q# ?' {9 b) m! w( F$ n
      flag=0;
& {( x+ _1 s  C: C6 C0 D, F      }; q$ \1 H* I' t% n5 m% I, X' w, ]
     else
  m& C$ W5 ?: v, W* o     {
& Z& Z) R# z7 Q8 G) Z      DisplayListChar(5,1,"error!      ");
9 j; ~  G" }+ n8 w, G8 `- C      flag=0;0 N6 _) c+ P/ T4 {, z, Q7 ~
     }
4 s1 S) T  u1 }     TH0=0;% o) U4 C( F" I) K) C& j
     TL0=0;
9 ^8 ?0 I0 Z, E3 B0 w) F' q! M5 t    Delay100Ms();
, K8 z$ h2 u7 G5 n    }; C/ w+ p* n6 v& t7 u3 f
}9 @( P5 v5 w5 u9 n+ e8 X& p( u
/ |' W  \4 f( D3 L1 e
! ^$ h) Z& ?) [! A6 |
' q/ L& w: M$ i2 A" P
void cs_r(void) interrupt 2  b9 k6 @" F$ H( J
{( ~) Y* K: V2 r4 \
TR0=0;
5 J0 @" i' g% Q8 p& \" UEX1=0;" V- t8 ?) I( P  u) e
ET0=0;5 T: s: B5 a( C5 @
flag=1;
  q% r4 x4 j" u1 X" w) r' [7 P}
, s9 V0 R, G" x- [0 s5 }2 p) \) f* [6 U
' {" x, F8 ~+ n
void overtime(void) interrupt 1
! o' W2 o$ _4 r& s; j" {{* H. ?  R. v4 `$ H! X; R( ?/ f; _
EX1=0;
, S6 [9 M! u. Q; V8 s4 qTR0=0;8 n4 V1 t3 H0 k7 r! Y9 H, C& C
ET0=0;
' O- V2 m* J2 l9 M) k' mflag=2;: k" ^; f/ p* b. ~. @+ F  S
}
# ]0 V3 Q( T: r9 ^1 `, q$ K! I. p: t0 b
% U/ w4 r2 `9 K& }' J: q/ A! w
//写数据
  N7 B) Q% J" Z+ D$ X. {void WriteDataLCM(uchar WDLCM)
% w( v- ]5 k- H, X+ {{
! ?# K# H- K+ L' N    ReadStatusLCM(); //检测忙
: p+ G8 W3 g& Q6 h* a" L    LCM_Data=WDLCM;" A7 i# h2 `4 d. i: A/ h8 }5 i
    LCM_RS=1;
/ [% T/ Z# d3 K6 y9 j    LCM_RW=0;
6 b4 S/ X, G1 g: \    LCM_E=0; //若晶振速度太高可以在这后加小的延时
& B% f' {: p) ]# z+ B1 U    LCM_E=0; //延时7 R: \  X% a% f3 {
    LCM_E=1;
' R, W% `  o/ W" A/ G}
. x, U( o, a9 ^$ e( X+ D3 g) \* a  N! g7 O' @
//写指令
; [! g3 Y% {! Y" _% c4 Ovoid WriteCommandLCM(uchar WCLCM,BuysC) //BuysC为0时忽略忙检测6 b+ @3 ]$ K* F7 V8 a
{
) c7 X# k6 M3 p% [( S) s    if (BuysC) ReadStatusLCM(); //根据需要检测忙
0 k) O8 w8 v) P, L. {  m    LCM_Data = WCLCM;( m( k( @* j% b: Q% u1 ?& c9 U
    LCM_RS = 0;5 }) n" k5 \: k) S
    LCM_RW = 0;    + ^8 k0 `" \5 Z) V1 t/ ~4 e. L$ ~0 w, Z
    LCM_E = 0;
/ b& i# }" M1 K0 e; @3 `% v    LCM_E = 0;
) e: [) E4 [/ {7 ?( n& y8 C    LCM_E = 1;    , r( }5 h8 M1 j
}
7 w7 K1 f6 B5 U' d5 R9 R9 c0 _9 w! e6 b$ x8 s
//读数据
) W2 z# U$ p; p$ [uchar ReadDataLCM(void)
) i0 p! z7 @3 W{1 J" B. n6 v) o6 L; E" e
    LCM_RS = 1;
* V; V! [& y4 S( I    LCM_RW = 1;. @9 t8 \/ p& i+ _! ]
    LCM_E = 0;
* ?, h% Q' C7 D, B    LCM_E = 0;
" V6 s/ Q3 L1 L; e- l3 d1 \    LCM_E = 1;4 l( c  t" M! P3 }4 m
    return(LCM_Data);0 B6 Z- r9 y8 N0 y% n
}; J9 v" m, o4 p' E

/ P) M2 O: K  {  M( a//读状态0 w' p  E# r( s
uchar ReadStatusLCM(void), R7 T+ u: A/ C8 ^# N/ w% V
{
/ p) B! r: Q: `; `5 T& ?6 L" w" ^/ `    LCM_Data=0xFF;
0 n0 j9 m3 M% Z, B' S  N+ G/ a    LCM_RS=0;
; m3 u- J0 n* R    LCM_RW=1;
3 D, F9 b9 k. n3 [4 o; q9 `- ^# M    LCM_E=0;
3 w: P$ W$ x! a; U" t2 T' b1 L    LCM_E=0;
8 j8 V; _  I; `* k    LCM_E=1;; e/ O! ?' T) d! c
    while(LCM_Data & Busy); //检测忙信号( d, }3 b( k, y( l3 p+ T1 m! J
    return(LCM_Data);
1 a% v: x9 U: p4 t& y}2 |/ c7 ]3 q3 o7 U; J
/ f- x9 j& @* m; L9 h
void LCMInit(void) //LCM初始化
8 I& s& z4 {. l. J1 ]6 A- g& P2 D{
3 R# d0 d4 g0 w. {/ e    LCM_Data=0;# Z  O1 P' d8 Z/ x0 a7 n  G% u
    WriteCommandLCM(0x38,0); //三次显示模式设置,不检测忙信号! d0 e9 p- G( k+ Y3 T" w3 {. y
    Delay5Ms();
8 ]2 P) g% x% z# E" D: a    WriteCommandLCM(0x38,0);6 i2 D- F) @3 R, i! Q
    Delay5Ms(); 5 Z: ^' {9 @1 }0 ^
    WriteCommandLCM(0x38,0);
. F; Y1 f$ G: `! [( F, F    Delay5Ms();
' D5 l6 I; \. z& Z" L+ a# f0 Z3 B7 C. \, O$ R- {
    WriteCommandLCM(0x38,1); //显示模式设置,开始要求每次检测忙信号# X+ }( ?1 N$ C4 N' R* g/ N/ N
    WriteCommandLCM(0x08,1); //关闭显示
" A6 m9 A. _& l5 O6 m4 n# s    WriteCommandLCM(0x01,1); //显示清屏
0 ]) o! v( y4 h9 L; _    WriteCommandLCM(0x06,1); // 显示光标移动设置- ~- C$ i: T+ E+ y) ~/ n  n& g
    WriteCommandLCM(0x0F,1); // 显示开及光标设置
( U% E+ h; W% J- P: m5 f* l}
$ @- k7 W# f& n) M: ^8 H" y
5 x. ~7 a* r) I8 K4 b. q//按指定位置显示一个字符; z/ M& a; v& S& k3 [( F$ ?
void DisplayOneChar(uchar X, uchar Y, uchar DData)
1 s& S/ S# c8 D9 S- [2 w{
9 C# w' w" }3 z& H8 r- {    Y &= 0x1;$ p! j4 F8 H" |+ y0 T
    X &= 0xF; //限制X不能大于15,Y不能大于1* Y3 O" z! t/ a) w! C- g: u
    if (Y) X |= 0x40; //当要显示第二行时地址码+0x40;" K9 x- O) B7 n  b* @6 \: I7 Z; k" {
    X |= 0x80; //算出指令码, ^6 Y* L6 F+ T$ {
    WriteCommandLCM(X, 1); //发命令字
% [+ x& y* ]6 r8 C, N! C    WriteDataLCM(DData); //发数据
; T# E' P1 u! p2 ^  e# Q$ H; w}/ f$ h. W, E3 l; }

( F3 q! P  }5 u! r/ J//按指定位置显示一串字符
3 c% K5 |$ N7 I* j; z1 F& Wvoid DisplayListChar(uchar X, uchar Y, uchar  *DData)
+ w) t8 y3 j$ b  G! j* z{, v: K+ E1 G3 i
    uchar ListLength;
5 c! H3 i( h7 @3 u1 h/ x
- g& {8 [* O& M0 n" a( Y  ListLength = 0;
7 Y. A+ v! U/ _0 I- g2 K. t) |    Y &= 0x1;
! S+ s4 L8 q9 b2 M; p    X &= 0xF; //限制X不能大于15,Y不能大于1. {  ^" L" V% T9 V0 g8 g
    while (DData[ListLength]>0x20) //若到达字串尾则退出5 s5 t- C5 h: [$ V
        {
4 Z8 c+ ~, x7 t- A  a6 T6 p            if (X <= 0xF) //X坐标应小于0xF
5 X( T# s. B/ C' p, }                {
7 Z7 Z! V  i$ F9 O                    DisplayOneChar(X, Y, DData[ListLength]); //显示单个字符+ x5 c/ `- _* k9 A" [" t6 |7 Y: e
                    ListLength++;
/ n3 C$ e5 t* W5 x0 Q0 Z                    X++;
! \# K! a- f. r/ h! Q& a- v                }
% c& w& k+ c; S- o        }8 [5 q) ^& W1 d, [8 U( U
}: p1 |$ M- t, R: ?% Q

+ k* ]9 R& t/ \; ~5 z3 J) y! X) G2 y//5ms延时
7 T3 T1 v" f3 Y8 `2 o  _1 |void Delay5Ms(void)/ X& B# L; j) x1 j3 B$ a  c
{4 v' h5 j9 G) h" ~
    uint TempCyc = 200;: T3 w1 X8 q1 d! c
    while(TempCyc--);) J. W: m6 f& ^! r+ G" X
}. k( V) J( I1 i4 i8 a: G6 V
9 |) ?3 D- K# Z/ @! {# g$ _# |
//400ms延时! u* |6 s: l6 D( I# {/ R
void Delay100Ms(void)
4 s2 X' S* D0 B  o+ a& s{
. ?2 j7 J* y; B0 v    uchar TempCycA = 1;7 v* w; e* K! y+ T
    uint TempCycB;
- F: q  F; v; f# v% [    while(TempCycA--)
" k% t  f7 A9 i% x( {: A        {
5 @2 [# I$ R9 H# |            TempCycB=7269;
  {8 f5 o0 l: ~/ g% i  @3 K            while(TempCycB--);
+ N! q4 t- k3 u; ^# x/ u        }- i  `. B# P  l, b; m
}
"真诚赞赏,手留余香"
还没有人打赏,支持一下
楼主热帖
帖文化:【文明发帖 和谐互动】 社区精神:【创新、交流、互助、共享】
您需要登录后才可以回帖 登录 | 立即加入

本版积分规则

招聘斑竹

小黑屋|手机版|APP下载(beta)|Archiver|电力研学网 ( 赣ICP备12000811号-1|赣公网安备36040302000210号 )|网站地图

GMT+8, 2026-10-10 07:05

Powered by Discuz! X3.5 Licensed

© 2001-2026 Discuz! Team.

快速回复 返回顶部 返回列表