MQ เป็นเซ็นเซอร์ก๊าซชนิดหนึ่งที่ถูกออกแบบมาเพื่อตรวจจับก๊าซที่ติดไฟได้หลายชนิด เช่น ก๊าซแอลกอฮอล์, ก๊าซธรรมชาติ และก๊าซไฮโดรเจน เซ็นเซอร์นี้ทำงานบนหลักการเปลี่ยนแปลงความต้านทานไฟฟ้าเมื่อสัมผัสกับก๊าซที่ต้องการตรวจจับ
แบบที่ 1 ใช้งานแบบ Digital
1.ต่ออุปกรณ์

MQ-2 > Arduino UNO
GND>GNDVCC>5VDO>Pin 7
2.ลงโปรแกรม
Copy โค้ดด้านล่าง
Arduino
1int sensor = 7;
2int val = 0;
3void setup() {
4 Serial.begin(9600);
5}
6void loop() {
7 val = digitalRead(sensor);
8 if (val == 0) {
9 Serial.println("MQ-2 Detected");
10 }
11 delay(500);
12}1int sensor = 7;
2int val = 0;
3void setup() {
4 Serial.begin(9600);
5}
6void loop() {
7 val = digitalRead(sensor);
8 if (val == 0) {
9 Serial.println("MQ-2 Detected");
10 }
11 delay(500);
12}
3.ผลลัพธ์
เมื่อเซนเซอร์พบแก๊ส จะขึ้นเตือน
.png?alt=media&token=991add17-565a-4d34-8967-46071e0c0efc)
แบบที่ 2 ใช้งานแบบ Analog
1.ต่ออุปกรณ์

MQ-2 > Arduino UNO
GND>GNDVCC>5VAO>A0
2.ลงโปรแกรม
Copy โค้ดด้านล่าง
Arduino
1int sensor = A0;
2int val = 0;
3void setup() {
4 Serial.begin(9600);
5}
6void loop() {
7 val = analogRead(sensor);
8 Serial.println(val);
9 delay(500);
10}1int sensor = A0;
2int val = 0;
3void setup() {
4 Serial.begin(9600);
5}
6void loop() {
7 val = analogRead(sensor);
8 Serial.println(val);
9 delay(500);
10}
3.ผลลัพธ์
เมื่อเซนเซอร์พบแก๊ส จะขึ้นเป็นค่าที่เซนเซอร์ส่งออกมา
.png?alt=media&token=72d4f9e8-f902-48ca-8404-4e7711bdffae)
แบบที่ 3 ใช้งานแบบ Analog หน่วย PPM
1.ต่ออุปกรณ์

MQ-2 > Arduino UNO
GND>GNDVCC>5VAO>A0
2.ลงโปรแกรม
Copy โค้ดด้านล่าง
Arduino
1/*******************Demo for MQ-2 Gas Sensor Module V1.0*****************************
2 Support: Tiequan Shao: support[at]sandboxelectronics.com
3 Lisence: Attribution-NonCommercial-ShareAlike 3.0 Unported (CC BY-NC-SA 3.0)
4 Note: This piece of source code is supposed to be used as a demostration ONLY. More
5 sophisticated calibration is required for industrial field application.
6 Sandbox Electronics 2011-04-25
7************************************************************************************/
8
9/************************Hardware Related Macros************************************/
10#define MQ_PIN (0) //define which analog input channel you are going to use
11#define RL_VALUE (5) //define the load resistance on the board, in kilo ohms
12#define RO_CLEAN_AIR_FACTOR (9.83) //RO_CLEAR_AIR_FACTOR=(Sensor resistance in clean air)/RO,
13//which is derived from the chart in datasheet
14
15/***********************Software Related Macros************************************/
16#define CALIBARAION_SAMPLE_TIMES (50) //define how many samples you are going to take in the calibration phase
17#define CALIBRATION_SAMPLE_INTERVAL (500) //define the time interal(in milisecond) between each samples in the
18//cablibration phase
19#define READ_SAMPLE_INTERVAL (50) //define how many samples you are going to take in normal operation
20#define READ_SAMPLE_TIMES (5) //define the time interal(in milisecond) between each samples in
21//normal operation
22
23/**********************Application Related Macros**********************************/
24#define GAS_LPG (0)
25#define GAS_CO (1)
26#define GAS_SMOKE (2)
27
28/*****************************Globals***********************************************/
29float LPGCurve[3] = {2.3, 0.21, -0.47}; //two points are taken from the curve.
30//with these two points, a line is formed which is "approximately equivalent"
31//to the original curve.
32//data format:{ x, y, slope}; point1: (lg200, 0.21), point2: (lg10000, -0.59)
33float COCurve[3] = {2.3, 0.72, -0.34}; //two points are taken from the curve.
34//with these two points, a line is formed which is "approximately equivalent"
35//to the original curve.
36//data format:{ x, y, slope}; point1: (lg200, 0.72), point2: (lg10000, 0.15)
37float SmokeCurve[3] = {2.3, 0.53, -0.44}; //two points are taken from the curve.
38//with these two points, a line is formed which is "approximately equivalent"
39//to the original curve.
40//data format:{ x, y, slope}; point1: (lg200, 0.53), point2: (lg10000, -0.22)
41float Ro = 10; //Ro is initialized to 10 kilo ohms
42
43void setup()
44{
45 Serial.begin(9600); //UART setup, baudrate = 9600bps
46 Serial.print("Calibrating...\n");
47 Ro = MQCalibration(MQ_PIN); //Calibrating the sensor. Please make sure the sensor is in clean air
48 //when you perform the calibration
49 Serial.print("Calibration is done...\n");
50 Serial.print("Ro=");
51 Serial.print(Ro);
52 Serial.print("kohm");
53 Serial.print("\n");
54}
55
56void loop()
57{
58 Serial.print("LPG:");
59 Serial.print(MQGetGasPercentage(MQRead(MQ_PIN) / Ro, GAS_LPG) );
60 Serial.print( "ppm" );
61 Serial.print(" ");
62 Serial.print("CO:");
63 Serial.print(MQGetGasPercentage(MQRead(MQ_PIN) / Ro, GAS_CO) );
64 Serial.print( "ppm" );
65 Serial.print(" ");
66 Serial.print("SMOKE:");
67 Serial.print(MQGetGasPercentage(MQRead(MQ_PIN) / Ro, GAS_SMOKE) );
68 Serial.print( "ppm" );
69 Serial.print("\n");
70 delay(200);
71}
72
73/****************** MQResistanceCalculation ****************************************
74 Input: raw_adc - raw value read from adc, which represents the voltage
75 Output: the calculated sensor resistance
76 Remarks: The sensor and the load resistor forms a voltage divider. Given the voltage
77 across the load resistor and its resistance, the resistance of the sensor
78 could be derived.
79************************************************************************************/
80float MQResistanceCalculation(int raw_adc)
81{
82 return ( ((float)RL_VALUE * (1023 - raw_adc) / raw_adc));
83}
84
85/***************************** MQCalibration ****************************************
86 Input: mq_pin - analog channel
87 Output: Ro of the sensor
88 Remarks: This function assumes that the sensor is in clean air. It use
89 MQResistanceCalculation to calculates the sensor resistance in clean air
90 and then divides it with RO_CLEAN_AIR_FACTOR. RO_CLEAN_AIR_FACTOR is about
91 10, which differs slightly between different sensors.
92************************************************************************************/
93float MQCalibration(int mq_pin)
94{
95 int i;
96 float val = 0;
97
98 for (i = 0; i < CALIBARAION_SAMPLE_TIMES; i++) { //take multiple samples
99 val += MQResistanceCalculation(analogRead(mq_pin));
100 delay(CALIBRATION_SAMPLE_INTERVAL);
101 }
102 val = val / CALIBARAION_SAMPLE_TIMES; //calculate the average value
103
104 val = val / RO_CLEAN_AIR_FACTOR; //divided by RO_CLEAN_AIR_FACTOR yields the Ro
105 //according to the chart in the datasheet
106
107 return val;
108}
109/***************************** MQRead *********************************************
110 Input: mq_pin - analog channel
111 Output: Rs of the sensor
112 Remarks: This function use MQResistanceCalculation to caculate the sensor resistenc (Rs).
113 The Rs changes as the sensor is in the different consentration of the target
114 gas. The sample times and the time interval between samples could be configured
115 by changing the definition of the macros.
116************************************************************************************/
117float MQRead(int mq_pin)
118{
119 int i;
120 float rs = 0;
121
122 for (i = 0; i < READ_SAMPLE_TIMES; i++) {
123 rs += MQResistanceCalculation(analogRead(mq_pin));
124 delay(READ_SAMPLE_INTERVAL);
125 }
126
127 rs = rs / READ_SAMPLE_TIMES;
128
129 return rs;
130}
131
132/***************************** MQGetGasPercentage **********************************
133 Input: rs_ro_ratio - Rs divided by Ro
134 gas_id - target gas type
135 Output: ppm of the target gas
136 Remarks: This function passes different curves to the MQGetPercentage function which
137 calculates the ppm (parts per million) of the target gas.
138************************************************************************************/
139int MQGetGasPercentage(float rs_ro_ratio, int gas_id)
140{
141 if ( gas_id == GAS_LPG ) {
142 return MQGetPercentage(rs_ro_ratio, LPGCurve);
143 } else if ( gas_id == GAS_CO ) {
144 return MQGetPercentage(rs_ro_ratio, COCurve);
145 } else if ( gas_id == GAS_SMOKE ) {
146 return MQGetPercentage(rs_ro_ratio, SmokeCurve);
147 }
148
149 return 0;
150}
151
152/***************************** MQGetPercentage **********************************
153 Input: rs_ro_ratio - Rs divided by Ro
154 pcurve - pointer to the curve of the target gas
155 Output: ppm of the target gas
156 Remarks: By using the slope and a point of the line. The x(logarithmic value of ppm)
157 of the line could be derived if y(rs_ro_ratio) is provided. As it is a
158 logarithmic coordinate, power of 10 is used to convert the result to non-logarithmic
159 value.
160************************************************************************************/
161int MQGetPercentage(float rs_ro_ratio, float *pcurve)
162{
163 return (pow(10, ( ((log(rs_ro_ratio) - pcurve[1]) / pcurve[2]) + pcurve[0])));
164}1/*******************Demo for MQ-2 Gas Sensor Module V1.0*****************************
2 Support: Tiequan Shao: support[at]sandboxelectronics.com
3 Lisence: Attribution-NonCommercial-ShareAlike 3.0 Unported (CC BY-NC-SA 3.0)
4 Note: This piece of source code is supposed to be used as a demostration ONLY. More
5 sophisticated calibration is required for industrial field application.
6 Sandbox Electronics 2011-04-25
7************************************************************************************/
8
9/************************Hardware Related Macros************************************/
10#define MQ_PIN (0) //define which analog input channel you are going to use
11#define RL_VALUE (5) //define the load resistance on the board, in kilo ohms
12#define RO_CLEAN_AIR_FACTOR (9.83) //RO_CLEAR_AIR_FACTOR=(Sensor resistance in clean air)/RO,
13//which is derived from the chart in datasheet
14
15/***********************Software Related Macros************************************/
16#define CALIBARAION_SAMPLE_TIMES (50) //define how many samples you are going to take in the calibration phase
17#define CALIBRATION_SAMPLE_INTERVAL (500) //define the time interal(in milisecond) between each samples in the
18//cablibration phase
19#define READ_SAMPLE_INTERVAL (50) //define how many samples you are going to take in normal operation
20#define READ_SAMPLE_TIMES (5) //define the time interal(in milisecond) between each samples in
21//normal operation
22
23/**********************Application Related Macros**********************************/
24#define GAS_LPG (0)
25#define GAS_CO (1)
26#define GAS_SMOKE (2)
27
28/*****************************Globals***********************************************/
29float LPGCurve[3] = {2.3, 0.21, -0.47}; //two points are taken from the curve.
30//with these two points, a line is formed which is "approximately equivalent"
31//to the original curve.
32//data format:{ x, y, slope}; point1: (lg200, 0.21), point2: (lg10000, -0.59)
33float COCurve[3] = {2.3, 0.72, -0.34}; //two points are taken from the curve.
34//with these two points, a line is formed which is "approximately equivalent"
35//to the original curve.
36//data format:{ x, y, slope}; point1: (lg200, 0.72), point2: (lg10000, 0.15)
37float SmokeCurve[3] = {2.3, 0.53, -0.44}; //two points are taken from the curve.
38//with these two points, a line is formed which is "approximately equivalent"
39//to the original curve.
40//data format:{ x, y, slope}; point1: (lg200, 0.53), point2: (lg10000, -0.22)
41float Ro = 10; //Ro is initialized to 10 kilo ohms
42
43void setup()
44{
45 Serial.begin(9600); //UART setup, baudrate = 9600bps
46 Serial.print("Calibrating...\n");
47 Ro = MQCalibration(MQ_PIN); //Calibrating the sensor. Please make sure the sensor is in clean air
48 //when you perform the calibration
49 Serial.print("Calibration is done...\n");
50 Serial.print("Ro=");
51 Serial.print(Ro);
52 Serial.print("kohm");
53 Serial.print("\n");
54}
55
56void loop()
57{
58 Serial.print("LPG:");
59 Serial.print(MQGetGasPercentage(MQRead(MQ_PIN) / Ro, GAS_LPG) );
60 Serial.print( "ppm" );
61 Serial.print(" ");
62 Serial.print("CO:");
63 Serial.print(MQGetGasPercentage(MQRead(MQ_PIN) / Ro, GAS_CO) );
64 Serial.print( "ppm" );
65 Serial.print(" ");
66 Serial.print("SMOKE:");
67 Serial.print(MQGetGasPercentage(MQRead(MQ_PIN) / Ro, GAS_SMOKE) );
68 Serial.print( "ppm" );
69 Serial.print("\n");
70 delay(200);
71}
72
73/****************** MQResistanceCalculation ****************************************
74 Input: raw_adc - raw value read from adc, which represents the voltage
75 Output: the calculated sensor resistance
76 Remarks: The sensor and the load resistor forms a voltage divider. Given the voltage
77 across the load resistor and its resistance, the resistance of the sensor
78 could be derived.
79************************************************************************************/
80float MQResistanceCalculation(int raw_adc)
81{
82 return ( ((float)RL_VALUE * (1023 - raw_adc) / raw_adc));
83}
84
85/***************************** MQCalibration ****************************************
86 Input: mq_pin - analog channel
87 Output: Ro of the sensor
88 Remarks: This function assumes that the sensor is in clean air. It use
89 MQResistanceCalculation to calculates the sensor resistance in clean air
90 and then divides it with RO_CLEAN_AIR_FACTOR. RO_CLEAN_AIR_FACTOR is about
91 10, which differs slightly between different sensors.
92************************************************************************************/
93float MQCalibration(int mq_pin)
94{
95 int i;
96 float val = 0;
97
98 for (i = 0; i < CALIBARAION_SAMPLE_TIMES; i++) { //take multiple samples
99 val += MQResistanceCalculation(analogRead(mq_pin));
100 delay(CALIBRATION_SAMPLE_INTERVAL);
101 }
102 val = val / CALIBARAION_SAMPLE_TIMES; //calculate the average value
103
104 val = val / RO_CLEAN_AIR_FACTOR; //divided by RO_CLEAN_AIR_FACTOR yields the Ro
105 //according to the chart in the datasheet
106
107 return val;
108}
109/***************************** MQRead *********************************************
110 Input: mq_pin - analog channel
111 Output: Rs of the sensor
112 Remarks: This function use MQResistanceCalculation to caculate the sensor resistenc (Rs).
113 The Rs changes as the sensor is in the different consentration of the target
114 gas. The sample times and the time interval between samples could be configured
115 by changing the definition of the macros.
116************************************************************************************/
117float MQRead(int mq_pin)
118{
119 int i;
120 float rs = 0;
121
122 for (i = 0; i < READ_SAMPLE_TIMES; i++) {
123 rs += MQResistanceCalculation(analogRead(mq_pin));
124 delay(READ_SAMPLE_INTERVAL);
125 }
126
127 rs = rs / READ_SAMPLE_TIMES;
128
129 return rs;
130}
131
132/***************************** MQGetGasPercentage **********************************
133 Input: rs_ro_ratio - Rs divided by Ro
134 gas_id - target gas type
135 Output: ppm of the target gas
136 Remarks: This function passes different curves to the MQGetPercentage function which
137 calculates the ppm (parts per million) of the target gas.
138************************************************************************************/
139int MQGetGasPercentage(float rs_ro_ratio, int gas_id)
140{
141 if ( gas_id == GAS_LPG ) {
142 return MQGetPercentage(rs_ro_ratio, LPGCurve);
143 } else if ( gas_id == GAS_CO ) {
144 return MQGetPercentage(rs_ro_ratio, COCurve);
145 } else if ( gas_id == GAS_SMOKE ) {
146 return MQGetPercentage(rs_ro_ratio, SmokeCurve);
147 }
148
149 return 0;
150}
151
152/***************************** MQGetPercentage **********************************
153 Input: rs_ro_ratio - Rs divided by Ro
154 pcurve - pointer to the curve of the target gas
155 Output: ppm of the target gas
156 Remarks: By using the slope and a point of the line. The x(logarithmic value of ppm)
157 of the line could be derived if y(rs_ro_ratio) is provided. As it is a
158 logarithmic coordinate, power of 10 is used to convert the result to non-logarithmic
159 value.
160************************************************************************************/
161int MQGetPercentage(float rs_ro_ratio, float *pcurve)
162{
163 return (pow(10, ( ((log(rs_ro_ratio) - pcurve[1]) / pcurve[2]) + pcurve[0])));
164}
3.ผลลัพธ์
เมื่อเซนเซอร์พบแก๊ส จะขึ้นค่า หน่วยเป็น ppm
.png?alt=media&token=ca78505c-d495-4614-bb50-0db1f70086f4)
