一、MQ-2烟雾传感器简介

      MQ-2烟雾传感器采用在清洁空气中电导率较低的二氧化锡(SnO2),属于表面离子式N型半导体。当MQ-2烟雾传感器在200到300摄氏度环境时,二氧化锡吸附空气中的氧,形成氧的负离子吸附,使半导体中的电子密度减少,从而使其电阻值增加。当与烟雾接触时,如果晶粒间界处的势垒收到烟雾的调至而变化,就会引起表面导电率的变化。利用这一点就可以获得这种烟雾存在的信息,烟雾的浓度越大,导电率越大,输出电阻越低,则输出的模拟信号就越大。MQ-2烟雾传感器的探测范围极其的广泛,常用于家庭和工厂的气体泄漏监测装置,适宜于液化气、苯、烷、酒精、氢气、烟雾等的探测。

MQ-2具有以下特点:

  1. 具有信号输出指示。
  2. 双路信号输出(模拟量输出及TTL电平输出)
  3. TTL输出有效信号为低电平,当输出低电平时信号灯亮,可直接接单片机。
  4. 模拟量输出0~5V电压,浓度越高电压越高。
  5. 对液化气,天然气,城市煤气有较好的灵敏度。
  6. 具有长期的使用寿命和可靠的稳定性。
  7. 快速的响应恢复特性。

mq2烟雾传感器 esp32 引脚接线图 mq2烟雾传感器的参数_单片机

mq2烟雾传感器 esp32 引脚接线图 mq2烟雾传感器的参数_工程应用_02

图一 MQ-2烟雾传感器的外观图                         图二 MQ-2烟雾传感器的内部电路图

二、MQ-2烟雾传感器测量气体浓度的基本原理

      MQ-2烟雾传感器输出0~5V的测量信号电压,浓度越高电压越高。这样将MQ-2烟雾传感器的模拟输出信号管脚接到处理器的一个ADC(模数转换)管脚进行模数转换,得出MQ-2烟雾传感器信号管脚上输出的电压值。我们知道MQ-2烟雾传感器信号管脚上输出的电压值是与电阻成反比关系的,而电阻值的大小是与气体浓度呈一定的线性关系的。这样一来,我们就能通过测量MQ-2烟雾传感器的输出电压值推导得到气体的浓度。

 

mq2烟雾传感器 esp32 引脚接线图 mq2烟雾传感器的参数_工程应用_03

                                           图三 MQ-2烟雾传感器气敏元件的灵敏度特性

三、MQ-2烟雾传感器测量气体浓度的程序实现

      在我们的实际工程应用中,将MQ-2烟雾传感器的模拟信号输出管脚接到STM32F103ZET6的ADC管脚上(PA4管脚)。下面列出AD采样的相关代码:

void MQ2_Init(void)                                                                  
{
 MQ2_GPIO_Configuration();
 MQ2_DMA_Configuration();
 MQ2_Configuration();
}
void MQ2_GPIO_Configuration(void)                                            
{
 GPIO_InitTypeDef GPIO_InitStructure;   
 RCC_AHBPeriphClockCmd(RCC_AHBPeriph_DMA1,ENABLE);
 RCC_APB2PeriphClockCmd(RCC_APB2Periph_ADC1|RCC_APB2Periph_GPIOA,ENABLE); 
 GPIO_InitStructure.GPIO_Pin  =GPIO_Pin_4;
 GPIO_InitStructure.GPIO_Mode =GPIO_Mode_AIN; 
 GPIO_Init(GPIOA,&GPIO_InitStructure); 
}
void MQ2_DMA_Configuration(void)                                    
{
 DMA_InitTypeDef DMA_InitStructure;
 DMA_DeInit(DMA1_Channel1);                                                  
 DMA_InitStructure.DMA_PeripheralBaseAddr = ADC1_DR_Address;                 
 DMA_InitStructure.DMA_MemoryBaseAddr = (u32)MQ2_ADC_ConvertedValue;
 DMA_InitStructure.DMA_DIR = DMA_DIR_PeripheralSRC;                          
 DMA_InitStructure.DMA_BufferSize = ADC_NUM;                                 
 DMA_InitStructure.DMA_PeripheralInc = DMA_PeripheralInc_Disable;            
 DMA_InitStructure.DMA_MemoryInc = DMA_MemoryInc_Enable;                     
 DMA_InitStructure.DMA_PeripheralDataSize = DMA_PeripheralDataSize_HalfWord;
 DMA_InitStructure.DMA_MemoryDataSize = DMA_MemoryDataSize_HalfWord;
 DMA_InitStructure.DMA_Mode = DMA_Mode_Circular;                             
 DMA_InitStructure.DMA_Priority = DMA_Priority_High;                         
 DMA_InitStructure.DMA_M2M = DMA_M2M_Disable;                                
 DMA_Init(DMA1_Channel1,&DMA_InitStructure);                                 
 DMA_Cmd(DMA1_Channel1,ENABLE); 
}
void MQ2_Configuration(void)                                                     
{
 ADC_InitTypeDef ADC_InitStructure;
 ADC_DeInit(ADC1);                                                   
 ADC_InitStructure.ADC_Mode = ADC_Mode_Independent;                  
 ADC_InitStructure.ADC_ScanConvMode =ENABLE;                         
 ADC_InitStructure.ADC_ContinuousConvMode = ENABLE;                  
 ADC_InitStructure.ADC_ExternalTrigConv = ADC_ExternalTrigConv_None; 
 ADC_InitStructure.ADC_DataAlign = ADC_DataAlign_Right;              
 ADC_InitStructure.ADC_NbrOfChannel = ADC_NUM;                       
 ADC_Init(ADC1,&ADC_InitStructure);                                  
 RCC_ADCCLKConfig(RCC_PCLK2_Div6);
 ADC_RegularChannelConfig(ADC1,ADC_Channel_6,1,ADC_SampleTime_239Cycles5);
 ADC_DMACmd(ADC1, ENABLE);
 ADC_Cmd(ADC1,ENABLE);                                               
 ADC_ResetCalibration(ADC1);                                         
 while(ADC_GetResetCalibrationStatus(ADC1));                         
 ADC_StartCalibration(ADC1);                                         
 while(ADC_GetCalibrationStatus(ADC1));                                    
 ADC_SoftwareStartConvCmd(ADC1,ENABLE);
}
u16 Get_MQ2_Adc(u8 ch) 
{
ADC_RegularChannelConfig(ADC1,ch,1,ADC_SampleTime_239Cycles5);              
 ADC_SoftwareStartConvCmd(ADC1,ENABLE);                               
 while(!ADC_GetFlagStatus(ADC1,ADC_FLAG_EOC));                      
 return ADC_GetConversionValue(ADC1);                                 
}
u16 Get_MQ2_Adc_Average(u8 ch,u8 times)                             
{
 u32 temp_val=0;
 u8 t;
 for(t=0;t<times;t++)
 {
  temp_val+=Get_MQ2_Adc(ch);
  delay_ms(5);
 }
 return temp_val/times;
}

      在程序的main函数中调用Get_MQ2_Adc_Average(u8 ch,u8 times) 函数,得到MQ-2烟雾传感器的模拟信号电压值,再通过一系列的转换就能得出气体浓度。