找回密码
 立即注册

QQ登录

只需一步,快速开始

搜索
查看: 2598|回复: 4
收起左侧

为什么单片机按键两侧全为高电平?怎么改成左侧低电平?

[复制链接]
ID:495312 发表于 2019-3-25 14:35 | 显示全部楼层 |阅读模式
电路原理图如下:
P]ALRXYIUJZ1~0NR89XX5.png

单片机源程序如下:
  1. #include<REG51.h>
  2. #include<intrins.h>
  3. #defineLCM_Data  P0
  4. #define ucharunsigned char
  5. #define uint  unsigned int
  6. #define w 6                                  //定义密码位数
  7. sbit lcd1602_rs=P2^7;
  8. sbitlcd1602_rw=P2^6;
  9. sbitlcd1602_en=P2^5;
  10. sbit Scl=P3^4;                      //24C02串行时钟
  11. sbit Sda=P3^5;                     //24C02串行数据
  12. sbit ALAM = P2^1;              //报警        
  13. sbit KEY = P3^6;                 //开锁
  14. sbit open_led=P2^2;            //开锁指示灯
  15. bit  operation=0;                 //操作标志位
  16. bit  pass=0;                         //密码正确标志
  17. bit  ReInputEn=0;               //重置输入充许标志   
  18. bit  s3_keydown=0;           //3秒按键标志位
  19. bit  key_disable=0;             //锁定键盘标志
  20. unsigned charcountt0,second;     //t0中断计数器,秒计数器
  21. voidDelay5Ms(void);
  22. unsigned char codea[]={0xFE,0xFD,0xFB,0xF7};                                                                                                //控盘扫描控制表
  23. unsigned char codestart_line[]     = {"password:       "};
  24. unsigned char codename[]                  ={"===Coded Lock==="};                                                                                                   //显示名称
  25. unsigned char codeCorrect[]       = {"     correct   "};                                                                                             //输入正确
  26. unsigned char codeError[]         = {"      error     "};                                                                                            //输入错误
  27. unsigned char codecodepass[]     = {"      pass     "};
  28. unsigned char codeLockOpen[]  = {"      open     "};                                                                                                     //OPEN
  29. unsigned char codeSetNew[]      ={"SetNewWordEnable"};
  30. unsigned char codeInput[]        = {"input:         "};                                                                                                       //INPUT
  31. unsigned char codeResetOK[]    = {"ResetPasswordOK"};
  32. unsigned char codeinitword[]      = {"Initpassword..."};
  33. unsigned char codeEr_try[]                  ={"error,try again!"};
  34. unsigned char codeagain[]           = {"inputagain     "};
  35. unsigned charInputData[6];                                                                                                                                            //输入密码暂存区
  36. unsigned char CurrentPassword[6]={1,3,1,4,2,0};                                                                                                                           //当前密码值
  37. unsigned charTempPassword[6];
  38. unsigned char N=0;                               //密码输入位数记数
  39. unsigned charErrorCont;                      //错误次数计数
  40. unsigned charCorrectCont;                   //正确输入计数
  41. unsigned charReInputCont;                          //重新输入计数
  42. unsigned char codeinitpassword[6]={0,0,0,0,0,0};
  43. //=====================5ms延时==============================
  44. void Delay5Ms(void)
  45. {
  46.          unsigned int TempCyc = 5552;
  47.          while(TempCyc--);
  48. }
  49. //===================400ms延时==============================
  50. voidDelay400Ms(void)
  51. {
  52. unsigned char TempCycA = 5;
  53. unsigned int TempCycB;
  54. while(TempCycA--)
  55. {
  56.   TempCycB=7269;
  57.   while(TempCycB--);
  58. }
  59. }
  60. //=============================================================================================
  61. //================================24C02========================================================
  62. //=============================================================================================
  63. void mDelay(uint t)//延时
  64. {
  65.          uchar i;
  66.        while(t--)
  67.      {
  68.                for(i=0;i<125;i++)
  69.                {;}
  70.        }
  71. }
  72.    void Nop(void)                //空操作
  73. {
  74.         _nop_();
  75.         _nop_();
  76.         _nop_();
  77.         _nop_();
  78. }
  79. /*起始条件*/
  80. void Start(void)
  81. {
  82.         Sda=1;
  83.         Scl=1;
  84.         Nop();
  85.         Sda=0;
  86.         Nop();
  87. }
  88. /*停止条件*/
  89. void Stop(void)
  90. {
  91.         Sda=0;
  92.         Scl=1;
  93.         Nop();
  94.         Sda=1;
  95.         Nop();
  96. }
  97. /*应答位*/
  98. void Ack(void)
  99. {
  100.          Sda=0;
  101.          Nop();
  102.          Scl=1;
  103.          Nop();
  104.        Scl=0;
  105. }
  106. /*反向应答位*/
  107. void NoAck(void)
  108. {
  109.         Sda=1;
  110.         Nop();
  111.         Scl=1;
  112.         Nop();
  113.         Scl=0;
  114. }
  115. /*发送数据子程序,Data为要求发送的数据*/
  116. void Send(ucharData)
  117. {
  118.        ucharBitCounter=8;
  119.        uchartemp;
  120.        do
  121.        {
  122.                temp=Data;
  123.                Scl=0;
  124.                Nop();
  125.                if((temp&0x80)==0x80)
  126.                Sda=1;
  127.                else
  128.                Sda=0;
  129.                Scl=1;
  130.                temp=Data<<1;
  131.                Data=temp;
  132.                BitCounter--;
  133.        }
  134.        while(BitCounter);
  135.        Scl=0;
  136. }
  137. /*读一字节的数据,并返回该字节值*/
  138. uchar Read(void)
  139. {
  140.     uchar temp=0;
  141.          uchar temp1=0;
  142.          uchar BitCounter=8;
  143.          Sda=1;
  144.          do{
  145.          Scl=0;
  146.        Nop();
  147.          Scl=1;
  148.          Nop();
  149.          if(Sda)
  150.          temp=temp|0x01;
  151.          else
  152.          temp=temp&0xfe;
  153.          if(BitCounter-1)
  154.          {
  155.          temp1=temp<<1;
  156.          temp=temp1;
  157.          }
  158.          BitCounter--;
  159.          }
  160.          while(BitCounter);
  161.          return(temp);
  162.          }
  163. void WrToROM(ucharData[],uchar Address,uchar Num)
  164. {
  165.   uchar i;
  166.   uchar *PData;
  167.   PData=Data;
  168.   for(i=0;i<Num;i++)
  169.   {
  170.   Start();
  171.   Send(0xa0);
  172.   Ack();
  173.   Send(Address+i);
  174.   Ack();
  175.   Send(*(PData+i));
  176.   Ack();
  177.   Stop();
  178.   mDelay(20);
  179.   }
  180. }
  181. voidRdFromROM(uchar Data[],uchar Address,uchar Num)
  182. {
  183.   uchar i;
  184.   uchar *PData;
  185.   PData=Data;
  186.   for(i=0;i<Num;i++)
  187.   {
  188.   Start();
  189.   Send(0xa0);
  190.   Ack();
  191.   Send(Address+i);
  192.   Ack();
  193.   Start();
  194.   Send(0xa1);
  195.   Ack();
  196.   *(PData+i)=Read();
  197.   Scl=0;
  198.   NoAck();
  199.   Stop();
  200.   }
  201. }
  202. //==================================================================================================
  203. //=======================================LCD1602====================================================
  204. //==================================================================================================
  205. #define yi 0x80//LCD第一行的初始位置,因为LCD1602字符地址首位D7恒定为1(100000000=80)
  206. #define er0x80+0x40 //LCD第二行初始位置(因为第二行第一个字符位置地址是0x40)
  207. //----------------延时函数,后面经常调用----------------------
  208. void delay(uintxms)//延时函数,有参函数
  209. {
  210.          uint x,y;
  211.          for(x=xms;x>0;x--)
  212.           for(y=110;y>0;y--);
  213. }
  214. //--------------------------写指令---------------------------
  215. write_1602com(ucharcom)//****液晶写入指令函数****
  216. {
  217.          lcd1602_rs=0;//数据/指令选择置为指令
  218.          lcd1602_rw=0; //读写选择置为写
  219.          P0=com;//送入数据
  220.          delay(1);
  221.          lcd1602_en=1;//拉高使能端,为制造有效的下降沿做准备
  222.          delay(1);
  223.          lcd1602_en=0;//en由高变低,产生下降沿,液晶执行命令
  224. }

  225. //-------------------------写数据-----------------------------
  226. write_1602dat(uchardat)//***液晶写入数据函数****
  227. {
  228.          lcd1602_rs=1;//数据/指令选择置为数据
  229.          lcd1602_rw=0; //读写选择置为写
  230.          P0=dat;//送入数据
  231.          delay(1);
  232.          lcd1602_en=1; //en置高电平,为制造下降沿做准备
  233.          delay(1);
  234.          lcd1602_en=0; //en由高变低,产生下降沿,液晶执行命令
  235. }
  236. //-------------------------初始化-------------------------
  237. void lcd_init(void)
  238. {
  239.          write_1602com(0x38);//设置液晶工作模式,意思:16*2行显示,5*7点阵,8位数据
  240.          write_1602com(0x0c);//开显示不显示光标
  241.          write_1602com(0x06);//整屏不移动,光标自动右移
  242.          write_1602com(0x01);//清显示
  243. }
  244. //========================================================================================
  245. //=========================================================================================
  246. //==============将按键值编码为数值=========================
  247. unsigned char coding(unsignedchar m)         
  248. {
  249.          unsigned char k;
  250.          
  251.          switch(m)
  252.          {
  253.                   case (0x11): k=1;break;
  254.                   case (0x21): k=2;break;
  255.                   case (0x41): k=3;break;
  256.                   case (0x81): k='A';break;
  257.                   case (0x12): k=4;break;
  258.                   case (0x22): k=5;break;
  259.                   case (0x42): k=6;break;
  260.                   case (0x82): k='B';break;
  261.                   case (0x14): k=7;break;
  262.                   case (0x24): k=8;break;
  263.                   case (0x44): k=9;break;
  264.                   case (0x84): k='C';break;
  265.                   case (0x18): k='*';break;
  266.                   case (0x28): k=0;break;
  267.                   case (0x48): k='#';break;
  268.                   case (0x88): k='D';break;
  269.          }
  270.          return(k);
  271. }
  272. //=====================按键检测并返回按键值===============================
  273. unsigned charkeynum(void)
  274. {
  275.         unsignedchar row,col,i;
  276.         P1=0xf0;
  277.         if((P1&0xf0)!=0xf0)
  278.         {
  279.                Delay5Ms();
  280.         Delay5Ms();
  281.                if((P1&0xf0)!=0xf0)
  282.                   {
  283.                row=P1^0xf0;          //确定行线
  284.                           i=0;
  285.                           P1=a[ i];              //[ i]精确定位
  286.                           while(i<4)
  287.                           {
  288.                                    if((P1&0xf0)!=0xf0)
  289.                                  {
  290.                                          col=~(P1&0xff);          //确定列线
  291.                                          break;            //已定位后提前退出   
  292.                                  }
  293.                                    else
  294.                                  {
  295.                                          i++;
  296.                                          P1=a[ i];
  297.                                  }
  298.                           }
  299.                   }
  300.                   else
  301.                   {
  302.                           return 0;
  303.                   }
  304.               while((P1&0xf0)!=0xf0);
  305.        return (row|col);                       //行线与列线组合后返回
  306.         }
  307.         elsereturn 0;                          //无键按下时返回0
  308. }
  309. //=======================一声提示音,表示有效输入========================
  310. void OneAlam(void)
  311. {
  312.          ALAM=0;
  313.          Delay5Ms();
  314.     ALAM=1;
  315. }
  316. //========================二声提示音,表示操作成功========================
  317. void TwoAlam(void)
  318. {
  319.          ALAM=0;
  320.          Delay5Ms();
  321.     ALAM=1;
  322.     Delay5Ms();
  323.          ALAM=0;
  324.          Delay5Ms();
  325.     ALAM=1;
  326. }
  327. //========================三声提示音,表示错误========================
  328. voidThreeAlam(void)
  329. {
  330.          ALAM=0;
  331.          Delay5Ms();
  332.     ALAM=1;
  333.     Delay5Ms();
  334.          ALAM=0;
  335.          Delay5Ms();
  336.     ALAM=1;
  337.     Delay5Ms();
  338.          ALAM=0;
  339.          Delay5Ms();
  340.     ALAM=1;

  341. }
  342. //=====================显示输入的N个数字,用H代替以便隐藏============================
  343. voidDisplayOne(void)
  344. {
  345. //       DisplayOneChar(9+N,1,'*');
  346.          write_1602com(yi+5+N);
  347.          write_1602dat('*');
  348. }
  349. //=======================显示提示输入=========================
  350. voidDisplayChar(void)
  351. {
  352.          unsigned char i;
  353.          if(pass==1)
  354.          {
  355.                   //DisplayListChar(0,1,LockOpen);
  356.                   write_1602com(er);
  357.                   for(i=0;i<16;i++)
  358.                   {
  359.                           write_1602dat(LockOpen[ i]);      
  360.                   }
  361.          }
  362.          else
  363.          {
  364.                   if(N==0)
  365.                   {
  366.                           //DisplayListChar(0,1,Error);
  367.                           write_1602com(er);
  368.                           for(i=0;i<16;i++)
  369.                           {
  370.                                    write_1602dat(Error[ i]);      
  371.                           }
  372.                   }
  373.                   else
  374.                   {
  375.                           //DisplayListChar(0,1,start_line);  
  376.                           write_1602com(er);
  377.                           for(i=0;i<16;i++)
  378.                           {
  379.                                    write_1602dat(start_line[ i]);         
  380.                           }
  381.                   }
  382.          }
  383. }

  384. voidDisplayInput(void)
  385. {
  386.          unsigned char i;
  387.          if(CorrectCont==1)
  388.          {
  389.                   //DisplayListChar(0,0,Input);
  390.                   write_1602com(er);
  391.                   for(i=0;i<16;i++)
  392.                   {
  393.                           write_1602dat(Input[ i]);      
  394.                   }
  395.          }
  396. }


  397. //========================重置密码==================================================
  398. //==================================================================================
  399. voidResetPassword(void)
  400. {
  401.          unsigned char i;  
  402.          unsigned char j;
  403.          if(pass==0)
  404.          {
  405.                   pass=0;
  406.                   DisplayChar();
  407.                   ThreeAlam();
  408.          }
  409.          else
  410.          {
  411.       if(ReInputEn==1)
  412.                   {
  413.                           if(N==6)
  414.                           {
  415.                                    ReInputCont++;                           
  416.                                    if(ReInputCont==2)
  417.                                    {
  418.                                             for(i=0;i<6;)
  419.                                             {
  420.                                                      if(TempPassword[ i]==InputData[ i])      //将两次输入的新密码作对比
  421.                                                              i++;
  422.                                                      else
  423.                                                      {
  424.                                                              //DisplayListChar(0,1,Error);
  425.                                                              write_1602com(er);
  426.                                                              for(j=0;j<16;j++)
  427.                                                              {
  428.                                                                       write_1602dat(Error[j]);      
  429.                                                              }
  430.                                                              ThreeAlam();                       //错误提示
  431.                                                              pass=0;
  432.                                                              ReInputEn=0;                      //关闭重置功能,
  433.                                                              ReInputCont=0;
  434.                                                              DisplayChar();
  435.                                                              break;
  436.                                                      }
  437.                                             }
  438.                                             if(i==6)
  439.                                             {
  440.                                                      //DisplayListChar(0,1,ResetOK);
  441.                                                      write_1602com(er);
  442.                                                      for(j=0;j<16;j++)
  443.                                                      {
  444.                                                              write_1602dat(ResetOK[j]);         
  445.                                                      }

  446.                                                      TwoAlam();                                  //操作成功提示
  447.                                                     WrToROM(TempPassword,0,6);           //将新密码写入24C02存储
  448.                                                      ReInputEn=0;
  449.                                             }
  450.                                             ReInputCont=0;
  451.                                             CorrectCont=0;
  452.                                    }
  453.                                    else
  454.                                    {
  455.                                             OneAlam();
  456.                                             //DisplayListChar(0,1, again);              //显示再次输入一次
  457.                                             write_1602com(er);
  458.                                             for(j=0;j<16;j++)
  459.                                             {
  460.                                                      write_1602dat(again[j]);      
  461.                                             }                                          
  462.                                             for(i=0;i<6;i++)
  463.                                             {
  464.                                                      TempPassword[ i]=InputData[ i];            //将第一次输入的数据暂存起来                                             
  465.                                             }
  466.                                    }

  467.                           N=0;                                             //输入数据位数计数器清零
  468.                      }
  469.             }
  470.          }

  471. }



  472. //=======================输入密码错误超过三过,报警并锁死键盘======================
  473. voidAlam_KeyUnable(void)
  474. {
  475.          P1=0x00;
  476.          {
  477.                   ALAM=~ALAM;
  478.                   Delay5Ms();
  479.          }
  480. }


  481. //=======================取消所有操作============================================
  482. void Cancel(void)
  483. {      
  484.          unsigned char i;
  485.          unsigned char j;
  486.          //DisplayListChar(0, 1, start_line);
  487.          write_1602com(er);
  488.          for(j=0;j<16;j++)
  489.          {
  490.                   write_1602dat(start_line[j]);         
  491.          }
  492.          TwoAlam();                                  //提示音
  493.          for(i=0;i<6;i++)
  494.          {
  495.                   InputData[ i]=0;
  496.          }
  497.          KEY=1;                                        //关闭锁
  498.          ALAM=1;                                     //报警关
  499.          operation=0;                        //操作标志位清零
  500.          pass=0;                                         //密码正确标志清零
  501.          ReInputEn=0;                      //重置输入充许标志清零
  502.          ErrorCont=0;                       //密码错误输入次数清零
  503.          CorrectCont=0;                    //密码正确输入次数清零
  504.          ReInputCont=0;                   //重置密码输入次数清零
  505.          open_led=1;
  506.          s3_keydown=0;
  507.          key_disable=0;
  508.          N=0;                                    //输入位数计数器清零
  509. }


  510. //==========================确认键,并通过相应标志位执行相应功能===============================
  511. void Ensure(void)
  512. {      
  513.          unsigned char i,j;
  514.          RdFromROM(CurrentPassword,0,6);                                       //从24C02里读出存储密码
  515.     if(N==6)
  516.          {
  517.             if(ReInputEn==0)                                                              //重置密码功能未开启
  518.                   {
  519.                           for(i=0;i<6;)
  520.                         {                                          
  521.                                    if(CurrentPassword[ i]==InputData[ i])
  522.                                    {
  523.                                             i++;
  524.                                    }
  525.                                    else
  526.                                    {                        
  527.                                             ErrorCont++;
  528.                                             if(ErrorCont==3)                          //错误输入计数达三次时,报警并锁定键盘
  529.                                             {
  530.                                                      write_1602com(er);
  531.                                                      for(i=0;i<16;i++)
  532.                                                      {
  533.                                                              write_1602dat(Error[ i]);      
  534.                                                      }
  535.                                                      do
  536.                                                      Alam_KeyUnable();
  537.                                                      while(1);
  538.                                             }
  539.                                             else
  540.                                             {
  541.                                                      TR0=1;                                //开启定时
  542.                                                      key_disable=1;                    //锁定键盘
  543.                                                      pass=0;
  544.                                                      break;
  545.                                             }
  546.                                    }
  547.                           }

  548.                           if(i==6)
  549.                           {
  550.                                    CorrectCont++;
  551.                                    if(CorrectCont==1)                               //正确输入计数,当只有一次正确输入时,开锁,
  552.                                    {
  553.                                             //DisplayListChar(0,1,LockOpen);
  554.                                             write_1602com(er);
  555.                                             for(j=0;j<16;j++)
  556.                                             {
  557.                                                      write_1602dat(LockOpen[j]);      
  558.                                             }
  559.                                             TwoAlam();                         //操作成功提示音
  560.                                             KEY=0;                                                                                            //开锁
  561.                                             pass=1;                                                                                             //置正确标志位
  562.                                             TR0=1;                                                                                             //开启定时
  563.                                             open_led=0;                                                                                      //开锁指示灯亮
  564.                                             for(j=0;j<6;j++)                                                               //将输入清除
  565.                                             {
  566.                                                      InputData[ i]=0;
  567.                                             }
  568.                                    }      
  569.                                    else                                                                                                   //当两次正确输入时,开启重置密码功能
  570.                                    {
  571.                                             //DisplayListChar(0,1,SetNew);
  572.                                             write_1602com(er);
  573.                                             for(j=0;j<16;j++)
  574.                                             {
  575.                                                      write_1602dat(SetNew[j]);  
  576.                                             }
  577.                                             TwoAlam();                                                                                  //操作成功提示
  578.                                             ReInputEn=1;                                                                           //允许重置密码输入
  579.                                             CorrectCont=0;                                                                        //正确计数器清零
  580.                                    }
  581.                         }
  582.          
  583.                           else                    //=========================当第一次使用或忘记密码时可以用131420对其密码初始化============
  584.                           {
  585.                            if((InputData[0]==1)&&(InputData[1]==3)&&(InputData[2]==1)&&(InputData[3]==4)&&(InputData[4]==2)&&(InputData[5]==0))
  586.                                  {
  587.                                             WrToROM(initpassword,0,6);                               //强制将初始密码写入24C02存储
  588.                                             //DisplayListChar(0,1,initword);                    //显示初始化密码
  589.                                             write_1602com(er);
  590.                                             for(j=0;j<16;j++)
  591.                                             {
  592.                                                      write_1602dat(initword[j]);
  593.                                             }
  594.                                             TwoAlam();
  595.                                             Delay400Ms();
  596.                                             TwoAlam();
  597.                                             N=0;
  598.                                    }
  599.                                    else
  600.                                    {
  601.                                             //DisplayListChar(0,1,Error);
  602.                                             write_1602com(er);
  603.                                             for(j=0;j<16;j++)
  604.                                             {
  605.                                                      write_1602dat(Error[j]);      
  606.                                             }
  607.                                            ThreeAlam();                                                                                    //错误提示音
  608.                                             pass=0;      
  609.                                    }
  610.                           }
  611.                   }

  612.                   else                                                                                          //当已经开启重置密码功能时,而按下开锁键,
  613.                   {
  614.                           //DisplayListChar(0,1,Er_try);
  615.                           write_1602com(er);
  616.                           for(j=0;j<16;j++)
  617.                           {
  618.                                    write_1602dat(Er_try[j]);     
  619.                           }
  620.                           ThreeAlam();
  621.                   }
  622.          }

  623.          else
  624.          {
  625.                   //DisplayListChar(0,1,Error);
  626.                   write_1602com(er);
  627.                   for(j=0;j<16;j++)
  628.                   {
  629.                           write_1602dat(Error[j]);      
  630.                   }

  631.                  ThreeAlam();                                                                                    //错误提示音
  632.                   pass=0;      
  633.          }
  634.          N=0;                                                                                                          //将输入数据计数器清零,为下一次输入作准备
  635.   operation=1;
  636. }
  637. //==============================主函数===============================
  638. void main(void)
  639. {
  640.         unsignedchar KEY,NUM;
  641.          unsigned char i,j;
  642.         P1=0xFF;
  643.          TMOD=0x11;
  644.         TL0=0xB0;
  645.         TH0=0x3C;
  646.         EA=1;
  647.         ET0=1;      
  648.         TR0=0;
  649.         Delay400Ms(); //启动等待,等LCM讲入工作状态
  650.         lcd_init(); //LCD初始化
  651.          write_1602com(yi);//日历显示固定符号从第一行第0个位置之后开始显示
  652.          for(i=0;i<16;i++)
  653.          {
  654.                   write_1602dat(name[ i]);//[ i]向液晶屏写日历显示的固定符号部分
  655.          }
  656.          write_1602com(er);//时间显示固定符号写入位置,从第2个位置后开始显示
  657.          for(i=0;i<16;i++)
  658.          {
  659.                   write_1602dat(start_line[ i]);//[ i]写显示时间固定符号,两个冒号
  660.          }
  661.          write_1602com(er+9);         //设置光标位置
  662.          write_1602com(0x0f);        //设置光标为闪烁
  663.         Delay5Ms();//延时片刻(可不要)

  664.         N=0;                                                                                                                   //初始化数据输入位数
  665.         while(1)
  666.                                    NUM=coding(KEY);
  667.                                    {
  668.                                             switch(NUM)
  669.                                             {
  670.                                                      case('A'):          ;                                          break;
  671.                                                      case('B'):           ;                                       break;
  672.                                                      case('C'):  ;                                          break;
  673.                                                      case('D'): ResetPassword();         break;      //重新设置密码
  674.                                                      case('*'): Cancel();                               break;      //取消当前输入
  675.                                                      case('#'): Ensure();                               break;      //确认键,
  676.                                                      default:
  677.                                                      {      
  678.                                                              //DisplayListChar(0,1,Input);
  679.                                                              write_1602com(er);
  680.                                                              for(i=0;i<16;i++)
  681.                                                              {
  682.                                                                       write_1602dat(Input[ i]);
  683.                                                              }
  684.                                                          operation=0;
  685.                                                              if(N<6)                                                              //当输入的密码少于6位时,接受输入并保存,大于6位时则无效。
  686.                                                              {  
  687.                                                                       OneAlam();                                                                     //按键提示音                                                  
  688.                                                                       //DisplayOneChar(6+N,1,'*');
  689.                                                                       for(j=0;j<=N;j++)
  690.                                                                       {
  691.                                                                                write_1602com(er+6+j);
  692.                                                                                write_1602dat('*');
  693.                                                                       }
  694.                                                                       InputData[N]=NUM;
  695.                                                                       N++;
  696.                                                              }
  697.                                                              else                                                                                  //输入数据位数大于6后,忽略输入
  698.                                                              {
  699.                                                                       N=6;
  700.                                                                       break;
  701.                                                              }
  702.                                                      }
  703.                                             }
  704.                                    }
  705.                           }
  706.                  //}
  707.          //}
  708. //}

  709. //*********************************中断服务函数**************************************
  710. void  time0_int(void) interrupt 1
  711. {
  712.         TL0=0xB0;
  713.         TH0=0x3C;      if(countt0==20)
  714.        {
  715.                   countt0=0;
  716.                   second++;
  717.                   if(pass==1)
  718.                   {
  719.                           if(second==1)
  720.                           {
  721.                                    open_led=1;                        //关指示灯
  722.                                    TR0=0;                                //关定时器
  723.                                    TL0=0xB0;
  724.                                   TH0=0x3C;
  725.                                    second=0;
  726.                           }
  727.                   }
  728.                   else
  729.                   {
  730.                           if(second==3)
  731.                           {
  732.                                    TR0=0;
  733.                                    second=0;
  734.                                    key_disable=0;   
  735.                                    s3_keydown=0;
  736.                                    TL0=0xB0;
  737.                                    TH0=0x3C;
  738.                           }
  739.                           else
  740.                               TR0=1;
  741.                   }
  742.                           
  743.        }
  744. }
复制代码


回复

使用道具 举报

ID:365802 发表于 2019-3-25 18:58 | 显示全部楼层
鍵盤掃描電路空閒狀態應該就是高電平呀, 掃描時控制行線或列線為低電平進行掃描.
回复

使用道具 举报

ID:466164 发表于 2019-3-25 22:00 | 显示全部楼层
你的问题很奇怪你程序里不是 if((P1&0xf0)!=0xf0)把P1口高4位变成高了,低四位变成低了啊!按键检测必须给行列给不同电平否则怎么检测。
回复

使用道具 举报

ID:213173 发表于 2019-3-26 07:34 | 显示全部楼层
只要矩阵键盘扫描程序运行正常,不必计较仿真显示的电平高低。因为扫描速度很快,仿真显示的不一定准确。不信你写一个简单的流水灯程序试试,描速度快了仿真就乱套,但用于实际电路是正常的。
回复

使用道具 举报

ID:495312 发表于 2019-3-28 11:23 | 显示全部楼层
7358655 发表于 2019-3-25 22:00
你的问题很奇怪你程序里不是 if((P1&0xf0)!=0xf0)把P1口高4位变成高了,低四位变成低了啊!按键检测必须给 ...

那不是应该一边低电平跟一边高电平吗?两边都高,按钮按下没反应了。
回复

使用道具 举报

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

本版积分规则

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

Powered by 单片机教程网

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