久久久久久久999_99精品久久精品一区二区爱城_成人欧美一区二区三区在线播放_国产精品日本一区二区不卡视频_国产午夜视频_欧美精品在线观看免费

 找回密碼
 立即注冊

QQ登錄

只需一步,快速開始

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

51單片機38k紅外解碼程序與制作

[復制鏈接]
跳轉到指定樓層
樓主
上次大神指點后做了一些改進顯示16位16進制的數據,二進制就是64位。頻率是38k的。空調,電視,風扇,只要是家電的紅外95%以上都可以解碼,如果解碼空調,建議每次使用前復位一次,清空數組的程序一直寫失敗,大神可以來改一下。另外發現部分手機(測試榮耀9)打開相機的時候會觸發中斷,讓數據變得不正常。

制作出來的實物圖如下:


單片機源程序如下:
  1. /*********************************************************************************************
  2. 程序名:    DHT11-1602
  3. 編寫人:    fby
  4. 硬件支持:  STC89C52RC  DHT11  LCD1602
  5. 接口說明:  DHT11:VCC DATA NC GND
  6. *********************************************************************************************
  7. 說明:1、單片機是STC89C52RC,晶振頻率11.0592MHz,實驗成功。
  8.           2、好東西要共享,大家隨意折騰~~
  9. *********************************************************************************************/
  10. #include<reg51.h>
  11. #include<intrins.h>
  12. #include<stdio.h>


  13. #define uchar unsigned char        //無符號字符型類型數據
  14. #define uint unsigned int //無符號整型數據
  15.         #define ulong unsigned long //無符號整型數據
  16.         #define xiao float //xiaoshu
  17. #define IODATA  P0
  18. unsigned char IrValue[24]; //接收收據
  19. unsigned char Time;

  20. sbit RS=P2^6; //定義rs端口
  21. sbit RW=P2^5; //定義rw端口
  22. sbit E=P2^7;
  23.        
  24. sbit IRIN=P3^2;//紅外數據io

  25.              
  26. /*******************************************************************************
  27. * 函數名         : DelayMs()
  28. * 函數功能                   : 延時
  29. * 輸入           : x
  30. * 輸出                  : 無
  31. *******************************************************************************/

  32. void DelayMs(unsigned int x)   //0.14ms誤差 0us
  33. {
  34. unsigned char i;
  35.   while(x--)
  36. {
  37.   for (i = 0; i<13; i++)
  38. {}
  39. }
  40. }
  41. /*******************************************************************************
  42. * 函數名         : IrInit()
  43. * 函數功能                   : 初始化紅外線接收
  44. * 輸入           : 無
  45. * 輸出                  : 無
  46. *******************************************************************************/

  47. void IrInit()
  48. {
  49.         IT0=1;//下降沿觸發
  50.         EX0=1;//打開中斷0允許
  51.         EA=1;        //打開總中斷

  52.         IRIN=1;//初始化端口
  53.        
  54. }
  55. /*******************************************************************************
  56. * 函數名         : ReadIr()
  57. * 函數功能                   : 讀取紅外數值的中斷函數
  58. * 輸入           : 無
  59. * 輸出                  : 無
  60. *******************************************************************************/
  61.    //數據處理

  62. void sjcl()
  63. {
  64.                 IrValue[8]=IrValue[0]>>4;                          //高位  用戶碼
  65.                 IrValue[9]=IrValue[0]&0x0f;                //低位       

  66.     IrValue[10]=IrValue[1]>>4;                          //高位   用戶反碼
  67.                 IrValue[11]=IrValue[1]&0x0f;                //低位       

  68.     IrValue[12]=IrValue[2]>>4;                          //高位   數據碼
  69.                 IrValue[13]=IrValue[2]&0x0f;                //低位

  70.     IrValue[14]=IrValue[3]>>4;                          //高位  數據反碼
  71.                 IrValue[15]=IrValue[3]&0x0f;                //低位       
  72.        
  73.           IrValue[16]=IrValue[4]>>4;                          //高位  數據反碼
  74.                 IrValue[17]=IrValue[4]&0x0f;                //低位       

  75.           IrValue[18]=IrValue[5]>>4;                          //高位  數據反碼
  76.                 IrValue[19]=IrValue[5]&0x0f;                //低位       

  77.           IrValue[20]=IrValue[6]>>4;                          //高位  數據反碼
  78.                 IrValue[21]=IrValue[6]&0x0f;                //低位       

  79.           IrValue[22]=IrValue[7]>>4;                          //高位  數據反碼
  80.                 IrValue[23]=IrValue[7]&0x0f;                //低位       


  81. }

  82. void ReadIr() interrupt 0
  83. {
  84.        
  85.         unsigned char j,k;
  86.         unsigned int err;
  87.        
  88.        
  89.         Time=0;                                         
  90.         DelayMs(70);

  91.         if(IRIN==0)                //確認是否真的接收到正確的信號
  92.         {         
  93.                
  94.           
  95.                 err=1000;                                //1000*10us=10ms,超過說明接收到錯誤的信號
  96.                 /*當兩個條件都為真是循環,如果有一個條件為假的時候跳出循環,免得程序出錯的時
  97.                 侯,程序死在這里*/       
  98.                 while((IRIN==0)&&(err>0))        //等待前面9ms的低電平過去                 
  99.                 {       
  100.                  
  101.                         DelayMs(1);
  102.                         err--;
  103.                 }
  104.                 if(IRIN==1)                        //如果正確等到9ms低電平
  105.                 {
  106.                        
  107.                         err=500;
  108.                         while((IRIN==1)&&(err>0))                 //等待4.5ms的起始高電平過去
  109.                         {
  110.                                
  111.                                 DelayMs(1);
  112.                                 err--;
  113.                         }
  114.                         for(k=0;k<8;k++)                //共有8組數據
  115.                         {                               
  116.                                 for(j=0;j<8;j++)        //接收一組數據
  117.                                 {

  118.                                         err=60;               
  119.                                         while((IRIN==0)&&(err>0))//等待信號前面的560us低電平過去
  120. //                                        while (!IRIN)
  121.                                         {
  122.                                                 DelayMs(1);
  123.                                                 err--;
  124.                                         }
  125.                                         err=500;
  126.                                         while((IRIN==1)&&(err>0))         //計算高電平的時間長度。
  127.                                         {
  128.                                                 DelayMs(1);//0.14ms
  129.                                                 Time++;
  130.                                                 err--;
  131.                                                 if(Time>30)
  132.                                                 {
  133.                                                         EX0=1;
  134.                                                         return;
  135.                                                 }
  136.                                         }
  137.                                         IrValue[k]>>=1;         //k表示第幾組數據
  138.                                         if(Time>=8)                        //如果高電平出現大于565us,那么是1
  139.                                         {
  140.                                                 IrValue[k]|=0x80;
  141.                                         }
  142.                                         Time=0;                //用完時間要重新賦值                                                       
  143.                                 }
  144.                         }
  145.                 }
  146.                
  147.                         return;
  148.                
  149.         }       
  150.        sjcl();  //數據處理       
  151. }



  152.        

  153. /*********************************************************************************************
  154. 函數名:延時函數
  155. 調  用:Delay30us();/Delay20ms();/Delay1s();
  156. 參  數:無
  157. 返回值:無
  158. 結  果:延時相應時間
  159. 備  注:振蕩晶體為11.0592MHz(所有延時函數Copy自STC-ISP(v6.85).exe)
  160. **********************************************************************************************/
  161. void Delay30us()                //@11.0592MHz-40
  162. {
  163.         unsigned char i;

  164.         i = 11;
  165.         while (--i);
  166. }


  167. void Delay20ms()                //@11.0592MHz
  168. {
  169.         unsigned char i, j;

  170.         i = 36;
  171.         j = 217;
  172.         do
  173.         {
  174.                 while (--j);
  175.         } while (--i);
  176. }


  177. void Delay1s()                //@11.0592MHz
  178. {
  179.         unsigned char i, j, k;

  180.         _nop_();
  181.         i = 8;
  182.         j = 1;
  183.         k = 243;
  184.         do
  185.         {
  186.                 do
  187.                 {
  188.                         while (--k);
  189.                 } while (--j);
  190.         } while (--i);
  191. }





  192. /********************************************************************
  193. * 名稱 : bit Busy(void)
  194. * 功能 : 這個是一個讀狀態函數,讀出函數是否處在忙狀態
  195. * 輸入 : 輸入的命令值
  196. * 輸出 : 無
  197. ***********************************************************************/
  198. void Busy(void)
  199. {
  200. bit busy_flag = 1;
  201. IODATA  = 0xff;
  202. RS = 0;          //指令關
  203. Delay30us();
  204. RW = 1;          //讀狀態
  205. Delay30us();
  206. E = 1;        //使能高電平
  207. while(1)
  208. {
  209. busy_flag = (bit)(IODATA  & 0x80); //強制取最高位
  210. if(busy_flag == 0)
  211. {
  212. break;
  213. }
  214. }
  215. E = 0;           //E 1->0,rs=0,rw=1,
  216.            //將數據寄存器內的數據讀到DB0~DB7,分別將狀態標志BF和地址計數器(AC)內容讀到DB7和DB6~DB0。

  217. }

  218. /********************************************************************
  219. * 名稱 : lcd1602_write_cmd(uchar del)
  220. * 功能 : 1602命令函數
  221. * 輸入 : 輸入的命令值
  222. * 輸出 : 無
  223. ***********************************************************************/
  224. void lcd1602_write_cmd(uchar del)
  225. {
  226. RS = 0;
  227. Delay30us();
  228. RW = 0;
  229. Delay30us();
  230. E = 0;
  231. Delay30us();
  232. IODATA  = del;
  233. Delay30us();
  234. E = 1;
  235. Delay30us();
  236. E = 0;                        //E 1->0,rs=0,rw=0, 將指令代碼寫入指令寄存器中
  237. }

  238. /********************************************************************
  239. * 名稱 : lcd1602_write_data(uchar del)
  240. * 功能 : 1602寫數據函數
  241. * 輸入 : 需要寫入1602的數據
  242. * 輸出 : 無
  243. ***********************************************************************/

  244. void lcd1602_write_data(uchar del)
  245. {
  246. Busy();      
  247. Delay30us();
  248. RS = 1;
  249. Delay30us();
  250. RW = 0;
  251. Delay30us();
  252. E = 0;
  253. Delay30us();
  254. IODATA  = del;
  255. Delay30us();
  256. E = 1;
  257. Delay30us();
  258. E = 0;                          //E 1->0,rs=1,rw=0, 數據寫入數據寄存器中
  259. }

  260. /********************************************************************
  261. * 名稱 : lcd1602_init()
  262. * 功能 : 1602初始化,請參考1602的資料
  263. * 輸入 : 無
  264. * 輸出 : 無
  265. ***********************************************************************/
  266. void lcd1602_init(void)
  267. {
  268. Delay20ms();
  269. lcd1602_write_cmd(0x38);         //8位數據,雙列,5*7字形
  270. Delay20ms();
  271. lcd1602_write_cmd(0x38);
  272. Delay20ms();
  273. lcd1602_write_cmd(0x38);
  274. Busy();
  275. lcd1602_write_cmd(0x08);// 只開顯示
  276. Busy();   
  277. lcd1602_write_cmd(0x01);        //清屏
  278. Busy();
  279. lcd1602_write_cmd(0x06);//顯示地址遞增,即寫一個數據后,顯示位置右移一位
  280. Busy();
  281. lcd1602_write_cmd(0x0c);        //開啟顯示屏,關光標,光標不閃爍
  282. }

  283. /********************************************************************
  284. * 名稱 : lcd1602_char(uchar hang,uchar lie,char sign)
  285. * 功能 : 改變液晶中某位的值,如果要讓第一行,第五個字符顯示"b" ,調用該函數如下
  286. L1602_char(1,5,'b')
  287. * 輸入 : 行,列,需要輸入1602的數據
  288. * 輸出 : 無
  289. ***********************************************************************/
  290. void lcd1602_char(uchar hang,uchar lie,char sign)
  291. {
  292. uchar a;
  293. if(hang == 1)
  294. {
  295. a = 0x80;
  296. }
  297. if(hang == 2)
  298. {
  299. a = 0xc0;
  300. }
  301. a = a + lie - 1;
  302. Busy();
  303. lcd1602_write_cmd(a);  //置數據存貯器地址
  304. Busy();
  305. lcd1602_write_data(sign);
  306. }




  307. /********************************************************************
  308. * 名稱 : lcd1602_string(uchar hang,uchar lie,uchar *p)
  309. * 功能 : 改變液晶中某位的值,如果要讓第一行,第五個字符開始顯示"ab cd ef" ,調用該函數如下
  310. L1602_string(1,5,"ab cd ef;")
  311. * 輸入 : 行,列,需要輸入1602的數據
  312. * 輸出 : 無
  313. ***********************************************************************/

  314. void lcd1602_string(uchar hang,uchar lie,uchar *p)
  315. {
  316. uchar a;
  317. if(hang == 1)
  318. {
  319. a = 0x80;
  320. }
  321. if(hang == 2)
  322. {
  323. a = 0xc0;
  324. }
  325. a = a + lie - 1;
  326. while(1)
  327. {
  328. Busy();
  329. lcd1602_write_cmd(a);
  330. Busy();
  331. lcd1602_write_data(*p);
  332. a++;
  333. p++;   
  334. if((*p == '\0')||(a==0x90)||(a==0xd0)) //字符結束或每行最后一個字符
  335. {
  336. break;
  337. }
  338. }
  339. }




  340. /*********************************************************************************************
  341. 函數名:主函數
  342. 調  用:無
  343. 參  數:無
  344. 返回值:無
  345. 結  果:讀DHT11數據并送到1602顯示
  346. 備  注:
  347. **********************************************************************************************/
  348. void main (void)
  349. {
  350.     unsigned char k;
  351.        Delay20ms();
  352.         lcd1602_init();         //LCD初始化
  353.               IrInit();             //紅外初始化
  354.                
  355.         while(1)
  356.         {
  357.                                        
  358.       
  359.                         //LcdWriteData(0x37+IrValue[4]);        //將數值轉換為該顯示的ASCII碼
  360.                         //LcdWriteData(IrValue[4]+0x30);        //將數值轉換為該顯示的ASCII碼
  361.      
  362.       lcd1602_string(1,1,"HWJM:");
  363.         for(k=0;k<16;k++)
  364.                         {
  365.                 if(IrValue[k+8]>9)
  366.                                                                 {
  367.                 lcd1602_char(2,k+1,IrValue[k+8]+0x37);
  368.                 }
  369.                                  else
  370.                            {
  371.                                  lcd1602_char(2,k+1,IrValue[k+8]+0x30);
  372.                                   }

  373.       

  374. }
  375. }
  376. }
  377.                                
  378.                                
復制代碼

所有資料51hei提供下載:
紅外解碼.zip (57.38 KB, 下載次數: 55)


評分

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

查看全部評分

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

使用道具 舉報

沙發
ID:499469 發表于 2019-6-8 20:50 | 只看該作者
后面為0的是沒有數據,可以不用看
回復

使用道具 舉報

板凳
ID:558095 發表于 2019-6-9 17:02 | 只看該作者
雖然看不懂,還是默默點個贊
回復

使用道具 舉報

地板
ID:796012 發表于 2023-3-2 15:16 | 只看該作者
我試了我只風扇遙控器,按同樣的鍵,每次顯示的碼都不一樣
回復

使用道具 舉報

您需要登錄后才可以回帖 登錄 | 立即注冊

本版積分規則

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

Powered by 單片機教程網

快速回復 返回頂部 返回列表
主站蜘蛛池模板: 国产精品久久久久久久久久不蜜臀 | 欧美1级| 欧美精品一区二区三 | 黄色毛片在线播放 | 在线观看中文字幕视频 | 久久九七| 亚洲第一黄色网 | 成人不卡 | 成人综合视频在线观看 | 九九热这里 | 国产aaaaav久久久一区二区 | 天天看逼| 国产网站在线 | 亚洲超碰在线观看 | 中文字幕在线视频免费视频 | 亚洲精品久久久久久一区二区 | 日韩在线免费 | 久久精品国产久精国产 | 久久99精品国产自在现线小黄鸭 | 亚洲在线免费观看 | 一区在线播放 | 精品国产91乱码一区二区三区 | 自拍 亚洲 欧美 老师 丝袜 | 精品一区二区三区日本 | 日韩三级在线观看 | 99久久久99久久国产片鸭王 | 成人a在线 | 福利视频网址 | 国产成人综合亚洲欧美94在线 | 国产伦精品一区二区三区视频金莲 | 一区在线观看 | 久久国产区 | 精品久 | 成人午夜在线 | 成年视频在线观看福利资源 | 日韩毛片视频 | 国产一区精品 | 国产成人精品一区二区三区视频 | 午夜在线影院 | 国产精品中文字幕在线 | 精品一区二区三区中文字幕 |