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

 找回密碼
 立即注冊

QQ登錄

只需一步,快速開始

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

STM32單片機ADC采樣+TM1637顯示程序

[復制鏈接]
跳轉到指定樓層
樓主
ID:540173 發表于 2022-5-20 16:24 | 只看該作者 回帖獎勵 |倒序瀏覽 |閱讀模式
本程序能使用STM32進行閾值檢測,并ADC采樣顯示,結果顯示在TM1637上。

單片機源程序如下:
  1. #include "led.h"
  2. #include "delay.h"
  3. #include "sys.h"
  4. #include "usart.h"
  5. #include "lcd.h"
  6. #include "adc.h"
  7. #include "TM1637.h"
  8. #include "timer.h"

  9. //ALIENTEK Mini STM32開發板范例代碼15
  10. //ADC實驗  
  11. #define   Code_Freq 20   //編碼輸出頻率
  12. u8 delay_time = 1000/Code_Freq;  //編碼延時時間          

  13. u8 DATA[4]={0};
  14. u8 wrong=0;  //記錄錯誤
  15. extern u8 DATA_Code[24];
  16. extern u8 count;
  17. extern u8 ADC_TIMES;
  18. int main(void)
  19. {

  20.         int i=0;
  21.         NVIC_InitTypeDef NVIC_InitStructure;
  22.         NVIC_InitStructure.NVIC_IRQChannel = TIM3_IRQn;  //TIM3中斷
  23.         NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0;  //先占優先級0級
  24.         NVIC_InitStructure.NVIC_IRQChannelSubPriority = 3;  //從優先級3級
  25.          TM1637_Init();//。。。。。。。。。。。。。。。數碼管初始化
  26.          LED0=!TM1637_VCC;//  led提示顯示數碼管
  27.         delay_init();                     //延時函數初始化          
  28.         uart_init(9600);                 //串口初始化為9600
  29.         LED_Init();                                  //初始化與LED連接的硬件接口
  30.         LCD_Init();
  31.         Adc_Init();                                  //ADC初始化            
  32.         POINT_COLOR=BLUE;//設置字體為藍色
  33.         LCD_ShowString(60,130,200,16,16,"ADC_CH1_VAL:");
  34.         TM1637_NixieTubeDisplay();
  35.         TM1637_NixieTubeDisplayChar(1,0);//第一位顯示1
  36.         TM1637_NixieTubeDisplayChar(2,1);//第二位顯示2
  37.         TM1637_NixieTubeDisplayChar(3,2);//第三位顯示3
  38.         TM1637_NixieTubeDisplayChar(4,3);//第四位顯示4         
  39.         GET_Range();//獲取最新范圍
  40.         NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);
  41.         TIM3_Int_Init(delay_time*5,7199);          //采樣頻率設置為Code_Freq兩倍
  42.         TM1637_VCC=0;
  43.         LED0=!TM1637_VCC;
  44.         LCD_ShowString(60,100,200,16,16,"Receiving");
  45.         while(1)
  46.         {   
  47.     if(DATA_Code[0]+DATA_Code[1]+DATA_Code[2]+DATA_Code[3]==0&&DATA_Code[4]+DATA_Code[5]+DATA_Code[6]+DATA_Code[7]==4)//判斷依據  用ADC_TIMES在第一次時候有問題
  48.                         {
  49.                                 NVIC_InitStructure.NVIC_IRQChannelCmd = DISABLE; //IRQ通道關閉
  50.                                 NVIC_Init(&NVIC_InitStructure);  //不過可能之后不通過卡進死循環
  51.                                 for(i=0;i<4;i++)
  52.                                 {
  53.                                  DATA[i]=DATA_Code[8+i*4]*8+DATA_Code[9+i*4]*4+DATA_Code[10+i*4]*2+DATA_Code[11+i*4];  //計算輸出顯示編碼
  54.          if(DATA[i]>9||(ADC_TIMES>8&&ADC_TIMES<23))  //大于9則錯誤  adc_times 不能解決隨時關閉造成的錯誤  要改關閉算法或者記錄長時間顯示的數值保持
  55.                                         { wrong++;
  56.                                         }       
  57.                                  DATA[i]=DATA[i]%10;                 
  58.                                  LCD_ShowxNum(16*(i+1),200,DATA[i],1,16,0);//實時顯示測得編碼
  59.                                 }
  60.                                 if(wrong==0)//沒有碼位錯誤才顯示
  61.                                 {
  62.                                         TM1637_VCC=1;
  63.                                         LED0=!TM1637_VCC;
  64.                                         delay_ms(1);
  65.                                         TM1637_NixieTubeDisplay();
  66.                                         TM1637_NixieTubeDisplayChar(DATA[0],0);//用i循環只顯示最后一位
  67.                                         TM1637_NixieTubeDisplayChar(DATA[1],1);
  68.                                         TM1637_NixieTubeDisplayChar(DATA[2],2);
  69.                                         TM1637_NixieTubeDisplayChar(DATA[3],3);
  70.                                         LCD_Fill(50,100,150,120,WHITE);
  71.                                         LCD_ShowString(60,100,200,16,16,"Received");
  72.                                         delay_ms(1000);
  73.                                 }
  74.                                 ADC_TIMES=0;
  75.                                 count=0;  //和中斷內數字有關系所以要先配置
  76.                                 NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; //IRQ通道開啟
  77.                                 NVIC_Init(&NVIC_InitStructure);  //根據NVIC_InitStruct中指定的參數初始化外設NVIC寄存器
  78.                                 wrong=0;
  79.                         }                 
  80.                 if(count>10&&TM1637_VCC==1)//不能在已經滅的時候進入 否則不靈
  81.                 {
  82.                         delay_ms(1000);//合計延遲5秒左右  但是不能大于1000
  83.                         delay_ms(1000);
  84.                         delay_ms(1000);
  85.                         //delay_ms(100);
  86.                         LCD_ShowString(60,100,200,16,16,"had stopped");
  87.                         TM1637_VCC=0;
  88.                         LED0=!TM1637_VCC;
  89.                         count=0;
  90.                 }
  91.         }                                                                                            
  92. }       
復制代碼
  1. #include "adc.h"
  2. #include "delay.h"
  3. #include "lcd.h"
  4. #include "math.h"

  5. u16 VAL_MAX=0;
  6. u16 VAL_MIN=0;
  7. u16 VAL_JUDGE=1300;
  8. u16 count=0;
  9. void  GET_Range(void)
  10. { int i=0;
  11.         int j=0;
  12.         int t=0;
  13.         u16 adcx;
  14.         u16 MAX[10]={100,100,100,100,100,100,100,100,100,100};//第一個最小
  15.         u16 MIN[10]={5000,5000,5000,5000,5000,5000,5000,5000,5000,5000};//第一個最大
  16.         for(i=0;i<100;i++)
  17.         {  
  18.                 adcx=Get_Adc_Average(ADC_Channel_1,10);
  19.                 if(adcx>=(MAX[7]+MAX[8]+MAX[9])/3-50)
  20.                 {
  21.                         MAX[0]=adcx;
  22.                         for(j=0;j<9;j++)
  23.                         {
  24.                                 if(MAX[j]>MAX[j+1]) //前面的要小
  25.                                         {t=MAX[j];
  26.                                          MAX[j]=MAX[j+1];
  27.                                          MAX[j+1]=t;
  28.                                         }
  29.                         }
  30.                                   //
  31.                 }
  32.                 if(adcx<=(MIN[7]+MIN[8]+MIN[9])/3+50)
  33.                 { MIN[0]=adcx;
  34.                         for(j=0;j<9;j++)
  35.                         {
  36.                                 if(MIN[j]<MIN[j+1]) //前面的要大
  37.                                         {
  38.                                                 t=MIN[j];
  39.                                                 MIN[j]=MIN[j+1];
  40.                                                 MIN[j+1]=t;
  41.                                         }
  42.                         }
  43.                        
  44.                 }
  45.         }
  46.         VAL_MAX=(MAX[3]+MAX[4]+MAX[5]+MAX[6]+MAX[7])/5;
  47.         VAL_MIN=(MIN[3]+MIN[4]+MIN[5]+MIN[6]+MIN[7])/5;
  48.         //VAL_JUDGE=(VAL_MAX+VAL_MIN)/2;
  49.         VAL_JUDGE=((VAL_MAX+VAL_MIN)/2-VAL_MIN)*0.9+VAL_MIN;//略微偏下
  50.         if(VAL_MAX-VAL_MIN<400)//200MV左右 防止檢測的都是一
  51.         { VAL_MIN=VAL_MIN-500;//有待商榷數值
  52.                 VAL_JUDGE=(VAL_MAX+VAL_MIN)/2;
  53.         }
  54.        
  55. }
  56. u8 GET_CODE(void)  //采集   現在只判斷一和零 沒有中間 正弦波時候清空  一定要特殊標記 延遲五秒關閉
  57. {         u16 adcx;
  58.           adcx=Get_Adc_Average(ADC_Channel_1,10);
  59.                 LCD_ShowxNum(156,130,adcx,4,16,0);//顯示ADC的值
  60.         if(adcx>VAL_JUDGE)  //閾值需要修改
  61.         {        count++;
  62.                 return 1;       
  63.         }
  64.         else
  65.         {       
  66.                 count=0;
  67.                 return 0;
  68.         }               
  69. }  
  70.                   
  71. //初始化ADC
  72. //這里我們僅以規則通道為例
  73. //我們默認將開啟通道0~3                                                                                                                                          
  74. void  Adc_Init(void)
  75. {        
  76.         ADC_InitTypeDef ADC_InitStructure;
  77.         GPIO_InitTypeDef GPIO_InitStructure;

  78.         RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA |RCC_APB2Periph_ADC1        , ENABLE );          //使能ADC1通道時鐘


  79.         RCC_ADCCLKConfig(RCC_PCLK2_Div6);   //設置ADC分頻因子6 72M/6=12,ADC最大時間不能超過14M

  80.         //PA1 作為模擬通道輸入引腳                        
  81.         GPIO_InitStructure.GPIO_Pin = GPIO_Pin_1;
  82.         GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AIN;                //模擬輸入引腳
  83.         GPIO_Init(GPIOA, &GPIO_InitStructure);       

  84.         ADC_DeInit(ADC1);  //復位ADC1,將外設 ADC1 的全部寄存器重設為缺省值

  85.         ADC_InitStructure.ADC_Mode = ADC_Mode_Independent;        //ADC工作模式:ADC1和ADC2工作在獨立模式
  86.         ADC_InitStructure.ADC_ScanConvMode = DISABLE;        //模數轉換工作在單通道模式
  87.         ADC_InitStructure.ADC_ContinuousConvMode = DISABLE;        //模數轉換工作在單次轉換模式
  88.         ADC_InitStructure.ADC_ExternalTrigConv = ADC_ExternalTrigConv_None;        //轉換由軟件而不是外部觸發啟動
  89.         ADC_InitStructure.ADC_DataAlign = ADC_DataAlign_Right;        //ADC數據右對齊
  90.         ADC_InitStructure.ADC_NbrOfChannel = 1;        //順序進行規則轉換的ADC通道的數目
  91.         ADC_Init(ADC1, &ADC_InitStructure);        //根據ADC_InitStruct中指定的參數初始化外設ADCx的寄存器   

  92.   
  93.         ADC_Cmd(ADC1, ENABLE);        //使能指定的ADC1
  94.        
  95.         ADC_ResetCalibration(ADC1);        //使能復位校準  
  96.          
  97.         while(ADC_GetResetCalibrationStatus(ADC1));        //等待復位校準結束
  98.        
  99.         ADC_StartCalibration(ADC1);         //開啟AD校準

  100.         while(ADC_GetCalibrationStatus(ADC1));         //等待校準結束

  101. //        ADC_SoftwareStartConvCmd(ADC1, ENABLE);                //使能指定的ADC1的軟件轉換啟動功能

  102. }                                  
  103. //獲得ADC值
  104. //ch:通道值 0~3
  105. u16 Get_Adc(u8 ch)   
  106. {
  107.           //設置指定ADC的規則組通道,一個序列,采樣時間
  108.         ADC_RegularChannelConfig(ADC1, ch, 1, ADC_SampleTime_239Cycles5 );        //ADC1,ADC通道,采樣時間為239.5周期                                      
  109.   
  110.         ADC_SoftwareStartConvCmd(ADC1, ENABLE);                //使能指定的ADC1的軟件轉換啟動功能       
  111.          
  112.         while(!ADC_GetFlagStatus(ADC1, ADC_FLAG_EOC ));//等待轉換結束

  113.         return ADC_GetConversionValue(ADC1);        //返回最近一次ADC1規則組的轉換結果
  114. }

  115. u16 Get_Adc_Average(u8 ch,u8 times)
  116. {
  117.         u32 temp_val=0;
  118.         u8 t;
  119.         for(t=0;t<times;t++)
  120.         {
  121.                 temp_val+=Get_Adc(ch);
  122.         }
  123.         return temp_val/times;
  124. }          
復制代碼

Keil代碼下載:
代碼.7z (233.59 KB, 下載次數: 71)

評分

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

查看全部評分

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

使用道具 舉報

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

本版積分規則

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

Powered by 單片機教程網

快速回復 返回頂部 返回列表
主站蜘蛛池模板: 中文字幕免费在线观看 | 九九九久久国产免费 | 九九爱这里只有精品 | 成人综合视频在线 | 国产一区二区三区不卡av | 青青草原精品99久久精品66 | 日本中文字幕一区 | 亚洲444eee在线观看 | 亚洲国产精品日韩av不卡在线 | 久久久91精品国产一区二区三区 | 色婷婷亚洲 | 欧美一区二区三区在线免费观看 | 九色视频网站 | 在线观看国产视频 | av永久| 日屁视频| 一区二区三区在线免费观看 | 一级片aaa | 日韩中文一区二区 | 亚洲精品一级 | 亚洲成年人免费网站 | 罗宾被扒开腿做同人网站 | 国产精品高潮呻吟久久av黑人 | 中文字幕在线观看一区 | 日本一区二区三区在线观看 | 久久99精品国产麻豆婷婷 | 视频在线亚洲 | 欧美亚洲第一区 | 国产乱码精品一区二区三区忘忧草 | 国产精品欧美一区二区三区不卡 | 91一区二区三区在线观看 | 亚洲一级淫片 | 欧美久久久久 | 免费成人高清在线视频 | 91综合在线观看 | 天天影视亚洲综合网 | 久久视频免费看 | 午夜精品导航 | 精产国产伦理一二三区 | 久草www| 久久91精品久久久久久9鸭 |