51單片機 | A/D轉換器實現數字電壓表實例


————————————————————————————————————————————

ADC0809

- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

工作原理:

  • ADDA/ADDB/ADDC 輸入3 位地址,並使ALE=1,將地址存入地址鎖存器中

    ALE:地址鎖存允許信號接入端,高電平時允許改變CBA的值,低電平時鎖死,防止在A/D轉換過程中切換通道

  • 地址經譯碼選通8路模擬輸入IN0~IN7之一到比較器,輸入與被選通道關系

通道

C

B

A

IN0

0

0

0

IN1

0

0

1

IN2

0

1

0

IN3

0

1

1

IN4

1

0

0

IN5

1

0

1

IN6

1

1

0

IN7

1

1

1

  • START端上升沿將逐次逼近寄存器復位,下降沿啟動A/D轉換
  • EOC輸出信號變低電平,表示正在轉換;當A/D轉換完成,EOC變為高電平,結果數據已存入鎖存器。
  • OE輸入高電平,輸出三態門打開,轉換結果的數字量輸出到數據總線上。

    OE=1時,D0-D7引腳上為轉換后的數據,當OE=0時,D0-D7為對外呈現高阻狀態

p.s.

其他引腳:

IN0~IN78路模擬量輸入引腳

CLK:時鍾信號輸入端

V_(REF(+)):參考電壓正端

V_(REF(-)):參考電壓負端

————————————————————————————————————————————

數字電壓表實驗

- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

實現效果:

  • 檢測外部模擬電壓,並用數字量將其電壓值表示出來

- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

實現思路:

  • A/D轉換
    • 初始化時啟動A/D轉換,轉換結束后OE自動置位
    • 檢查OE狀態,為高電平時讀取數據口數據並轉換成對應的電壓值
    • 顯示結束后啟動下一次A/D轉換
  • 數碼管顯示
    • 讀入數據並轉換成電壓值后,通過數碼管顯示,百位數值后顯示小數點

- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

連接說明:

ADC0808

OUT1-OUT8

89C51

P0.0-0.7

轉換后數據輸出到單片機

  

START

  

P3.0

  

  

EOC

  

P3.1

  

  

OE

  

P3.2

  

  

IN0

POT-HG

+

輸入模擬信號

  

ADDA/ADDB/ADDC/VREF(-)

GND

  

0 0 0 選擇通路IN0

  

ALE/VREF(+)

POWER

  

將地址存入地址鎖存器中

數碼管

1/2/3/4/5/6/7

89C51

P2

控制數碼管顯示位數

  

A/B/C/D/E/F/G/DP

  

P1

控制顯示段碼

- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

實現代碼:

 1 #include <reg52.h>
 2 typedef unsigned char uchar;
 3 typedef unsigned int uint;
 4 typedef unsigned long ulong;
 5 uchar code table[] =
 6 {
 7     0xfc, 0x60, 0xda, 0xf2, 0x66, 0xb6, 0xbe, 0xe0, 0xfe, 0xf6, 0xee, 0x3e, 0x9c, 0x7a, 0x9e, 0x8e
 8 };
 9 sbit start = P3 ^ 0; //控制start引腳
10 sbit eoc = P3 ^ 1; //查詢eoc引腳情況
11 sbit oe = P3 ^ 2; //輸出允許控制端
12 sbit dot = P1 ^ 0; //數碼管小數點
13 void Delay(uint m)
14 {
15     while(m--);
16 }
17 void main()
18 {
19     ulong temp, temp_data;
20     // uint temp;
21     start = 0;
22     oe = 0; //oe為高阻狀態
23     start = 1; //start下降沿開始轉換
24     start = 0;
25     while(1)
26     {
27         if (eoc == 1) //當eoc為1時轉換結束
28         {
29             /*讀入狀態*/
30             oe = 1; //打開oe,數據讀入引腳
31             temp = P0;
32             /*
33             讀入的數值轉換成模擬電壓對應的電壓值,由於ADC0809將0-5V平分為255份,每一份為5/255v,電壓=1.0v時,temp=1.0*(5/255),為了方便顯示小數,則擴大一百倍,得到公式temp=temp*1.0/255*500
34             但是在此處存在個問題,temp轉換成為flout類型后運算量過大,影響后數碼管顯示速度,在一定范圍內數碼管顯示錯誤
35             temp = temp * 1.0 / 255 * 500; → temp = temp * 500 / 255;
36             p.s. 修改后的temp要改成unsigned long, FF*500溢出int范圍
37             */
38             temp = temp * 500 / 255;
39             oe = 0; //oe呈高阻
40             /*數碼管顯示*/
41             temp_data = temp % 10;
42             P2 = 0xfe; //數碼管選擇最后一位
43             P1 = table[temp_data];
44             Delay(500);
45             temp_data = temp / 10 % 10;
46             P2 = 0xfd; //數碼管選擇十位
47             P1 = table[temp_data];
48             Delay(500);
49             temp_data = temp / 100 % 10;
50             P2 = 0xfb; //數碼管選擇百位
51             P1 = table[temp_data];
52             dot = 1; //顯示小數點
53             Delay(500);
54             /*啟動下一次轉換*/
55             start = 1;
56             start = 0;
57         }
58     }
59 }

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM