1.STM32有一个内部的温度传感器,可以用来测量CPU及周围的温度(TA)。
    2.该温度传感器在内部和ADCx_IN16输入通道相连接,此通道把传感器输出的电压转换成数字值。
	3.温度传感器模拟输入推荐采样时间是17.1μs。
	4.STM32的内部温度传感器支持的温度范围为:-40~125度。精度比较差,为±1.5℃左右。
     内部温度传感器更适合于检测温度的变化,而不是测量绝对温度。
     如果需要测量绝度温度,应该使用一个外部温度传感器。

获取STM32内部温度传感器温度值 CUBEMX stm32内部温度传感器不精确_STM32内部温度传感器


获取STM32内部温度传感器温度值 CUBEMX stm32内部温度传感器不精确_ADC_02


下边我们就开始配置独处芯片内部的温度值:【说白了内温度传感器还是属于ADC的一部分,所以,要懂内部传感器就必须懂ADC的配置 】

void  Adc_Temperature_Init(void)
{			
	//第一步:开启PA时钟以及ADC1的通道16的时钟。
	ADC_InitTypeDef ADC_InitStructure;
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA | RCC_APB2Periph_ADC1,ENABLE);

	//第二步:复位ADC1,并且设置ADC1的分频因子,让ADC1工作在多少Mhz。
	//		 最高不能超过14MHz.那么我们就6分频,让其工作在12Mhz,因为ADC挂载在
	//		 APB2总线下,也就对应的是PCLK2的时钟,72/6=12;
	RCC_ADCCLKConfig(RCC_PCLK2_Div6);//
	ADC_DeInit(ADC1);//ADC1去初始化

	//第三步:初始化ADC1的相关参数,设置ADC1的工作模式以及规则序列的相关信息
	ADC_InitStructure.ADC_ContinuousConvMode = DISABLE; //工作在单一模式而不是循环模式
	ADC_InitStructure.ADC_DataAlign = ADC_DataAlign_Right;//数据右对齐
	ADC_InitStructure.ADC_ExternalTrigConv = ADC_ExternalTrigConv_None;//转换是没有外部出发启动的。是同过软件转换触发启动
	ADC_InitStructure.ADC_Mode = ADC_Mode_Independent;	//独立模式
	ADC_InitStructure.ADC_NbrOfChannel = 1;							//顺序进行规则转换的ADC1通道数目。这里只有一个通道。
	ADC_InitStructure.ADC_ScanConvMode = DISABLE;				//扫描模式关闭 。扫描模式是用来扫描一组通道的这里我们只用到了一个通道,也就用不到扫描模式,所以失能
	ADC_Init(ADC1,&ADC_InitStructure);//ADC1的初始化。	
	ADC_TempSensorVrefintCmd(ENABLE);//这一步不能忘记了。AD通道方面的配置的差不多了,就要开启内部温度传感器。
	//第四步:使能ADC1并且校准ADC1,【校准之前要进行去校准,等待去校准完成后再进行校准】
	ADC_Cmd(ADC1,ENABLE);
	ADC_GetResetCalibrationStatus(ADC1);//ADC1的去校准
	*while(ADC_GetResetCalibrationStatus(ADC1));	//等待去校准完成。*//当没玩成校准时是1,在循环内死这呢。等待脚注完成,ADC->CR2中的位3就变成0,就跳出循环。哈哈
	
	
	ADC_StartCalibration(ADC1);//ADC1开始校准
	while(ADC_GetCalibrationStatus(ADC1));//等待校准完成	
	}

ps:【以上斜体的部分:while(ADC_GetResetCalibrationStatus(ADC1)); //等待去校准完成。】

RSTCAL:复位校准

该位由软件设置并由硬件清除。在校准寄存器被初始化后该位将被清除。

0:校准寄存器已初始化

1:初始化校准寄存器

注:当正在进行转换时,如果设置RSTCAL,清除校准寄存器需要额外的周期

获取STM32内部温度传感器温度值 CUBEMX stm32内部温度传感器不精确_STM32内部温度传感器_03


//得到AD转化值函数

u16 Get_Adc(u8 ch)
{
	//第五步:配置工作通道参数,设置指定的ADC规则通道数,一个序列,采样时间239.5个周期
	ADC_RegularChannelConfig(ADC1,ch,ADC_SampleTime_239Cycles5);//ADC1,ADC通道16,一个序列,采样时间239.5个周期

	//第六步:开启软件转换功能
	ADC_SoftwareStartConvCmd(ADC1,ENABLE);//使能ADC1的软件转换功能	
	
	while(!ADC_GetFlagStatus(ADC1,ADC_FLAG_EOC) != RESET);//等待转换完成
	
	return ADC_GetConversionValue(ADC1);//把转换的AD值返回回去。
}

得到的ADC内部温度传感器的采样值。值取10次求平均,更加准确。

u16 T_Get_Temp(void)
{
	u16 temp_val=0;
	u8 t;
	for(t=0;t<10;t++)
	{
	temp_val+=Get_Adc(ADC_Channel_16);	  //TampSensor
	delay_ms(5);
	}
	return temp_val/10;
}

//得到通道ch的转换平均值。取times次然后求平均。

u16 T_Get_Adc_Average(u8 ch,u8 times)
{
	u32 temp_val=0;
	u8 t;
	for(t=0;t<times;t++)
	{
	temp_val+=Get_Adc(ch);
	delay_ms(5);
	}
	return temp_val/times;
}

//得到温度值。温度值扩大了100倍,单位:摄氏度。

short Get_Temprate(void)	//获取内部温度传感器的温度值
{
	u32 adcx;
	short result;
	double temperate;
	adcx=T_Get_Adc_Average(ADC_Channel_16,20);	//通道16,读取20次
	temperate=(float)adcx*(3.3/4096);		//得到的电压值。 
	temperate=(1.43-temperate)/0.0043+25;	//转换为温度值
	result=temperate*=100;					//扩大100倍。好放在LCD上显示
	return result;
}