ผู้เริ่มต้น
สร้างเครื่องแสดงตำแหน่ง GPS
เซ็นเซอร์จอแสดงผลIoT
รู้ตำแหน่งของคุณอย่างแม่นยำภายในไม่กี่เมตร จากสัญญาณดาวเทียมจริง ไม่ต้องใช้โทรศัพท์ ไม่ต้องเชื่อมต่ออินเทอร์เน็ต
รวมชิ้นส่วนจริง 6 รายการ
ราคารวมชุดนี้: 1,685.00 ฿
ยังไม่รวมส่วนลดคำสั่งซื้อที่คุณอาจได้รับตอนชำระเงิน
สิ่งที่คุณต้องใช้
เป้าหมายของโครงการ
โครงการนี้สร้างอุปกรณ์แสดงตำแหน่งแบบสแตนด์อะโลน: ตัวควบคุมจะอ่านค่าตำแหน่งดาวเทียมจริงจากโมดูล GPS โดยเฉพาะ และแสดงละติจูดและลองจิจูดปัจจุบันของคุณบนหน้าจอขนาดเล็ก โดยทำงานแบบออฟไลน์ทั้งหมด ไม่มีการใช้โทรศัพท์ สัญญาณโทรศัพท์มือถือ หรือการเชื่อมต่ออินเทอร์เน็ตเมื่อโค้ดทำงานแล้ว – ตำแหน่งจะมาจากดาวเทียม GPS โดยตรง
สิ่งที่ตัวควบคุมทำ
ESP32-C3 SuperMini จะอ่านกระแสข้อมูลต่อเนื่องจากโมดูล GPS ผ่านการเชื่อมต่อแบบอนุกรม (UART) แยกข้อมูลที่สำคัญ เช่น ละติจูด ลองจิจูด และระดับความสูง และวาดจอแสดงผล OLED ใหม่ด้วยตำแหน่งปัจจุบันในช่วงเวลาปกติ
สิ่งที่โมดูล GPS ทำ
โมดูล GPS NEO-6M ทำงานเกี่ยวกับดาวเทียมจริง: มันติดตามดาวเทียม GPS คำนวณค่าตำแหน่ง และส่งผลลัพธ์ออกมาอย่างต่อเนื่องในรูปแบบประโยค NMEA มาตรฐานผ่าน UART NMEA เป็นรูปแบบข้อความที่ได้รับการยอมรับและรองรับอย่างกว้างขวาง ซึ่งเป็นเหตุผลที่มีไลบรารีการแยกวิเคราะห์ที่มีประสิทธิภาพสำหรับแพลตฟอร์มไมโครคอนโทรลเลอร์เกือบทุกชนิด – คุณไม่จำเป็นต้องแยกวิเคราะห์ประโยคดิบด้วยตนเอง
สิ่งที่จอแสดงผล OLED ทำ
OLED ขนาด 0.96 นิ้วเพียงแค่แสดงผลสิ่งที่ตัวควบคุมแยกวิเคราะห์ล่าสุดจาก GPS – ละติจูด ลองจิจูด และอาจเป็นระดับความสูงหรือสถานะการแก้ไข – ซึ่งจะรีเฟรชทุกรอบเพื่อให้หน้าจอแสดงข้อมูลล่าสุดที่โมดูลรายงานเสมอ
พื้นฐานการเดินสาย UART
โมดูล GPS สื่อสารผ่าน UART ซึ่งเป็นการเชื่อมต่อแบบอนุกรมสองสายง่ายๆ: พิน TX (ส่ง) ของโมดูลเชื่อมต่อกับพิน RX (รับ) ของตัวควบคุม และในทางกลับกัน การเชื่อมต่อ TX และ RX ผิดพลาด – การเชื่อมต่อ TX กับ TX – เป็นข้อผิดพลาดที่พบได้บ่อยมากสำหรับผู้เริ่มต้น และเป็นสิ่งแรกที่ต้องตรวจสอบหากไม่มีข้อมูลเข้ามา
แนวคิดซอฟต์แวร์และไลบรารี
เริ่มต้นจากไลบรารีการแยกวิเคราะห์ NMEA ที่ได้รับการทดสอบอย่างดีสำหรับแพลตฟอร์มตัวควบคุมของคุณ แทนที่จะเขียนการแยกวิเคราะห์ประโยคตั้งแต่เริ่มต้น – NMEA มีโครงสร้างตรวจสอบและโครงสร้างฟิลด์ที่กำหนดไว้ ซึ่งง่ายต่อการทำผิดพลาดเล็กน้อยด้วยมือ เมื่อไลบรารีรายงานว่าได้รับประโยคที่ถูกต้องแล้ว การดึงละติจูดและลองจิจูดมักจะเป็นการเรียกใช้ฟังก์ชันเพียงไม่กี่ครั้ง
การทดสอบและการแก้ไขปัญหา
- ไม่พบตำแหน่งเลย แม้จะรอไปแล้ว – ให้ย้ายไปยังตำแหน่งที่มีมุมมองท้องฟ้าที่ชัดเจนและไม่มีสิ่งกีดขวาง การรับสัญญาณ GPS จะไม่ทำงานในอาคารหรือภายใต้การปกคลุมหนาแน่น และนี่คือสาเหตุที่พบบ่อยที่สุดที่ทำให้โมดูล GPS 'ไม่ทำงาน'
- การเริ่มต้นแบบเย็นใช้เวลานานในการรับตำแหน่งแรก – นี่เป็นพฤติกรรม GPS ปกติ ไม่ใช่ข้อบกพร่อง เวลาในการรับตำแหน่งแรกอาจใช้เวลาประมาณ 30 วินาทีถึงหลายนาทีในการเริ่มต้นแบบเย็น ขึ้นอยู่กับการมองเห็นดาวเทียม
- ข้อมูลอนุกรมดูสับสนหรือไม่ปรากฏเลยในการเชื่อมต่อ UART – ตรวจสอบอีกครั้งว่า TX และ RX ไม่ได้สลับกันระหว่างโมดูลและตัวควบคุม นี่เป็นข้อผิดพลาดในการเดินสายที่พบบ่อยที่สุดกับอุปกรณ์เสริม UART ใดๆ
- หน้าจอแสดง 0,0 เป็นพิกัด – นี่หมายความว่ายังไม่ได้รับตำแหน่งที่ถูกต้อง ไม่ใช่ข้อบกพร่องในโค้ดของคุณ รอนานขึ้นและ/หรือย้ายไปยังที่ที่มีมุมมองท้องฟ้าที่ชัดเจนกว่าก่อนที่จะสรุปว่ามีบางอย่างเสีย
การอัปเกรดเสริมในอนาคต: การบันทึกเส้นทางเมื่อเวลาผ่านไป
เมื่อตำแหน่งปัจจุบันแสดงผลได้อย่างน่าเชื่อถือ ขั้นตอนต่อไปคือการบันทึกชุดของตำแหน่งเมื่อเวลาผ่านไป – ไม่ว่าจะบันทึกลงในหน่วยเก็บข้อมูลภายใน หรือรวมกับแนวคิดจากโครงการบันทึกข้อมูลไร้สาย ส่งออกผ่านเครือข่าย – เพื่อสร้างเส้นทางการเคลื่อนที่ที่เรียบง่ายแทนที่จะแสดงเพียงตำแหน่งปัจจุบัน
การเดินสาย
- NEO-6M VCC → ESP32-C3 SuperMini 5V (โมดูลมีตัวควบคุมในตัว, ทนต่อ 5V)
- NEO-6M GND → GND
- NEO-6M TX → GPIO20 (`GPS_RX_PIN`) — TX ของโมดูลเข้าสู่ RX ของตัวควบคุม
- NEO-6M RX → GPIO21 (`GPS_TX_PIN`) — RX ของโมดูลจาก TX ของตัวควบคุม (การไขว้ UART มาตรฐาน)
- OLED VCC → 3.3V
- OLED GND → GND
- OLED SDA → GPIO8 (`SDA_PIN`)
- OLED SCL → GPIO9 (`SCL_PIN`)
GPS ต้องการมุมมองท้องฟ้าที่ชัดเจน – ในอาคาร คาดว่า 'ไม่มีการแก้ไข' และจำนวนดาวเทียมเป็น 0 เป็นเวลานาน หรือตลอดไป; นั่นเป็นเรื่องปกติ ไม่ใช่ข้อบกพร่องในการเดินสาย การแก้ไขครั้งแรก ('cold start') มักใช้เวลา 30 วินาทีถึงสองสามนาที; การแก้ไขครั้งต่อๆ ไปหลังจากการสูญเสียพลังงานชั่วคราวมักจะเร็วกว่ามาก เมทริกซ์พินของ ESP32-C3 ช่วยให้สามารถแมป `HardwareSerial` ไปยัง GPIO แทบทุกพินได้ ดังนั้น GPS_RX_PIN/GPS_TX_PIN จึงไม่ใช่พิน UART ฮาร์ดแวร์ที่ตายตัว – ปรับ `#define`s หากคุณเดินสายไปยัง GPIO อื่นๆ
แผนภาพการต่อสาย
โค้ดเริ่มต้น
#include <Wire.h>
#include <Adafruit_GFX.h>
#include <Adafruit_SSD1306.h>
#include <TinyGPSPlus.h>
#define SDA_PIN 8 // ESP32-C3 default I2C SDA - adjust if your board differs
#define SCL_PIN 9 // ESP32-C3 default I2C SCL - adjust if your board differs
#define GPS_RX_PIN 20 // to GPS module TX - any free GPIO (remapped via pin matrix)
#define GPS_TX_PIN 21 // to GPS module RX - adjust to match your wiring if different
#define GPS_BAUD 9600 // NEO-6M default NMEA output baud rate
#define OLED_ADDRESS 0x3C
Adafruit_SSD1306 display(128, 64, &Wire, -1);
TinyGPSPlus gps;
HardwareSerial gpsSerial(1); // use UART1
unsigned long lastFixTime = 0;
void setup() {
Serial.begin(115200);
gpsSerial.begin(GPS_BAUD, SERIAL_8N1, GPS_RX_PIN, GPS_TX_PIN);
Wire.begin(SDA_PIN, SCL_PIN);
if (!display.begin(SSD1306_SWITCHCAPVCC, OLED_ADDRESS)) {
Serial.println("SSD1306 init failed");
while (true) delay(1000);
}
display.clearDisplay();
display.setTextColor(SSD1306_WHITE);
display.setTextSize(1);
display.setCursor(0, 0);
display.println("Waiting for GPS fix...");
display.println("(needs clear sky view,");
display.println("can take a few minutes)");
display.display();
}
void loop() {
while (gpsSerial.available() > 0) {
gps.encode(gpsSerial.read());
}
if (gps.location.isUpdated() && gps.location.isValid()) {
lastFixTime = millis();
display.clearDisplay();
display.setTextSize(1);
display.setCursor(0, 0);
display.println("GPS Fix");
display.setCursor(0, 14);
display.printf("Lat: %.6f\n", gps.location.lat());
display.printf("Lon: %.6f\n", gps.location.lng());
if (gps.altitude.isValid()) {
display.printf("Alt: %.1f m\n", gps.altitude.meters());
}
if (gps.satellites.isValid()) {
display.printf("Sats: %d\n", gps.satellites.value());
}
display.display();
Serial.printf("Lat: %.6f Lon: %.6f Sats: %d\n",
gps.location.lat(), gps.location.lng(), gps.satellites.value());
} else if (lastFixTime == 0 && millis() % 2000 < 20) {
// still searching for first fix - a normal wait indoors or under poor sky view
Serial.println("Searching for GPS fix...");
}
}
ไม่แน่ใจขั้นตอนไหน?
ถามเรา