แนะนำการใช้งานโมดูล PMS5003 สำหรับ PM2.5 เซ็นเซอร์ตรวจจับฝุ่นละออง วัดคุณภาพอากาศ

PMS5003 คืออะไร

PMS5003 (Plantower PMS5003 G5) เป็นเซ็นเซอร์ตรวจวัดฝุ่นละอองในอากาศ (Laser Particle Sensor) ที่ได้รับความนิยมอย่างมากในงานด้าน IoT, Smart Home, Smart City และระบบตรวจวัดคุณภาพอากาศ เนื่องจากมีขนาดเล็ก ราคาไม่สูง ติดตั้งง่าย และสามารถวัดค่าฝุ่นละอองได้แบบ Real-time ผ่านการสื่อสารแบบ UART

ภายในตัวเซ็นเซอร์ประกอบด้วย

  • Laser Diode
  • Photodiode Receiver
  • พัดลมดูดอากาศ (Fan)
  • ห้องวัด (Measurement Chamber)
  • Microprocessor สำหรับประมวลผลข้อมูล

เซ็นเซอร์จะดูดอากาศเข้าไปในห้องวัด จากนั้นยิงลำแสงเลเซอร์ผ่านอากาศ เมื่อฝุ่นละอองผ่านลำแสง จะเกิดการกระเจิงของแสง (Laser Scattering) เซ็นเซอร์จะตรวจจับแสงที่สะท้อนกลับและคำนวณขนาดกับความเข้มข้นของฝุ่นละอองด้วยอัลกอริทึมภายใน ก่อนส่งข้อมูลออกทาง UART เป็นค่าดิจิทัลพร้อมใช้งาน

หลักการทำงาน (Laser Scattering Principle)

        Air Inlet


┌────────────┐
│ Cooling Fan│
└─────┬──────┘


┌───────────────────┐
│ Laser Diode │
│ ●──────────►│
│ │
│ Dust Particle │
│ ○ │
│ ╱ │
│ ╱ │
│ Photodiode │
└───────────────────┘


Digital Processing


UART Output
PM1.0
PM2.5
PM10

ข้อดีของเทคนิค Laser Scattering คือสามารถตรวจจับฝุ่นขนาดเล็กได้ละเอียดกว่าวิธีแบบอินฟราเรดทั่วไป และตอบสนองต่อการเปลี่ยนแปลงของสภาพอากาศได้รวดเร็ว

ข้อมูลที่ PMS5003 สามารถวัดได้

เซ็นเซอร์สามารถรายงานข้อมูลหลายชนิด เช่น

รายการความหมาย
PM1.0ฝุ่นขนาดไม่เกิน 1 ไมครอน
PM2.5ฝุ่นขนาดไม่เกิน 2.5 ไมครอน
PM10ฝุ่นขนาดไม่เกิน 10 ไมครอน
Particle Countจำนวนอนุภาคหลายช่วงขนาด (0.3, 0.5, 1.0, 2.5, 5.0 และ 10 µm) ต่อปริมาตรอากาศ (ขึ้นอยู่กับข้อมูลที่อ่านจากแพ็กเก็ต UART)

Specifications

รายการค่า
รุ่นPMS5003 G5
ผู้ผลิตPlantower
หลักการวัดLaser Scattering
ช่วงการวัด0–500 µg/m³
ความละเอียด1 µg/m³
ขนาดอนุภาคต่ำสุดที่ตรวจจับได้0.3 µm
Accuracy±10 µg/m³ (0–100 µg/m³), ±10% (100–500 µg/m³)
Response Time<10 วินาที
InterfaceUART TTL
Baud Rate9600 bps
Data Bits8
Stop Bits1
ParityNone
แรงดันไฟเลี้ยง5V DC
กระแสทำงานประมาณ 100–120 mA
ขนาดประมาณ 50 × 38 × 21 มม.
อายุการใช้งานมากกว่า 3 ปี (ใช้งานต่อเนื่อง)

ขาเชื่อมต่อ (Pinout)

Pinหน้าที่
VCC5V
GNDGround
TXDส่งข้อมูลออกจากเซ็นเซอร์
RXDรับคำสั่งจาก MCU (Sleep/Wake, Passive Mode)
SETเลือกโหมด Active/Passive (บางรุ่น)
RESETรีเซ็ตเซ็นเซอร์ (บางรุ่น)

โดยทั่วไปสำหรับ ESP32 จะใช้เพียง VCC, GND, TXD และ RXD ก็เพียงพอ

จุดเด่นของ PMS5003

  • ใช้เลเซอร์ ทำให้ความแม่นยำสูงกว่าเซ็นเซอร์ฝุ่นแบบ LED
  • มีพัดลมดูดอากาศในตัว
  • ส่งข้อมูลเป็นดิจิทัล ไม่ต้องแปลงค่า Analog
  • เชื่อมต่อกับ ESP32, ESP8266, Arduino, Raspberry Pi ได้ง่าย
  • วัดค่าได้แบบ Real-time
  • รองรับการทำงานต่อเนื่อง 24 ชั่วโมง
  • มีอัลกอริทึมชดเชยผลกระทบจากสภาพแวดล้อมภายในตัวเซ็นเซอร์

ข้อจำกัด

แม้ PMS5003 จะเป็นเซ็นเซอร์ที่มีประสิทธิภาพสูง แต่ก็มีข้อจำกัดที่ควรทราบ

  • ไม่สามารถตรวจวัดก๊าซ เช่น CO₂, CO, NH₃, NO₂ หรือ VOC ได้
  • ค่าที่รายงานเป็นค่าประมาณจากการกระเจิงของแสง ไม่ใช่เครื่องมืออ้างอิงระดับห้องปฏิบัติการ
  • ความชื้นสูงอาจทำให้ค่าฝุ่นสูงกว่าความเป็นจริง เนื่องจากละอองน้ำกระเจิงแสงคล้ายฝุ่น
  • พัดลมและเลเซอร์มีการสึกหรอตามอายุการใช้งาน

การประยุกต์ใช้งาน

PMS5003 เหมาะกับงานด้านต่าง ๆ ดังนี้

1. Smart Home

  • ตรวจวัด PM2.5 ภายในบ้าน
  • ควบคุมเครื่องฟอกอากาศอัตโนมัติ
  • แจ้งเตือนผ่านแอปพลิเคชัน

2. Smart City

  • สถานีตรวจวัดคุณภาพอากาศ
  • เครือข่ายเซ็นเซอร์ IoT
  • แผนที่คุณภาพอากาศแบบ Real-time

3. Smart Agriculture

  • ตรวจคุณภาพอากาศในโรงเรือน
  • ตรวจฝุ่นในฟาร์มปศุสัตว์
  • ควบคุมระบบระบายอากาศ

4. โรงงานอุตสาหกรรม

  • ตรวจฝุ่นในพื้นที่ผลิต
  • เฝ้าระวังฝุ่นจากกระบวนการผลิต
  • แจ้งเตือนเมื่อค่าฝุ่นเกินมาตรฐาน

5. งานวิจัยและการศึกษา

  • โครงงาน Arduino
  • โครงงาน ESP32
  • งาน IoT
  • งาน AIoT
  • ระบบ Smart Environment

6. ระบบ AI และ Cloud

  • ส่งข้อมูลไปยัง MQTT
  • บันทึกข้อมูลลงฐานข้อมูล
  • วิเคราะห์แนวโน้มด้วย AI
  • พยากรณ์คุณภาพอากาศ
/*
  ==========================================
      PMS5003 Air Quality Test V1.0
      ESP32-S3 + KY-016 RGB LED
  ==========================================
*/

#include <HardwareSerial.h>

HardwareSerial pmsSerial(2);

// UART
#define PMS_RX 16
#define PMS_TX 17

// RGB LED
#define RED_PIN     25
#define GREEN_PIN   26
#define BLUE_PIN    27

uint16_t pm1 = 0;
uint16_t pm25 = 0;
uint16_t pm10 = 0;

void setup() {

  Serial.begin(115200);

  pmsSerial.begin(9600, SERIAL_8N1, PMS_RX, PMS_TX);

  pinMode(RED_PIN, OUTPUT);
  pinMode(GREEN_PIN, OUTPUT);
  pinMode(BLUE_PIN, OUTPUT);

  setColor(false, false, false);

  Serial.println();
  Serial.println("=================================");
  Serial.println(" PMS5003 Air Quality Monitor");
  Serial.println("=================================");
}

void loop() {

  if (readPMS()) {

    Serial.println("--------------------------------");

    Serial.print("PM1.0  : ");
    Serial.print(pm1);
    Serial.println(" ug/m3");

    Serial.print("PM2.5  : ");
    Serial.print(pm25);
    Serial.println(" ug/m3");

    Serial.print("PM10   : ");
    Serial.print(pm10);
    Serial.println(" ug/m3");

    Serial.print("Status : ");

    showAQI(pm25);

    Serial.println("--------------------------------");
    Serial.println();
  }

}
//////////////////////////////////////////////////////////////

bool readPMS() {

  if (pmsSerial.available() < 32)
    return false;

  if (pmsSerial.read() != 0x42)
    return false;

  if (pmsSerial.read() != 0x4D)
    return false;

  uint8_t buffer[30];

  pmsSerial.readBytes(buffer, 30);

  uint16_t checksum = 0x42 + 0x4D;

  for (int i = 0; i < 28; i++)
    checksum += buffer[i];

  uint16_t received =
      (buffer[28] << 8) | buffer[29];

  if (checksum != received)
    return false;

  pm1 =
      (buffer[8] << 8) | buffer[9];

  pm25 =
      (buffer[10] << 8) | buffer[11];

  pm10 =
      (buffer[12] << 8) | buffer[13];

  return true;
}

//////////////////////////////////////////////////////////////

void showAQI(int value) {

  if (value <= 15) {

    Serial.println("Excellent");

    setColor(false, true, false);
  }

  else if (value <= 25) {

    Serial.println("Good");

    setColor(false, true, true);
  }

  else if (value <= 37) {

    Serial.println("Moderate");

    setColor(true, true, false);
  }

  else if (value <= 50) {

    Serial.println("Sensitive");

    setColor(true, true, true);
  }

  else if (value <= 90) {

    Serial.println("Unhealthy");

    setColor(true, false, false);
  }

  else {

    Serial.println("Hazardous");

    setColor(true, false, true);
  }

}

//////////////////////////////////////////////////////////////

void setColor(bool r, bool g, bool b) {

  digitalWrite(RED_PIN, r);
  digitalWrite(GREEN_PIN, g);
  digitalWrite(BLUE_PIN, b);

}