Guide to NEO-6M GPS Module with Arduino

This guide shows how to use the NEO-6M GPS module with the Arduino to get GPS data. GPS stands for Global Positioning System and can be used to determine position, time, and speed if you’re travelling.

You’ll learn how to:

  • Wire the NEO-6M GPS module to the Arduino UNO
  • Get raw GPS data
  • Parse raw data to obtain selected and readable GPS information
  • Get location

Introducing the NEO-6M GPS Module

The NEO-6M GPS module is shown in the figure below. It comes with an external antenna, and does’t come with header pins. So, you’ll need to get and solder some.

  • This module has an external antenna and built-in EEPROM.
  • Interface: RS232 TTL
  • Power supply: 3V to 5V
  • Default baudrate: 9600 bps
  • Works with standard NMEA sentences

The NEO-6M GPS module is also compatible with other microcontroller boards. To learn how to use the NEO-6M GPS module with the Raspberry Pi, you can read: Email Alert System on Location Change with Raspberry Pi and GPS Module.

Where to buy?

You can get the NEO-6M GPS module for a price between $5 to $20. We recommend checking the NEO-6M GPS module page on Maker Advisor to compare the price in different stores and find the best one.

Pin Wiring

The NEO-6M GPS module has four pins: VCC, RX, TX, and GND. The module communicates with the Arduino via serial communication using the TX and RX pins, so the wiring couldn’t be simpler:

NEO-6M GPS ModuleWiring to Arduino UNO
VCC5V
RXTX pin defined in the software serial
TXRX pin defined in the software serial
GNDGND

Getting GPS Raw Data

To get raw GPS data you just need to start a serial communication with the GPS module using Software Serial. Continue reading to see how to do that.

Parts Required

For testing this example you’ll need the following parts:

You can use the preceding links or go directly to MakerAdvisor.com/tools to find all the parts for your projects at the best price!

Schematics

Wire the NEO-6M GPS module to your Arduino by following the schematic below.

  • The module GND pin is connected to Arduino GND pin
  • The module RX pin is connected to Arduino pin 3
  • The module TX pin is connected to Arduino pin 4
  • The module VCC pin is connected to Arduino 5V pin

Code

Copy the following code to your Arduino IDE and upload it to your Arduino board.

/*
 * Rui Santos 
 * Complete Project Details https://randomnerdtutorials.com
 */
 
#include <SoftwareSerial.h>

// The serial connection to the GPS module
SoftwareSerial ss(4, 3);

void setup(){
  Serial.begin(9600);
  ss.begin(9600);
}

void loop(){
  while (ss.available() > 0){
    // get the byte data from the GPS
    byte gpsData = ss.read();
    Serial.write(gpsData);
  }
}

View raw code

This sketch assumes you are using pin 4 and pin 3 as RX and TX serial pins to establish serial communication with the GPS module. If you’re using other pins you should edit that on the following line:

SoftwareSerial ss(4, 3);

Also, if your module uses a different default baud rate than 9600 bps, you should modify the code on the following line:

ss.begin(9600);

This sketch listen to the GPS serial port, and when data is received from the module, it is sent to the serial monitor.

while (ss.available() > 0){
  // get the byte data from the GPS
  byte gpsData = ss.read();
  Serial.write(gpsData);
}

Open the Serial Monitor at a baud rate of 9600.

You should get a bunch of information in the GPS standard language, NMEA. Each line you get int the serial monitor is an NMEA sentence.

NMEA stands for National Marine Electronics Association, and in the world of GPS, it is a standard data format supported by GPS manufacturers.

Understanding NMEA Sentences

NMEA sentences start with the $ character, and each data field is separated by a comma.

$GPGGA,110617.00,41XX.XXXXX,N,00831.54761,W,1,05,2.68,129.0,M,50.1,M,,*42
$GPGSA,A,3,06,09,30,07,23,,,,,,,,4.43,2.68,3.53*02
$GPGSV,3,1,11,02,48,298,24,03,05,101,24,05,17,292,20,06,71,227,30*7C
$GPGSV,3,2,11,07,47,138,33,09,64,044,28,17,01,199,,19,13,214,*7C
$GPGSV,3,3,11,23,29,054,29,29,01,335,,30,29,167,33*4E
$GPGLL,41XX.XXXXX,N,00831.54761,W,110617.00,A,A*70
$GPRMC,110618.00,A,41XX.XXXXX,N,00831.54753,W,0.078,,030118,,,A*6A 
$GPVTG,,T,,M,0.043,N,0.080,K,A*2C

There are different types of NMEA sentences. The type of message is indicated by the characters before the first comma.

The GP after the $ indicates it is a GPS position.  The $GPGGA is the basic GPS NMEA message, that provides 3D location and accuracy data. In the following sentence:

$GPGGA,110617.00,41XX.XXXXX,N,00831.54761,W,1,05,2.68,129.0,M,50.1,M,,*42
  • 110617 – represents the time at which the fix location was taken, 11:06:17 UTC
  • 41XX.XXXXX,N – latitude 41 deg XX.XXXXX’ N
  • 00831.54761,W – Longitude 008 deg 31.54761′ W
  • 1 – fix quality (0 = invalid; 1= GPS fix; 2 = DGPS fix; 3 = PPS fix; 4 = Real Time Kinematic; 5 = Float RTK; 6 = estimated (dead reckoning); 7 = Manual input mode; 8 = Simulation mode)
  • 05 – number of satellites being tracked
  • 2.68 – Horizontal dilution of position
  • 129.0, M – Altitude, in meters above the sea level
  • 50.1, M – Height of geoid (mean sea level) above WGS84 ellipsoid
  • empty field – time in seconds since last DGPS update
  • empty field – DGPS station ID number
  • *42 – the checksum data, always begins with *

The other NMEA sentences provide additional information:

  • $GPGSA – GPS DOP and active satellites
  • $GPGSV – Detailed GPS satellite information
  • $GPGLL – Geographic Latitude and Longitude
  • $GPRMC – Essential GPS pvt (position, velocity, time) data
  • $GPVTG – Velocity made good

To know what each data field means in each of these sentences, you can consult NMEA data here.

Parsing NMEA Sentences with TinyGPS++ Library

You can work with the raw data from the GPS, or you can convert those NMEA messages into a readable and useful format, by saving the characters sequences into variables. To do that, we’re going to use the TinyGPS++ library.

This library makes it simple to get information on location in a format that is useful and easy to understand.

Installing the TinyGPS++ Library

In the Arduino IDE, go to Sketch > Include Library > Manage Libraries or click on the Libary Manager icon at the left sidebar.

Search for TinyGPSPlus and install the library by Mikal Hart.

Installing TinyGPSPlus Library Arduino IDE

The library provides several examples of how to use it. In your Arduino IDE, you just need to go to File Examples > TinyGPS++, and choose from the examples provided.

Note: the examples provided in the library assume a baud rate of 4800 for the GPS module. You need to change that to 9600, if you’re using the NEO-6M GPS module.

Getting Location Using the NEO-6M GPS Module and the TinyGPS++ Library

You can get the location in a format that is convenient and useful by using the TinyGPS++ library. Below, we provide a code to get the location from the GPS. This is a simplified version of one of the library examples.

/*
 * Rui Santos 
 * Complete Project Details https://randomnerdtutorials.com
 */
 
#include <TinyGPS++.h>
#include <SoftwareSerial.h>

static const int RXPin = 4, TXPin = 3;
static const uint32_t GPSBaud = 9600;

// The TinyGPS++ object
TinyGPSPlus gps;

// The serial connection to the GPS device
SoftwareSerial ss(RXPin, TXPin);

void setup(){
  Serial.begin(9600);
  ss.begin(GPSBaud);
}

void loop(){
  // This sketch displays information every time a new sentence is correctly encoded.
  while (ss.available() > 0){
    gps.encode(ss.read());
    if (gps.location.isUpdated()){
      Serial.print("Latitude= "); 
      Serial.print(gps.location.lat(), 6);
      Serial.print(" Longitude= "); 
      Serial.println(gps.location.lng(), 6);
    }
  }
}

View raw code

You start by importing the needed libraries: TinyGPSPlus and SoftwareSerial

#include <TinyGPS++.h>
#include <SoftwareSerial.h>

Then, you define the software serial RX and TX pins, as well as the GPS baud rate. If you are using other pins for software serial you need to change that here. Also, if your GPS module uses a different default baud rate, you should also modify that.

static const int RXPin = 4, TXPin = 3;
static const uint32_t GPSBaud = 9600;

Then, you create a TinyGPS++ object:

TinyGPSPlus gps;

And start a serial connection on the pins you’ve defined earlier

SoftwareSerial ss(RXPin, TXPin);

In the setup(), you initialize serial communication, both to see the readings on the serial monitor and to communicate with the GPS module.

void setup() {
  Serial.begin(9600);
  ss.begin(GPSBaud);
}

In the loop is where you request the information. To get TinyGPS++ to work, you have to repeatedly funnel the characters to it from the GPS module using the encode() method.

while (ss.available() > 0){
 gps.encode(ss.read());

Then, you can query the gps object to see if any data fields have been updated:

if (gps.location.isUpdated()){
  Serial.print("Latitude="); Serial.print(gps.location.lat(), 6);
  Serial.print("Longitude="); Serial.println(gps.location.lng(), 6);
}

Getting the latitude and longitude is as simple has using gps.location.lat(), and gps.location.lng(), respectively.

Upload the code to your Arduino, and you should see the location displayed on the serial monitor. After uploading the code, wait a few minutes while the module adjusts the position to get more accurate data.

Getting More GPS Information Using the TinyGPS++ Library

The TinyGPS++ library allows you to get way more information than just the location, and in a simple way. Besides the location, you can get:

  • date
  • time
  • speed
  • course
  • altitude
  • satellites
  • hdop

The code below exemplifies how you can get all that information in a simple way.

/*
 * Rui Santos 
 * Complete Project Details https://randomnerdtutorials.com
 *
 * Based on the example TinyGPS++ from arduiniana.org
 *
 */
 
#include <TinyGPS++.h>
#include <SoftwareSerial.h>

static const int RXPin = 4, TXPin = 3;
static const uint32_t GPSBaud = 9600;

// The TinyGPS++ object
TinyGPSPlus gps;

// The serial connection to the GPS device
SoftwareSerial ss(RXPin, TXPin);

void setup(){
  Serial.begin(9600);
  ss.begin(GPSBaud);
}

void loop(){
  // This sketch displays information every time a new sentence is correctly encoded.
  while (ss.available() > 0){
    gps.encode(ss.read());
    if (gps.location.isUpdated()){
      // Latitude in degrees (double)
      Serial.print("Latitude= "); 
      Serial.print(gps.location.lat(), 6);      
      // Longitude in degrees (double)
      Serial.print(" Longitude= "); 
      Serial.println(gps.location.lng(), 6); 
       
      // Raw latitude in whole degrees
      Serial.print("Raw latitude = "); 
      Serial.print(gps.location.rawLat().negative ? "-" : "+");
      Serial.println(gps.location.rawLat().deg); 
      // ... and billionths (u16/u32)
      Serial.println(gps.location.rawLat().billionths);
      
      // Raw longitude in whole degrees
      Serial.print("Raw longitude = "); 
      Serial.print(gps.location.rawLng().negative ? "-" : "+");
      Serial.println(gps.location.rawLng().deg); 
      // ... and billionths (u16/u32)
      Serial.println(gps.location.rawLng().billionths);

      // Raw date in DDMMYY format (u32)
      Serial.print("Raw date DDMMYY = ");
      Serial.println(gps.date.value()); 

      // Year (2000+) (u16)
      Serial.print("Year = "); 
      Serial.println(gps.date.year()); 
      // Month (1-12) (u8)
      Serial.print("Month = "); 
      Serial.println(gps.date.month()); 
      // Day (1-31) (u8)
      Serial.print("Day = "); 
      Serial.println(gps.date.day()); 

      // Raw time in HHMMSSCC format (u32)
      Serial.print("Raw time in HHMMSSCC = "); 
      Serial.println(gps.time.value()); 

      // Hour (0-23) (u8)
      Serial.print("Hour = "); 
      Serial.println(gps.time.hour()); 
      // Minute (0-59) (u8)
      Serial.print("Minute = "); 
      Serial.println(gps.time.minute()); 
      // Second (0-59) (u8)
      Serial.print("Second = "); 
      Serial.println(gps.time.second()); 
      // 100ths of a second (0-99) (u8)
      Serial.print("Centisecond = "); 
      Serial.println(gps.time.centisecond()); 

      // Raw speed in 100ths of a knot (i32)
      Serial.print("Raw speed in 100ths/knot = ");
      Serial.println(gps.speed.value()); 
      // Speed in knots (double)
      Serial.print("Speed in knots/h = ");
      Serial.println(gps.speed.knots()); 
      // Speed in miles per hour (double)
      Serial.print("Speed in miles/h = ");
      Serial.println(gps.speed.mph()); 
      // Speed in meters per second (double)
      Serial.print("Speed in m/s = ");
      Serial.println(gps.speed.mps()); 
      // Speed in kilometers per hour (double)
      Serial.print("Speed in km/h = "); 
      Serial.println(gps.speed.kmph()); 

      // Raw course in 100ths of a degree (i32)
      Serial.print("Raw course in degrees = "); 
      Serial.println(gps.course.value()); 
      // Course in degrees (double)
      Serial.print("Course in degrees = "); 
      Serial.println(gps.course.deg()); 

      // Raw altitude in centimeters (i32)
      Serial.print("Raw altitude in centimeters = "); 
      Serial.println(gps.altitude.value()); 
      // Altitude in meters (double)
      Serial.print("Altitude in meters = "); 
      Serial.println(gps.altitude.meters()); 
      // Altitude in miles (double)
      Serial.print("Altitude in miles = "); 
      Serial.println(gps.altitude.miles()); 
      // Altitude in kilometers (double)
      Serial.print("Altitude in kilometers = "); 
      Serial.println(gps.altitude.kilometers()); 
      // Altitude in feet (double)
      Serial.print("Altitude in feet = "); 
      Serial.println(gps.altitude.feet()); 

      // Number of satellites in use (u32)
      Serial.print("Number os satellites in use = "); 
      Serial.println(gps.satellites.value()); 

      // Horizontal Dim. of Precision (100ths-i32)
      Serial.print("HDOP = "); 
      Serial.println(gps.hdop.value()); 
    }
  }
}

View raw code

Wrapping Up

We hope you’ve found this guide useful. We intend to make a GPS data logger with the NEO-6M GPS module and the SD card module, so stay tuned.

If you liked this project you may also like:

Thanks for reading.



Learn how to build a home automation system and we’ll cover the following main subjects: Node-RED, Node-RED Dashboard, Raspberry Pi, ESP32, ESP8266, MQTT, and InfluxDB database DOWNLOAD »
Learn how to build a home automation system and we’ll cover the following main subjects: Node-RED, Node-RED Dashboard, Raspberry Pi, ESP32, ESP8266, MQTT, and InfluxDB database DOWNLOAD »

Enjoyed this project? Stay updated by subscribing our newsletter!

161 thoughts on “Guide to NEO-6M GPS Module with Arduino”

  1. 1:
    why this void setup() {
    Serial.begin(115200);
    ss.begin(GPSBaud);
    }
    erlier you said 9600

    2:
    Serial.print(gps.location.lat(), 6);

    what makes the number 6 ?

    3:
    Howe can I write to get the readings in “Degrees minutes seconds formats (DDD MM SS)”

    Regards

    Bertil

    Reply
    • Hi Bertil.

      1. It is 9600. I’ve already corrected that. Thanks for noticing.
      2. The 6 specifies the number of decimal places.
      3. You can get the location in that format in the $GPGLL NMEA sentence, when you get the raw data. To do that with the library, check the “Custom NMEA Sentence Extraction” in the library documentation here http://arduiniana.org/libraries/tinygpsplus/

      Thanks.
      Sara

      Reply
      • NEO-6M can do upto 14 decimal places for Lat & Lon

        = > (gps.location.lat(), 14)
        => (gps.location.lng(), 14)

        and 7 decimal places for Altitude

        => (gps.altitude.meters(), 7);

        Thanks for wonderful tutorials Rui Santos

        Reply
        • Those extra decimals in output are just noise. One degree in earth surface means about 110km. So 6th decimal (in latitude) means 10cm which is for standard GPS just enough. For high precision GPS (which this is not) you can achieve cm level accuracy. And of course for altitude you don’t get real micrometer accuracy 😉

          Reply
  2. Thank you very much for this Guide. I have had this module for several weeks now and followed many guides but I could not get it to receive GPS DATA, yet alone to display it in the Serial Monitor. The I found your Guide to the NEO-6M GPS Module.
    When I first ran the “Getting GPS Raw Data” code, I was excited that it worked first time.
    I then tried the “Getting Location ” code. After 5 seconds it started to display the Lat & Long location. Two successes.
    Thirdly, I had a go at the “Getting More GPS Information” code. After several tries I was disappointed that I was seeing no GPS DATA on the monitor. I spent the next 5 minutes looking over the code, trying to find out where I had gone wrong. Then suddenly, the monitor came to life and there was the GPS DATA being displayed and updating. I was impressed. You had done what many other codes could not do, you enabled me to receive the GPS DATA.

    Next project – Add a 0.96” OLED display and make the PGS portable.

    Kudos for this guide..

    Reply
    • Hi Lance!
      We always do our best to make our guides easy to follow, so that anyone is able to follow along.
      We’re happy to hear that you’ve found this guide useful, and that your GPS module is working perfectly.
      We also intend to make a new GPS project – a GPS datalogger – in a near future, so stay tuned.
      Regards,
      Sara 🙂

      Reply
  3. Hello!
    Thank you for the tutorial!
    Can I get a signal to synchronize time with my DS3231? Are new sentences sent in 00 seconds?

    Reply
  4. Hello! I need a clock that contains the RTC block DS3231 to be precisely tuned to the other, which is several kilometers away. In my opinion, the only way through the GPS. How do i do this?

    Reply
  5. Hi, I have a NEO6M GPS board from Wish, following this guide does not give me the NMEA sentences, all I get on the serial monitor is
    UBX-G60xx 00040007 FF47FFFFp)Z⸮b*ROM CORE 7.03 (45969) Mar 1
    repeating over and over again. My baud rate is set at 57600. My board is connected to the arduino 3.3V out and I have a voltage divider between Arduino TX and the module RX. The red light on the board is always on, and it does feel hot to the touch.

    Any ideas?

    Reply
  6. Yet another well presented tutorial – Thank You.
    Questions:
    Why is some data reported as zero: altitude = 0.00, number of satellites = 0?
    Is there an equivalent SoftwareSerial library for the ESP32?
    Why do several of the items have “double” in the comments in the code? Is the data presented half of the real value or twice the real value?

    Reply
    • Hi Stew! Thanks for your kind words. The variable declared as double simply means “Double variable = Double precision floating point number. On the Uno and other ATMEGA based boards, this occupies 4 bytes. That is, the double implementation is exactly the same as the float, with no gain in precision.” More information here: arduino.cc/reference/en/language/variables/data-types/double/

      I guess that happens (altitude = 0) when the requests fails to retrieve the data properly…

      Reply
  7. Hey! Thanks for such a useful tutorial. I was wondering if there is any way to reduce the time taken by the GPS module before it starts displaying data?

    Reply
  8. do you by any chance have a code that also saves it to a SD card? I am trying to figure that out but it not going well.

    Reply
  9. Great tutorial you got here..I would like to take this project a step further and turn on and off a relay once a certain speed is output. How can this be achieved? do you already have any tutorial to demonstrate this? Thanks in advance!

    Reply
      • ss.read() function is reading character but they are not valid so the location is not show can you provide your email so that i can contact you.

        Reply
        • We receive lots of questions everyday. Unfortunately, we’re not able to provide email support to all our readers.
          Have you tried both codes on our tutorial?
          The one with the TinyGPS++ Library??
          Are you wiring your GPS module correctly? Our sketch assumes you are using pins 4 and 3 as RX and TX serial pins to establish serial communication with the GPS module.
          Try swapping the RX with the TX wires and see if you’re able to get the right information.
          I hope this helps.
          Regards,
          Sara 🙂

          Reply
          • /*
            * Rui Santos
            * Complete Project Details https://randomnerdtutorials.com
            */

            #include
            #include

            static const int RXPin = 4, TXPin = 3;
            static const uint32_t GPSBaud = 9600;

            // The TinyGPS++ object
            TinyGPSPlus gps;

            // The serial connection to the GPS device
            SoftwareSerial ss(RXPin, TXPin);

            void setup(){
            Serial.begin(9600);
            ss.begin(GPSBaud);
            }

            void loop(){
            // This sketch displays information every time a new sentence is correctly encoded.
            while (ss.available() > 0){
            gps.encode(ss.read());
            if (gps.location.isUpdated()){
            Serial.print(“Latitude= “);
            Serial.print(gps.location.lat(), 6);
            Serial.print(” Longitude= “);
            Serial.println(gps.location.lng(), 6);
            }
            else{
            Serial.print(“L”);
            }
            }
            }

            this code always return else statement not return if?

          • That means that your Arduino is not receiving any information from the GPS module.
            Please double check the wiring and try to change the RX with the TX pins and the other way around and see if you can get something.
            If not, maybe your GPS module is broken or something 🙁

  10. Wow, great tutorial, really helped a lot but the problem I am facing is that, when I tried to use this code with the GSM module, trying to send the coordinates in a message to a specified number, the line
    ss.begin (GPSBaud)
    does not allow my message to be sent. Message will send if I comment that line out. Anyone who can help?

    Reply
  11. Hi,

    I’ve a problem with my GPS module. After connecting it to Uno, a red LED on the GPS module blinks once, and then nothing. There is no further blinking, and no data is received on the serial monitor.
    I tried it outside in open sky, waited for around an hour, still no fix.
    I connected VCC of the module directly to the 5V pin of the Uno, no pull-up resistors were used.

    Is it a wiring/connection problem? I’ve soldered header pins to the Neo 6M GPS module, and there is no shorting.

    Please reply asap.

    Thanks and regards,
    Joe

    Reply
  12. Two comments
    1. Re the accuracy/stability of the NEO-6M itself.
    In the example the longitude is given as 8.525774 with variations in the last digit – my experience with the device over several hours the variation could be in the last 3 figures. Reading two devices at the same time they did not give the same result and they did not track.
    2.Re the TinyGPS++ in general I obtained the same results as the example except every 10 seconds or so the display had a glitch. By lowering the baud rate of the output to 9600 – the same as the GPS – the issue went away. Going to higher baud rates the issue became worse. I wonder if the output was “catching” up to the input – I think one would really need to know the nuts and bolts of the TinyGPS++ and Serial Libraries to really figure it out.

    Reply
    • Hi.
      Can you check you have the TX and RX cables correctly wired?
      Also check you are setting the right baud rate on the Serial monitor.
      If you don’t get any response from the sensor, it may be something wrong with the sensor itself.
      Regards,
      Sara.

      Reply
  13. If precise readings are required I think there is an issue with the GPS examples due to the limited precision of the Arduino UNO. In the Uno using double only gives the same precision as float – ie 4 bytes which from the Arduino reference is approximately 6-7 decimal digits. Since in Rui/Sara’s example the longitude is only 8 degrees their example has only 7 digits so does not appear to run into problems.
    However I’m at 145.073736 which is 9 digits. Using TinyGPS++ always gives a “0” in that 6th decimal place – I suspect the 5th place is also subject to some error. I’ve looked at the TinyGPS++ code and the only issue is they convert their readings into double. The problem then is that for the Arduino Uno double precision is the same as float and is only 4 bytes – not sufficient for the GPS. Refer to Arduino Reference for “double” – they warn about being aware when importing code into the Arduino. Note for the Due double is 8 bytes so will be OK.
    Having said all that – using the GPS can give some fun projects but don’t expect to drive a robot down the centre line of the highway!

    Reply
  14. Hello,
    Great tutorial guys and a great code. I have a problem with the altitude it is showing always as zero. Does it need some calibration first or there is some other fix? All other data are showing nicely (altitude, longitude, date, time, number of satellites, speed…)

    Thanks a lot

    Reply
    • Hi Anthony.
      It doesn’t need any calibration. At least, in our example, we’ve just uploaded the sample code, and everything worked nicely.
      Did you experiment the simple example sketch that returns NMEA sentences? And using TinyGPS library? Do you get the same results using both methods?
      Regards,
      Sara 🙂

      Reply
  15. Hi, I have try for the second code that display longitude and latitude, but nothing come out from serial monitor….Can help me ? Thank you

    Reply
    • Hi Min.
      What about the first code? Did it worked well?
      It’s weird that the code with the library is not working :/
      Regards,
      Sara 🙂

      Reply
  16. Hey guys! Great tutorial!
    I tried out the code and everything was working perfectly fine at first. Unfortunately, the only values that seem to be updating are those for Latitude and Longitude, all other values display 0. Is there any way to solve this?

    Reply
    • Hi Hector.
      Other readers reported the same problem.
      Unfortunately I have no idea why that is happening.
      If you find a solution please let as know.
      Regards,
      Sara 🙂

      Reply
  17. In the final code you have RXPin = 4, TXPin = 3; but above the first code with serial it says RXPin is pin 3 and TXPin is pin 4 ? Please explain! The first code works, but not the final code

    Reply
  18. am using ublox-neo 6m and arduino uno am getting imformation but time is behinde by 2hrs… How can I correct my code to get the right time am in Malawi (Africa) below is my code am using
    #include
    #include
    /*
    This sample code demonstrates the normal use of a TinyGPS++ (TinyGPSPlus) object.
    It requires the use of SoftwareSerial, and assumes that you have a
    4800-baud serial GPS device hooked up on pins 4(rx) and 3(tx).
    */
    static const int RXPin = 11, TXPin = 10;
    static const uint32_t GPSBaud = 9600;

    // The TinyGPS++ object
    TinyGPSPlus gps;

    // The serial connection to the GPS device
    SoftwareSerial ss(RXPin, TXPin);

    void setup()
    {
    Serial.begin(115200);
    ss.begin(GPSBaud);

    Serial.println(F(“FullExample.ino”));
    Serial.println(F(“An extensive example of many interesting TinyGPS++ features”));
    Serial.print(F(“Testing TinyGPS++ library v. “)); Serial.println(TinyGPSPlus::libraryVersion());
    Serial.println(F(“by Rodrick Custom Dzonzi”));
    Serial.println();
    Serial.println(F(“Sats HDOP Latitude Longitude Fix Date Time Date Alt Course Speed Card Distance Course Card Chars Sentences Checksum”));
    Serial.println(F(” (deg) (deg) Age Age (m) — from GPS —- —- to London —- RX RX Fail”));
    Serial.println(F(“—————————————————————————————————————————————-“));
    }

    void loop()
    {
    static const double LONDON_LAT = 0.00, LONDON_LON = 0.00;

    printInt(gps.satellites.value(), gps.satellites.isValid(), 5);
    printFloat(gps.hdop.hdop(), gps.hdop.isValid(), 6, 1);
    printFloat(gps.location.lat(), gps.location.isValid(), 11, 6);
    printFloat(gps.location.lng(), gps.location.isValid(), 12, 6);
    printInt(gps.location.age(), gps.location.isValid(), 5);
    printDateTime(gps.date, gps.time);
    printFloat(gps.altitude.meters(), gps.altitude.isValid(), 7, 2);
    printFloat(gps.course.deg(), gps.course.isValid(), 7, 2);
    printFloat(gps.speed.kmph(), gps.speed.isValid(), 6, 2);
    printStr(gps.course.isValid() ? TinyGPSPlus::cardinal(gps.course.deg()) : “*** “, 6);

    unsigned long distanceKmToLondon =
    (unsigned long)TinyGPSPlus::distanceBetween(
    gps.location.lat(),
    gps.location.lng(),
    LONDON_LAT,
    LONDON_LON) / 1000;
    printInt(distanceKmToLondon, gps.location.isValid(), 9);

    double courseToLondon =
    TinyGPSPlus::courseTo(
    gps.location.lat(),
    gps.location.lng(),
    LONDON_LAT,
    LONDON_LON);

    printFloat(courseToLondon, gps.location.isValid(), 7, 2);

    const char *cardinalToLondon = TinyGPSPlus::cardinal(courseToLondon);

    printStr(gps.location.isValid() ? cardinalToLondon : “*** “, 6);

    printInt(gps.charsProcessed(), true, 6);
    printInt(gps.sentencesWithFix(), true, 10);
    printInt(gps.failedChecksum(), true, 9);
    Serial.println();

    smartDelay(10000);

    if (millis() > 5000 && gps.charsProcessed() < 10)
    Serial.println(F("No GPS data received: check wiring"));
    }

    // This custom version of delay() ensures that the gps object
    // is being "fed".
    static void smartDelay(unsigned long ms)
    {
    unsigned long start = millis();
    do
    {
    while (ss.available())
    gps.encode(ss.read());
    } while (millis() – start 1)
    Serial.print(‘*’);
    Serial.print(‘ ‘);
    }
    else
    {
    Serial.print(val, prec);
    int vi = abs((int)val);
    int flen = prec + (val = 1000 ? 4 : vi >= 100 ? 3 : vi >= 10 ? 2 : 1;
    for (int i=flen; i<len; ++i)
    Serial.print(' ');
    }
    smartDelay(0);
    }

    static void printInt(unsigned long val, bool valid, int len)
    {
    char sz[32] = "*****************";
    if (valid)
    sprintf(sz, "%ld", val);
    sz[len] = 0;
    for (int i=strlen(sz); i 0)
    sz[len-1] = ‘ ‘;
    Serial.print(sz);
    smartDelay(0);
    }

    static void printDateTime(TinyGPSDate &d, TinyGPSTime &t)
    {
    if (!d.isValid())
    {
    Serial.print(F(“********** “));
    }
    else
    {
    char sz[32];
    sprintf(sz, “%02d/%02d/%02d “, d.month(), d.day(), d.year());
    Serial.print(sz);
    }

    if (!t.isValid())
    {
    Serial.print(F(“++3600000 “));
    }
    else
    {
    char sz[32];
    sprintf(sz, “%02d:%02d:%02d “, t.hour(), t.minute(), t.second());
    Serial.print(sz);

    }

    printInt(d.age(), d.isValid(), 5);
    smartDelay(0);
    }

    static void printStr(const char *str, int len)
    {
    int slen = strlen(str);
    for (int i=0; i<len; ++i)
    Serial.print(i<slen ? str[i] : ' ');
    smartDelay(0);
    }

    please help me how I can edit my code to have correct time

    my email: [email protected]

    Reply
    • Hi.
      Take a look at the following example.
      It might help. instructables.com/id/Adjusting-GPS-Date-and-Time-to-your-Time-Zone/
      Regards,
      Sara

      Reply
  19. Hi Rui.

    I cannot get your sketch to display gps data frommy neo-6m.

    I know the gps unit has a fix and generating NMEA sentences with full location data by using the u-blox u-center software. When I disconnect U-center from the gps unit and try to read the messages with your sketch it displays zeros, not valid data.

    I have baud rates correct. I have the pin connection correct.

    Can you advise me what I can do to learn why the sketch is not seeing the gps data,please?

    Thanks.

    Reply
  20. Hi I’m still having difficulty downloading TinyGPSPlus from github. I’ve tried downloading by ZIP and recently by cloning and it downloads all but the .CPP and .H files. So far Github has been unable to help. Is there any other source besides Github for this library? Thanks

    Reply
  21. How do I connect my GPS to a 16*2 lcd with potentiometer? And what changes do I need to make to the code in order display all GPS data on my lcd?

    Reply
  22. At first, the two TinyGPS++ sketches didn’t show any data. But after five minutes, the module’s LED began blinking and all the data began to appear in the serial monitor.

    Great project, Rui and Sara!

    Reply
    • Hi Joel.
      I’m happy that it worked.
      Maybe the GPS module just needed some time to connect and find satellites.

      Regards,
      Sara

      Reply
  23. Hi guys, thanks for this tutorial well explained, as always 🙂

    I have a question, I tried to execute the first program and I got those results :

    $GPRMC,,V,,,,,,,,,,N*53
    $GPVTG,,,,,,,,,N*30
    $GPGGA,,,,,,0,00,99.99,,,,,,*48
    $GPGSA,A,1,,,,,,,,,,,,,99.99,99.99,99.99*30
    $GPGSV,1,1,00*79
    $GPGLL,,,,,,V,N*64

    After looking on others forums it seems that satellites don’t see my GPS, do you have any idea of how could I get normal sentences ?

    Thanks !

    Reply
    • Hi.
      What do you mean by “satellites don’t see my GPS”?
      Have you tried this library: arduiniana.org/libraries/tinygpsplus/
      Did you get weird results with this library too?
      Regards,
      Sara

      Reply
      • Hi tanks for reply !
        Well I meant : It seems that my gps isn’t able to get informations from satellites, because the NMEA sentences returned are “empty”.

        When I used the tinygpsplus library, I firstly got nothing, then I deleted the iteration “if (gps.location.isUpdated())”, and I got everything at 0 :
        Latitude= 0.000000 Longitude= 0.000000
        Raw date DDMMYY = 0
        Speed in m/s = 0.00
        Speed in km/h = 0.00
        Altitude in meters = 0.00
        Number os satellites in use = 0
        So not weird results (because my NMEA sentences are empty), but not good to…

        Reply
  24. Hello, I want to read exact location of mobile ( longitude and latitude ) by using bluetooth HC-05 Module.
    is it possible? or please tell me if there is any other way…

    Reply
  25. Hi, thank you for the article.
    When I open my serial monitor, all I get is a bunch of weird gibberish characters. Do you know how to fix the problem?
    Thank you

    Reply
  26. Hi
    I wanted to make a GPS logger. I have been trying to follow tutorials on the internet but I have had no luck yet. Could anyone please help? my hardware is and arduino uno which it temporary replacing a nano, neo m6 ublox GPS module and an SD card module.

    Thank You

    Reply
  27. I have Got Longitude and latitude successfully now i want to save these longitude and latitude in database. i am using esp8266 esp01 with arduino uno and neo6m gps. can you please guide me how i can send it to database using esp8266.

    Reply
  28. A number of people are having a problem with the number of satellites and the altitude reporting 0. I changed the serial baud rate at Serial.begin to 115200 in the code and also in the serial monitor to 115200 and it is now giving me the number of satellites and altitude.
    Everything is working great now. Thanks so much for this tutorial.

    Reply
  29. Hello, great piece of code, was wondering on the code I would use to display output from the Serial.print to lcd.print, how can I connect the output of latitude and longitude from the serial print to my LCD.

    Reply
  30. Would like to make a clock – shift registers to LED display using the GPS – any future project?
    Purely Hours – minutes and seconds.
    How do you alter Hours to GMT +2 ??

    Reply
  31. I have Got Longitude and latitude successfully now i want to save these longitude and latitude in database online. i am using esp8266 esp01 and neo6m gps. can you please guide me how i can send it to database using esp8266.

    Reply
  32. Hi! This might be a stupid question but why do I have to use the TX/RX pins? Can I use other Digital Pins? I’m asking because I’d like to output the information to another software (Max/MSP) to be interpreted there by another kind of code but.

    Thanks!

    Reply
    • Hi Pedro.
      As we’re using software serial, you can choose any pins to connect.
      You just need to modify your code accordingly.
      Regards,
      Sara

      Reply
  33. hi sara
    just i have done it by pic micro controller using mp lab IDE c code.
    but i will like to do again by Arduino, sis could you help me please just what is the difference between them

    Reply
      • hi sara & Rui santos
        this is great tutorial thanks to you and your members keep it up pleas.
        just i have read all even if the coments your respond is amazing .
        i pass to my point i am doing GPS with Arduino using simulation now so i would like to display this your code to LCD not to com pleas help with same explaination
        regards,
        tesfalem

        Reply
  34. Hi Sara,
    Great help! I have been trying for ages to parse data ready for assembling a string that can be sent to an SD card. Your noted helped me to do this in minutes. Thank you.
    However, using Lat = (gps.location.lat(),6); Lon = (gps.location.lng(),6); just produces: (2020/3/19)(20/27/59) 6 6 94.40 8, where the two sixes were the fields for Lat and Lon. Removing the sixes: Lat = (gps.location.lat()); Lon = (gps.location.lng()); prints Lat Lon values.
    Any suggestions.
    Colin H.

    Reply
      • Hi Sara,
        It is just the latitude and longitude that prints out using your code are only printed out to two decimal places.
        When the ‘6’ is added to the codes, the serial print out only prints out ‘6’, and not the GPS values.
        Hope that helps.
        Thank you for getting back.
        Colin.

        Reply
        • Hi Colin.
          I don’t know why that happens. Maybe it is because you don’t have enough signal for the module to get the coordinates?
          Does your GPS module’s blue LED blinks? That means it is catching satellite signal and can calculate the position.
          Regards,
          Sara

          Reply
      • Thanks for getting back, Sara.
        The last bit of the message, I see, got garbled.
        Basically, the codes for latitude and longitude only showed two decimal places. And, when I added the code: (gps. location. lat(), 6);, the Serial print printed ‘6’, and no GPS value.
        Best wishes
        Colin.

        Reply
  35. I have found a NEO-6M-GPS shield for arduino Uno/Mega with SD on it for Datalogging. Do you know more about this shield. Where can I get more information about this shield . I like to build a tracking project. Catch gps data, show the data on a oled 1.3 display and save the data on SD-Card. Do you know a tutorial I can use? I´m a beginner.

    Greatings

    Reply
  36. Hello,
    I am a researcher and currently study slipping of tractor’s tires on muddy and sandy grounds, so I need to measure the actual speed of the tractor through GPS and measure the theoretical speed of the tires through a tachometer.

    Do you recommend a GPS device that can be connected to a laptop to read the tractor speed data, record it, deal with it on a program, and compare it with the theoretical speed of tires??

    Will its accuracy and response be good??

    What is the lowest speed that GPS can read it with good accuracy?

    Do you recommend any device that can measure the actual speed of a tractor?

    What about NEO-6M for this project?

    Reply
    • Hi Mohamed.
      I’m not familiar with sensors for your project.
      The NEO-6M is not very accurate, specially if it doesn’t get signal from many satellites. However, if the place where you’ll use it has a good signal, maybe you can get good results.
      You really need to experiment and see if it is appropriate for your project or not.
      Regards,
      Sara

      Reply
    • Mohamed, Guidance on achievable accuracy, time to acquire satellites etc. is very thin on the ground. It would be good to see a proper article written to make clear what is achievable with these low cost devices and limited precision processors like the UNO. Is there anyone out there who can do that?
      The projects described here are an excellent introduction and very helpful in understanding how it all works. But I doubt that the precision comes close to what you need for monitoring low speed movement of a tractor. I think the positional accuracy is unlikely to be better than about 2m. (Does anyone know otherwise?)

      I have a similar interest in monitoring the speed of a passenger carrying miniature railway train (speeds below 5mph). I gave up because GPS modules that can achieve positional accuracy below 1m cost hundreds if not thousands of dollars. I stayed with axle speed monitoring using a sensor that gave 22 pulses per revolution – and positional accuracy of close to a couple of centimeters – which works for me, but doesn’t solve your problem of wheel slip.
      I hope someone is able to give you a more positive and helpful response.

      Reply
  37. hi sara
    thanks alot for your tutorial.
    in serial monitor, i see Latitude= 36.125423 Longitude= 43.998405
    i want to store those into string variables as below:
    String lati = gps.location.lat(), 6;
    String logi = gps.location.lng(), 6;
    but in serial monitor shows this :
    lati= 36.13
    logi= 44.00
    i want data store in string whith decimal.
    please help me
    thanks

    Reply
  38. Hi. Great tutorial. It works fine. A detailed explanation helped a lot.

    I have another issue. I’m trying to combine neo 6m and dht22 with esp8266. It works fine when I use they delay of 500 ms or below. Unfortunately, it doesn’t work when I use a delay above 500ms. With 500ms or no delay, there are a lot of duplicate readings and a lot of data to handle. Can you guide any solution to that? A delay of 5000ms would be fine. Thanks

    Reply
  39. Hi
    Thanks a lot for your useful tutorials .
    I am used NEO-6M GPS Module with ESP32 and connect Vcc with 3.3V also used your code but the module didn’t work (no output on serial monitor)
    Can you tell me where the problem, please?

    Reply
  40. Hello Sara Santos,

    thank you for your interesting project and it was very beneficial to me.

    Now I am trying to adapt your code with the stm32 bluebill for a current project but I am having problems.

    Could you help me because I’m new to programming?

    Reply
  41. Hallo,
    I wanted to run the sketch with an ESP32. It did not work. Compilation Error ! It takes me one and a half day to find the right SoftwareSerial.h . There are a few different Libraries. So be so kind and give a hint at the beginning of the Tutorial. The library is in the Arduino core.

    Reply
    • Hi.
      This code is not compatible with the ESP32.
      It is for the Arduino board.
      Search on google for “ESP32 with NEO-6M” and you’ll find some sample codes for the ESP32.
      At the moment, we don’t have any examples for this module with the ESP32.
      Regards,
      Sara

      Reply
      • Hi, When i tried the first code which gave Dan output of NMEA sentences it worked.
        But fated install the TinyGPS++ library and running the new code nothing appears on the serial monitor at all.

        Ps. My baud rate is 9600

        Reply
    • Hello Ernst,

      I think I can help. I have a project ‘Navigator-II’, using an NodeMCU ESP-32, GPS Neo-M8N and OLED display, last worked on it on 6/2022. I am using a SoftwareSerial.h library, just have to check the version.
      I can send you the info, code and picture. I am sure you will find the answer.

      Reply
      • Hallo Danni,
        ich habe dieses Tutorial mit der passenden SoftwareSerial Datei in Betrieb. Ich möchte jetzt aber mehr. Ihr Angebot nehme ich daher gerne an.
        Zu meiner Person: Anfänger mit Arduino Programmierung, Teste gerne Tutorials. Mein Alter: 80 Jahre.
        Meine E-mail Adresse oldschueller at t-online.de

        Reply
      • Hello Danny,
        thank you very much for your offer. I appreciate your help. I am a newcommer in Arduino and like it very much to get Tutorials working. I am in the age of 80 and therefore a little bit slow. If you able to send me your work then please to my e-mail [email protected]. Greetings from Germany.

        Reply
  42. the first code that displays the nmea sentences works for me but the last two codes using the tinygpsplus library doesnt work at all, i dont know why. but the last two codes worked a couple of times before but for two weeks now ive not been able to get it to work
    my serial monitor doesnt show any errors as well.

    Reply
  43. Hi , i tried my best to get this module work but i not connecting tothe satellite or even u center software. It not showing anything on serial monitor . I need to know, is it need to connect Satellite before everything? And how much time will it take to connect . Thanks

    Reply
    • Hi.
      After uploading the code, you need to place the sensor outside or near a window to catch the satellite signal.
      It will display information on the serial monitor, once it has found a stable number of satellites.
      Regards,
      Sara

      Reply
  44. Thanks for the excellent tutorial.
    I am confused about one thing.
    In your article, you say:

    The module GND pin is connected to Arduino GND pin
    The module RX pin is connected to Arduino pin 3
    The module TX pin is connected to Arduino pin 4
    The module VCC pin is connected to Arduino 5V pin

    Code

    Copy the following code to your Arduino IDE and upload it to your Arduino board.

    /*
    * Rui Santos
    * Complete Project Details https://randomnerdtutorials.com
    */

    #include <SoftwareSerial.h>

    // The serial connection to the GPS module
    SoftwareSerial ss(4, 3);

    void setup(){
    Serial.begin(9600);
    ss.begin(9600);
    }

    void loop(){
    while (ss.available() > 0){
    // get the byte data from the GPS
    byte gpsData = ss.read();
    Serial.write(gpsData);
    }
    }

    View raw code

    This sketch assumes you are using pin 4 and pin 3 as RX and TX

    At the start of this extract, you say RX is pin 3 and TX is pin4.
    But the last line suggests the opposite.
    Which one is right?

    Reply
  45. After coding and all set up, i connect arduino with battery for power and disconnect with laptop still i will get output coordinate ? or what else i need to do if my arduino connect with battery and i want output?

    Reply
  46. How do you get away with connecting the Neo-6M to the
    5V Vcc pin on the Arduino, when the spec for the module
    from U-Blox clearly states 3.6vdc MAXIMUM Vcc input?

    Reply
  47. Hello, I connected the NEO-6M to the ESP8266 according to your tutorial, using a 3.3V power supply, but there is a problem with the connection, I don’t know why? I changed the GPIO pin several times, but it still doesn’t work. I don’t know where the problem lies.

    Reply
    • Hi.
      What’s exactly the issue?
      Do you get any errors on the serial monitor?
      Please note that the module needs to be outside or very close to a window to be able to catch wi-fi signal.
      Regards,
      Sara

      Reply
      • Thank you very much for your reply. The problem has been solved. You can use USB to TTL to connect 3 wires, but you need 4 wires to use ESP8266. I have no data before. It should be that RX and TX are reversed.

        Reply
  48. Thank you for your wonderful tutorial!
    I get it to work on the Arduino Uno.
    However, on my iLabs Challenger RP2040 it almost works, and I want to use that one because it has WiFi built-in. This is the output from SoftwareSerial. Is it something with the baud rate or is it simply incompatible?

    $GPRMC,145049.00,A,5904.35602,N,01418.09638�������������������������������������������������i�)JI�jR”:A����������������������9���������������Y`rXb\dfXph\hX�Xfd\dX�

    Reply
  49. i would like to get more accurate positioning using dgps. my setup works and i get the nmea messages. i have tried to use pygpsclient to get correction data for my rover but so far had no luck. the neo6m does not see a sbas satellite and trying to include an ntrip client is not working.

    Reply
  50. Hello Dear Brother can you help me I want to control arduino with GPS module. Please teach me how to connect the GPS module to the satellite. Thank you in advance

    Reply
  51. Hi – Great guide and all work excellently except…I find that if I look at the longitude and latitude values at more the 4 decimal places they are constantly changing while the GPS unit is stationary. Is this to be expected and if I want a stable reading I need to trim to 4 decimal places (11.12 meters longitude and latitude accuracy) or is there something I am doing wrong?

    Reply
  52. Nice tutorial. How should the antenna be placed, the ceramic part facing up or the metal plate up to the sky to get the satellite signals? Many videos have shown both ways.

    Reply

Leave a Comment

Download Our Free eBooks and Resources

Get instant access to our FREE eBooks, Resources, and Exclusive Electronics Projects by entering your email address below.