|
EDA365欢迎您登录!
您需要 登录 才可以下载或查看,没有帐号?注册
x
简易自行车里程计仿真图及单片机源程序 X/ {) P, s8 _. L0 P0 K* d
k( m' s7 U; ?+ I8 h
+ Z% z. g _* Y' g$ ]; t O$ T
3 i7 i( l1 D4 Q2 c! X1 w. a由于仿真中没有霍尔传感器,实际呢霍尔就是感应磁信号,输出高低电平的脉冲信号,这样用脉冲就可以了,不同的频率代表电机转速的快慢 7 G9 F. {; F) p6 o- B
单片机源程序: #include<reg52.h>: W k8 e( p- N' c" R: ]
# b8 `* i6 Y* |#define uchar unsigned char1 z* e% s) H" u
#define uint unsigned int0 z. C' x9 D/ s* G
$ O `+ i6 u$ l, A; s k% A
sbit COUNT_IN=P3^2;$ ~9 G% m! Q9 i4 Q1 X# Y2 G
1 F2 d1 K$ d. [0 [3 O6 h( d//定义1602相关管脚
) `9 N7 V& A' \* T4 f i6 [+ A3 Nsbit rs=P2^7;! q) a0 s: X# _* D
sbit en=P2^6;
( B4 O& ^2 p# ]7 E: V+ j C9 ?- r
uint count;, O1 S, H7 K$ D- j% E
unsigned long Velocity,Mileage;
9 K0 x1 L0 k. j1 @bit flag;
" ?" P$ g+ K0 I h0 O, L2 ruchar code tab1[]={" Speed: km/h"}; 6 s0 [; A: Z: O
uchar code tab2[]={"Mileage: . km"}; W9 _8 y0 ^( G: l
' \! R: L9 w/ Cvoid delay(uint x) T$ ` L1 N( j5 s7 @, Y
{* G* d& U8 m+ C* Y
uint i,j;; Z, K/ u) m& \5 k1 b
for(i=0;i<x;i++)- P* [; _* b g! T) {. D! j$ ?. A
for(j=0;j<110;j++);
. t) l8 U& T# [; n& ^}
' |! e" [* `% E8 z8 p$ Ovoid init()
) v" z+ v- r! {{/ ^4 W; z4 V6 Q, p8 d. r
IT0=1; //INT0负跳变触发
! R2 p e" O( B% F4 f( ]' S, | TMOD=0x01;//定时器工作于方式1
, E9 q/ Y9 F8 Q TH0=0x3c; //50ms
) C& a4 V( I! @! S3 L. ~( g TL0=0xb0;5 |5 m0 g! B/ d/ ^
EA=1; //CPU开中断总允许
( V9 r) F7 z3 }3 r8 x3 U ET0=1;//开定时中断/ h' s0 x# f0 T1 ^) L3 s
EX0=1;//开外部INTO中断
- L4 }* Q) e( W TR0=1;//启动定时3 W1 x, Q C, Y; P
}
# r. \1 S) ~& {/********液晶写入指令函数与写入数据函数,以后可调用**************/; l8 z( Q' a5 u: x5 o$ q) N, x
. l# z) A( Q7 Q' Y; U5 p1 k3 i: Ivoid write_1602com(uchar com)//****液晶写入指令函数****/ t& Y' Z$ ]. o1 x: L
{' W0 g3 |7 X9 X5 K$ j
rs=0;//数据/指令选择置为指令
$ A Y+ M7 l5 d- g& e Y P0=com;//送入数据
3 o0 e0 o o! N# {3 Q8 M, ]0 J3 e delay(1);2 x' J9 t5 q4 L% F. I
en=1;//拉高使能端,为制造有效的下降沿做准备
5 B/ R2 R% j9 ~& P# R' H) \) _# s delay(1);
. s: u8 Z4 c* Q8 } en=0;//en由高变低,产生下降沿,液晶执行命令
' A) i j* o( w- y" X/ D1 R1 L% F& L8 f: B0 E& g
}
% m6 `$ i) l4 V$ w; ]) X5 w% x* e5 n! ?
]2 p, R- i+ }, a& t! c
void write_1602dat(uchar dat)//***液晶写入数据函数****) y$ O4 ]) O* B9 R. O. ?4 ^
{
! U) D- J" t% S4 a rs=1;//数据/指令选择置为数据
5 D! u# R' ~5 y8 J' e% j9 z6 z P0=dat;//送入数据
0 p8 e5 J+ Y0 Q9 x" R0 N* k delay(1);
4 b/ Z+ F F0 j8 a+ G en=1; //en置高电平,为制造下降沿做准备6 a3 j! T9 V$ |1 I
delay(1);+ I- w' e* [; E9 a$ @, p5 \
en=0; //en由高变低,产生下降沿,液晶执行命令( \/ P. J0 ^( H
}
5 B- _9 A- k% v4 r6 Y3 y. m- x6 o2 A% G
4 `3 M+ Q& `) Z+ y
void lcd_init()//***液晶初始化函数****
' C7 i+ b; D5 T% M r{% v* b3 n- Z. ?8 q: b
uchar a;
2 X& K) e' V8 J* i8 z write_1602com(0x38);//设置液晶工作模式,意思:16*2行显示,5*7点阵,8位数据) ^& }7 L$ @% n
write_1602com(0x0c);//开显示不显示光标
4 K* G& A# \' c+ b# B3 U4 k7 D8 T6 h write_1602com(0x06);//整屏不移动,光标自动右移
! e* d" [& e9 e. T/ E; n write_1602com(0x01);//清显示
) j2 D! c0 n9 \' V( O& ]: G! _) b4 C5 j- K+ t" }5 k, J
write_1602com(0x80);//显示固定符号从第一行第1个位置之后开始显示
3 f8 n3 \/ m0 \ for(a=0;a<16;a++)5 G$ }# Q ~( V U* [3 |
{, _5 L* Z- s h
write_1602dat(tab1[a]);//向液晶屏写固定符号部分8 v K4 N2 s- G! y ]4 ]% d% J
}
8 |7 E; p% i$ T) K) s write_1602com(0x80+0x40);//显示固定符号写入位置,从第2个位置后开始显示/ k3 ^' A# w: Q& H, ?+ P' ]
for(a=0;a<16;a++)
0 V, B& H* ?0 m/ n {1 g$ J5 e7 V/ D( n4 r8 X
write_1602dat(tab2[a]);//写显示固定符号
9 t( t4 Y! n' Q% p& f- Q& ] }- d& Z( A8 |( o, U. T
}
% t3 B/ s. r) t7 R/ g2 K/ R, _3 a. n
void display()+ N- H- X. ^. n0 E6 b1 k1 e0 @
{
( Z/ @2 q; L2 H( U0 E- s // 1km/h=100m/0.1h 360s
* r6 [& I# D" \% o6 p. R6 T // 10km/h=100m/0.01h 36s
2 s# V. h( y. H: A // 100km/h=100m/0.001h 3.6s
, s" V, x" \, k
) i: j# t- Q/ @! z) s$ | write_1602com(0x80+9);( [5 ^1 h3 ~% q1 }+ e
if(Velocity/100==0)
1 V1 q r6 c' Z% c0 G8 p! ~8 a write_1602dat(' ');) s* `: j/ H+ T) `% W9 }6 ]
else/ Y: F9 l1 l6 l5 M
write_1602dat(0x30+Velocity/100);( k2 p+ q4 z4 i8 h
if((Velocity/100+Velocity%100/10)==0)2 c9 L2 ?' R3 z
write_1602dat(' ');) z$ N+ Q9 b1 Y: f$ ]
else) z& ~0 K" V8 `, j* d
write_1602dat(0x30+Velocity%100/10);
# g( O, W( X' w, [ R write_1602dat(0x30+Velocity%10);//数字+30得到该数字的LCD1602显示码
9 R& K5 `0 D: U. S& w* D1 Y9 T- v. a/ G
write_1602com(0x80+0x40+8);% n9 ?9 O2 t L0 B) {
write_1602dat(0x30+Mileage/1000000);//数字+30得到该数字的LCD1602显示码* C; }- S; g* U' Q" j# @0 j6 M
write_1602dat(0x30+Mileage%1000000/100000);//数字+30得到该数字的LCD1602显示码
7 F! e1 `! F5 P6 r write_1602com(0x80+0x40+11);
# h1 H/ `; J: E1 w4 J# e m. k& c0 l5 g write_1602dat(0x30+Mileage%100000/10000);//数字+30得到该数字的LCD1602显示码
$ g& G4 {& ]: b, k write_1602dat(0x30+Mileage%10000/1000);//数字+30得到该数字的LCD1602显示码$ G1 O9 |) q7 P5 m
N7 t" Z- x& U& L8 m+ s: U7 y
write_1602dat(0x30+Mileage%1000/100);//数字+30得到该数字的LCD1602显示码0 [4 E( t: V5 Q9 W
}8 R' h; W* y7 h7 }! R
) J$ g$ `6 l* g9 p: Zvoid main()2 O$ a, `0 d! h1 ?
{
0 m6 h' M! k( T0 B init();
" M7 q2 a' X. E2 @8 k( _: D lcd_init();6 L* x- C: s5 f" ^+ Z" U+ J3 K* j6 v
while(1)' J7 U1 B, H5 N+ B7 Z
{" n2 N$ q1 o2 D
display();
6 q' B) S$ s$ Y$ D- _) P }/ \# l3 D" a7 S, k
}6 e& D4 D# S+ q5 w' s
W) ]" X: \! x' H& S- _3 gvoid EXINT0() interrupt 0
$ S( H# L6 T. a3 v2 j; w5 m{
6 V. c, V6 G- p& f count++;* n* f& V* W+ k1 \, t# z
}
( @/ y7 ], c/ ?& i2 \# C. G- _8 y% W3 I
void time0() interrupt 1
2 w( \9 M' u6 y5 a' w{) O7 D. y2 {# o0 G
uchar m;
( h2 U- d% R+ H TH0=0x3c;
c% x0 Z( V8 j; _* j! S TL0=0xb0; //50ms
# d& N/ [4 s' d% a m++;
% {2 y i9 X& x% t f ^8 J if(m>=10)' }8 b J, G3 a7 {
{
- T, o( D+ t, k J) }3 a5 ^. W3 F m=0;
9 ?6 E( e" n: o2 A! m6 x Mileage=Mileage+Velocity*500/36; //里程m=速度km/h*1000*5/3.6
! }! _! R9 d2 I6 ^5 K Velocity=count/5;//将100ms内的脉冲数
( f5 J/ L) Q) h$ f3 [5 Y count=0;
4 v& T4 ~( ~! o; P% ?5 X) o0 n8 c/ z) x+ U' c6 V8 l! ^1 M
( {' m% R; ^5 J, ?9 Y( A* [. S/ U
…………限于本文篇幅 余下代码请从论坛下载附件…………
: Y! X7 k' G9 U' v1 W: D! f
* j( l1 D1 h+ Z& C+ d | 4 `' J8 N0 n8 e
|
|