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

 找回密碼
 立即注冊

QQ登錄

只需一步,快速開始

搜索
查看: 2497|回復: 4
收起左側

STC12C5A60S2單片機pwm可調之旋轉編碼器動態賦值問題

[復制鏈接]
ID:254747 發表于 2019-8-9 23:14 | 顯示全部樓層 |閱讀模式
經過不斷的努力調試  現在程序基本可以動態賦值給定時器了 可以實現連續可調頻率   但是需要把定時器重裝初值的過程放到 旋轉編碼器的函數里面才可以 “  //  pinlvgengxin(Sd_Key_Value );”就是這個函數我放里面就能正常工作      如果通過旋轉編碼器的返回值來賦值的話,就不能正常工作了,請問有什么辦法解決嗎  單片機程序如下
  1. #include <STC12C5A60S2.H>
  2. #define FOSC 18432000
  3. unsigned char  Data_key();
  4. unsigned int TH,TL;XHZ;          //xhz在下面算出來的時候是一個長整形的數所以用 long
  5. unsigned char  Last_Bmb_Status;      //上一個B口的狀態
  6. unsigned char  Curent_Bmb_Status;  //當前的狀態
  7. unsigned char   Sd_flag=10;              //按鍵被轉動,標志位,初始狀態為0;     flag不是C語句的關鍵語言,可以是其它名字,但是在語句里面主要起
  8.                                            //暫停程序,轉去執行其它程序的作用,在當前狀態要做一個標記,故用標志這個單詞;
  9. unsigned char  Sd_Key_Value;        //   鍵值  初始值為0
  10. sbit    BUZ=P3^0;
  11. sbit    Pin_Portry_A=P2^4;
  12. sbit    Pin_Portry_B=P2^3;      //編碼器三個腳的定義,sd為開關按鍵,sd為按下的縮寫單詞;
  13. sbit    Pin_Portry_Sd=P2^2;
  14. sbit    LED=P3^7;
  15. void    pinlvgengxin(unsigned char x );

  16. /*
  17. void delay1_key_ms(unsigned int xms)          //表示在key.c這個文件中使用的延時函數
  18. {                                       
  19.      unsigned int i,j;                                         
  20.          for(i=xms;i>0;i--)
  21.            for (j=960;j>0;j--);
  22. }  */


  23. static void   Timer0Init(void)        
  24. {


  25.          XHZ=10;
  26.     AUXR |= 0x80;                //定時器時鐘1T模式
  27.     TMOD &= 0xF0;                //設置定時器模式
  28.     TMOD |= 0x01;                //設置定時器模式
  29.         TH0 =TH=(65536-18432000/((unsigned long)XHZ*256))/256;                //設置定時初值
  30.     TL0 =TL=(65536-18432000/((unsigned long)XHZ*256))%256;                //設置定時初值
  31.         TF0 = 0;                //清除TF0標志
  32.         TR0 = 1;                //定時器0開始計時        
  33.         EA=1;
  34.         ET0=1;
  35. }

  36. void main()
  37. {
  38.         Timer0Init();
  39.     CCON = 0;                       
  40.     CL = 0;                        
  41.     CH = 0;
  42.     CMOD = 0x04;                    
  43.     CCAP0H = CCAP0L = 0x80;         //PWM0 port output 50% duty cycle square wave
  44.     CCAPM0 = 0x42;                  //PCA module-0 work in 8-bit PWM mode and no PCA interrupt
  45.          
  46.     CCAP1H = CCAP1L = 0x80;         //PWM1 port output 0% duty cycle square wave
  47.     PCA_PWM1 = 0x00;
  48.     CCAPM1 = 0x42;
  49.     CR = 1;                         //PCA timer start run

  50.     while (1)
  51.         {
  52.                
  53.            pinlvgengxin(Data_key() );
  54.             
  55.          }  

  56. }

  57. void  pinlvgengxin(unsigned char x )

  58. {

  59.                  
  60.                  TR0=0;
  61.                 XHZ=x;//Sd_Key_Value;//把Sd_Key_Value每次變化的值寫XHZ
  62.          TH0 =TH=(65536-18432000/((unsigned long)XHZ*256))/256;                //設置定時初值
  63.          TL0 =TL=(65536-18432000/((unsigned long)XHZ*256))%256;                //設置定時初值
  64.                  TR0=1;
  65.                  
  66.         
  67. }  




  68. /*按鍵函數*/
  69. unsigned char  Data_key()
  70. {
  71.         
  72.            Last_Bmb_Status=Pin_Portry_B; //第一步讀出B口的值,b口接在P2.1上面的,上電后單片機默認高電平,故B口也是高電平;
  73.         while(!Pin_Portry_A)  //當A口等于0表示,開個被轉動,然后while取反為1,此時為真進入while語句,
  74.         {
  75.            Sd_flag=1;
  76.            Curent_Bmb_Status=Pin_Portry_B;//在把B口的值保存為當前狀態加以判斷;
  77.                                    //當flag為1的時候,表示開個被旋動過;
  78.         }

  79.         if(1== Sd_flag)  
  80.         {                                       
  81.             Sd_flag=0;     //開關旋動標志位清0      
  82.                     

  83.         if((0==Last_Bmb_Status)&&(1==Curent_Bmb_Status))  //順時針旋轉   如果Last __Bmb__Status=0,并且Curent__Bmb__Status=1;
  84.         {                                                                                                   //的時候滿足條件,也就是if(0,1),故B口當前為(0,1)狀態為順時針模式
  85.         
  86.            
  87.            if(Sd_Key_Value<255)          //判斷Sd_Key_Value是否小于225,如果是自++1
  88.               {
  89.                   Sd_Key_Value++;
  90.                         
  91.               }
  92.           else                                         //否則
  93.              {
  94.                   Sd_Key_Value=0;   //如果大于255的時候就 清0;防止溢出;
  95.                         
  96.              }
  97.            }
  98.             
  99.         if((1==Last_Bmb_Status)&&(0==Curent_Bmb_Status))  //逆時針旋轉    如果Last __Bmb__Status=1,并且Curent__Bmb__Status=0;
  100.         {                                                                                                   //的時候滿足條件,也就是if(1,0),故B口當前為(1,0)狀態為逆時針模式
  101.         
  102.            
  103.           if(Sd_Key_Value>0)       //判斷Sd_Key_Value是否大于255.如果大于就--1
  104.             {
  105.                     Sd_Key_Value--;
  106.                  
  107.             }
  108.          else                                    //否則
  109.             {
  110.              Sd_Key_Value=255;   //如果小于0的時候就給 Sd__Key___Value賦值為255.
  111.                           
  112.             }
  113.          
  114.          }
  115.            //  pinlvgengxin(Sd_Key_Value );
  116.                  


  117.         
  118.     }

  119.    return  Sd_Key_Value;    //把Sd_Key_Value的值返回到unsigned char  Data_key()函數里面  
  120.                             //在調用unsigned char  Data_key()這個函數的時候就相當于是調用
  121.                                                         //這個Sd_Key_Valued的實時值
  122. }





  123. void tm0_isr() interrupt 1 using 1
  124. {
  125.          

  126.      TH0 =TH;                //設置定時初值
  127.      TL0 =TL;                //設置定時初值
  128. }
復制代碼


回復

使用道具 舉報

ID:401564 發表于 2019-8-10 09:16 | 顯示全部樓層
1,編碼開關設定為1mS左右的中斷,在定時器的中斷程序中判斷編碼開關是正轉動還是反轉動
2,設定一個變量,進入定時器中斷一次就減1,編碼開關有效轉動一次就賦值一次,可以是100或者200之類的,這樣一來就可以實現:只要你編碼開關還在轉動,這個變量就一直在賦值,當編碼開關不再轉動,也要進入定時器中斷很多次才能讓這個變量為0
3,寫入PWM要先查詢之前設定的變量,不為0就不寫入
回復

使用道具 舉報

ID:254747 發表于 2019-8-10 11:22 | 顯示全部樓層
Y_G_G 發表于 2019-8-10 09:16
1,編碼開關設定為1mS左右的中斷,在定時器的中斷程序中判斷編碼開關是正轉動還是反轉動
2,設定一個變量 ...

非常感謝您的回答   我去嘗試一下  那我就需要在開一個定時器了哦  因為定時器0的溢出是隨時發生變化的
回復

使用道具 舉報

ID:401564 發表于 2019-8-10 16:20 | 顯示全部樓層
不將就123 發表于 2019-8-10 11:22
非常感謝您的回答   我去嘗試一下  那我就需要在開一個定時器了哦  因為定時器0的溢出是隨時發生變化的

是要在定時器中斷程序里面檢測編碼開關的有效與否,定時器中斷設定在1mS或者是2mS,這樣的話就不會丟碼了,而且,編碼開關各類是有幾種的,就算是一樣的型號,編碼有效的確認方式也是不同的
像我用的EC11就有兩種:步數是一樣的,一種是:編碼開關停止轉動之后,兩邊的引腳和中間的引腳是固定為短路狀態的。
另一種是:編碼開關停止轉動之后,有時候是短路,有時候是開路
所以,你要先確定好你的開關是哪種的的,但如果你的代碼現在已經能用了,就說明已經對了
回復

使用道具 舉報

ID:254747 發表于 2019-8-12 13:59 | 顯示全部樓層
Y_G_G 發表于 2019-8-10 16:20
是要在定時器中斷程序里面檢測編碼開關的有效與否,定時器中斷設定在1mS或者是2mS,這樣的話就不會丟碼了 ...

哎呀  非常 改下您的解答 ,目前所有的問題已經得到了解決  
回復

使用道具 舉報

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

本版積分規則

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

Powered by 單片機教程網

快速回復 返回頂部 返回列表
主站蜘蛛池模板: 天天综合永久入口 | 久久综合一区二区 | 一区天堂 | 国产精品美女久久久 | 精品伊人久久 | 日本成人中文字幕 | 高清国产午夜精品久久久久久 | 成人日韩av | 男女网站免费观看 | 精品久久国产老人久久综合 | 国产精品久久久久久福利一牛影视 | 亚洲精品无 | 黄色成人av | 蜜月va乱码一区二区三区 | 欧美日韩国产精品一区 | www.嫩草 | 拍真实国产伦偷精品 | 偷拍亚洲色图 | 亚洲一区二区三区在线免费观看 | 亚洲精品福利在线 | 天天拍天天操 | 亚洲成人福利在线观看 | 男女搞网站 | 日韩在线三级 | 亚洲一区二区精品视频在线观看 | 美国黄色一级片 | 久久久精品国产 | 欧美日在线 | 久久精品国产久精国产 | 日屁网站 | 天天操天天天干 | 成人在线国产 | 国产99免费 | 国产综合网址 | 久久福利网站 | 亚洲视频在线播放 | 中文字幕精品视频在线观看 | 久久久久91| 天堂亚洲 | 国产一区二区在线视频 | 午夜免费视频 |