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

 找回密碼
 立即注冊

QQ登錄

只需一步,快速開始

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

再次發帖 STC12 STC15 STC8單片機PCA_PWM頻率可調1HZ步進 高精度

  [復制鏈接]
跳轉到指定樓層
樓主
上次也發過類似的帖子  但是那個帖子 里面調節頻率的時候  精度不是特別的高  現在修改了方法  精度還是可以的   
利用電位器調節    占空比也可以調節   這樣方便驅動電動機 調節燈泡的亮度   

下面上圖    有偶數HZ  奇數HZ  目的就是檢查精度怎么樣   

HZ數 請看數碼管前兩位即可 其它不用管  




下面是單片機程序   不對的地方 請大家指教
  1. #include <STC15F2K60S2.H>
  2. #include "intrins.h"

  3. //數碼管延時
  4. void Delay100us()                //@24.000MHz
  5. {
  6.         unsigned char i, j;

  7.         i = 3;
  8.         j = 82;
  9.         do
  10.         {
  11.                 while (--j);
  12.         } while (--i);
  13. }


  14. #define ADC_POWER   0x80          //ADC電源控制位
  15. #define ADC_FLAG    0x10          //ADC完成標志
  16. #define ADC_START   0x08          //ADC起始控制位
  17. #define ADC_SPEEDLL 0x40          //180個時鐘

  18. unsigned char ch2 = 0X02;         //通道選擇變量 0x02;選擇P1.2
  19. unsigned char ch3 = 0X03;         //選擇P1.3
  20. unsigned char ch1 = 0X04;                                        //選擇P1.4
  21. unsigned int  fupingjishu = 0;    //中斷計數的


  22. unsigned char count();



  23. //void INT0_TEST();
  24. void ADC_INIT ();
  25. void PCA_REG_PWM();
  26. void PCA_PIN_LV_ADJ(unsigned char );
  27. void Timer0Init(void);
  28. void Timer1Init(void);


  29. unsigned int  ZHU_PIN_JIE_GUO_GetADCResult();
  30. unsigned char FU_PIN_JIE_GUO_GetADCResult();
  31. unsigned char ZHAN_KONG_BI_JIE_GUO_GetADCResult();


  32. void   JI_SHUAN();

  33. //連接138譯碼器  
  34. sbit   LSA = P5^1;   
  35. sbit   LSB = P5^2;
  36. sbit   LSC = P5^3;
  37. sbit   LED1 = P0^3;

  38. //0-9 數碼段位顯示數字
  39. unsigned  code   sumaguan_duan[10] = {0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f};     

  40. //位選信號
  41. unsigned  char  displaydata[7] ;   
  42. void  shu_ma_guan();
  43. void  shumaguan_shuju_chuli(unsigned int zhupin,unsigned char fupin,unsigned char fupin_zhankongbi);


  44. main()
  45. {
  46.                  P5M0        =   0x00;   //0000,0000 端口5模式寄存器0
  47.      P5M1        =   0x00;   //0000,0000 端口5模式寄存器1
  48.      P4M0        =   0x00;   //0000,0000 端口4模式寄存器0  數碼管用
  49.      P4M1        =   0x00;
  50.            P1M0        =   0x00;   //
  51.      P1M1       |=   0x1C;   //  設置P1.2為高阻輸入模式
  52.            P0M0        =   0x00;   //0000,0000 端口4模式寄存器0  數碼管用
  53.      P0M1        =   0x00;

  54.      ADC_INIT ();
  55.            PCA_REG_PWM();
  56.            Timer0Init();
  57. //           Timer1Init();

  58.     while (1)
  59.                 {


  60.                         

  61.                   shu_ma_guan();
  62.                   shumaguan_shuju_chuli(ZHU_PIN_JIE_GUO_GetADCResult(),FU_PIN_JIE_GUO_GetADCResult(),ZHAN_KONG_BI_JIE_GUO_GetADCResult());
  63.       PCA_PIN_LV_ADJ(FU_PIN_JIE_GUO_GetADCResult());     
  64.                         CCAP0H = CCAP0L = ZHAN_KONG_BI_JIE_GUO_GetADCResult();   
  65. //      JI_SHUAN();
  66.                         
  67.                         

  68.          
  69.                  }



  70. }



  71. // ADC初始化
  72. void ADC_INIT ()
  73.         
  74. {
  75.       P1ASF |= 0X1C;                       //  將P1.2 P1.3 P1.4 口作為ADC輸入信號
  76.             ADC_RES=0;                           //清零轉換結果寄存器高8位
  77.             ADC_RESL=0;                          //清零轉換結果寄存器低2位
  78.       ADC_CONTR = ADC_POWER | ADC_SPEEDLL | ADC_START ;

  79. }

  80. //高頻結果轉換  P1.2
  81. unsigned int ZHU_PIN_JIE_GUO_GetADCResult()
  82. {
  83.             unsigned int  zhupinjieguo;

  84.                   ADC_RES=0;                           //清零轉換結果寄存器高8位
  85.             ADC_RESL=0;
  86.                         ADC_CONTR = ADC_POWER | ADC_SPEEDLL | ch1 | ADC_START;  //打開電源 速度180個時鐘 選擇通道2 啟動轉換
  87.                         _nop_();                             //等待4個NOP
  88.                         _nop_();
  89.                         _nop_();
  90.                         _nop_();
  91.                         while (!(ADC_CONTR & ADC_FLAG));     //等待ADC轉換完成  全部為1 表示轉換完成
  92.              ADC_CONTR &= ~0X80;                  //關閉ADC電源  節約功耗
  93.                         ADC_CONTR &= ~ADC_FLAG;              //Close ADC  清楚標識位
  94.                         zhupinjieguo =(ADC_RES<<2)+ADC_RESL; //將高2兩位  和低8位的結果相加得到10位的結果

  95.       zhupinjieguo /= 4;                   //ad輸出的結果最大是1024按照,但是只要0-300
  96.                                                  //縮小倍率就是1023除以300就是3.41 故用1023除以3.41即可轉換為300
  97.             return zhupinjieguo;                 //返回ADC結果
  98. }
  99. //PCA_PWM_頻率控制結果 P1.3
  100. unsigned char FU_PIN_JIE_GUO_GetADCResult()
  101. {
  102.             unsigned  int xdata fupingjieguo;
  103.                   ADC_RES=0;                           //清零轉換結果寄存器高8位
  104.             ADC_RESL=0;
  105.            
  106.                         ADC_CONTR = ADC_POWER | ADC_SPEEDLL | ch2 | ADC_START;  //打開電源 速度180個時鐘 選擇通道2 啟動轉換
  107.                         _nop_();                             //等待4個NOP
  108.                         _nop_();
  109.                         _nop_();
  110.                         _nop_();
  111.                         while (!(ADC_CONTR & ADC_FLAG));     //等待ADC轉換完成  全部為1 表示轉換完成
  112.              ADC_CONTR &= ~0X80;                  //關閉ADC電源  節約功耗
  113.                         ADC_CONTR &= ~ADC_FLAG;              //Close ADC  清楚標識位
  114.                         fupingjieguo = (ADC_RES<<2)+ADC_RESL;    //將高2兩位  和低8位的結果相加得到10位的結果

  115.             fupingjieguo /= 41;   //ad輸出的結果最大是1024按照,但是只要0-25
  116.                                                  //縮小倍率就是1023除以25就是40.92 故用1023除以40.92即可轉換為25

  117.             return fupingjieguo;                 //返回ADC結果
  118. }
  119. //PCA_PWM占空比結果  P1.4
  120. unsigned char ZHAN_KONG_BI_JIE_GUO_GetADCResult()
  121. {
  122.             unsigned int  zhankongbijieguo;
  123.             
  124.                   ADC_RES=0;                           //清零轉換結果寄存器高8位
  125.             ADC_RESL=0;
  126.          
  127.                         ADC_CONTR = ADC_POWER | ADC_SPEEDLL | ch3 | ADC_START;  //打開電源 速度180個時鐘 選擇通道2 啟動轉換
  128.                         _nop_();                             //等待4個NOP
  129.                         _nop_();
  130.                         _nop_();
  131.                         _nop_();
  132.                         while (!(ADC_CONTR & ADC_FLAG));     //等待ADC轉換完成  全部為1 表示轉換完成
  133.              ADC_CONTR &= ~0X80;                  //關閉ADC電源  節約功耗
  134.                         ADC_CONTR &= ~ADC_FLAG;              //Close ADC  清楚標識位
  135.                         zhankongbijieguo =(ADC_RES<<2)+ADC_RESL;     //將高2兩位  和低8位的結果相加得到10位的結果

  136.             zhankongbijieguo /= 4;       //ad輸出的結果最大是1024按照,但是占空比只要0-98可調
  137.                                                             //縮小倍率就是1023除以100就是10.43 故用1023除以10.43即可轉換為98

  138.             return zhankongbijieguo;                        //返回ADC結果
  139. }





  140. //數碼管顯示屏函數 初始化函數
  141. void  shu_ma_guan()
  142. {
  143.   unsigned  char xdata  i ,count;
  144.         count++;
  145.         if(count == 10)
  146.                  count = 0;

  147.                  for(i=0;i<7;i++)    //0 1 2 3 4 5 6
  148.                                  {
  149.                                                         switch(i)         //位選,選擇點亮的數碼管,
  150.                                                         {
  151.                                                                         case(0):
  152.                                                                                 LSA=0;LSB=0;LSC=0; break;//顯示第0位
  153.                                                                         case(1):
  154.                                                                                 LSA=1;LSB=0;LSC=0; break;//顯示第1位
  155.                                                                         case(2):
  156.                                                                                 LSA=0;LSB=1;LSC=0; break;//顯示第2位
  157.                                                                         case(3):
  158.                                                                                 LSA=1;LSB=1;LSC=0; break;//顯示第3位
  159.                                                                         case(4):
  160.                                                                                 LSA=0;LSB=0;LSC=1; break;//顯示第4位
  161.                                                                         case(5):
  162.                                                                                 LSA=1;LSB=0;LSC=1; break;//顯示第5位
  163.                                                                         case(6):
  164.                                                                                 LSA=0;LSB=1;LSC=1; break;//顯示第6位
  165.                                                         }
  166.                                                                                                 
  167.                                                                          P4=displaydata[i];
  168.                                                                          Delay100us();
  169.                                                                          P4 = 0X00;   //消影信號
  170.                                  }


  171. }

  172. //數碼管 數據接收與處理函數
  173. void  shumaguan_shuju_chuli(unsigned int zhupin,unsigned char fupin,unsigned char fupin_zhankongbi)
  174. {
  175. //       //低頻頻率
  176.                displaydata[0] = sumaguan_duan[fupin/10%10];
  177.                displaydata[1] = sumaguan_duan[fupin%10];
  178.             
  179.             
  180. //             //低頻占空比
  181.                displaydata[2] = sumaguan_duan[fupin_zhankongbi/10%10];
  182.                displaydata[3] = sumaguan_duan[fupin_zhankongbi%10];
  183.         
  184.                                         //主頻頻率
  185.                                  displaydata[4] = sumaguan_duan[zhupin/100%10];
  186.                                  displaydata[5] = sumaguan_duan[zhupin/10%10];
  187.                                  displaydata[6] = sumaguan_duan[zhupin%10];
  188.         
  189. }

  190. //PCA_PWM寄存器配置
  191. void PCA_REG_PWM()
  192. {
  193.          
  194.      CMOD |=0X04;   //1、CPS2、CPS1、CPS0系統時鐘,定時器0的溢出 脈沖
  195.                     //2、當CIDL=0時, 空閑模式下PCA計數器繼續工作;
  196.                           //允許ECF溢出中斷
  197.         
  198.      CCON &=0X00;   //不需要中斷標志位和中斷溢出所以并且初始化的時
  199.                     //候需要關閉PWM所以全部設置位0        
  200.         
  201.            CCAPM0 |=0X42; //允許比較器功能控制位  允許脈寬調節模式    P1.1
  202.                     //ECOM0:允許比較器功能控制位。 允許比較器
  203.                     //CAPP0: 正捕獲控制位。        不允許
  204.                     //CAPN0:負捕獲控制位。         不允許
  205.                                                                                 //MAT0: 匹配 控制位 。         不允許
  206.                                                                                 //TOG0: 翻轉控制位。           不允許
  207.                                                                                 //PWM0: 脈寬調節模式           允許
  208.                                                                                 //ECCF0: 使能CCF0中斷          不允許
  209.         
  210. //    CCAPM1 |=0X42; //同上                                      P1.0
  211.                  
  212.            CL = 0;        //低位初值設置為0
  213.            CH = 0;        //高位初值設置為0
  214.                  
  215.            CCAP0H = CCAP0L = 0x80;   //PWM    設置占空比為50%                              
  216.                                           
  217. //           CCAP1L = 0x80;   //PWM    設置占空比為50%                                   
  218. //           CCAP1H = 0x60;   //PWM    設置占空比為50%
  219.                  
  220.            PCA_PWM0 = 0X00; //PCA模塊0工作于8位PWM功能
  221. //     PCA_PWM1 = 0X00; //PCA模塊1工作于8位PWM功能                 
  222.      CR = 1 ;

  223. }




  224. ///*------------------------------------------
  225. //函數名:   定時器0
  226. //函數原型: void   Timer0Init(void)
  227. //所在文件: TIMER_DOC.c
  228. //功能描述: timer0定時的時間主要是給內部的
  229. //            PCA_PWM提供時鐘頻率
  230. //            請設置timer0為16位自動動重裝  
  231. //            這樣出來的頻率精度高
  232. //輸入參數: 無
  233. //返回:     無
  234. //作者:     Alan
  235. //時間:     2021年8月30日22:05:59

  236. //-------------------------------------------*/
  237. //定時器0溢出  設置PCA時鐘用于調節頻率
  238. void   Timer0Init(void)
  239. {

  240.         AUXR |= 0x80;                //定時器時鐘1T模式
  241.         TMOD &= 0xF0;                //設置定時器模式
  242.         TL0 = 0xA0;                //設置定時初值
  243.         TH0 = 0xF6;                //設置定時初值
  244.         TF0 = 0;                //清除TF0標志
  245.         TR0 = 1;                //定時器0開始計時

  246. }


  247. //頻率可調更新函數
  248. void PCA_PIN_LV_ADJ(unsigned char fuping)
  249. {
  250.         unsigned long  temp;

  251.         //重新初始化定時初值
  252.         temp = 0x10000-24000000/(fuping*256);
  253.         TH0 = temp>>8;                //設置定時初值
  254.         TL0 = temp;                  //設置定時初值


  255. }



  256. //void Timer1Init()                //1毫秒@24MHz
  257. //{
  258. //                        AUXR |= 0x40;                //定時器時鐘1T模式
  259. //                        TMOD &= 0x0F;                //設置定時器模式
  260. //                        TL1 = 0x40;                  //設置定時初值
  261. //                        TH1 = 0xA2;                  //設置定時初值
  262. //                        TF1 = 0;                    //清除TF1標志
  263. //                        TR1 = 1;                    //定時器1開始計時
  264. //                        ET1 = 1;
  265. //                        EA = 1;
  266. //}


  267. //void tm1_isr() interrupt 3
  268. //{
  269. //          fupingjishu++;
  270. //}

  271. //void JI_SHUAN()
  272. //{
  273. //   
  274. //        unsigned char  temp;
  275. //        
  276. //        temp = 1000UL/ZHU_PIN_JIE_GUO_GetADCResult()/2;
  277. //         
  278. //         if(fupingjishu >= temp )
  279. //         {
  280. //                    fupingjishu = 0;
  281. //                     LED1 = ~LED1; //將測試口取反
  282. //         }

  283. //}





  284. 其實沒有什么好深奧的地方  核心地方就是這里
  285. //頻率可調更新函數
  286. void PCA_PIN_LV_ADJ(unsigned char fuping)
  287. {
  288.         unsigned long  temp;

  289.         //重新初始化定時初值
  290.         temp = 0x10000-24000000/(fuping*256);
  291.         TH0 = temp>>8;                //設置定時初值
  292.         TL0 = temp;                  //設置定時初值


  293. }
復制代碼


24000000是晶振的頻率   后面的fuping是你要多少HZ就填多少即可   最大值是有限制的   和你的晶振 還是定時器溢出的PCA時鐘頻率有關系 這個可以自己去調節  設置即可

評分

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

查看全部評分

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

使用道具 舉報

沙發
ID:230742 發表于 2021-9-19 23:59 | 只看該作者
好,太好了。感覺下載了學習學習PCA和PWM。感謝分享。
回復

使用道具 舉報

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

本版積分規則

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

Powered by 單片機教程網

快速回復 返回頂部 返回列表
主站蜘蛛池模板: 老司机成人在线 | 午夜男人天堂 | 91中文字幕在线 | 日本又色又爽又黄又高潮 | 成人在线免费电影 | 精品一区二区三区免费视频 | 亚av在线| www.黄网| 精品视频一区二区三区在线观看 | 在线看免费的a | 久久国产秒 | 手机看片在线播放 | 国产一区二 | 国产精品久久久久久久久图文区 | 韩日av片 | 永久免费视频 | 午夜免费观看体验区 | 亚洲精品在线视频 | 一区观看| 成人水多啪啪片 | 成年人黄色小视频 | 99国产精品99久久久久久粉嫩 | 日本在线免费看最新的电影 | 米奇成人网 | 欧美日本韩国一区二区 | 蜜桃av一区二区三区 | 天天操天天射综合 | 一区二区三区四区不卡 | 成人三级在线观看 | 亚洲精品国产一区 | 一级免费看片 | 国产一级在线 | 亚洲婷婷六月天 | 精品福利在线 | 91色在线视频 | 日韩欧美中文在线 | 国产成人综合久久 | 亚洲免费视频一区 | 国产成人精品一区二区三区四区 | 四虎最新视频 | 欧美视频一区二区三区 |