内部温度传感器(ADC采集)

STM32 有一个内部的温度传感器,可以用来测量 CPU 及周围的温度(TA)。该温度传感器在内部和 ADCx_IN16 输入通道相连接,此通道把传感器输出的电压转换成数字值。温度传感器模拟输入推荐采样时间是 17.1μ s。 STM32 的内部温度传感器支持的温度范围为: -40~125度,精度为± 1.5℃左右( 实际效果不咋地 )。
效果确实不咋地。。大冬天的测出来是20多度。。

STM32 内部温度传感器的使用很简单,只要设置一下内部 ADC,并激活其内部通道就差不多了。关于 ADC 的设置,我们在第上一章已经进行了详细的介绍,这里就不再多说。接下来我们介绍一下和温度传感器设置相关的 2 个地方。


第一个地方,我们要使用 STM32 的内部温度传感器,必须先激活 ADC 的内部通道,这里通过 ADC_CR2 的 AWDEN 位( bit23)设置。设置该位为 1 则启用内部温度传感器。第二个地方, STM32 的内部温度传感器固定的连接在 ADC 的通道 16 上,所以,我们在设置好 ADC 之后只要读取通道 16 的值,就是温度传感器返回来的电压值了。根据这个值,我们就可以计算出当前温度。计算公式如下:
T(℃) ={( V25-Vsense) /Avg_Slope}+25
上式中:
V25=Vsense 在 25 度时的数值(典型值为: 1.43)。
Avg_Slope=温度与 Vsense 曲线的平均斜率(单位: mv/℃或 uv/℃)(典型值: 4.3mv/℃)。
利用以上公式,我们就可以方便的计算出当前温度传感器的温度了。


上一节的ADC是读取外部通道的值,而内部温度传感器相当与把通道端口连接在内部温度传感器上。

配置ADC和上一节大体类似,只不过不用初始化外部IO,但要增加一句开启内部温度传感器的语句。
temperate.c

[html]  view plain  copy
 print ? 在CODE上查看代码片 派生到我的代码片
  1. #include "temperate.h"  
  2. void T_Adc_Init(void)  
  3. {  
  4.     ADC_InitTypeDef ADC_ist;  
  5.     RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA|RCC_APB2Periph_ADC1,ENABLE );  
  6.     //72M/6=12,ADC 最大时间不能超过 14M  
  7.     RCC_ADCCLKConfig(RCC_PCLK2_Div6);//设置 ADC分频因子6  
  8.     ADC_DeInit(ADC1);//复位 ADC1,将外设 ADC1 的全部寄存器重设为缺省值  
  9.       
  10.     ADC_ist.ADC_ModeADC_Mode_Independent;//ADC 独立模式  
  11.     ADC_ist.ADC_ScanConvMode=DISABLE;//单通道模式  
  12.     ADC_ist.ADC_ContinuousConvMode=DISABLE;//单次转换模式  
  13.     //转换由软件而不是外部触发启动  
  14.     ADC_ist.ADC_ExternalTrigConv=ADC_ExternalTrigConv_None;  
  15.     ADC_ist.ADC_DataAlign=ADC_DataAlign_Right;//ADC 数据右对齐  
  16.     ADC_ist.ADC_NbrOfChannel=1;//顺序进行规则转换的 ADC 通道的数目  
  17.     ADC_Init(ADC1,&ADC_ist);  
  18.       
  19.     ADC_TempSensorVrefintCmd(ENABLE);  //开启内部温度传感器  
  20.     ADC_Cmd(ADC1,ENABLE);//使能指定的 ADC1  
  21.     ADC_ResetCalibration(ADC1);//开启复位校准  
  22.     while(ADC_GetResetCalibrationStatus(ADC1));//等待复位校准结束  
  23.     ADC_StartCalibration(ADC1);//开启 AD 校准  
  24.     while(ADC_GetCalibrationStatus(ADC1));//等待校准结束  
  25. }  
  26. //获得 ADC 值  
  27. //ch:通道值 0~3  
  28. u16 T_Get_Adc(u8 ch)  
  29. {  
  30.     //设置指定 ADC 的规则组通道设置它们的转化顺序和采样时间  
  31.     ADC_RegularChannelConfig(ADC1,ch,1,ADC_SampleTime_239Cycles5);   
  32.     ADC_SoftwareStartConvCmd(ADC1, ENABLE);//使能指定的 ADC1 的软件转换功能  
  33.     while(!ADC_GetFlagStatus(ADC1,ADC_FLAG_EOC));//等待转换结束  
  34.     return ADC_GetConversionValue(ADC1);//返回最近一次 ADC1 规则组的转换结果  
  35. }  
  36. u16 T_Get_Temp(void)  
  37. {  
  38.     u16 temp_val=0;u8 i;  
  39.     for(i=0;i<10;i++)  
  40.     {  
  41.         temp_val+=T_Get_Adc(ADC_Channel_16);  
  42.         delay_ms(5);  
  43.     }  
  44.     return temp_val/10;  
  45. }  
  46. u16 T_Get_Adc_Average(u8 ch,u8 times)  
  47. {  
  48.     u32 tem_val=0;  
  49.     u8 i;  
  50.     for(i=0;i<times;i++)  
  51.     {  
  52.         tem_val+=T_Get_Adc(ch);  
  53.         delay_ms(5);  
  54.     }  
  55.     return tem_val/times;  
  56. }  
temperate.h
[html]  view plain  copy
 print ? 在CODE上查看代码片 派生到我的代码片
  1. #ifndef _TEMP_H  
  2. #define _TEMP_H  
  3. #include "sys.h"  
  4. #include "delay.h"  
  5.   
  6. #define ADC_CH_TEMP     ADC_Channel_16 //温度传感器通道  
  7. void T_Adc_Init(void);  
  8. u16 T_Get_Adc(u8 ch);  
  9. u16 T_Get_Temp(void);  
  10. u16 T_Get_Adc_Average(u8 ch,u8 times);  
  11. #endif  

主函数是在上一节的基础上修改的。。

[html]  view plain  copy
 print ? 在CODE上查看代码片 派生到我的代码片
  1. #include "led.h"  
  2. #include "delay.h"  
  3. #include "sys.h"  
  4. #include "usart.h"  
  5. #include "lcd.h"  
  6. #include "temperate.h"  
  7. void init()  
  8. {  
  9.     delay_init();            //延时函数初始化      
  10.     uart_init(9600);        //串口初始化为9600  
  11.     LED_Init();             //初始化与LED连接的硬件接口  
  12.     LCD_Init();  
  13.     T_Adc_Init();  
  14.     POINT_COLOR=RED;//设置字体为红色  
  15.     LCD_ShowString(60,40,200,24,24,"ADC Test ^-^");  
  16.     LCD_ShowString(60,70,200,16,16,"Medium difficulty");  
  17.     LCD_ShowString(60,90,200,16,16,"2015/1/25");  
  18.     LCD_ShowString(60,110,200,16,16,"By--Mr yh");  
  19.     //显示提示信息  
  20.     POINT_COLOR=BLUE;//设置字体为蓝色  
  21.     LCD_ShowString(60,130,200,16,16,"TEMP_VAL:");           
  22.     LCD_ShowString(60,150,200,16,16,"TEMP_VOL:0.000V");         
  23.     LCD_ShowString(60,170,200,16,16,"TEMPERATE:00.00C");        
  24. }  
  25. int main(void)  
  26. {  
  27.     u16 adcnum;  
  28.     float tem,temperate;  
  29.     init();  
  30.     while(1)  
  31.     {  
  32.         adcnum=T_Get_Adc_Average(ADC_CH_TEMP,10);  
  33.         LCD_ShowxNum(132,130,adcnum,4,16,0);//显示ADC的值  
  34.         tem=(float)adcnum*(3.3/4096);  
  35.         temperate=tem;  
  36.         adcnum=tem;  
  37.         LCD_ShowxNum(132,150,adcnum,1,16,0);//显示电压值的整数位  
  38.         tem-=(u8)tem;  
  39.         LCD_ShowxNum(148,150,(u32)(tem*1000),3,16,0X80);//显示电压值的小数位  
  40.         temperate=(1.43-temperate)/0.0043+25;       //计算出当前温度值  
  41.         LCD_ShowxNum(140,170,(u8)temperate,2,16,0); //显示温度整数部分  
  42.         temperate-=(u8)temperate;  
  43.         LCD_ShowxNum(164,170,temperate*100,2,16,0X80);//显示温度小数部分  
  44.         LED0=!LED0;  
  45.         delay_ms(250);  
  46.     }  
  • 4
    点赞
  • 23
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值