|
EDA365欢迎您登录!
您需要 登录 才可以下载或查看,没有帐号?注册
x
51单片机学习:利用ADC0804模数转换器采集电压7 }! q5 l* [: `, y3 r. D
* @8 k% y- M2 U6 B2 k
9 ^4 ~- y& i# A9 o. D电位器调节待检测电压值,在数码管上显示出来,. L% n0 g! a7 W- c+ b/ [" a
代码大多从书上搬过来的,书上例5.3.1要求前3个数码管显示AD转换后的8位数字量(即0~255)& p! P# h9 g# j& ?+ V" l8 P" |
我这里让前4个数码管显示具体电压值,比如1.352; A7 g: o, m$ ^, e# u5 j- u
! J2 P( Q, K' j% s" W0 w
" @5 Y5 A8 m% y) g3 {1 ~+ n+ D #include <reg52.h> : l5 R% a0 C; k t0 [; g) E
#include "MY51.H"
. F5 h! r% F0 N1 K/ h/ p! j0 M
+ q& \: U+ E% g3 @- G void initSMG() //数码管初始化信息 j, f, A& u9 C" C( x9 s: C0 J
{
# R: a! b/ x9 ]' u# B0 h: N //上电时,都为高电平
2 H4 ~/ w" t% Z1 u P0=0xff;
. M6 _. ^6 G( O wela=open; 7 L. O( }9 }* P+ J6 I
P0=0xff; $ K4 S8 N+ S! J! B, A6 v5 X! N
wela=lock; 8 {$ @4 t- a% t& I
& G0 ]$ w8 i' F; }( r2 y8 a D5 |5 H P0=0; " T+ i! _$ H5 A
dula=open; # Z" Y. x& k: e& m; e/ [! L- X
P0=0; $ ^* B2 X, H( n# ]% S) g' E+ ?- J
dula=lock; % X& [7 B( ~& Y) V; |
} ' ~$ A+ J3 ~# X1 x' |3 z- ?
+ u4 n# T0 h6 n, ^
void ADC0804_csToLow() //cs置低电平 & s" ?1 n/ m3 M/ [9 A
{ " g! [; V X+ _/ y
wela=open; //打开锁存器 9 Z$ S4 R% K7 f0 k# z' a
P0=0x7f; //锁存器最高位送0,也就是CSAD置0
' c" g' m; V- S; j5 q, i Q wela=lock;
! b T* m& R: f4 E2 m- ~ }
; S W6 ?+ y0 H v! Z( X
8 |* e3 C! d9 a. J void ADC0804_startConvert() //P3.6口是wr,由高到底,再拉高后,ad开始转换
$ H1 C% L: P7 u; ?$ }2 U! O { 0 b, M# m* T7 k( F6 h' c5 a9 v
adwr=high; //虽然原本就是高的,但我们要养成好习惯,该是什么就是什么
4 L9 ]$ e2 R' {, {) b6 G# y9 H( g _nop_();
9 Q5 ~8 x, E8 u- a, r7 d& @/ t adwr=low; //wr置低后,过小会后AD内部开始执行转换,转换完成后INTR自动置低触发中断 $ p; p( S3 G o' W' J
_nop_();
p+ c$ t+ U) g adwr=high; 1 \0 Q0 s" d( H6 y
//由于我们用的不是150pF电容,而是104pF,所以转换比较慢,在调用本函数后最好延时10毫秒以上 4 d2 ?3 G4 g. u
} 6 C" F1 A& ^7 k0 ^
6 d( j/ m0 G7 s3 n) P
uint8 ADC0804_readResult() //读转换结果
, }7 u0 o3 r% s" G Q# b; v2 g {
& f/ y' o3 J7 i o& [3 g# U1 r" J uint8 result=0;
& I9 k1 f" w* n% Y8 Y/ q5 z //延时一会儿,转换就完成了,由于我们将INTR和CS都拉低了,直接操作RD后就可以读了 C. k% {5 `' ~' `/ V* t
P1=0xff; //防止由于转换未完成原因引起的误读
8 |- j. k$ h$ {$ o4 A8 P( B8 ^% \ adrd=high; % W8 N9 m2 w S* }7 i2 f+ P
_nop_(); 9 x9 ] B/ g5 a. [3 X# d! M
adrd=low; //rd置低电平后数据总线P1口得到数据,并由led显示现象
% @" _+ q4 ?; y" t# x! ?- x/ A" w! w _nop_();
" Y4 P6 X1 z+ D. f1 ^( l result=P1; 1 [/ K" L0 Y b7 P# U
adrd=high;
% @$ {8 o, k7 ~ //读完以后,如果ad芯片不用了,就把cs拉高,注销片选 1 y' L9 J" j7 K5 S9 n
return result;
) k5 Z% _& z3 O. J, y: k$ A } ) R* `- c2 ] ]" }" ^+ O7 P
6 Q" t- w8 R; Y3 r l; F6 ?* o void show(uint8 value) //基准电压是2.5V 为了计算方便扩大到2500 # l n( Q" z$ q* B
{ ' K: \6 s8 e. h* C5 w
uint16 temp=value*(2500/255.0); //扩大到4位整数,小数点另外附加显示 # H/ f m" }' a5 u% h
uint8 oneWela,twoWela,threeWela,fourWela; //oneWela是最左边的数码管
$ y1 [+ X( ~5 U: k+ S. |8 I oneWela=temp/1000;
( I5 n5 f2 E! h, e twoWela=temp%1000/100;
4 ~" ~2 I: }5 b* k7 _) r threeWela=temp%100/10;
. |0 A" [8 @7 [2 ~* G8 R" l3 r0 e fourWela=temp%10;
8 p0 R2 R# T1 F* ^ displaySMG(oneWela,twoWela,threeWela,fourWela,dark,dark,dotTable[1]); //最左边的数码管显示小数点 1 w8 @( a2 o7 Q0 W% E2 x* Y
}
2 C5 c5 P( O4 }! |7 F' H H4 n7 d- A$ }1 O2 M
void main() 8 ?" q, p9 ~" k
{
' [1 O: E `# x C; F9 E. K, E& V) {( j2 z. {/ q }2 s& S
uchar i=0;
6 @" a& ?: ^5 a/ f ~( ~* }. d uchar adTemp=0; - ^# M- ]. I7 f9 _8 U& _
initSMG(); //数码管数据初始化
! x' P. {3 b6 c2 Y* l6 P6 ? ADC0804_csToLow(); //cs置低
9 y/ \9 C2 J2 j3 F while(1)
N4 t% [) }$ y- r4 A7 T& e {
8 E& n' O! q8 W; X9 s ADC0804_startConvert(); //开始将电压数据转换成数字信号 ) ~' n" Q0 e" ~* m3 ]
for(i=5;i>0;i--) //主要是延时一段时间,让ad完成转换 8 v* j- \4 h3 [- N8 b. f7 C
{ " J" h: h g" I7 E% E+ H
delayms(1); $ w1 R7 J' e* p2 A5 Z
show(adTemp); //延时的时候,数码管继续动态显示 # N S0 M7 y4 m. n+ x$ Y
}
& Y# q7 n T( Z; W* f; h7 ^ adTemp=ADC0804_readResult(); //读取数据
9 @5 C7 g" M- H: y8 s show(adTemp); 4 V$ y5 T' z& n5 _* W
} * h* m6 o4 B# t6 p
} 4 Q/ q2 U+ h2 J+ q7 L% ]
( v. N/ m" A J8 _: C9 M. q
+ v: }& O+ K- ^. @" w5 _# A- W3 Y; c% E3 S3 ]
- N* k9 s" q: o% E1 f9 e' x
' d/ \ ` Z2 v- q5 Q8 o
( t5 `3 y% X! M9 y# W+ f# s3 l |
|