欧美极品高清xxxxhd,国产日产欧美最新,无码AV国产东京热AV无码,国产精品人与动性XXX,国产传媒亚洲综合一区二区,四库影院永久国产精品,毛片免费免费高清视频,福利所导航夜趣136

 找回密碼
 立即注冊

QQ登錄

只需一步,快速開始

搜索
查看: 6162|回復: 3
打印 上一主題 下一主題
收起左側

基于51單片機的4人搶答器代碼

[復制鏈接]
跳轉到指定樓層
樓主
ID:498742 發表于 2019-4-30 19:37 | 只看該作者 回帖獎勵 |倒序瀏覽 |閱讀模式
  1. /*
  2. 此程序為4人搶答器。
  3. 搶答者4人對應,K1-4的按鈕
  4. 裁判可操作Ks,Kr,Kc,Ka4個按鈕
  5. Ks:按下就進入搶答倒計時
  6. Kr:按下復位,準備下次搶答
  7. Kc,Ka:用于調整倒計時。
  8. 在復位之前使用,且當前的操作是對復位之后的倒計時有用
  9. 保證沒有人按下除了Kc,Ka之外的按鈕。
  10. 最大設置為1分鐘,最小10s
  11. 按一次Kc加1s
  12. 操作步驟:按下Kr,后要按住Ka不松的狀態按Kc加時間,然后再次按下Kr

  13. 顯示器第一行顯示倒計時的時間
  14. 例如:countdown:10s
  15. 顯示器第二行顯示違規者和搶答成功者的對應按鈕
  16. 例如:error:0 win:2  表示:無人違規,2號搶答成功
  17. 例如:error:2 win:0  表示:有人違規,2號違規
  18. */

  19. #include "reg52.h"
  20. #include "lcd.h"

  21. #define uchar unsigned char
  22. #define uint unsigned int

  23. sbit K1=P1^0;
  24. sbit K2=P1^1;
  25. sbit K3=P1^2;
  26. sbit K4=P1^3;
  27. sbit Ks=P3^0;   //按下就進入搶答倒計時
  28. sbit Kr=P3^2;   //按下復位,準備下次搶答
  29. sbit Kc=P3^3;   //按下調整倒計時,注意事項見timeset()
  30. sbit Ka=P3^4;   //配合Kc
  31. sbit beep=P3^7;
  32. sbit led=P3^1;

  33. uchar fallflag=0,sflag=0,jflag=0,sjflag=0;
  34. uchar win,time=10;     //time為倒計時秒數,num為程序中控制倒計時的變量,win為搶答成功的按鈕
  35. uchar num,numf;        //numf為配合num來顯示lcd

  36. uchar Disp1[16]="countdown:00s   ";
  37. uchar Disp2[16]="error:0 win:0   ";

  38. void judge();
  39. void search();

  40. void delay(uchar ms)
  41. {
  42.         uchar y;
  43.         for(;ms>0;ms--)
  44.                 for(y=120;y>0;y--);
  45. }



  46. void T0_Init()
  47. {
  48.         TMOD=0X11;
  49.         TH0=(65536-1000)/256;
  50.         TL0=(65536-1000)%256;
  51.         TH1=(65536-1000)/256;
  52.         TL1=(65536-1000)%256;
  53.         ET0=1;
  54.         ET1=1;
  55.                                 TR0=1;    //定時器0開
  56.                                 TR1=0;    //定時器1關
  57.         EA=1;
  58. }
  59. /*lcd1602顯示程序*/
  60. void display(uchar date1,uchar date2)
  61. {
  62.         uchar i,a;
  63.         LcdInit();
  64.         Disp1[10]=num/10+'0';
  65.         Disp1[11]=num%10+'0';
  66.         Disp2[6]=date1+'0';
  67.         Disp2[12]=date2+'0';
  68.         for(i=0;i<16;i++)
  69.         {
  70.                 LcdWriteData(Disp1[i]);        
  71.         }
  72.         LcdWriteCom(0x80+0x40);
  73.         for(a=0;a<16;a++)
  74.         {
  75.                 LcdWriteData(Disp2[a]);        
  76.         }
  77. }

  78. /*
  79. 開始準備搶答,開始倒計時
  80. */
  81. void Ks_Scan()
  82. {
  83.         if(Ks==0)
  84.         {
  85.                 delay(10);
  86.                 if(Ks==0)
  87.                 {
  88.                         TR1=1;              //開啟倒計時
  89.                         sjflag=1;           //開啟犯規判斷
  90.                         while(num!=0)      //如果在期間有人搶答,fallflag=1,此程序執行完后,后續程序會判犯規
  91.                         {
  92.                                 if(num==numf-1)
  93.                                 {
  94.                                         numf=numf-1;
  95.                                         display(0,0);  //不能顯示num=0時
  96.                                 }
  97.                         }
  98.                         sflag=1;       //搶答開始
  99.                         if(sjflag==0)  //有人犯規
  100.                         {
  101.                                 sflag=0;
  102.                         }
  103.                         sjflag=0;        //關閉犯規判斷
  104.                         display(0,0);    //顯示num=0時
  105.                         beep=0;             //蜂鳴
  106.                 }
  107.                 while(!Ks);
  108.         }
  109. }
  110. /*
  111. 復位
  112. */
  113. void restoration()
  114. {
  115.         if(Kr==0)
  116.         {
  117.                 delay(10);
  118.                 if(Kr==0)
  119.                 {
  120.                         sflag=0;
  121.                         sjflag=0;
  122.                         jflag=0;
  123.                         win=0;
  124.                         fallflag=0;
  125.                         TR1=0;
  126.                         num=time;
  127.                         numf=num;
  128.                         beep=1;
  129.                         led=1;
  130.                         display(0,0);              //清除顯示屏
  131.                 }
  132.                 while(!Kr);
  133.         }
  134. }
  135. /*
  136. 在復位之前使用,且當前的操作是對復位之后的倒計時有用
  137. 保證沒有人按下除了Kc,Ka之外的按鈕。
  138. 最大設置為1分鐘,最小10s
  139. 按一次Kc加1s
  140. 操作步驟:按下Kr,后要按住Ka不松的狀態按Kc加時間,然后再次按下Kr
  141. */
  142. void timeset()   //改變搶答時間
  143. {
  144.         uchar a=0;
  145.         if(Ka==0)
  146.         {
  147.                 delay(10);
  148.                 if(Ka==0)
  149.                 {
  150.                         while(!Ka)
  151.                         {
  152.                         if(Kc==0)
  153.                         {
  154.                         delay(10);
  155.                         if(Kc==0)
  156.                         {
  157.                                 a++;
  158.                         }
  159.                         while(!Kc);
  160.                         }
  161.                         }
  162.                         time=time+a;
  163.                 }
  164.         }
  165.         if(time>=60)
  166.         {
  167.                 time=10;
  168.         }
  169. }


  170. void main()
  171. {
  172.         T0_Init();
  173.         while(1)
  174.         {
  175.                 Ks_Scan();
  176.                 if((sflag==0)&(fallflag==0))   //沒開始沒人搶答
  177.                 {
  178.                         timeset();
  179.                 }
  180.                 if((sflag==0)&(fallflag!=0))  //有人違規搶答
  181.                 {
  182.                         led=0;   //亮燈警告
  183.                         beep=1;  //關閉蜂鳴
  184.                         display(fallflag,0);         //顯示有人犯規,并顯示犯規按鈕,根據fallflag
  185.                 }
  186.                 if((sflag==1)&(fallflag==0))   //無人違規
  187.                 {
  188.                         while(jflag==0)
  189.                         {
  190.                                 judge();
  191.                         }
  192.                         judge();  //防止jflag=1時,judge()沒執行
  193.                         beep=1;  //關閉蜂鳴
  194.                         display(0,win);         //顯示搶答成功按鈕,根據win
  195.                 }
  196.                 restoration();  //復位
  197.         }
  198. }

  199. /*不停的掃描k1-4的狀態,每隔1ms掃描一次*/
  200. void timer0() interrupt 1
  201. {
  202.         TH0=(65536-1000)/256;
  203.   TL0=(65536-1000)%256;
  204.         search();
  205. }


  206. void timer1() interrupt 3
  207. {
  208.         static i;
  209.         TH0=(65536-1000)/256;
  210.   TL0=(65536-1000)%256;
  211.         i++;
  212.         if(i==1000)
  213.         {
  214.                 i=0;
  215.                 num--;
  216.                 //display(0,0);     //為什么此時加上這個程序就報warning
  217.                 if(num==0)          //放在內部保證定時器的準確性
  218.                 {
  219.                         TR1=0;
  220.                 }
  221.         }
  222. }




  223. //先丟后面的代碼


  224. /*
  225. 配合定時器0使用
  226. 如果k1-4有按鍵按下,fallflag=1
  227. */
  228. void search()
  229. {
  230.         if((K1==0)&(sjflag==1))   //按下Ks開始后(sjflag=1)如果有人按了K1就會進入程序
  231.         {
  232.                 delay(10);
  233.                 if(K1==0)
  234.                 {
  235.                         fallflag=1;
  236.                         sjflag=0;             //互鎖,并配合Ks_Scan()中的犯規判斷語句
  237.                 }
  238.                 while(!K1);
  239.         }
  240.         if((K2==0)&(sjflag==1))
  241.         {
  242.                 delay(10);
  243.                 if(K2==0)
  244.                 {
  245.                         fallflag=2;
  246.                         sjflag=0;
  247.                 }
  248.                 while(!K2);
  249.         }
  250.         if((K3==0)&(sjflag==1))
  251.         {
  252.                 delay(10);
  253.                 if(K3==0)
  254.                 {
  255.                         fallflag=3;
  256.                         sjflag=0;
  257.                 }
  258.                 while(!K3);
  259.         }
  260.         if((K4==0)&(sjflag==1))
  261.         {
  262.                 delay(10);
  263.                 if(K4==0)
  264.                 {
  265.                         fallflag=4;
  266.                         sjflag=0;
  267.                 }
  268.                 while(!K4);
  269.         }
  270. }

  271. void judge()           
  272. {
  273.         if((K1==0)&(jflag==0))
  274.         {
  275.                 delay(10);
  276.                 if((K1==0)&(jflag==0))
  277.                 {
  278.                         win=1;
  279.                         jflag=1;    //鎖住其他按鈕
  280.                 }
  281.                 while(!K1);
  282.         }
  283.         if((K2==0)&(jflag==0))
  284.         {
  285.                 delay(10);
  286.                 if((K2==0)&(jflag==0))
  287.                 {
  288.                         win=2;
  289.                         jflag=1;    //鎖住其他按鈕
  290.                 }
  291.                 while(!K2);
  292.         }
  293.         if((K3==0)&(jflag==0))
  294.         {
  295.                 delay(10);
  296.                 if((K3==0)&(jflag==0))
  297.                 {
  298.                         win=3;
  299.                         jflag=1;    //鎖住其他按鈕
  300.                 }
  301.                 while(!K3);
  302.         }
  303.         if((K4==0)&(jflag==0))
  304.         {
  305.                 delay(10);
  306.                 if((K4==0)&(jflag==0))
  307.                 {
  308.                         win=4;
  309.                         jflag=1;    //鎖住其他按鈕
  310.                 }
  311.                 while(!K4);
  312.         }
  313. }

  314. 以下是“lcd.c”
  315. #include "lcd.h"

  316. /*******************************************************************************
  317. * 函 數 名         : Lcd1602_Delay1ms
  318. * 函數功能                   : 延時函數,延時1ms
  319. * 輸    入         : c
  320. * 輸    出         : 無
  321. * 說    名         : 該函數是在12MHZ晶振下,12分頻單片機的延時。
  322. *******************************************************************************/

  323. void Lcd1602_Delay1ms(uint c)   //誤差 0us
  324. {
  325.     uchar a,b;
  326.         for (; c>0; c--)
  327.         {
  328.                  for (b=199;b>0;b--)
  329.                  {
  330.                           for(a=1;a>0;a--);
  331.                  }      
  332.         }
  333.             
  334. }

  335. /*******************************************************************************
  336. * 函 數 名         : LcdWriteCom
  337. * 函數功能                   : 向LCD寫入一個字節的命令
  338. * 輸    入         : com
  339. * 輸    出         : 無
  340. *******************************************************************************/
  341. #ifndef         LCD1602_4PINS         //當沒有定義這個LCD1602_4PINS時
  342. void LcdWriteCom(uchar com)          //寫入命令
  343. {
  344.         LCD1602_E = 0;     //使能
  345.         LCD1602_RS = 0;           //選擇發送命令
  346.         LCD1602_RW = 0;           //選擇寫入
  347.         
  348.         LCD1602_DATAPINS = com;     //放入命令
  349.         Lcd1602_Delay1ms(1);                //等待數據穩定

  350.         LCD1602_E = 1;                  //寫入時序
  351.         Lcd1602_Delay1ms(5);          //保持時間
  352.         LCD1602_E = 0;
  353. }
  354. #else
  355. void LcdWriteCom(uchar com)          //寫入命令
  356. {
  357.         LCD1602_E = 0;         //使能清零
  358.         LCD1602_RS = 0;         //選擇寫入命令
  359.         LCD1602_RW = 0;         //選擇寫入

  360.         LCD1602_DATAPINS = com;        //由于4位的接線是接到P0口的高四位,所以傳送高四位不用改
  361.         Lcd1602_Delay1ms(1);

  362.         LCD1602_E = 1;         //寫入時序
  363.         Lcd1602_Delay1ms(5);
  364.         LCD1602_E = 0;

  365.         LCD1602_DATAPINS = com << 4; //發送低四位
  366.         Lcd1602_Delay1ms(1);

  367.         LCD1602_E = 1;         //寫入時序
  368.         Lcd1602_Delay1ms(5);
  369.         LCD1602_E = 0;
  370. }
  371. #endif
  372. /*******************************************************************************
  373. * 函 數 名         : LcdWriteData
  374. * 函數功能                   : 向LCD寫入一個字節的數據
  375. * 輸    入         : dat
  376. * 輸    出         : 無
  377. *******************************************************************************/                  
  378. #ifndef         LCD1602_4PINS                  
  379. void LcdWriteData(uchar dat)                        //寫入數據
  380. {
  381.         LCD1602_E = 0;        //使能清零
  382.         LCD1602_RS = 1;        //選擇輸入數據
  383.         LCD1602_RW = 0;        //選擇寫入

  384.         LCD1602_DATAPINS = dat; //寫入數據
  385.         Lcd1602_Delay1ms(1);

  386.         LCD1602_E = 1;   //寫入時序
  387.         Lcd1602_Delay1ms(5);   //保持時間
  388.         LCD1602_E = 0;
  389. }
  390. #else
  391. void LcdWriteData(uchar dat)                        //寫入數據
  392. {
  393.         LCD1602_E = 0;          //使能清零
  394.         LCD1602_RS = 1;          //選擇寫入數據
  395.         LCD1602_RW = 0;          //選擇寫入

  396.         LCD1602_DATAPINS = dat;        //由于4位的接線是接到P0口的高四位,所以傳送高四位不用改
  397.         Lcd1602_Delay1ms(1);

  398.         LCD1602_E = 1;          //寫入時序
  399.         Lcd1602_Delay1ms(5);
  400.         LCD1602_E = 0;

  401.         LCD1602_DATAPINS = dat << 4; //寫入低四位
  402.         Lcd1602_Delay1ms(1);

  403.         LCD1602_E = 1;          //寫入時序
  404.         Lcd1602_Delay1ms(5);
  405.         LCD1602_E = 0;
  406. }
  407. #endif
  408. /*******************************************************************************
  409. * 函 數 名       : LcdInit()
  410. * 函數功能                 : 初始化LCD屏
  411. * 輸    入       : 無
  412. * 輸    出       : 無
  413. *******************************************************************************/                  
  414. #ifndef                LCD1602_4PINS
  415. void LcdInit()                                                  //LCD初始化子程序
  416. {
  417.          LcdWriteCom(0x38);  //開顯示
  418.         LcdWriteCom(0x0c);  //開顯示不顯示光標
  419.         LcdWriteCom(0x06);  //寫一個指針加1
  420.         LcdWriteCom(0x01);  //清屏
  421.         LcdWriteCom(0x80);  //設置數據指針起點
  422. }
  423. #else
  424. void LcdInit()                                                  //LCD初始化子程序
  425. {
  426.         LcdWriteCom(0x32);         //將8位總線轉為4位總線
  427.         LcdWriteCom(0x28);         //在四位線下的初始化
  428.         LcdWriteCom(0x0c);  //開顯示不顯示光標
  429.         LcdWriteCom(0x06);  //寫一個指針加1
  430.         LcdWriteCom(0x01);  //清屏
  431.         LcdWriteCom(0x80);  //設置數據指針起點
  432. }
  433. #endif

  434. 以下是“lcd.h”
  435. #ifndef __LCD_H_
  436. #define __LCD_H_
  437. /**********************************
  438. 當使用的是4位數據傳輸的時候定義,
  439. 使用8位取消這個定義
  440. **********************************/
  441. //#define LCD1602_4PINS

  442. /**********************************
  443. 包含頭文件
  444. **********************************/
  445. #include <reg52.h>

  446. //---重定義關鍵詞---//
  447. #ifndef uchar
  448. #define uchar unsigned char
  449. #endif

  450. #ifndef uint
  451. #define uint unsigned int
  452. #endif

  453. /**********************************
  454. PIN口定義
  455. **********************************/
  456. #define LCD1602_DATAPINS P2
  457. sbit LCD1602_E=P0^7;
  458. sbit LCD1602_RW=P0^6;
  459. sbit LCD1602_RS=P0^5;

  460. /**********************************
  461. 函數聲明
  462. **********************************/
  463. /*在51單片機12MHZ時鐘下的延時函數*/
  464. void Lcd1602_Delay1ms(uint c);   //誤差 0us
  465. /*LCD1602寫入8位命令子函數*/
  466. void LcdWriteCom(uchar com);
  467. /*LCD1602寫入8位數據子函數*/        
  468. void LcdWriteData(uchar dat)        ;
  469. /*LCD1602初始化子程序*/               
  470. void LcdInit();                                                  

  471. #endif
復制代碼

評分

參與人數 1黑幣 +50 收起 理由
admin + 50 共享資料的黑幣獎勵!

查看全部評分

分享到:  QQ好友和群QQ好友和群 QQ空間QQ空間 騰訊微博騰訊微博 騰訊朋友騰訊朋友
收藏收藏1 分享淘帖 頂 踩
回復

使用道具 舉報

沙發
ID:518357 發表于 2019-5-6 08:20 | 只看該作者
感覺不錯哦,謝謝大佬分享
回復

使用道具 舉報

板凳
ID:743691 發表于 2020-6-20 22:23 | 只看該作者
寫的很詳細了,謝謝分享
回復

使用道具 舉報

地板
ID:785570 發表于 2020-6-21 10:39 | 只看該作者
有仿真圖嗎?

回復

使用道具 舉報

5#
無效樓層,該帖已經被刪除
您需要登錄后才可以回帖 登錄 | 立即注冊

本版積分規則

小黑屋|51黑電子論壇 |51黑電子論壇6群 QQ 管理員QQ:125739409;技術交流QQ群281945664

Powered by 單片機教程網

快速回復 返回頂部 返回列表