Build Project

Sensor Projects

Build a Local NEO-6M GPS Reader

Build an ESP32 NEO-6M GPS reader with UART wiring, TinyGPS++ parsing, no-fix handling, sky-view guidance, and location privacy limits.

IntermediateAges 13+60-90 minUnder 25 USDParent Safe
Project Mission

Build a Local NEO-6M GPS Reader

The Story

The project is a receiver, not a cellular tracker or theft-recovery device. It does not upload location anywhere.

Explain Like I'm 12

The GPS module listens to satellites and sends text lines to the ESP32. The ESP32 waits until the lines contain a real fix before printing coordinates.

Learning Support

  • Recommended ageAges 13+
  • Adult supervisionAdult supervision recommended for outdoor testing and location privacy decisions.
  • Classroom useUse fake printed coordinates for discussion and test real fixes only with consent.
  • Parent promptAsk why a location project needs consent before tracking people or property.
  • Screen-free activityDraw how satellites, antenna sky view, UART bytes, and valid fixes connect.
  • Next challengeAdd an OLED display after the serial fix state is reliable.
  • Skills practiced
    • UART2 wiring
    • NMEA parsing
    • No-fix handling
    • Privacy boundaries
  • Learning outcomes
    • Wire GPS TX to ESP32 RX2 GPIO16.
    • Parse NMEA using TinyGPS++.
    • Print coordinates only when the fix is valid.
    • Explain cold start, sky view, and privacy limits.
  • Mini experiments
    • Compare no-fix and valid-fix Serial output.
    • Move the antenna from indoors to a window.
    • Log satellite count without sharing coordinates.

Safety Standards

  • Unplug USB before changing jumper wires. Recheck 3.3 V, 5 V, and GND before reconnecting power.
  • Do not power motors, pumps, LED strips, or servos from the ESP32 3.3 V pin. Use a suitable external supply and common ground.
  • Breadboards are for low-current prototypes. Move high-current or unattended builds to proper terminals, enclosure, strain relief, and fusing.

What You Will Build

A local GPS/GNSS reader that prints valid coordinates from a NEO-6M module to Serial Monitor.

Learning Objectives

  • Wire GPS TX to ESP32 RX2 GPIO16.
  • Parse NMEA using TinyGPS++.
  • Print coordinates only when the fix is valid.
  • Explain cold start, sky view, and privacy limits.

Components List

  • ESP32 DevKit boardUSB-programmable ESP32 board for the low-voltage logic side.
  • NEO-6M GPS/GNSS module with antennaUART module; use its documented supply range and logic level.
  • Breadboard and jumper wiresKeep UART wiring short for bench testing.
  • Optional USB power bankUseful for outdoor sky-view tests without exposing location online.

Bill of Materials

PartQtyEstimated CostNotes
ESP32 DevKit board1VariesUSB-programmable ESP32 board for the low-voltage logic side.
NEO-6M GPS/GNSS module with antenna1VariesUART module; use its documented supply range and logic level.
Breadboard and jumper wires1VariesKeep UART wiring short for bench testing.
Optional USB power bank1VariesUseful for outdoor sky-view tests without exposing location online.

Wiring

GPS TX connects to ESP32 GPIO16 RX2. GPS RX can connect to GPIO17 TX2 if configuration commands are needed.

Build a Local NEO-6M GPS Reader wiring diagram
  1. 1

    Unplug USB before wiring.

  2. 2

    Connect GPS GND to ESP32 GND.

  3. 3

    Connect GPS VCC to the voltage specified by your module breakout.

  4. 4

    Connect GPS TX to ESP32 GPIO16.

  5. 5

    Optionally connect GPS RX to ESP32 GPIO17.

  6. 6

    Place the antenna with clear sky view before expecting a valid fix.

GPIO Mapping

SignalESP32 PinDirectionNotes
NEO-6M TXGPIO16UART RX inputGPS transmits NMEA to ESP32 RX2.
NEO-6M RXGPIO17UART TX outputOptional; not needed for basic reading.
GPS VCC/GNDModule-rated VCC / GNDPowerFollow the breakout's voltage rating.

Circuit Explanation

The GNSS module streams NMEA sentences at 9600 baud. TinyGPS++ decodes bytes into fix status, coordinates, satellites, and HDOP.

Engineering Explanation

GPS needs sky view and time for a cold start. Indoor tests often receive UART text but no valid coordinates.

Libraries

  • TinyGPSPlusInstall TinyGPS++ from Arduino Library Manager.

Code

Copy into Arduino IDE. Install any libraries noted in the component guides first.

esp32-gps-tracker.ino
// ESP32 NEO-6M GPS reader
// Prints only valid fixes; no fabricated coordinates are used.
#include <TinyGPS++.h>

TinyGPSPlus gps;
HardwareSerial gpsSerial(2);

const int GPS_RX = 16; // ESP32 receives GPS TX here
const int GPS_TX = 17; // Optional ESP32 TX to GPS RX

unsigned long lastStatusMs = 0;

void setup() {
  Serial.begin(115200);
  gpsSerial.begin(9600, SERIAL_8N1, GPS_RX, GPS_TX);
  Serial.println("GPS reader ready. Place the antenna with a clear sky view.");
}

void loop() {
  while (gpsSerial.available()) {
    gps.encode(gpsSerial.read());
  }

  if (gps.location.isUpdated()) {
    if (gps.location.isValid()) {
      Serial.print("Latitude: ");
      Serial.println(gps.location.lat(), 6);
      Serial.print("Longitude: ");
      Serial.println(gps.location.lng(), 6);
      Serial.print("Satellites: ");
      Serial.println(gps.satellites.value());
      Serial.print("HDOP: ");
      Serial.println(gps.hdop.isValid() ? gps.hdop.hdop() : 0.0, 2);
      Serial.println("---");
    } else {
      Serial.println("GPS data received, but no valid location fix yet.");
    }
  }

  if (millis() - lastStatusMs > 5000) {
    lastStatusMs = millis();
    if (gps.charsProcessed() < 10) {
      Serial.println("No NMEA characters yet. Check TX-to-RX wiring and module power.");
    } else if (!gps.location.isValid()) {
      Serial.println("Waiting for satellite lock. Move antenna near a window or outdoors.");
    }
  }
}

Code Explanation

UART2 reads GPS bytes on GPIO16/GPIO17. The sketch prints location only when TinyGPS++ reports a valid updated fix.

Expected Output

Before satellite lock, Serial Monitor says it is waiting for a fix. After a valid fix, it prints latitude, longitude, satellites, and HDOP.

Troubleshooting

  • No characters processed Check that GPS TX goes to GPIO16 and the baud rate is 9600.
  • No valid fix Move outdoors or near a window and wait for cold start.
  • Coordinates look stale Check location.isUpdated() and antenna placement.

Common Mistakes

  • Swapping GPS TX/RX incorrectly.
  • Publishing real private coordinates.
  • Expecting indoor fixes.
  • Claiming guaranteed precision.

Testing Checklist

  • Confirm NMEA bytes are received before expecting a fix.
  • Test outdoors with consent.
  • Record only satellite count if privacy matters.

Engineering Tips

  • Keep the patch antenna facing upward.
  • Use fake example coordinates in notes.
  • Separate GPS from Wi-Fi geolocation in explanations.

Upgrade Ideas

  • Add OLED display.
  • Save local CSV logs only with consent.
  • Add a waypoint distance calculator using fake demo coordinates.

Real-World Applications

  • Satellite navigation lesson
  • Outdoor data logger prototype
  • Consent-based field mapping demo

FAQs

Is this a real-time tracker?

No. This page reads local GNSS data and does not upload it.

Can I track someone with it?

Only with clear consent and appropriate legal permission.

Why are coordinates missing indoors?

GPS signals are weak indoors and usually need sky view.

Review, Testing, and References

Author: Abdul Mubeen and the ESP32 Engine editorial team. Last updated: 2026-06-27. Reviewed: wiring logic, Arduino code structure, beginner safety, and learning sequence.

Educational level: Intermediate. Estimated completion time: 60-90 min. This project is for learning and prototyping; production or unattended hardware needs additional engineering review.

Project Complete!

You completed Build a Local NEO-6M GPS Reader with matching wiring, code, tests, and limitations.

  • UART2 wiring
  • NMEA parsing
  • No-fix handling