找回密码
 立即注册

QQ登录

只需一步,快速开始

搜索
查看: 2147|回复: 1
打印 上一主题 下一主题
收起左侧

单片机计算器程序数码管显示及38k遥控cd1602显示遥控键值读取

[复制链接]
跳转到指定楼层
楼主
38k遥控器

全部代码下载: 38k红外遥控器(用).rar (14.75 KB, 下载次数: 12)

单片机计算器程序 数码管显示:
  1. #include<reg51.h>
  2. #include<math.h>
  3. #define   uchar   unsigned  char
  4. #define   uint    unsigned   int
  5. #define   ulong   unsigned  long
  6. uchar code tab[]={0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90,0x06,0xbf};//共阳极
  7. ulong  num=0,qnum=0;
  8. uchar  key0=0,ikey0=0,kkey=0;   //qnum为前一个键值,当为0时表示没有前一个键值,ikey0表示当存在前一个键值下进行加减乘除运算
  9. //uchar  num1,num2,num3,num4,num5,num6;  //key0表示当为1时,是数字键,为0时,是清零键,为2时,是运算键,为3时,等号键
  10. void  delay(uint d)                    
  11. {
  12.      while(d-->0);
  13. }

  14. void  error()    //当数值溢出的时候                       
  15. {   
  16.      P2 = 0x00;
  17.      P2 = 0xff;
  18.      P0 = tab[10];
  19.      delay(100);
  20.      P2 = 0x00;
  21.      P0 = 0xff;
  22. }
  23. void  display(ulong num0)   //显示函数
  24. {
  25.      if(num0>999999&&num0<-99999)                      //当数值溢出时
  26.           error();
  27.      else if(num0>=0&&num0<=999999)                         //当数值为正数时
  28.      {
  29.           P2 = 0x00;
  30.           dis1 = 1;     //显示最高位,第一位
  31.           P0 = tab[num0/100000];
  32.           delay(100);
  33.           dis1 = 0;
  34.           P0 = 0xff;
  35.          
  36.           P2 = 0x00;
  37.           dis2 = 1;       //第二位
  38.           P0 = tab[(num0/10000)%10];
  39.           delay(100);
  40.           dis2 = 0;
  41.           P0 = 0xff;
  42.          
  43.          
  44.           P2 = 0x00;
  45.           dis3 = 1;       //第三位
  46.           P0 = tab[(num0/1000)%10];
  47.           delay(100);
  48.           dis3 = 0;
  49.           P0 = 0xff;
  50.          
  51.           P2 = 0x00;
  52.           dis4 = 1;         //第四位
  53.           P0 = tab[(num0/100)%10];
  54.           delay(100);
  55.           dis4 = 0;
  56.           P0 = 0xff;
  57.          
  58.           P2 = 0x00;
  59.           dis5 = 1;        //第五位
  60.           P0 = tab[(num0/10)%10];
  61.           delay(100);
  62.           dis5 = 0;
  63.           P0 = 0xff;
  64.          
  65.           P2 = 0x00;
  66.           dis6 = 1;        //显示最低位,第六位
  67.           P0 = tab[num0%10];
  68.           delay(100);
  69.           dis6 = 0;
  70.           P0 = 0xff;
  71.       }
  72.       else                             //当数值为负数时
  73.       {
  74.           num0 = abs(num0);
  75.           P2 = 0x00;
  76.           dis1 = 1;     //显示最高位,第一位
  77.           P0 = tab[11];
  78.           delay(100);
  79.           dis1 = 0;
  80.           P0 = 0xff;
  81.          
  82.           P2 = 0x00;
  83.           dis2 = 1;       //第二位
  84.           P0 = tab[(num0/10000)%10];
  85.           delay(100);
  86.           dis2 = 0;
  87.           P0 = 0xff;
  88.          
  89.          
  90.           P2 = 0x00;
  91.           dis3 = 1;       //第三位
  92.           P0 = tab[(num0/1000)%10];
  93.           delay(100);
  94.           dis3 = 0;
  95.           P0 = 0xff;
  96.          
  97.           P2 = 0x00;
  98.           dis4 = 1;         //第四位
  99.           P0 = tab[(num0/100)%10];
  100.           delay(100);
  101.           dis4 = 0;
  102.           P0 = 0xff;
  103.          
  104.           P2 = 0x00;
  105.           dis5 = 1;        //第五位
  106.           P0 = tab[(num0/10)%10];
  107.           delay(100);
  108.           dis5 = 0;
  109.           P0 = 0xff;
  110.          
  111.           P2 = 0x00;
  112.           dis6 = 1;        //显示最低位,第六位
  113.           P0 = tab[num0%10];
  114.           delay(100);
  115.           dis6 = 0;
  116.           P0 = 0xff;         
  117.       }
  118. }

  119. void  key()         //键盘扫描函数
  120. {
  121.      uchar  temp;
  122.      P1 = 0xff;
  123.      P1 = 0Xef;   //检测第一行
  124.      temp = P1;
  125.      temp = temp&0x0f;
  126.      if(P1!=0X0f)
  127.      {
  128.           delay(5);
  129.           temp = P1;
  130.           temp = temp&0x0f;
  131.           if(P1!=0X0f)
  132.           {
  133.                temp = P1;

  134.                switch(temp)
  135.                {
  136.                     case 0xe7:  key0 = 0; break;                  //-----清屏键
  137.                     case 0xeb:  key0 = 1; num = num*10+0; kkey = 1; break;  //-------'0'
  138.                     case 0xed:  key0 = 3; break;                  //-----等号键=
  139.                     case 0xee:  key0 = 2; ikey0 = 10; break;      //------加号键+
  140.                }
  141.          
  142.           while(temp!=0x0f)
  143.           {
  144.                temp = P1;
  145.                temp = temp&0x0f;
  146.           }
  147.           //P0 = tab[h];
  148.          }
  149.      }


  150.      P1 = 0xff;
  151.      P1 = 0Xdf;   //检测第二行
  152.      temp = P1;
  153.      temp = temp&0x0f;
  154.      if(P1!=0X0f)
  155.      {
  156.           delay(5);
  157.           temp = P1;
  158.           temp = temp&0x0f;
  159.           if(P1!=0X0f)
  160.           {
  161.                temp = P1;

  162.                switch(temp)
  163.                {
  164.                     case 0xd7:  key0 = 1; num = num*10+1; kkey = 1; break;   //------'1'
  165.                     case 0xdb:  key0 = 1; num = num*10+2; kkey = 1; break;   //------'2'
  166.                     case 0xdd:  key0 = 1; num = num*10+3; kkey = 1; break;   //-------'3'
  167.                     case 0xde:  key0 = 2; ikey0 = 11; break;       //-----减号键-
  168.                }
  169.          
  170.           while(temp!=0x0f)
  171.           {
  172.                temp = P1;
  173.                temp = temp&0x0f;
  174.           }
  175.           //P0 = tab[h];
  176.          }
  177.      }


  178.      P1 = 0xff;
  179.      P1 = 0Xbf;   //检测第三行
  180.      temp = P1;
  181.      temp = temp&0x0f;
  182.      if(P1!=0X0f)
  183.      {
  184.           delay(5);
  185.           temp = P1;
  186.           temp = temp&0x0f;
  187.           if(P1!=0X0f)
  188.           {
  189.                temp = P1;

  190.                switch(temp)
  191.                {
  192.                     case 0xb7:  key0 = 1; num = num*10+4; kkey = 1; break;    //-------'4'
  193.                     case 0xbb:  key0 = 1; num = num*10+5; kkey = 1; break;    //-------'5'
  194.                     case 0xbd:  key0 = 1; num = num*10+6; kkey = 1; break;    //-------'6'
  195.                     case 0xbe:  key0 = 2; ikey0 = 12; break;        //------乘号键*
  196.                }
  197.          
  198.           while(temp!=0x0f)
  199.           {
  200.                temp = P1;
  201.                temp = temp&0x0f;
  202.           }
  203.           //P0 = tab[h];
  204.          }
  205.      }


  206.      P1 = 0xff;
  207.      P1 = 0X7f;   //检测第四行
  208.      temp = P1;
  209.      temp = temp&0x0f;
  210.      if(P1!=0X0f)
  211.      {
  212.           delay(5);
  213.           temp = P1;
  214.           temp = temp&0x0f;
  215.           if(P1!=0X0f)
  216.           {
  217.                temp = P1;
  218.                
  219.                switch(temp)
  220.                {
  221.                     case 0x77:  key0 = 1; num = num*10+7; kkey = 1; break;     //-------'7'
  222.                     case 0x7b:  key0 = 1; num = num*10+8; kkey = 1; break;     //--------'8'
  223.                     case 0x7d:  key0 = 1; num = num*10+9; kkey = 1; break;     //--------'9'
  224.                     case 0x7e:  key0 = 2; ikey0 = 13; break;         //-------除号键
  225.                     
  226.                }
  227.          
  228.           while(temp!=0x0f)
  229.           {
  230.                temp = P1;
  231.                temp = temp&0x0f;
  232.           }
  233.          }
  234.      }
  235.               
  236. }

  237. void  count()
  238. {
  239.      key();
  240.      if(key0 == 0)         //清零
  241.      {
  242.           num = 0;qnum = 0;
  243.           display(num);
  244.      }
  245.      else  if(key0 == 1)       //数字键,显示数字
  246.      {     
  247.           display(num);
  248.          
  249.      }
  250.      else if(key0 == 8)
  251.      {
  252.           display(qnum);
  253.      }
  254.      else if(key0 == 2)        //当为运算符号键时
  255.      {
  256.           qnum = num;
  257.           num = 0;
  258.           key0 = 8;
  259.                
  260.      }
  261.      else if(key0 == 3)        //等号键
  262.      {
  263.           switch(ikey0)
  264.                {
  265.                     case 10:num = num + qnum;  key0 = 2; break;
  266.                     case 11:num = qnum - num;  key0 = 2; break;
  267.                     case 12:num = num * qnum;  key0 = 2; break;
  268.                     case 13:num = qnum / num;  key0 = 2; break;
  269.                     //default  break;
  270.                }        
  271.           //}
  272.      }

  273. }

  274.          
  275. void  main()
  276. {    while(1)
  277.      {   
  278.           //display(num);
  279.           count();
  280.      }     
  281. }

复制代码



  1. /********************************************************************************
  2. *                                                                              *
  3. *         lcd1602显示遥控键值读取                                              *
  4. *         lcd1602显示 红外接收头接p3.2                                         *
  5. *         蜂鸣器接p3.7                                                         *
  6. *                                                                              *
  7. ********************************************************************************/

  8. #include <reg51.h>
  9. #include <intrins.h>

  10. #define uchar unsigned char
  11. #define uint  unsigned int
  12. #define delayNOP(); {_nop_();_nop_();_nop_();_nop_();};

  13. void delay(uchar x);  //x*0.14MS
  14. void delay1(int ms);
  15. void beep();

  16. sbit IRIN = P3^2;         //红外接收器数据线
  17. //sbit BEEP = P3^7;         //蜂鸣器驱动线


  18. uchar IRCOM[7];

  19. sbit LCD_RS = P2^1;            
  20. sbit LCD_RW = P2^2;
  21. sbit LCD_EN = P2^3;

  22. uchar code  cdis1[ ] = {" Remote Control "};
  23. uchar code  cdis2[ ] = {"  IR-CODE: --H  "};

  24. /*******************************************************************/
  25. /*                                                                 */
  26. /*检查LCD忙状态                                                    */
  27. /*lcd_busy为1时,忙,等待。lcd-busy为0时,闲,可写指令与数据。      */
  28. /*                                                                 */
  29. /*******************************************************************/

  30. bit lcd_busy()
  31. {                          
  32.     bit result;
  33.     LCD_RS = 0;
  34.     LCD_RW = 1;
  35.     LCD_EN = 1;
  36.     delayNOP();
  37.     result = (bit)(P0&0x80);
  38.     LCD_EN = 0;
  39.     return(result);
  40. }

  41. /*******************************************************************/
  42. /*                                                                 */
  43. /*写指令数据到LCD                                                  */
  44. /*RS=L,RW=L,E=高脉冲,D0-D7=指令码。                             */
  45. /*                                                                 */
  46. /*******************************************************************/

  47. void lcd_wcmd(uchar cmd)

  48. {                          
  49.    while(lcd_busy());
  50.     LCD_RS = 0;
  51.     LCD_RW = 0;
  52.     LCD_EN = 0;
  53.     _nop_();
  54.     _nop_();
  55.     P0 = cmd;
  56.     delayNOP();
  57.     LCD_EN = 1;
  58.     delayNOP();
  59.     LCD_EN = 0;  
  60. }

  61. /*******************************************************************/
  62. /*                                                                 */
  63. /*写显示数据到LCD                                                  */
  64. /*RS=H,RW=L,E=高脉冲,D0-D7=数据。                               */
  65. /*                                                                 */
  66. /*******************************************************************/

  67. void lcd_wdat(uchar dat)
  68. {                          
  69.    while(lcd_busy());
  70.     LCD_RS = 1;
  71.     LCD_RW = 0;
  72.     LCD_EN = 0;
  73.     P0 = dat;
  74.     delayNOP();
  75.     LCD_EN = 1;
  76.     delayNOP();
  77.     LCD_EN = 0;
  78. }

  79. /*******************************************************************/
  80. /*                                                                 */
  81. /*  LCD初始化设定                                                  */
  82. /*                                                                 */
  83. /*******************************************************************/

  84. void lcd_init()
  85. {
  86.     delay1(15);                  
  87.     lcd_wcmd(0x38);      //16*2显示,5*7点阵,8位数据
  88.     delay1(5);
  89.     lcd_wcmd(0x38);         
  90.     delay1(5);
  91.     lcd_wcmd(0x38);         
  92.     delay1(5);

  93.     lcd_wcmd(0x0c);      //显示开,关光标
  94.     delay1(5);
  95.     lcd_wcmd(0x06);      //移动光标
  96.     delay1(5);
  97.     lcd_wcmd(0x01);      //清除LCD的显示内容
  98.     delay1(5);
  99. }

  100. /*******************************************************************/
  101. /*                                                                 */
  102. /*  设定显示位置                                                   */
  103. /*                                                                 */
  104. /*******************************************************************/

  105. void lcd_pos(uchar pos)
  106. {                          
  107.   lcd_wcmd(pos | 0x80);  //数据指针=80+地址变量
  108. }

  109. /*******************************************************************/
  110. main()
  111. {
  112.    uchar m;
  113.    
  114.     IRIN=1;                    //I/O口初始化
  115.     //BEEP=1;
  116.        
  117.     delay1(10);                 //延时
  118.     lcd_init();                //初始化LCD            
  119.         
  120.     lcd_pos(0);                //设置显示位置为第一行的第1个字符

  121.      m = 0;
  122.     while(cdis1[m] != '\0')
  123.      {                         //显示字符
  124.        lcd_wdat(cdis1[m]);
  125.        m++;
  126.      }

  127.     lcd_pos(0x40);             //设置显示位置为第二行第1个字符
  128.      m = 0;
  129.     while(cdis2[m] != '\0')
  130.      {
  131.        lcd_wdat(cdis2[m]);      //显示字符
  132.        m++;
  133.      }


  134.         IE = 0x81;                 //允许总中断中断,使能 INT0 外部中断
  135.         TCON = 0x01;               //触发方式为脉冲负边沿触发

  136.    while(1)        ;

  137. } //end main
  138. /**********************************************************/
  139. void IR_IN() interrupt 0 using 0
  140. {
  141.   unsigned char j,k,N=0;
  142.      EX0 = 0;   
  143.          delay(15);
  144.          if (IRIN==1)
  145.      { EX0 =1;
  146.            return;
  147.           }
  148.                            //确认IR信号出现
  149.   while (!IRIN)            //等IR变为高电平,跳过9ms的前导低电平信号。
  150.     {delay(1);}

  151. for (j=0;j<4;j++)         //收集四组数据
  152. {
  153.        for (k=0;k<8;k++)        //每组数据有8位
  154.        {
  155.              while (IRIN)            //等 IR 变为低电平,跳过4.5ms的前导高电平信号。
  156.                {delay(1);}
  157.               while (!IRIN)          //等 IR 变为高电平
  158.                {delay(1);}
  159.                while (IRIN)           //计算IR高电平时长
  160.                 {
  161.                    delay(1);
  162.                    N++;           
  163.                    if (N>=30)
  164.                         {
  165.                           EX0=1;
  166.                              return;
  167.                      }                  //30*0.14ms=4.2ms计数过长自动离开。
  168.                 }                        //高电平计数完毕               
  169.                IRCOM[j]=IRCOM[j] >> 1;                  //数据最高位补“0”
  170.                if (N>=8) {IRCOM[j] = IRCOM[j] | 0x80;}  //数据最高位补“1”
  171.                N=0;
  172.        }//end for k
  173. }//end for j
  174.    
  175.    if (IRCOM[2]!=~IRCOM[3])
  176.    {
  177.      EX0=1;
  178.      return;
  179.    }

  180.    IRCOM[5]=IRCOM[2] & 0x0F;     //取键码的低四位
  181.    IRCOM[6]=IRCOM[2] >> 4;       //右移4次,高四位变为低四位

  182.    if(IRCOM[5]>9)                  //将16进制数用ASCLL码中的字符表示
  183.     { IRCOM[5]=IRCOM[5]+0x37;}
  184.    else
  185.           IRCOM[5]=IRCOM[5]+0x30;    //0x30是ASCLL码的’0‘

  186.    if(IRCOM[6]>9)
  187.     { IRCOM[6]=IRCOM[6]+0x37;}
  188.    else
  189.           IRCOM[6]=IRCOM[6]+0x30;

  190.      lcd_pos(0x4b);            
  191.      lcd_wdat(IRCOM[6]);        //第一位数显示
  192.      lcd_pos(0x4c);            
  193.      lcd_wdat(IRCOM[5]);        //第二位数显示

  194.      //beep();
  195.      EX0 = 1;
  196. }

  197. /**********************************************************/
  198. /*void beep()
  199. {
  200.   unsigned char i;
  201.   for (i=0;i<100;i++)
  202.    {
  203.    delay(4);
  204.    BEEP=!BEEP;                 //BEEP取反
  205.    }
  206.   BEEP=1;                      //关闭蜂鸣器
  207. }*/
  208. /**********************************************************/
  209. void delay(unsigned char x)    //x*0.14MS
  210. {
  211. unsigned char i;
  212.   while(x--)
  213. {
  214.   for (i = 0; i<13; i++) {}
  215. }
  216. }

  217. /**********************************************************/
  218. void delay1(int ms)
  219. {
  220. unsigned char y;
  221.   while(ms--)
  222. {
  223.   for(y = 0; y<250; y++)
  224.   {
  225.    _nop_();
  226.    _nop_();
  227.    _nop_();
  228.    _nop_();
  229.   }
  230. }
  231. }

复制代码


评分

参与人数 1黑币 +50 收起 理由
admin + 50 共享资料的黑币奖励!

查看全部评分

分享到:  QQ好友和群QQ好友和群 QQ空间QQ空间 腾讯微博腾讯微博 腾讯朋友腾讯朋友
收藏收藏1 分享淘帖 顶 踩
回复

使用道具 举报

沙发
ID:240693 发表于 2017-10-21 15:40 | 只看该作者
可以运行吗
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

手机版|小黑屋|51黑电子论坛 |51黑电子论坛6群 QQ 管理员QQ:125739409;技术交流QQ群281945664

Powered by 单片机教程网

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