找回密码
 注册
关于网站域名变更的通知
查看: 625|回复: 1
打印 上一主题 下一主题

51单片机加法器的制作

[复制链接]

该用户从未签到

跳转到指定楼层
1#
发表于 2019-1-16 06:30 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式

EDA365欢迎您登录!

您需要 登录 才可以下载或查看,没有帐号?注册

x
51单片机加法器的制作" `3 i: P+ H' b+ }/ r" |9 t
% y. A1 U3 e+ k6 }6 M% r

. {5 Q6 ?/ ~# F完成数码管显示,按键相加的要求" S; x$ B  J' i, A- ^, [, W
此程序的电路图下载:

. L5 g. w5 X* y8 q  w; c5 X9 u
游客,如果您要查看本帖隐藏内容请回复

0 c) c5 R, W6 _: t: T' ]# k# p! H  ]9 d- D' f: G6 V" [
' n6 @* p" ?: E; _8 T6 _
只需要看数码管部分即可,其他部分可忽略掉. 2 C7 w5 t# e/ c8 c
! m' ~* Y' E( _# S, K- P
代码如下#include<reg52.h>
6 B" p" y1 D7 o, h, F# H' w. b
. q+ t( B! z- E& V

- U) K8 N- U# q! r' T3 J. Y1 Z1 Qsbit ADDR0 = P1^0;
) F. c, _- v9 i, v' J# L# nsbit ADDR1 = P1^1;
4 _2 D7 G6 o6 `8 Y7 S& csbit ADDR2 = P1^2;2 h( I: d  a, ~( i5 A
sbit ADDR3 = P1^3;
3 U0 W6 f# O2 R- T/ ?sbit ENLED = P1^4;
5 R. U1 k. \/ I, R4 u* E
) l* e! `3 |$ s

& v: A9 P+ @' n) bsbit KEY_IN_1 = P2^4;
+ l6 O( I5 M' v7 r; Z, [sbit KEY_IN_2 = P2^5;
1 e  {% G" e8 Z0 g7 G. zsbit KEY_IN_3 = P2^6;; B) o/ Z; [* j8 E- w2 @" M) C& @) {- S
sbit KEY_IN_4 = P2^7;' y% L. O: S- W( |
sbit KEY_OUT_1 = P2^3;1 ~0 ]2 }6 i0 Q; N) {
sbit KEY_OUT_2 = P2^2;+ v" x, X7 u* m+ t' ^
sbit KEY_OUT_3 = P2^1;
* h# e  {( V+ w$ Fsbit KEY_OUT_4 = P2^0;
+ o6 M. V$ V# b  L" e! v' [' p& q
3 B# A! ^- b  `* b8 d( Z

8 c6 F  l) p- T" n; m! ]unsigned char code LedChar[]={
- a" ]3 w% ^- `3 T2 e7 s2 @# t        0xC0, 0xF9, 0xA4, 0xB0, 0x99, 0x92, 0x82, 0xF8,
: d# i0 @! V% {/ q) M& H2 [1 |        0x80, 0x90, 0x88, 0x83, 0xC6, 0xA1, 0x86, 0x8E0 Y# K% E1 {( N; K. Q1 Y  V
        };3 t  {& m8 E; B* O) S$ T! I
unsigned char KeySta[4][4] = {
$ w7 S! B0 o6 T: y, k7 T# t        {1,1,1,1},{1,1,1,1},{1,1,1,1},{1,1,1,1}5 q+ l  P2 P9 }4 h7 }: M2 }
        };
* W) T8 ^( v3 C& \unsigned char LedBuff[6] = {
# X$ S) p: X# l: R5 [4 E: s        0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF
! s" E+ q+ D( _) F        };) ?) A6 z6 o5 V5 a  {0 L! s& X
unsigned char code KeyCodeMap[4][4] = { //矩阵按键编号到标准键盘键码的映射表4 A0 J( j; K) _8 y* M# n1 x; n! P
    { 0x31, 0x32, 0x33, 0x26 }, //数字键1、数字键2、数字键3、向上键
8 E5 c) u. j( L# n+ X  `    { 0x34, 0x35, 0x36, 0x25 }, //数字键4、数字键5、数字键6、向左键$ g1 ?2 R* H: `# t
    { 0x37, 0x38, 0x39, 0x28 }, //数字键7、数字键8、数字键9、向下键5 b" P; P: r0 L- @7 N
    { 0x30, 0x1B, 0x0D, 0x27 }  //数字键0、ESC键、  回车键、 向右键' E) M8 G- D5 _" K5 S% e9 S
        };
1 J* Q# ]4 X( G' Evoid  KeyDriver();/ A; C+ v; D% F( H% b) [
void main()
) t& L' i: C8 t7 E( v( m( S- g( X6 O{
7 L3 ?; Q. L$ q+ G, c    EA = 1;       //使能总中断7 U) m  P; k; y5 ^& y
    ENLED = 0;    //选择数码管进行显示3 L: s6 M9 e5 j! g; l
    ADDR3 = 1;4 E) |! d' D6 B) t# d
    TMOD = 0x01;  //设置T0为模式1) N; }0 M  y; @8 D. t6 c
    TH0  = 0xFC;  //为T0赋初值0xFC67,定时1ms: ~/ {+ x5 ]( w0 j' Q
    TL0  = 0x67;. p9 R2 L/ i2 K. @: N
    ET0  = 1;     //使能T0中断
+ n) I6 z& q( L7 M    TR0  = 1;     //启动T0# `1 M6 D, @; H  t& T+ |5 x& I: c3 c
    LedBuff[0] = LedChar[0];  //上电显示0
3 S  }6 ^+ C2 V. c$ E! t        ) d  c( ^# x( A3 t0 Y. J! |1 N6 i
    while (1)" t! u6 Y3 Z! k9 i7 G
    {
5 ^0 c7 B4 t# h6 D& g6 l( V        KeyDriver();   //调用按键驱动函数2 W/ B. l' {: [' \! D5 W7 v
    }! Q' d7 ~# p! T: Q+ p6 ?7 T
}4 b& K; `8 t9 v! L8 y8 U- L
) }" g+ E; F4 F6 \- ?) A- e

1 r# O( L6 f( S2 ~: V5 @- Evoid ShowNumber(unsigned long num)
( g; ]! n; ?0 R" W8 r3 W{
9 y% F# e$ u$ ]9 t        signed char i;* ?$ ^7 ~( Y# e1 t# r. n
        unsigned char buf[6];) c" R/ `+ L9 E' H: U6 S

$ G9 l4 I' v0 E* R6 C" {! p" N7 L7 a
, R# S) b9 A  O9 J9 d- i
        for(i=0; i<6; i++)+ S8 ~8 _8 b+ q* g# S0 W7 M
        {
' O9 ]! q" f2 h                buf = num % 10;3 @5 M7 F$ f: y  Y% a
                num = num / 10;
9 G. A& i& y& d6 Q6 L: B* p        }+ v! _5 W9 B. `8 m: u

3 x1 r! A; t* \2 g6 e* K

0 b5 W4 h- a& J! u3 y* L# T        for(i=5; i>=1; i--)  \\gaoweibuxianshi 0 \4 Y* f( X! w0 P( A' i1 @4 c
        {
/ \6 O: [; ?6 A7 f4 E5 Z9 ?                if(buf == 0)9 u; O2 m9 a" s1 u1 h
                {' v! M3 f3 t; o* z' q
                        LedBuff = 0xFF;
. w  `( I0 q1 `; _" w                }
$ r* d& K2 D8 K; i                else
4 N2 k: t1 h, o9 N                        break;
) Z. H3 v) [) e8 i6 A        }- A" X0 p0 e) d. K/ @& r/ f7 j
        
& x8 S0 w$ ^6 R8 j' g        for(; i>=0; i--) \\
% Y! Z2 J$ Y8 ?  S6 m3 F        {- B/ \2 A0 D: L( W# v$ F7 D3 g1 e9 q( A
                LedBuff = LedChar[buf];        
0 a1 Y8 g9 S. E. n5 e% `* o        }3 ]1 o! F0 o5 B* {4 m. B- B
5 R: ~& j/ y/ `

1 ~! d. m3 e/ k7 q6 X}3 s' ]4 b% m5 \- I8 b0 L+ e1 ?* D9 A
void KeyAction(unsigned char keycode)
' I" b/ S8 ]6 D* s{
( u# t1 q& g$ l" P8 o- V, M        static unsigned long result = 0;
6 }" |- Y$ x' p% M* v, x. W        static unsigned long addend = 0;
& [2 K3 h" n+ i+ Z8 @4 b        
6 y" B% q* E( l2 K2 `8 I        if((keycode >= 0x30) &&(keycode <= 0x39))( k1 |# S; x$ z1 v$ U; s( j9 U: Z0 D
        {/ u4 y, C' K& @6 k% R3 x) q
                addend = (addend *10) + (keycode - 0x30);   7 u  |' t" @9 ~8 v) u2 O
                ShowNumber(addend); - f5 Y/ }2 g; ~1 o+ I
        }( o; a; C8 c- o7 G1 \0 A
        
8 {4 Y+ E7 H$ G. q        else if(keycode == 0x26)" l: O$ r( o& h1 o+ }
        {# e! U: ^2 R. W% }, c/ ?
                result += addend;* L0 f; |" @! t+ C) B! o- q- s/ [* O
                addend = 0;" R  Z" E; N# w7 E. o1 a& j0 t4 l
                ShowNumber(result);
, u7 W; r9 u. W6 v' Z        }
( }: v7 v, O0 o9 m& N( B+ f        else if(keycode == 0x0D)% i5 a: C& d2 Y4 O) w* F% W5 c
        {
* I2 L, ]5 c& a1 N& m6 J                result += addend;; [2 K7 U9 s! f+ d0 I
                addend = 0;8 l2 [7 u( ~+ K7 J) _  {( w* S- b
                ShowNumber(result);
' [7 h7 ^" g) t3 i! A" z7 w5 a        }4 `. m( q% U6 {+ m4 b+ A, h1 m: F
        else if(keycode == 0x1B)8 v7 r7 l% T+ k+ E" _! c/ K4 ?! T
        {' Y& E% @! j4 K2 _" ^/ L" H8 E
                addend = 0;  w* }: s( m; ~% K% q
                result = 0;
1 b! h7 u) G# j                ShowNumber(addend);         
5 X' @2 a5 F! ~3 {* \3 m& g        }        
3 A& n$ p% E* ?* d2 B# f- n         ; q2 Q* R9 H  H$ v/ _* \
}
# \5 C& y# Z. `2 Avoid  KeyDriver()1 Y# R) D7 E4 j
{
: ?% J! k9 Q; u: b8 T+ b6 i        unsigned char i, j;9 M- _' ^+ l2 D& _' }: ]
        static        unsigned char backup [4][4] = {. q- x, l" K5 a# q! |: c
        {1,1,1,1},{1,1,1,1},{1,1,1,1},{1,1,1,1}; R  e' ]+ T" W- E4 Z, ?
        };
% d+ }# Z# l8 s# |( [
5 S& s+ E, g( G. l# ^
* j; K! t+ _" U- v  e0 p, r
        for(i=0; i<4; i++)( s; g4 {. _! k. _0 N
                {( Y. \, G: B- k2 d
                        for(j=0; j<4; j++)* b. S. y5 h. j( L) G  O
                        {
3 p* ~) h# E5 n+ U                                if(backup[j] != KeySta[j])8 y6 ]: A  ?) I1 @5 O3 X5 A, a' V
                                {
, m$ A4 X6 H5 ^6 _2 T- F/ f: ~                                        if(backup[j] == 0)
' C# t' `# r6 \, A9 w( p                                        {
- j& N; s  g* u5 V1 g                                                KeyAction(KeyCodeMap[j]);
- @5 y2 y; ]8 q7 B                                        }) S  f3 l/ F( p" ?
                                        backup[j] = KeySta[j];
5 C0 a, N- O; n' d                                }! m: Q% y; `7 R0 Q& P
                        }        8 w. p: ^0 r* o2 P2 }1 t4 x0 P, j
                }  `* u# \1 @# N9 e
. `3 s$ s) Y& E& e

1 O. ]6 S  v" G3 {6 W        : g8 P! i7 c9 j" p
}
! L  U6 O( C3 K8 W9 `) W. m# e0 t
; X9 D" d3 a8 k. X
9 x- L) Q. ]6 }: B
/* 按键扫描函数,需在定时中断中调用,推荐调用间隔1ms */
! l- Z8 a, V3 R* \- Jvoid KeyScan()! x. [1 y; E1 l: a+ r
{
5 I- l+ W: ^  B6 `& z9 S  J    unsigned char i;( o0 N1 F6 C2 z3 a8 Q# H4 q" m
    static unsigned char keyout = 0;   //矩阵按键扫描输出索引
* ]& j5 f$ ]0 u7 F! q    static unsigned char keybuf[4][4] = {  //矩阵按键扫描缓冲区6 F. V1 P: p1 z: I! J, }( e8 U8 B
        {0xFF, 0xFF, 0xFF, 0xFF},  {0xFF, 0xFF, 0xFF, 0xFF},! B0 W* ?7 ?4 j4 |# G0 X
        {0xFF, 0xFF, 0xFF, 0xFF},  {0xFF, 0xFF, 0xFF, 0xFF}
' P9 p" ]2 M" o    };7 z5 c6 z) d% }' C* b" H

% n1 @2 ~: ?3 j7 l

) W- s& \$ [0 R2 d    //将一行的4个按键值移入缓冲区
. s, S- @0 O8 Q& B# |9 E2 |5 s$ ^: K    keybuf[keyout][0] = (keybuf[keyout][0] << 1) | KEY_IN_1;
  f4 G' n6 U, g9 U) B    keybuf[keyout][1] = (keybuf[keyout][1] << 1) | KEY_IN_2;0 x8 w7 ?  C' H7 s! t6 s9 f; F& C
    keybuf[keyout][2] = (keybuf[keyout][2] << 1) | KEY_IN_3;
; A2 ?  d3 @+ S9 B/ F    keybuf[keyout][3] = (keybuf[keyout][3] << 1) | KEY_IN_4;
# ]) B* r) P4 _5 ~, R1 S8 n; L    //消抖后更新按键状态0 b) Y7 w* }/ @" [
    for (i=0; i<4; i++)  //每行4个按键,所以循环4次2 D: }+ N- a% A( }* [3 r! ^  [
    {
0 P/ U) J; z1 U) K& r" f  K        if ((keybuf[keyout] & 0x0F) == 0x00)2 s4 U5 D5 P. ~7 Z5 w; u9 b
        {   //连续4次扫描值为0,即4*4ms内都是按下状态时,可认为按键已稳定的按下  e' E) P; X, r, v* ?8 B6 W, ~
            KeySta[keyout] = 0;
, I% O, x& q5 Z4 G* ~9 d) |- r        }- F: y/ B0 z3 z
        else if ((keybuf[keyout] & 0x0F) == 0x0F)4 ?: R) F, U9 d3 p: e% F
        {   //连续4次扫描值为1,即4*4ms内都是弹起状态时,可认为按键已稳定的弹起
+ K1 ?5 W5 O2 R1 s9 W4 ^1 t            KeySta[keyout] = 1;
9 \6 P" y2 J% M7 W: w        }
, F: k0 k  u/ }    }9 H0 k' B7 d5 _* h. Y
    //执行下一次的扫描输出* B2 }- \" \' I
    keyout++;                //输出索引递增  f9 `3 Q3 ?8 ?8 ^. \" v: Z6 y
    keyout = keyout & 0x03;  //索引值加到4即归零
% `& Y; N& p- x. g* w    switch (keyout)          //根据索引,释放当前输出引脚,拉低下次的输出引脚
  Z' c6 W7 [# d2 W$ L    {- h2 o. K) w/ `! A; q) f3 r9 `
        case 0: KEY_OUT_4 = 1; KEY_OUT_1 = 0; break;
/ |3 F4 [5 u! D5 j8 o7 `        case 1: KEY_OUT_1 = 1; KEY_OUT_2 = 0; break;1 S3 V6 N7 e& I
        case 2: KEY_OUT_2 = 1; KEY_OUT_3 = 0; break;
, i8 y2 M8 `) P; s  ^3 q6 q        case 3: KEY_OUT_3 = 1; KEY_OUT_4 = 0; break;
" o+ N- l: Q( X* M        default: break;4 u) M8 U) T" U/ L- R7 u
    }
9 v, K) B7 ]+ y* e1 Z' u; p# B5 o8 F}! Q# @6 o& j" @
/* 数码管动态扫描刷新函数,需在定时中断中调用 */
5 s* B# p* n9 ^) @/ s: W& evoid LedScan()
4 U  W( g- ~5 G6 ]{( j' m! k: d3 C5 I
    static unsigned char i = 0;  //动态扫描的索引
, |5 F2 H& u7 Y' }! _4 J
% Q$ j5 t) C  r
) @  s  {0 z! F/ d" |
    P0 = 0xFF;   //显示消隐
6 X% H% v/ K3 e+ z& J    switch (i)
$ \4 a8 [! J& [" z3 ]% Z  X    {# D( I7 c# e. t  o
        case 0: ADDR2=0; ADDR1=0; ADDR0=0; i++; P0=LedBuff[0]; break;, L9 F4 d: l2 f4 ~
        case 1: ADDR2=0; ADDR1=0; ADDR0=1; i++; P0=LedBuff[1]; break;( i/ O/ u# ?6 L/ i1 x6 s/ [
        case 2: ADDR2=0; ADDR1=1; ADDR0=0; i++; P0=LedBuff[2]; break;
) I7 M" M/ f3 r% F        case 3: ADDR2=0; ADDR1=1; ADDR0=1; i++; P0=LedBuff[3]; break;
! O( t6 e& n6 I* w4 j! m3 n# Y        case 4: ADDR2=1; ADDR1=0; ADDR0=0; i++; P0=LedBuff[4]; break;3 W9 F! f4 Q2 h2 \9 E# C- {* W
        case 5: ADDR2=1; ADDR1=0; ADDR0=1; i=0; P0=LedBuff[5]; break;3 I) B* l4 Q3 [/ {* ?+ C3 W
        default: break;
2 O# R! Q4 s. ]2 d2 G# m    }5 P# `  u/ ?- b  P& J" r
}
: n5 B* l% \7 l* l- W# e; F5 S9 s1 _5 ]. ~3 x, {
6 |6 l- t) b; N+ Y! a2 Y
/* T0中断服务函数,用于数码管显示扫描与按键扫描 */
: [2 J9 N# v) [# k# q6 xvoid InterruptTimer0() interrupt 1
/ c) p( L6 n2 u$ \$ W{6 K; m$ g' J% y1 ~
        TH0 = 0xFC;* o5 C# k3 ]7 b- f- }
        TL0 = 0x67;
! P' A  D+ {% I4 J        LedScan();
+ g( P4 x1 `( F        KeyScan();
! H% N0 H4 Q" p: S4 C- X3 ]1 ^}# F; O" i7 ^6 R0 J
& B- a3 C  S- e! E, b6 w

7 q8 L/ W; m! d, ^. B

该用户从未签到

2#
发表于 2019-1-16 22:04 | 只看该作者
谢谢楼主分享
您需要登录后才可以回帖 登录 | 注册

本版积分规则

关闭

推荐内容上一条 /1 下一条

EDA365公众号

关于我们|手机版|EDA365电子论坛网 ( 粤ICP备18020198号-1 )

GMT+8, 2025-10-9 00:05 , Processed in 0.156250 second(s), 27 queries , Gzip On.

深圳市墨知创新科技有限公司

地址:深圳市南山区科技生态园2栋A座805 电话:19926409050

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